Subversion Repositories wimsdev

Rev

Rev 16722 | Rev 17351 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | RSS feed

  1. #include "canvasdraw.h"
  2. /* used multidraw primitives : identifier in canvasmultidraw.c is index of this array */
  3. static char multidraw_primitives[MAX_MULTI_PRIMITIVES][32] = {"point","points","circle","circles",
  4. "line","lines","segment","segments",
  5. "arrow","arrows","triangle","triangles",
  6. "closedpoly","text","rect","rects",
  7. "poly","polys","parallelogram","parallelograms",
  8. "images","curvedarrow","curvedarrows","curvedarrow2","curvedarrows2",
  9. "crosshair","crosshairs","function","functions"};
  10. /*size of words "point","points",... == 6,7,..*/
  11. static int multidraw_primitives_length[MAX_MULTI_PRIMITIVES] = {6,7,8,7,6,5,9,8,7,6,10,9,11,5,6,5,6,5,15,14,7,14,13,13,12,10,11,9,10};
  12.  
  13. void add_js_multidraw(char *draw_types,char *table_css,int use_offset,int no_controls,int crosshair_size,int use_zoom){
  14.  int i=0;int p;int found = 0;
  15.  size_t L0 = 1 + snprintf(NULL,0,"%s",draw_types);
  16.  char *str = my_newmem(L0);snprintf(str,L0,"%s",draw_types);char *array[L0];
  17.  int user_nums[MAX_MULTI_PRIMITIVES]; /* we don't know the number of different draw primitives: so assume MAX */
  18.  int draw_nums[MAX_MULTI_PRIMITIVES];
  19.  for(i=0;i<MAX_MULTI_PRIMITIVES;i++){draw_nums[i] = -1;user_nums[i] = -1;}
  20. /* link the user given primitives to the internal indexes of the draw primitives */
  21.  int equal = -1; i = 0;
  22.  array[i] = strtok(str,",");
  23.  int polynum = -1;
  24.  char *pp;int safe=0;
  25.  while(array[i]!=NULL){
  26.   found = 0;
  27.   if( strstr(array[i],"poly") != NULL ){/* getting the numerical argument from: poly3...polys9 */
  28.    if( strstr(array[i],"closedpoly") == NULL && strstr(array[i],"polygon") == NULL){
  29.     pp = array[i];while( *pp ){safe++;
  30.     if(safe > MAX_MULTI_PRIMITIVES){break;}
  31.     if( isdigit(*pp) ){ polynum = atoi(pp);if( strstr( array[i],"polys") != NULL ) {array[i] = "polys";}else{ array[i] = "poly";}break;} else { pp++;}
  32.     }
  33.    }
  34.   }
  35.   for( p = 0 ; p < MAX_MULTI_PRIMITIVES; p++){
  36.   /* multidraw_primitives defined in canvasdraw.h */
  37.    equal = strncmp(multidraw_primitives[p],array[i],multidraw_primitives_length[p]);
  38.    if (equal == 0 ){
  39. /*    fprintf(stdout,"found %s i=%d p=%d<br />",multidraw_primitives[p],i,p);*/
  40.     draw_nums[p]= p;user_nums[p] = i;
  41.     found=1; break;
  42.    }
  43.   }
  44.   if( found == 0 ){canvas_error("unknown multidraw primitive found...typo?");}
  45.   array[++i] = strtok(NULL,",");
  46.  }
  47. /* multilabel is js-array */
  48.  if( no_controls != 1 ){ fprintf(js_include_file,"var inner_html=\"<table class='%s'>\";",table_css); }else{fprintf(js_include_file,"var inner_html = \"\";");}
  49.  
  50.  /* some default stuff */
  51.  fprintf(js_include_file,"\n/* multidraw  */\
  52. var canvas_userdraw = create_canvas%d(1000,xsize,ysize);var context_userdraw = canvas_userdraw.getContext(\"2d\");\
  53. var multidraw_object_cnt = 0;\
  54. var tooltip_div = document.getElementById(\"tooltip_placeholder_div%d\");\
  55. function multi_snap_check(x,y,snap){switch(snap){case 1:return [snap_to_x(x),snap_to_y(y)];break;case 2:return [snap_to_x(x),y];break;case 3:return [x,snap_to_y(y)];break;case 4:return snap_to_points(x,y);break;default: return [x,y];break;};};\
  56. function coord_split(coord){if(coord.indexOf(':') > 0 ){return coord.split(':');}else{if(coord.indexOf(';') > 0 ){return coord.split(';');}else{if(coord.indexOf(',') > 0 ){return coord.split(',');}else{alert(coord+'-- X : Y ');return;};};};};",canvas_root_id,canvas_root_id);
  57.  
  58.  
  59.  
  60. if( use_zoom == 1 ){/* only use zoom when command 'zoom color' is given before command 'multidraw' */
  61. fprintf(js_include_file,"forbidden_zone = [%d,%d];\
  62. function recalculate_multidraw(xmin0,xmax0,ymin0,ymax0){\
  63. function scale_xy(type,xy){var tmp_xmin = xmin;var tmp_xmax = xmax;var tmp_ymin = ymin;var tmp_ymax = ymax;xmin=xmin0;xmax=xmax0;ymin=ymin0;ymax=ymax0;if(type == 1 ){for(var p=0;p<xy.length;p++){xy[p] = px2x(xy[p]);};}else{for(var p=0;p<xy.length;p++){xy[p] = px2y(xy[p]);};};xmin = tmp_xmin;ymin = tmp_ymin;xmax = tmp_xmax;ymax = tmp_ymax;if(type == 1){for(var p=0;p<xy.length;p++){xy[p] = x2px(xy[p]);}}else{for(var p=0;p<xy.length;p++){xy[p] = y2px(xy[p]);};};return xy;};\
  64. function scale_multi_radius(r){for(var p = 0 ; p < r.length;p++ ){r[p] = zoom_xy[0]/xmin*r[p];};return r;};",xsize-115,ysize - 20);
  65.  
  66.  
  67.  for(i=0; i < MAX_MULTI_PRIMITIVES ; i++ ){
  68.   switch( draw_nums[i] ){
  69.    case -1        : break;
  70.    case 0 ... 1   :fprintf(js_include_file,"if( points_x && points_x.length > 0 ){points_x = scale_xy(1,points_x);points_y = scale_xy(1,points_y);draw_points();};");break;
  71.    case 2 ... 3   :fprintf(js_include_file,"if( circles_x && circles_x.length > 0 ){circles_x = scale_xy(1,circles_x);circles_y = scale_xy(1,circles_y);multi_radius = scale_multi_radius(multi_radius);draw_circles();};");break;
  72.    case 4 ... 5   :fprintf(js_include_file,"if( lines_x && lines_x.length > 0 ){lines_x = scale_xy(1,lines_x);lines_y = scale_xy(2,lines_y);draw_lines();};");break;
  73.    case 6 ... 7   :fprintf(js_include_file,"if( segments_x && segments_x.length > 0 ){segments_x = scale_xy(1,segments_x);segments_y = scale_xy(1,segments_y);draw_segments();};");break;
  74.    case 8 ... 9   :fprintf(js_include_file,"if( arrows_x && arrows_x.length > 0 ){arrows_x = scale_xy(1,arrows_x);arrows_y = scale_xy(2,arrows_y);draw_arrows();};");break;
  75.    case 10 ... 11 :fprintf(js_include_file,"if( triangles_x && triangles_x.length > 0 ){triangles_x = scale_xy(1,triangles_x);triangles_y = scale_xy(2,triangles_y);draw_triangles();};");break;
  76.    case 14 ... 15 :fprintf(js_include_file,"if( rects_x && rects_x.length > 0 ){rects_x = scale_xy(1,rects_x);rects_y = scale_xy(2,rects_y);draw_rects();};");break;
  77.    case 12        :fprintf(js_include_file,"if( closedpoly_x && closedpoly_x.length > 0 ){closedpoly_x = scale_xy(1,closedpoly_x);closedpoly_y = scale_xy(2,closedpoly_y);draw_closedpoly();};");break;
  78.    case 13        :fprintf(js_include_file,"if( text_x && text_x.length > 0 ){text_x = scale_xy(1,text_x);text_y = scale_xy(2,text_y);draw_text();};");break;
  79.    case 16 ... 17 :fprintf(js_include_file,"if( polys_x && polys_x.length > 0 ){polys_x = scale_xy(1,polys_x);polys_y = scale_xy(2,polys_y);draw_polys();};");break;
  80.    case 18 ... 18 :fprintf(js_include_file,"if( parallelogram_x && parallelogram_x.length > 0 ){parallelogram_x = scale_xy(1,parallelogram_x);parallelogram_y = scale_xy(2,parallelogram_y);draw_parallelogram();};");break;
  81.    case 20        :fprintf(js_include_file,"if( images_x && images_x.length > 0 ){images_x = scale_xy(1,images_x);images_y = scale_xy(2,images_y);draw_images();};");break;
  82.    case 21 ... 22 :fprintf(js_include_file,"if( curvedarrows_x && curvedarrows_x.length > 0 ){curvedarrows_x = scale_xy(1,curvedarrows_x);curvedarrows_y = scale_xy(2,curvedarrows_y);draw_curvedarrows();};");break;
  83.    case 23 ... 24 :fprintf(js_include_file,"if( curvedarrows2_x && curvedarrows2_x.length > 0 ){curvedarrows2_x = scale_xy(1,curvedarrows2_x);curvedarrows2_y = scale_xy(2,curvedarrows2_y);draw_curvedarrows2();};");break;
  84.    case 25 ... 26 :fprintf(js_include_file,"if( crosshairs_x && crosshairs_x.length > 0 ){crosshairs_x = scale_xy(1,crosshairs_x);crosshairs_y = scale_xy(1,crosshairs_y);draw_crosshairs();};");break;
  85.    case 27:break;
  86.    default        : break;
  87.   }
  88.  }
  89.  fprintf(js_include_file," return;};");
  90. }
  91.  /* begin user_draw() */
  92.  fprintf(js_include_file,"function user_draw(evt){\
  93. if(evt.button == 3){clear_draw_area%d(userdraw_primitive,0);return;};\
  94. var mouse = getMouse(evt,canvas_userdraw);\
  95. var x = mouse.x;var y = mouse.y;\
  96. user_is_dragging = false;\
  97. if(x>forbidden_zone[0] && y>forbidden_zone[1]){console.log('drawing in zoom area...');return;};\
  98. switch(userdraw_primitive){",canvas_root_id);
  99.  for(i=0; i < MAX_MULTI_PRIMITIVES ; i++ ){
  100.   switch( draw_nums[i] ){
  101.    case -1: break;
  102.    case 0:fprintf(js_include_file,"case 0: points(x,y,0,0);break;");break;
  103.    case 1:fprintf(js_include_file,"case 1: points(x,y,0,1);break;");break;
  104.    case 2:fprintf(js_include_file,"case 2: circles(x,y,0,0);break;");break;
  105.    case 3:fprintf(js_include_file,"case 3: circles(x,y,0,1);break;");break;
  106.    case 4:fprintf(js_include_file,"case 4: lines(x,y,0,0);break;");break;
  107.    case 5:fprintf(js_include_file,"case 5: lines(x,y,0,1);break;");break;
  108.    case 6:fprintf(js_include_file,"case 6: segments(x,y,0,0);break;");break;
  109.    case 7:fprintf(js_include_file,"case 7: segments(x,y,0,1);break;");break;
  110.    case 8:fprintf(js_include_file,"case 8: arrows(x,y,0,0);break;");break;
  111.    case 9:fprintf(js_include_file,"case 9: arrows(x,y,0,1);break;");break;
  112.    case 10:fprintf(js_include_file,"case 10: triangles(x,y,0,0);break;");break;
  113.    case 11:fprintf(js_include_file,"case 11: triangles(x,y,0,1);break;");break;
  114.    case 12:fprintf(js_include_file,"case 12: closedpoly(x,y,0,0);break;");break;
  115.    case 13:fprintf(js_include_file,"case 13: text(x,y,0,1);break;");break;
  116.    case 14:fprintf(js_include_file,"case 14: rects(x,y,0,0);break;");break;
  117.    case 15:fprintf(js_include_file,"case 15: rects(x,y,0,1);break;");break;
  118.    case 16:fprintf(js_include_file,"case 16: polys(x,y,0,0);break;");break;
  119.    case 17:fprintf(js_include_file,"case 17: polys(x,y,0,1);break;");break;
  120.    case 18:fprintf(js_include_file,"case 18: parallelogram(x,y,0,0);break;");break;
  121.    case 19:fprintf(js_include_file,"case 19: parallelogram(x,y,0,1);break;");break;
  122.    case 20:fprintf(js_include_file,"case 20: images(x,y,0,1);break;");break;
  123.    case 21:fprintf(js_include_file,"case 21: curvedarrows(x,y,0,0);break;");break;
  124.    case 22:fprintf(js_include_file,"case 22: curvedarrows(x,y,0,1);break;");break;
  125.    case 23:fprintf(js_include_file,"case 23: curvedarrows2(x,y,0,0);break;");break;
  126.    case 24:fprintf(js_include_file,"case 24: curvedarrows2(x,y,0,1);break;");break;
  127.    case 25:fprintf(js_include_file,"case 25: crosshairs(x,y,0,0);break;");break;
  128.    case 26:fprintf(js_include_file,"case 26: crosshairs(x,y,0,1);break;");break;
  129.    case 27:fprintf(js_include_file,"case 27:break;");break;
  130.    default: break;
  131.   }
  132.  }
  133.  fprintf(js_include_file,"default:break;};return;};");
  134.  /* end user_draw()*/
  135.  
  136. /* should we use a fillpattern ? */
  137.  
  138.  /* begin user_drag() */
  139.  fprintf(js_include_file,"function user_drag(evt){\
  140. var mouse = getMouse(evt,canvas_userdraw);\
  141. var x = mouse.x;var y = mouse.y;\
  142. user_is_dragging = true;\
  143. if(x>forbidden_zone[0] && y>forbidden_zone[1]){console.log('drawing in zoom area...');return;};\
  144. switch(userdraw_primitive){");
  145.  for(i=0; i < MAX_MULTI_PRIMITIVES ; i++ ){
  146.   switch( draw_nums[i] ){
  147.    case -1: break;
  148.    case 0:fprintf(js_include_file,"case 0: break;");break;
  149.    case 1:fprintf(js_include_file,"case 1: break;");break;
  150.    case 2:fprintf(js_include_file,"case 2: circles(x,y,1,0);break;");break;
  151.    case 3:fprintf(js_include_file,"case 3: circles(x,y,1,1);break;");break;
  152.    case 4:fprintf(js_include_file,"case 4: lines(x,y,1,0);break;");break;
  153.    case 5:fprintf(js_include_file,"case 5: lines(x,y,1,1);break;");break;
  154.    case 6:fprintf(js_include_file,"case 6: segments(x,y,1,0);break;");break;
  155.    case 7:fprintf(js_include_file,"case 7: segments(x,y,1,1);break;");break;
  156.    case 8:fprintf(js_include_file,"case 8: arrows(x,y,1,0);break;");break;
  157.    case 9:fprintf(js_include_file,"case 9: arrows(x,y,1,1);break;");break;
  158.    case 10:fprintf(js_include_file,"case 10: triangles(x,y,1,0);break;");break;
  159.    case 11:fprintf(js_include_file,"case 11: triangles(x,y,1,1);break;");break;
  160.    case 12:fprintf(js_include_file,"case 12: closedpoly(x,y,1,0);break;");break;
  161.    case 13:fprintf(js_include_file,"case 13: break;");break;
  162.    case 14:fprintf(js_include_file,"case 14: rects(x,y,1,0);break;");break;
  163.    case 15:fprintf(js_include_file,"case 15: rects(x,y,1,1);break;");break;
  164.    case 16:fprintf(js_include_file,"case 16: polys(x,y,1,0);break;");break;
  165.    case 17:fprintf(js_include_file,"case 17: polys(x,y,1,1);break;");break;
  166.    case 18:fprintf(js_include_file,"case 18: parallelogram(x,y,1,0);break;");break;
  167.    case 19:fprintf(js_include_file,"case 19: parallelogram(x,y,1,1);break;");break;
  168.    case 20:fprintf(js_include_file,"case 20: images(x,y,1,1);break;");break;
  169.    case 21:fprintf(js_include_file,"case 21: curvedarrows(x,y,1,0);break;");break;
  170.    case 22:fprintf(js_include_file,"case 22: curvedarrows(x,y,1,1);break;");break;
  171.    case 23:fprintf(js_include_file,"case 23: curvedarrows2(x,y,1,0);break;");break;
  172.    case 24:fprintf(js_include_file,"case 24: curvedarrows2(x,y,1,1);break;");break;
  173.    case 25:fprintf(js_include_file,"case 25: break;");break;
  174.    case 26:fprintf(js_include_file,"case 26: break;");break;
  175.    case 27:fprintf(js_include_file,"case 27: break;");break;
  176.    default:break;
  177.   }
  178.  }
  179.  fprintf(js_include_file,"default:break; };return;};");
  180.  /* end user_drag() */
  181. /* 17/1/2021 corrected syntax issue signalled by Opera Presto : 'forbidden function user_drawstop(evt) declaration in statement'*/
  182. fprintf(js_include_file,"if(wims_status != \"done\"){\
  183. canvas_div.addEventListener('mousedown',user_draw,false);\
  184. canvas_div.addEventListener('mousemove',user_drag,false);\
  185. canvas_div.addEventListener('touchstart'  , function(e) { e.preventDefault(); user_draw(e.changedTouches[0]);},false);\
  186. canvas_div.addEventListener('touchmove'  , function(e) { e.preventDefault(); user_drag(e.changedTouches[0]);},false);\
  187. canvas_div.addEventListener('touchend'  , function(e) { e.preventDefault(); user_drawstop(e.changedTouches[0]);},false);\
  188. var user_is_dragging = false;\
  189. var user_drawstop = function(evt){\
  190.  if(!user_is_dragging){user_drag(evt);return;};\
  191.  if(user_is_dragging){user_draw(evt);return;};\
  192. };\
  193. };");
  194.  
  195. /* add all stuff needed ti draw the selected primitives... */
  196. int u;
  197.  for(u=0; u < MAX_MULTI_PRIMITIVES ; u++ ){
  198.   i = user_nums[u];
  199.   /*
  200.   u = index of technical draw primitive
  201.   i = index of user defined draw primitive
  202.   */
  203.   switch( draw_nums[u] ){
  204.   /* point/points */
  205.   case -1 : break;
  206.   case 0 ... 1:
  207.   fprintf(js_include_file,"function points(x,y,event_which,num){\
  208.   if(event_which == 1){ return; };\
  209.   var xy = multi_snap_check(x,y,points_snap);\
  210.   if( num == 0 ){\
  211.    points_x[0] = xy[0];\
  212.    points_y[0] = xy[1];\
  213.   }else{\
  214.    points_x.push(xy[0]);\
  215.    points_y.push(xy[1]);\
  216.   };\
  217.   draw_points();\
  218.  };\
  219.  function draw_points(){\
  220.   var radius = 2*(context_points.lineWidth);\
  221.   context_points.clearRect(0,0,xsize,ysize);\
  222.   for(var p = 0 ; p < points_x.length ; p++ ){\
  223.    context_points.beginPath();\
  224.    context_points.arc(points_x[p],points_y[p],radius,0,2*Math.PI,false);\
  225.    context_points.closePath();\
  226.    context_points.fill();\
  227.   };\
  228.  };\
  229.  var canvas_points = create_canvas%d(100%d,xsize,ysize);var context_points = canvas_points.getContext(\"2d\");\
  230.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  231.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  232.  context_points.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  233.  context_points.fillStyle = context_points.strokeStyle;\
  234.  context_points.lineWidth = multilinewidth[%d];if(multilinewidth[%d] %%2 == 1){ context_points.translate(0.5,0.5);};\
  235.  var points_x = new Array();var points_y = new Array();\
  236.  var points_snap = multisnaptogrid[%d];",canvas_root_id,i,i,i,i,i,i,i,i,i,i,i,i);
  237.   if( no_controls != 1){
  238.    fprintf(js_include_file,"\
  239.   inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  240.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='5' value='' id='input_points_x' />:<input type='text' size='5' value='' id='input_points_y' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_points_x,input_points_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  241.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  242.   }
  243.   else
  244.   {
  245.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  246.   }
  247.   break;
  248.  
  249.  
  250.   /* circle/circles */
  251.   case 2 ... 3 :
  252.   fprintf(js_include_file,"function circles(x,y,event_which,num){\
  253.   var xy = multi_snap_check(x,y,circles_snap);\
  254.   var last = circles_x.length - 1;\
  255.   var xc = circles_x[last];\
  256.   var yc = circles_y[last];\
  257.   if(event_which == 0){\
  258.    if( multidraw_object_cnt == 0 ){\
  259.     if( num  == 0 ){\
  260.       circles_x[0]=xy[0];circles_y[0]=xy[1];multi_radius[0]=4;\
  261.     }\
  262.     else\
  263.     {\
  264.       circles_x.push(xy[0]);circles_y.push(xy[1]);multi_radius.push(4);\
  265.     };\
  266.    };\
  267.    multidraw_object_cnt++;\
  268.   }\
  269.   else\
  270.   {\
  271.    if( multidraw_object_cnt == 1 ){\
  272.     multi_radius[last] = parseInt(Math.sqrt( (xy[0] - xc)*(xy[0] - xc) + (xy[1] - yc)*(xy[1] - yc) ));\
  273.    };\
  274.   };\
  275.   if( multidraw_object_cnt == 2 ){\
  276.    multidraw_object_cnt = 0;\
  277.    if( num == 0 ){\
  278.     circles_x = [];circles_y = [];\
  279.     circles_x[0] = xc;circles_y[0] = yc;\
  280.    };\
  281.   };\
  282.   draw_circles();\
  283.  };function draw_circles(){\
  284.   context_circles.clearRect(0,0,xsize,ysize);\
  285.   for(var p = 0 ; p < circles_x.length ; p++ ){\
  286.    context_circles.beginPath();\
  287.    context_circles.arc(circles_x[p],circles_y[p],multi_radius[p],0,2*Math.PI,false);\
  288.    context_circles.closePath();\
  289.    context_circles.fill();\
  290.    context_circles.stroke();\
  291.   };\
  292.   return;\
  293.  };var canvas_circles = create_canvas%d(100%d,xsize,ysize);var context_circles = canvas_circles.getContext(\"2d\");\
  294.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  295.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  296.  context_circles.lineWidth = multilinewidth[%d];\
  297.  if(multilinewidth[%d]%%2 == 1){ context_circles.translate(0.5,0.5);};\
  298.  context_circles.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  299.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_circles.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_circles.fillStyle = my_fill_color;};}else{context_circles.fillStyle = \"rgba( 255,255,255,0)\";};\
  300.  if(multidash[%d] == 1 ){ if( context_circles.setLineDash ){context_circles.setLineDash([2,4]);}else{if(context_circles.mozDash){context_circles.mozDash = [2,4]};};};\
  301.  var circles_x = new Array();var circles_y = new Array();var multi_radius = new Array();\
  302.  var circles_snap = multisnaptogrid[%d];",canvas_root_id,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  303.  
  304.   if(no_controls != 1 ){  /* for BPR...*/
  305.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  306.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td>M:(<input type='text' size='3' value='' id='input_circles_x' /> : <input type='text' size='3' value='' id='input_circles_y'/>) R:<input type='text' size='3' value='' id='input_circles_r'/></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_circles_x,input_circles_y,input_circles_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  307.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  308.   }
  309.   else
  310.   {
  311.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  312.   }
  313.   break;
  314.   /* line/lines */
  315.   case 4 ... 5 :
  316.   fprintf(js_include_file,"function calc_lines(){\
  317.   var marge = 2;var len = lines_x.length;\
  318.   var tmp_x = new Array(len);\
  319.   var tmp_y = new Array(len);\
  320.   var pp;\
  321.   for(var p = 0 ; p < len ; p = p+2){\
  322.    pp = p+1;\
  323.    if(lines_x[p] < lines_x[pp]+marge && lines_x[p] > lines_x[pp]-marge){\
  324.     tmp_x[p] = lines_x[p];tmp_x[pp] = lines_x[pp];\
  325.     tmp_y[p] = 0;tmp_y[pp] = ysize;\
  326.    }\
  327.    else\
  328.    {\
  329.     if(lines_y[p] < lines_y[pp]+marge && lines_y[p] > lines_y[pp]-marge){\
  330.      tmp_x[p] = 0;tmp_x[pp] = xsize;\
  331.      tmp_y[p] = lines_y[p];tmp_y[pp] = lines_y[pp];\
  332.     }\
  333.     else\
  334.     {\
  335.      tmp_x[p] = 0;tmp_x[pp] = xsize;\
  336.      tmp_y[p] = lines_y[p] - (lines_x[p])*(lines_y[pp] - lines_y[p])/(lines_x[pp] - lines_x[p]);\
  337.      tmp_y[pp] = lines_y[p] + (xsize - lines_x[p])*(lines_y[pp] - lines_y[p])/(lines_x[pp] - lines_x[p]);\
  338.     };\
  339.    };\
  340.   };\
  341.   return {x:tmp_x,y:tmp_y};\
  342.  };function lines(x,y,event_which,num){\
  343.   var xy = multi_snap_check(x,y,lines_snap);\
  344.   if(event_which == 0){\
  345.    if( num == 0 && multidraw_object_cnt == 0 ){lines_x = [];lines_y = [];};\
  346.    lines_x.push(xy[0]);lines_y.push(xy[1]);\
  347.    multidraw_object_cnt++;\
  348.   }\
  349.   else\
  350.   {\
  351.    if( multidraw_object_cnt == 1 ){\
  352.     lines_x.push(xy[0]);lines_y.push(xy[1]);\
  353.     draw_lines();\
  354.     lines_x.pop();lines_y.pop();\
  355.    };\
  356.   };\
  357.   if( multidraw_object_cnt == 2 ){\
  358.    multidraw_object_cnt = 0;\
  359.    draw_lines();\
  360.   };\
  361.  };function draw_lines(){\
  362.   var len = lines_x.length;\
  363.   if( len %%2 == 0 ){\
  364.    var xy = calc_lines();\
  365.    context_lines.clearRect(0,0,xsize,ysize);\
  366.    for(var p = 0 ; p < len ; p = p+2 ){\
  367.     context_lines.beginPath();\
  368.     context_lines.moveTo(xy.x[p],xy.y[p]);\
  369.     context_lines.lineTo(xy.x[p+1],xy.y[p+1]);\
  370.     context_lines.closePath();\
  371.     context_lines.stroke();\
  372.    };\
  373.   };\
  374.   return;\
  375.  };var canvas_lines = create_canvas%d(100%d,xsize,ysize);var context_lines = canvas_lines.getContext(\"2d\");\
  376.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  377.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  378.  context_lines.lineWidth = multilinewidth[%d];if(multilinewidth[%d]%%2 == 1){ context_lines.translate(0.5,0.5);};\
  379.  context_lines.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  380.  if(multidash[%d] == 1 ){ if( context_lines.setLineDash ){context_lines.setLineDash([2,4]);}else{\
  381.  if(context_lines.mozDash){context_lines.mozDash = [2,4]};};};\
  382.  var lines_x = new Array();var lines_y = new Array();var lines_snap = multisnaptogrid[%d];",canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i);
  383.  
  384.   if( no_controls != 1 ){  /* for BPR...*/
  385.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  386.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='5' value='x1 : y1' id='input_lines_x' style='text-align:center;'/>) --- ( <input type='text' size='5' value='x2 : y2' id='input_lines_y' style='text-align:center;' /> )</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_lines_x,input_lines_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  387.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  388.   }
  389.   else
  390.   {
  391.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  392.   }
  393.   break;
  394.   /* segment/segments */
  395.   case 6 ... 7 :
  396.   fprintf(js_include_file,"function segments(x,y,event_which,num){\
  397.   var xy = multi_snap_check(x,y,segments_snap);\
  398.   if(event_which == 0){\
  399.    if( num == 0 && multidraw_object_cnt == 0 ){segments_x = [];segments_y = [];};\
  400.    segments_x.push(xy[0]);segments_y.push(xy[1]);\
  401.    multidraw_object_cnt++;\
  402.   }\
  403.   else\
  404.   {\
  405.    if( multidraw_object_cnt == 1 ){\
  406.     segments_x.push(xy[0]);segments_y.push(xy[1]);\
  407.     draw_segments();\
  408.     segments_x.pop();segments_y.pop();\
  409.    };\
  410.   };\
  411.   if( multidraw_object_cnt == 2 ){\
  412.    multidraw_object_cnt = 0;\
  413.    draw_segments();\
  414.   };\
  415.  };function draw_segments(){\
  416.   var len = segments_x.length;\
  417.   if( len%%2 == 0 ){\
  418.    context_segments.clearRect(0,0,xsize,ysize);\
  419.    for(var p = 0 ; p < len ; p = p+2 ){\
  420.     context_segments.beginPath();\
  421.     context_segments.moveTo(segments_x[p],segments_y[p]);\
  422.     context_segments.lineTo(segments_x[p+1],segments_y[p+1]);\
  423.     context_segments.closePath();\
  424.     context_segments.stroke();\
  425.    };\
  426.   };\
  427.   return;\
  428.  };var canvas_segments = create_canvas%d(100%d,xsize,ysize);var context_segments = canvas_segments.getContext(\"2d\");\
  429.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  430.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  431.  context_segments.lineWidth = multilinewidth[%d];\
  432.  if(multilinewidth[%d]%%2 == 1){ context_segments.translate(0.5,0.5);};\
  433.  context_segments.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  434.  if(multidash[%d] == 1 ){ if( context_segments.setLineDash ){context_segments.setLineDash([2,4]);}\
  435.  else{if(context_segments.mozDash){context_segments.mozDash = [2,4]};};};\
  436.  var segments_x = new Array();var segments_y = new Array();var segments_snap = multisnaptogrid[%d];",
  437.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i);
  438.  
  439.   if( no_controls != 1 ){  /* for BPR...*/
  440.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  441.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='5' value='x1 : y1' id='input_segments_x' style='text-align:center;' />) --- ( <input type='text' size='5' value='x2 : y2' id='input_segments_y' style='text-align:center;'/>)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_segments_x,input_segments_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  442.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  443.   }
  444.   else
  445.   {
  446.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  447.   }
  448.   break;
  449.   /* arrow/arrows */
  450.   case 8 ... 9 :
  451.   fprintf(js_include_file,"function arrows(x,y,event_which,num){\
  452.   var xy = multi_snap_check(x,y,arrows_snap);\
  453.   if(event_which == 0){\
  454.    if( num == 0 && multidraw_object_cnt == 0 ){arrows_x = [];arrows_y = [];};\
  455.    arrows_x.push(xy[0]);arrows_y.push(xy[1]);\
  456.    multidraw_object_cnt++;\
  457.   }\
  458.   else\
  459.   {\
  460.    if( multidraw_object_cnt == 1 ){\
  461.     arrows_x.push(xy[0]);arrows_y.push(xy[1]);\
  462.     draw_arrows();\
  463.     arrows_x.pop();arrows_y.pop();\
  464.    };\
  465.   };\
  466.   if( multidraw_object_cnt == 2 ){\
  467.    multidraw_object_cnt = 0;\
  468.    draw_arrows();\
  469.   };\
  470.  };function draw_arrows(){\
  471.   var len = arrows_x.length;\
  472.   var x1,y1,x2,y2,dx,dy,h;\
  473.   if( len%%2 == 0 ){\
  474.    context_arrows.clearRect(0,0,xsize,ysize);\
  475.    for(var p = 0 ; p < len ; p = p+2 ){\
  476.     x1 = arrows_x[p];y1 = arrows_y[p];x2 = arrows_x[p+1];y2 = arrows_y[p+1];dx = x2 - x1;dy = y2 - y1;\
  477.     h = Math.sqrt(dx*dx+dy*dy);\
  478.     context_arrows.save();\
  479.     context_arrows.setLineDash([]);\
  480.     context_arrows.translate(x2,y2);\
  481.     context_arrows.rotate(Math.atan2(dy,dx));\
  482.     context_arrows.beginPath();\
  483.     context_arrows.moveTo(0,0);\
  484.     context_arrows.lineTo(-1*arrow_head,-0.5*arrow_head);\
  485.     context_arrows.lineTo(-1*arrow_head, 0.5*arrow_head);\
  486.     context_arrows.closePath();\
  487.     context_arrows.fill();\
  488.     context_arrows.stroke();\
  489.     context_arrows.restore();\
  490.     context_arrows.beginPath();\
  491.     context_arrows.moveTo(x1,y1);\
  492.     context_arrows.lineTo(x2,y2);\
  493.     context_arrows.closePath();\
  494.     context_arrows.stroke();\
  495.    };\
  496.   };\
  497.   return;\
  498.  };var canvas_arrows = create_canvas%d(100%d,xsize,ysize);var context_arrows =  canvas_arrows.getContext(\"2d\");\
  499.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  500.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  501.  if(multidash[%d] == 1 ){ if( context_arrows.setLineDash ){context_arrows.setLineDash([2,4]);}else{if(context_arrows.mozDash){context_arrows.mozDash = [2,4]};};};\
  502.  context_arrows.lineWidth = multilinewidth[%d];if(multilinewidth[%d]%%2 == 1){ context_arrows.translate(0.5,0.5);};\
  503.  context_arrows.lineCap = \"round\";\
  504.  context_arrows.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  505.  context_arrows.fillStyle = context_arrows.strokeStyle;\
  506.  var arrows_x = new Array();var arrows_y = new Array();var arrows_snap = multisnaptogrid[%d];",
  507.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i);
  508.  
  509.   if( no_controls != 1 ){  /* for BPR...*/
  510.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  511.   if( multiuserinput[%d] == 1){inner_html+=\"<td>(<input type='text' size='5' value='x1 : y1' id='input_arrows_x' style='text-align:center;' /><b>) --- (</b> <input type='text' size='5' value='x2 : y2' id='input_arrows_y' style=';text-align:center;' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_arrows_x,input_arrows_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  512.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  513.   }
  514.   else
  515.   {
  516.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  517.   }
  518.   break;
  519.  
  520.   /* triangle/triangles */
  521.   case 10 ... 11:
  522.   fprintf(js_include_file,"function triangles(x,y,event_which,num){\
  523.   var xy = multi_snap_check(x,y,triangles_snap);\
  524.   var last = triangles_x.length - 1;\
  525.   if(event_which == 0){\
  526.    if(num == 0 && multidraw_object_cnt == 0){\
  527.     triangles_x = [];triangles_y = [];\
  528.     triangles_x[0] = xy[0];triangles_y[0] = xy[1];\
  529.    }\
  530.    else\
  531.    {\
  532.     triangles_x.push(xy[0]);triangles_y.push(xy[1]);\
  533.    };\
  534.    multidraw_object_cnt++;\
  535.   }\
  536.   else\
  537.   {\
  538.    if( multidraw_object_cnt < 3 ){\
  539.     triangles_x.push(xy[0]);triangles_y.push(xy[1]);\
  540.     draw_triangles();\
  541.     triangles_x.pop();triangles_y.pop();\
  542.    };\
  543.   };\
  544.   if( multidraw_object_cnt == 3 ){\
  545.    triangles_x.pop();triangles_y.pop();\
  546.    triangles_x.push(xy[0]);triangles_y.push(xy[1]);\
  547.    multidraw_object_cnt = 0;\
  548.    draw_triangles();\
  549.   };\
  550.  };function draw_triangles(){\
  551.   var len = triangles_x.length - 1;\
  552.   context_triangles.clearRect(0,0,xsize,ysize);\
  553.   for(var p = 0 ; p < len ; p = p+3){\
  554.    context_triangles.beginPath();\
  555.    context_triangles.moveTo(triangles_x[p],triangles_y[p]);\
  556.    for( var m = p+1 ;m < p+3 ; m++){\
  557.     context_triangles.lineTo(triangles_x[m],triangles_y[m]);\
  558.    };\
  559.    context_triangles.lineTo(triangles_x[p],triangles_y[p]);\
  560.    context_triangles.closePath();\
  561.    context_triangles.fill();\
  562.    context_triangles.stroke();\
  563.   };\
  564.   return;\
  565.  };var canvas_triangles = create_canvas%d(10%d,xsize,ysize);var context_triangles = canvas_triangles.getContext(\"2d\");\
  566.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2);};\
  567.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  568.  context_triangles.lineCap = \"round\";context_triangles.lineWidth = multilinewidth[%d];\
  569.  if(multilinewidth[%d]%%2 == 1){ context_triangles.translate(0.5,0.5);};\
  570.  context_triangles.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  571.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_triangles.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_triangles.fillStyle = my_fill_color;};}else{context_triangles.fillStyle = \"rgba( 255,255,255,0)\";};\
  572.  if(multidash[%d] == 1 ){ if( context_triangles.setLineDash ){\
  573.  context_triangles.setLineDash([2,4]);}else{if(context_triangles.mozDash){context_triangles.mozDash = [2,4]};};};\
  574.  var triangles_x = new Array();var triangles_y = new Array();var triangles_snap = multisnaptogrid[%d];",
  575.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  576.  
  577.   if(no_controls != 1 ){  /* for BPR...*/
  578.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  579.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td><b>(<input type='text' size='5' value='x1 : y1' id='input_triangles_x' />) -- (<input type='text' size='5' value='x2 : y2' id='input_triangles_y' />) -- (<input type='text' size='5' value='x3 : y3' id='input_triangles_r' />)</b></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_triangles_x,input_triangles_y,input_triangles_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  580.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  581.   }
  582.   else
  583.   {
  584.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  585.   }
  586.   break;
  587.   /* closedpoly */
  588.   case 12 :
  589.   fprintf(js_include_file,"function check_closed(x1,y1,X,Y){\
  590.   var marge=10;\
  591.   var len = X.length-1;\
  592.   for(var p = 0 ; p < len ; p++){\
  593.    if(x1 < X[p] + marge && x1 > X[p] - marge ){\
  594.     if(y1 < Y[p] + marge && y1 > Y[p] - marge ){\
  595.      return 1;\
  596.     };\
  597.    };\
  598.   };\
  599.   return 0;\
  600.  };function closedpoly(x,y,event_which,num){\
  601.   var xy = multi_snap_check(x,y,closedpoly_snap);\
  602.   if(event_which == 0){\
  603.    if(multidraw_object_cnt == 0){\
  604.     closedpoly_x = [];closedpoly_y = [];\
  605.     closedpoly_x[0] = xy[0];closedpoly_y[0] = xy[1];\
  606.    }\
  607.    else\
  608.    {\
  609.     closedpoly_x.push(xy[0]);closedpoly_y.push(xy[1]);\
  610.    };\
  611.    multidraw_object_cnt++;\
  612.    if( multidraw_object_cnt > 2 ){\
  613.     if( check_closed(x,y,closedpoly_x,closedpoly_y) == 1){\
  614.      draw_closedpoly();\
  615.      multidraw_object_cnt = 0;\
  616.     };\
  617.    };\
  618.   }\
  619.   else\
  620.   {\
  621.    if( multidraw_object_cnt > 0 ){\
  622.     closedpoly_x.push(xy[0]);closedpoly_y.push(xy[1]);\
  623.     draw_closedpoly();\
  624.     closedpoly_x.pop();closedpoly_y.pop();\
  625.    };\
  626.   };\
  627.  };function draw_closedpoly(){\
  628.   var len = closedpoly_x.length;\
  629.   context_closedpoly.clearRect(0,0,xsize,ysize);\
  630.   var p = 0;\
  631.   context_closedpoly.beginPath();\
  632.   context_closedpoly.moveTo(closedpoly_x[0],closedpoly_y[0]);\
  633.   for(var p = 1 ; p < len ; p++){\
  634.    context_closedpoly.lineTo(closedpoly_x[p],closedpoly_y[p]);\
  635.   };\
  636.   context_closedpoly.lineTo(closedpoly_x[0],closedpoly_y[0]);\
  637.   context_closedpoly.closePath();\
  638.   context_closedpoly.fill();\
  639.   context_closedpoly.stroke();\
  640.   return;\
  641.  };var canvas_closedpoly = create_canvas%d(10%d,xsize,ysize);\
  642.  var context_closedpoly =  canvas_closedpoly.getContext(\"2d\");\
  643.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  644.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  645.  context_closedpoly.lineCap = \"round\";context_closedpoly.lineWidth = multilinewidth[%d];\
  646.  if(multilinewidth[%d]%%2 == 1){ context_closedpoly.translate(0.5,0.5);};context_closedpoly.lineCap = \"round\";\
  647.  context_closedpoly.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  648.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_closedpoly.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_closedpoly.fillStyle = my_fill_color;};}else{context_closedpoly.fillStyle = \"rgba( 255,255,255,0)\";};\
  649.  if(multidash[%d] == 1 ){ if( context_closedpoly.setLineDash ){context_closedpoly.setLineDash([2,4]);}else{\
  650.  if(context_closedpoly.mozDash){context_closedpoly.mozDash = [2,4]};};};\
  651.  var closedpoly_x = new Array();var closedpoly_y = new Array();\
  652.  var closedpoly_snap = multisnaptogrid[%d];",
  653.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  654.  
  655.   if( no_controls != 1 ){  /* for BPR...*/
  656.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  657.   if( multiuserinput[%d] == 1){inner_html+=\"<td>(<input type='text' size='5' value='x1:x2:x3:...' id='input_closedpoly_x' style='text-align:center;' /><b>) --- (</b> <input type='text' size='5' value='y1:y2:y3:...' id='input_closedpoly_y' style='text-align:center;'/>)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_closedpoly_x,input_closedpoly_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  658.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  659.   }
  660.   else
  661.   {
  662.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  663.   }
  664.   break;
  665.   /* text : always uses user input field !! */
  666.   case 13:
  667.   fprintf(js_include_file,"function text(x,y,event_which,num){\
  668.   if(event_which == 1){ return; };\
  669.   var xy = multi_snap_check(x,y,text_snap);\
  670.   if( num == 0 ){\
  671.    text_x[0] = xy[0];\
  672.    text_y[0] =xy[1];\
  673.   }else{\
  674.    text_x.push(xy[0]);\
  675.    text_y.push(xy[1]);\
  676.   };\
  677.   draw_text();\
  678.  };function conv_to_unicode(str){\
  679.   return str.replace(/\\u[\\dA-F]{4}/gi,function(match){\
  680.   return String.fromCharCode(parseInt(match.replace(/\\u/g,''), 16));});\
  681.  };function draw_text(){\
  682.   var half = 0;\
  683.   var height = 0.3 * (context_text.measureText('M').width);\
  684.   context_text.clearRect(0,0,xsize,ysize);\
  685.   for(var p = 0 ; p < text_x.length ; p++ ){\
  686.    if( typeof(text_abc[p]) === 'undefined'){\
  687.     var txt = conv_to_unicode(document.getElementById('input_text_r').value);\
  688.     text_abc.push(txt);\
  689.    };\
  690.    half = 0.5*( context_text.measureText(text_abc[p]).width );\
  691.    if(text_abc[p].indexOf('_') > 0 || text_abc[p].indexOf('^') > 0 ){\
  692.    draw_subsup(context_text,text_x[p],text_y[p],text_abc[p],4);}else{context_text.fillText(text_abc[p],text_x[p] - half,text_y[p] + height);};\
  693.   };\
  694.  };var canvas_text = create_canvas%d(10%d,xsize,ysize);\
  695.  var context_text = canvas_text.getContext(\"2d\");\
  696.  context_text.font = multifont_family;\
  697.  context_text.fillStyle = \"rgba(\"+multifont_color+\",\"+multistrokeopacity[%d]+\")\";\
  698.  var text_snap = multisnaptogrid[%d];\
  699.  var text_x = new Array();var text_y = new Array(); var text_abc = new Array();",canvas_root_id,u,i,i);
  700.  
  701.   if( no_controls != 1 ){  /* for BPR...*/
  702.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt=0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td><td><input type='text' size='6' value='' id='input_text_r' />\";if( multiuserinput[%d] == 1){inner_html+=\"(<input type='text' size='2' value='x' id='input_text_x' style='text-align:center;' />:<input type='text' size='2' value='y' id='input_text_y' style='text-align:center;'/>)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_text_x,input_text_y,input_text_r);' value='OK' /></td>\";}else{inner_html+=\"</td>\";};",u,i,canvas_root_id,u,i,canvas_root_id,u);
  703.   }
  704.   else
  705.   {
  706.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  707.   }
  708.   fprintf(js_include_file,"inner_html+=\"</tr>\";");
  709.   break;
  710.   /* rect/rects */
  711.   case 14 ... 15 :
  712.   fprintf(js_include_file,"function rects(x,y,event_which,num){\
  713.   var xy = multi_snap_check(x,y,rects_snap);\
  714.   if(event_which == 0){\
  715.    if( num == 0 && multidraw_object_cnt == 0 ){rects_x = [];rects_y = [];};\
  716.    rects_x.push(xy[0]);rects_y.push(xy[1]);\
  717.    multidraw_object_cnt++;\
  718.   }\
  719.   else\
  720.   {\
  721.    if( multidraw_object_cnt == 1 ){\
  722.     rects_x.push(xy[0]);rects_y.push(xy[1]);\
  723.     draw_rects();\
  724.     rects_x.pop();rects_y.pop();\
  725.    };\
  726.   };\
  727.   if( multidraw_object_cnt == 2 ){\
  728.    multidraw_object_cnt = 0;\
  729.    draw_rects();\
  730.   };\
  731.  };function draw_rects(){\
  732.   var len = rects_x.length;\
  733.   if( len %%2 == 0 ){\
  734.    context_rects.clearRect(0,0,xsize,ysize);\
  735.    for(var p = 0 ; p < len ; p = p+2 ){\
  736.     context_rects.beginPath();\
  737.     context_rects.rect(rects_x[p],rects_y[p],rects_x[p+1]-rects_x[p],rects_y[p+1]-rects_y[p]);\
  738.     context_rects.closePath();\
  739.     context_rects.fill();\
  740.     context_rects.stroke();\
  741.    };\
  742.   };\
  743.   return;\
  744.  };var canvas_rects = create_canvas%d(10%d,xsize,ysize);var context_rects = canvas_rects.getContext(\"2d\");\
  745.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  746.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  747.  context_rects.lineWidth = multilinewidth[%d];if(multilinewidth[%d]%%2 == 1){ context_rects.translate(0.5,0.5);};\
  748.  context_rects.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  749.  if(multidash[%d] == 1 ){ if( context_rects.setlineDash ){context_rects.setlineDash([2,4]);}else{\
  750.  if(context_rects.mozDash){context_rects.mozDash = [2,4]};};};\
  751.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_rects.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_rects.fillStyle = my_fill_color;};}else{context_rects.fillStyle = \"rgba( 255,255,255,0)\";};\
  752.  var rects_x = new Array();var rects_y = new Array();var rects_snap = multisnaptogrid[%d];",
  753.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  754.  
  755.   if( no_controls != 1 ){
  756.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  757.   if( multiuserinput[%d] == 1){inner_html+=\"<td>(<input type='text' size='5' value='x1 : y1' id='input_rects_x' style='text-align:center;' />) --- (<input type='text' size='5' value='x2 : y2' id='input_rects_y' style='text-align:center;' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_rects_x,input_rects_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  758.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  759.   }
  760.   else
  761.   {
  762.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  763.   }
  764.   break;
  765.   /* poly/polys */
  766.   case 16 ... 17 :
  767.   fprintf(js_include_file,"var polynum = %d;function polys(x,y,event_which,num){\
  768.   var last = polys_x.length - 1;\
  769.   var xy = multi_snap_check(x,y,polys_snap);\
  770.   if(event_which == 0){\
  771.    if(num == 0 && multidraw_object_cnt == 0){\
  772.     polys_x = [];polys_y = [];\
  773.     polys_x[0] = xy[0];polys_y[0] = xy[1];\
  774.    }\
  775.    else\
  776.    {\
  777.     polys_x.push(xy[0]);polys_y.push(xy[1]);\
  778.    };\
  779.    multidraw_object_cnt++;\
  780.   }\
  781.   else\
  782.   {\
  783.    if( multidraw_object_cnt < polynum ){\
  784.     polys_x.push(xy[0]);polys_y.push(xy[1]);\
  785.     draw_polys();\
  786.     polys_x.pop();polys_y.pop();\
  787.    };\
  788.   };\
  789.   if( multidraw_object_cnt == polynum ){\
  790.    polys_x.pop();polys_y.pop();\
  791.    polys_x.push(xy[0]);polys_y.push(xy[1]);\
  792.    multidraw_object_cnt = 0;\
  793.    draw_polys();\
  794.   };\
  795.  };function draw_polys(){\
  796.   var len = polys_x.length - 1;\
  797.   context_polys.clearRect(0,0,xsize,ysize);\
  798.   for(var p = 0 ; p < len ; p = p+polynum){\
  799.    context_polys.beginPath();\
  800.    context_polys.moveTo(polys_x[p],polys_y[p]);\
  801.    for( var m = p+1 ;m < p+polynum ; m++){\
  802.     context_polys.lineTo(polys_x[m],polys_y[m]);\
  803.    };\
  804.    context_polys.lineTo(polys_x[p],polys_y[p]);\
  805.    context_polys.closePath();\
  806.    context_polys.fill();\
  807.    context_polys.stroke();\
  808.   };\
  809.   return;\
  810.  };var canvas_polys = create_canvas%d(10%d,xsize,ysize);var context_polys = canvas_polys.getContext(\"2d\");\
  811.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  812.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  813.  context_polys.lineCap = \"round\";context_polys.lineWidth = multilinewidth[%d];\
  814.  if(multilinewidth[%d]%%2 == 1){ context_polys.translate(0.5,0.5);};\
  815.  context_polys.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  816.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_polys.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_polys.fillStyle = my_fill_color;};}else{context_polys.fillStyle = \"rgba( 255,255,255,0)\";};\
  817.  if(multidash[%d] == 1 ){ if( context_polys.setLineDash ){context_polys.setLineDash([2,4]);}\
  818.  else{if(context_polys.mozDash){context_polys.mozDash = [2,4]};};};\
  819.  var polys_x = new Array();var polys_y = new Array();\
  820.  var polys_snap = multisnaptogrid[%d];",
  821.   polynum,canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  822.  
  823.   if( no_controls != 1 ){
  824.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  825.   if(multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='8' value='x1,x2...x_n' id='input_polys_x' /> ---- <input type='text' size='8' value='y1,y2...y_n' id='input_polys_y' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_rects_x,input_rects_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  826.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  827.   }
  828.   else
  829.   {
  830.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  831.   }
  832.   break;
  833.   /* parallelogram/parallelograms */
  834.   case 18 ... 19:
  835.   fprintf(js_include_file,"function parallelogram(x,y,event_which,num){\
  836.   var l2 = parallelogram_x.length;\
  837.   var l1 = l2 - 1;var l0 = l2 - 2;\
  838.   var xy = multi_snap_check(x,y,parallelogram_snap);\
  839.   if(event_which == 0){\
  840.    if(multidraw_object_cnt == 0){\
  841.     if(num == 0){parallelogram_x = [];parallelogram_y = [];};\
  842.     parallelogram_x.push(xy[0]);parallelogram_y.push(xy[1]);\
  843.    }\
  844.    else\
  845.    {\
  846.     parallelogram_x.push(xy[0]);parallelogram_y.push(xy[1]);\
  847.     if(multidraw_object_cnt == 2){\
  848.      var xy = multi_snap_check(parallelogram_x[l2] - parallelogram_x[l1] + parallelogram_x[l0],parallelogram_y[l2] - parallelogram_y[l1] + parallelogram_y[l0],parallelogram_snap);\
  849.      parallelogram_x.push(xy[0]);\
  850.      parallelogram_y.push(xy[1]);\
  851.     };\
  852.    };\
  853.    multidraw_object_cnt++;\
  854.   }\
  855.   else\
  856.   {\
  857.    if(multidraw_object_cnt == 1){\
  858.     var xxyy = multi_snap_check(parallelogram_x[l1],parallelogram_y[l1],parallelogram_snap);\
  859.     parallelogram_x.push(xxyy[0]);\
  860.     parallelogram_y.push(xxyy[1]);\
  861.     parallelogram_x.push(xy[0]);\
  862.     parallelogram_y.push(xy[1]);\
  863.     draw_parallelogram();\
  864.     parallelogram_x.pop();parallelogram_y.pop();\
  865.     parallelogram_x.pop();parallelogram_y.pop();\
  866.    }\
  867.    else\
  868.    {\
  869.     if(multidraw_object_cnt == 2){\
  870.      var xxyy = multi_snap_check(parallelogram_x[l2]-parallelogram_x[l1] + parallelogram_x[l0],parallelogram_y[l2]-parallelogram_y[l1] + parallelogram_y[l0],parallelogram_snap);\
  871.      parallelogram_x.push(xy[0]);parallelogram_y.push(xy[1]);\
  872.      parallelogram_x.push(xxyy[0]);\
  873.      parallelogram_y.push(xxyy[1]);\
  874.      draw_parallelogram();\
  875.      parallelogram_x.pop();parallelogram_y.pop();\
  876.      parallelogram_x.pop();parallelogram_y.pop();\
  877.     };\
  878.    };\
  879.   };\
  880.   if( multidraw_object_cnt == 3 ){\
  881.    parallelogram_x.pop();parallelogram_y.pop();\
  882.    var xxyy = multi_snap_check(parallelogram_x[l2]-parallelogram_x[l1] + parallelogram_x[l0],parallelogram_y[l2]-parallelogram_y[l1] + parallelogram_y[l0],parallelogram_snap);\
  883.    parallelogram_x.push(xxyy[0]);\
  884.    parallelogram_y.push(xxyy[1]);\
  885.    parallelogram_x.push(xy[0]);parallelogram_y.push(xy[1]);\
  886.    parallelogram_x.pop();parallelogram_y.pop();\
  887.    multidraw_object_cnt = 0;\
  888.    draw_parallelogram();\
  889.   };\
  890.  };function draw_parallelogram(){\
  891.   var len = parallelogram_x.length-1;\
  892.   context_parallelogram.clearRect(0,0,xsize,ysize);\
  893.   for(var p = 0 ; p < len ; p = p+4){\
  894.    context_parallelogram.beginPath();\
  895.    context_parallelogram.moveTo(parallelogram_x[p],parallelogram_y[p]);\
  896.    for( var m = p+1 ;m < p+4 ; m++){\
  897.     context_parallelogram.lineTo(parallelogram_x[m],parallelogram_y[m]);\
  898.    };\
  899.    context_parallelogram.lineTo(parallelogram_x[p],parallelogram_y[p]);\
  900.    context_parallelogram.closePath();\
  901.    context_parallelogram.fill();\
  902.    context_parallelogram.stroke();\
  903.   };\
  904.   return;\
  905.  };var canvas_parallelogram = create_canvas%d(10%d,xsize,ysize);var context_parallelogram = canvas_parallelogram.getContext(\"2d\");\
  906.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2);};\
  907.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2);};\
  908.  context_parallelogram.lineCap = \"round\";context_parallelogram.lineWidth = multilinewidth[%d];\
  909.  if(multilinewidth[%d]%%2 == 1){ context_parallelogram.translate(0.5,0.5);};\
  910.  context_parallelogram.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  911.  if(multifill[%d] != 0 ){var my_fill_color=\"rgba(\"+multifillcolors[%d]+\",\"+multifillopacity[%d]+\")\";if( multifill[%d] > 1 ){context_parallelogram.fillStyle = create_Pattern(0,0,parseInt(multifill[%d]),my_fill_color);}else{context_parallelogram.fillStyle = my_fill_color;};}else{context_parallelogram.fillStyle = \"rgba( 255,255,255,0)\";};\
  912.  if(multidash[%d] == 1 ){ if( context_parallelogram.setLineDash ){context_parallelogram.setLineDash([2,4]);}\
  913.  else{if(context_parallelogram.mozDash){context_parallelogram.mozDash = [2,4]};};};\
  914.  var parallelogram_x = new Array();var parallelogram_y = new Array();var parallelogram_snap = multisnaptogrid[%d];",
  915.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i,i);
  916.  
  917.   if( no_controls != 1 ){
  918.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt=0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  919.   if(multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='8' value='x1,x2...x_n' id='input_parallelogram_x' /> --- <input type='text' size='8' value='y1,y2...y_n' id='input_parallelogram_y' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_parallelogram_x,input_parallelogram_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  920.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  921.   }
  922.   else
  923.   {
  924.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  925.   }
  926.   break;
  927.   /*
  928.   images : identical ! to userdraw images,bogus_color
  929.   15/1/2021 : corrected long standing flaw regarding "centered" on external stuff
  930.   tested: bitmap,svg,TeX [tested KaTeX]
  931.   */
  932.   case 20:
  933.   fprintf(js_include_file,"var current_id = null;var external_div_cnt=0;\
  934.  function image_adjust(image,x,y){\
  935.   var centered = %d;\
  936.   var w = parseInt(image.width);var h = parseInt(image.height);\
  937.   if(w == 0 || h == 0 ){\
  938.    w = parseInt(window.getComputedStyle(image).width);\
  939.    h = parseInt(window.getComputedStyle(image).height);\
  940.   };\
  941.   switch(centered){\
  942.    case 0: return [x,y];break;\
  943.    case 1: return [x,parseInt(y-0.5*h)];break;\
  944.    case 2: return [parseInt(x+0.5*h),y];break;\
  945.    case 3: return [parseInt(x+0.5*h),parseInt(y-0.5*h)];break;\
  946.    case 4: return [parseInt(x-0.5*w),parseInt(y-0.5*h)];break;\
  947.    default: return [x,y];break;\
  948.   };\
  949.  };\
  950.  place_image_on_canvas = function(id){\
  951.   var thing = document.getElementById(id);\
  952.   var tag = thing.tagName;\
  953.   if(tag == 'SVG'){draw_mathml_svg(thing,id);return;};\
  954.   if(tag == 'DIV' || tag == 'SPAN' || tag == 'P' || tag == 'TD' || tag == 'TH'){draw_mathml_div(thing,id);return;};\
  955.   var src = thing.src;\
  956.   var image = new Image();\
  957.   image.src = src;\
  958.   image.id = 'placed_'+id;\
  959.   image.width = thing.width;\
  960.   image.height = thing.height;\
  961.   image.onload = function(){ current_id = id; };\
  962.   return;\
  963.  };\
  964.  function draw_mathml_div(thing,id){\
  965.   var fix_div = document.createElement('DIV');\
  966.   var new_id='placed_'+external_div_cnt+'_'+id;\
  967.   fix_div.setAttribute('id',new_id);\
  968.   var w = parseInt(thing.clientWidth);\
  969.   var h = parseInt(thing.clientHeight);\
  970.   fix_div.innerHTML = thing.innerHTML;\
  971.   fix_div.setAttribute('style','display:none;position;absolute;width:'+w+'px;height:'+h+'px');\
  972.   fix_div.width = w;fix_div.height = h;\
  973.   canvas_div.appendChild(fix_div);\
  974.   current_id = new_id;\
  975.   external_div_cnt++;\
  976.   return;\
  977.  };\
  978.  function draw_mathml_svg(thing,id){\
  979.   var fix_div = document.createElement('DIV');\
  980.   fix_div.setAttribute('style','display:none;position;relative');\
  981.   canvas_div.appendChild(fix_div);\
  982.   var image = new Image();\
  983.   var svg_string = new XMLSerializer().serializeToString(thing);\
  984.   var dom = self.URL || self.webkitURL || self;\
  985.   var svg = new Blob([svg_string], {type: \"image/svg+xml;charset=utf-8\"});\
  986.   var url = dom.createObjectURL(svg);\
  987.   image.src= url;\
  988.   image.id = 'placed_'+id;\
  989.   image.onload = function(){\
  990.    current_id = image.id;\
  991.    fix_div.innerHTML='<img src='+image.src+' id='+image.id+' alt=\"this should not happen today...!\"/>';\
  992.   };\
  993.   return;\
  994.  };\
  995.  function images(x,y,event_which,num){\
  996.   if(event_which == 1){ return;};\
  997.   if(num == 1 && current_id){\
  998.    var xy = multi_snap_check(x,y,images_snap);\
  999.    images_x.push(xy[0]);\
  1000.    images_y.push(xy[1]);\
  1001.    images_id.push(current_id);\
  1002.    current_id = null;\
  1003.   };\
  1004.   draw_images();\
  1005.  };\
  1006.  function draw_images(){\
  1007.   var xy;var img;var tag;\
  1008.   for(var i=0; i<2;i++){\
  1009.    for(var p = 0 ; p < images_x.length; p++){\
  1010.     if( images_id[p] ){\
  1011.      img = document.getElementById(images_id[p]);\
  1012.      tag = img.tagName;\
  1013.      xy = image_adjust(img,images_x[p],images_y[p]);\
  1014.      if( tag != 'IMG' ){\
  1015.       img.setAttribute('style','display:block;position:absolute;top:'+xy[1]+'px;left:'+xy[0]+'px;');\
  1016.      }else{\
  1017.       context_images.drawImage(img,xy[0],xy[1],img.width,img.height);\
  1018.      };\
  1019.     };\
  1020.    };\
  1021.   };\
  1022.  };\
  1023.  var canvas_images = create_canvas%d(10%d,xsize,ysize);\
  1024.  var context_images = canvas_images.getContext(\"2d\");\
  1025.  context_images.font = multifont_family;\
  1026.  context_images.fillStyle = \"rgba(\"+multifont_color+\",\"+multistrokeopacity[%d]+\")\";\
  1027.  var images_snap = multisnaptogrid[%d];\
  1028.  var images_x = new Array();var images_y = new Array();\
  1029.  var images_id = new Array();",use_offset,canvas_root_id,u,i,i);
  1030.   if( no_controls != 1  ){
  1031.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt=0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1032.   if( typeof(imagepalette) === 'object' ){\
  1033.   inner_html+=\"<td><table class='%s'><tr>\";\
  1034.   for(var im=0; im < imagepalette.length; im++){\
  1035.   if( im %% 4 == 0 ){ inner_html+=\"</tr><tr>\";};\
  1036.   inner_html+=\"<td><img onclick='javascript:place_image_on_canvas(this.id);' src='\"+imagepalette[im]+\"' id='imagepalette_\"+im+\"' alt='none'/></td>\";};\
  1037.   inner_html+=\"</tr></table></td><td>&nbsp;</td></tr>\";}else{inner_html+=\"<td>&nbsp;</td><td>&nbsp;</td></tr>\";};",u,i,canvas_root_id,u,table_css);
  1038.   }
  1039.   else
  1040.   {
  1041.     fprintf(js_include_file,"inner_html+=\"</table>\";tooltip_div.innerHTML += inner_html;userdraw_primitive = %d;",u);
  1042.   }
  1043.   break;
  1044.   /* curvedarrow/curvedarrows */
  1045.   case 21 ... 22:
  1046.   fprintf(js_include_file,"function curvedarrows(x,y,event_which,num){\
  1047.   var xy = [x,y];\
  1048.   if(event_which == 0){\
  1049.     xy = multi_snap_check(x,y,curvedarrows_snap);\
  1050.     if(num == 0 && multidraw_object_cnt == 0){curvedarrows_x = [];curvedarrows_y = [];curvedarrows_x[0] = xy[0];curvedarrows_y[0] = xy[1];}\
  1051.    else{curvedarrows_x.push(xy[0]);curvedarrows_y.push(xy[1]);};multidraw_object_cnt++;\
  1052.   }\
  1053.   else\
  1054.   {\
  1055.    if( multidraw_object_cnt < 3 ){curvedarrows_x.push(xy[0]);curvedarrows_y.push(xy[1]);draw_curvedarrows();curvedarrows_x.pop();curvedarrows_y.pop();};\
  1056.    if( multidraw_object_cnt == 3 ){curvedarrows_x.pop();curvedarrows_y.pop();curvedarrows_x.push(xy[0]);curvedarrows_y.push(xy[1]);multidraw_object_cnt = 0;draw_curvedarrows();};\
  1057.   };\
  1058.  };function draw_curvedarrows(){\
  1059.   var len = curvedarrows_x.length;var x1,y1,x2,y2,x3,y3;\
  1060.   context_curvedarrows.clearRect(0,0,xsize,ysize);\
  1061.   for(var p = 0 ; p < len ; p = p+3){\
  1062.    x1 = curvedarrows_x[p];x2 = curvedarrows_x[p+1];x3 = curvedarrows_x[p+2];y1 = curvedarrows_y[p];y2 = curvedarrows_y[p+1];y3 = curvedarrows_y[p+2];\
  1063.    var angle1 = Math.atan2(x3 - x2,y3 - y2) + Math.PI;\
  1064.    context_curvedarrows.beginPath();\
  1065.    context_curvedarrows.moveTo(x1,y1);\
  1066.    context_curvedarrows.quadraticCurveTo(x3,y3,x2,y2);\
  1067.    context_curvedarrows.moveTo(x2 - (arrow_head * Math.sin(angle1 - Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 - Math.PI / 6)));\
  1068.    context_curvedarrows.lineTo(x2, y2);\
  1069.    context_curvedarrows.lineTo(x2 - (arrow_head * Math.sin(angle1 + Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 + Math.PI / 6)));\
  1070.    context_curvedarrows.stroke();\
  1071.    context_curvedarrows.closePath();\
  1072.   };\
  1073.   return;\
  1074.  };var canvas_curvedarrows = create_canvas%d(10%d,xsize,ysize);\
  1075.  var context_curvedarrows =  canvas_curvedarrows.getContext(\"2d\");\
  1076.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  1077.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  1078.  context_curvedarrows.lineWidth = multilinewidth[%d];\
  1079.  if(multilinewidth[%d]%%2 == 1){ context_curvedarrows.translate(0.5,0.5);};\
  1080.  context_curvedarrows.lineCap = \"round\";\
  1081.  context_curvedarrows.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  1082.  context_curvedarrows.fillStyle = context_curvedarrows.strokeStyle;\
  1083.  if(multidash[%d] == 1 ){ if( context_curvedarrows.setLineDash ){\
  1084.  context_curvedarrows.setLineDash([2,4]);}else{if(context_curvedarrows.mozDash){\
  1085.  context_curvedarrows.mozDash = [2,4]};};};\
  1086.  var curvedarrows_x = new Array();var curvedarrows_y = new Array();\
  1087.  var curvedarrows_snap = multisnaptogrid[%d];",
  1088.   canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i);
  1089.  
  1090.   if( no_controls != 1 ){
  1091.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1092.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td><b>(<input type='text' size='5' value='x1 : y1' id='input_curvedarrows_x' />) -- (<input type='text' size='5' value='x2 : y2' id='input_curvedarrows_y' />) -- (<input type='text' size='5' value='x3 : y3' id='input_curvedarrows_r' />)</b></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_curvedarrows_x,input_curvedarrows_y,input_curvedarrows_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  1093.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  1094.   }
  1095.   else
  1096.   {
  1097.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  1098.   }
  1099.   break;
  1100.   /* curvedarrow2/curvedarrows2 */
  1101.   case 23 ... 24:
  1102.   fprintf(js_include_file,"function curvedarrows2(x,y,event_which,num){\
  1103.   var xy=[x,y];\
  1104.   if(event_which == 0){\
  1105.     xy = multi_snap_check(x,y,curvedarrows2_snap);\
  1106.     if(num == 0 && multidraw_object_cnt == 0){curvedarrows2_x = [];curvedarrows2_y = [];curvedarrows2_x[0] = xy[0];curvedarrows2_y[0] = xy[1];}\
  1107.    else{curvedarrows2_x.push(xy[0]);curvedarrows2_y.push(xy[1]);};multidraw_object_cnt++;\
  1108.   }\
  1109.   else\
  1110.   {\
  1111.   if( multidraw_object_cnt < 3 ){curvedarrows2_x.push(xy[0]);curvedarrows2_y.push(xy[1]);draw_curvedarrows2();curvedarrows2_x.pop();curvedarrows2_y.pop();};\
  1112.   if( multidraw_object_cnt == 3 ){curvedarrows2_x.pop();curvedarrows2_y.pop();curvedarrows2_x.push(xy[0]);curvedarrows2_y.push(xy[1]);multidraw_object_cnt = 0;draw_curvedarrows2();};\
  1113.   };\
  1114.  };function draw_curvedarrows2(){\
  1115.   var len = curvedarrows2_x.length;var x1,y1,x2,y2,x3,y3;\
  1116.   context_curvedarrows2.clearRect(0,0,xsize,ysize);\
  1117.   for(var p = 0 ; p < len ; p = p+3){\
  1118.    x1 = curvedarrows2_x[p];x2 = curvedarrows2_x[p+1];x3 = curvedarrows2_x[p+2];y1 = curvedarrows2_y[p];y2 = curvedarrows2_y[p+1];y3 = curvedarrows2_y[p+2];\
  1119.    var angle1 = Math.atan2(x3 - x2,y3 - y2) + Math.PI;\
  1120.    var angle2 = Math.atan2(x3 - x1,y3 - y1) + Math.PI;\
  1121.    context_curvedarrows2.beginPath();\
  1122.    context_curvedarrows2.moveTo(x1,y1);\
  1123.    context_curvedarrows2.moveTo(x1 - (arrow_head * Math.sin(angle2 - Math.PI / 6)),y1 - (arrow_head * Math.cos(angle2 - Math.PI / 6)));\
  1124.    context_curvedarrows2.lineTo(x1, y1);\
  1125.    context_curvedarrows2.lineTo(x1 - (arrow_head * Math.sin(angle2 + Math.PI / 6)),y1 - (arrow_head * Math.cos(angle2 + Math.PI / 6)));\
  1126.    context_curvedarrows2.moveTo(x1,y1);\
  1127.    context_curvedarrows2.quadraticCurveTo(x3,y3,x2,y2);\
  1128.    context_curvedarrows2.moveTo(x2 - (arrow_head * Math.sin(angle1 - Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 - Math.PI / 6)));\
  1129.    context_curvedarrows2.lineTo(x2, y2);\
  1130.    context_curvedarrows2.lineTo(x2 - (arrow_head * Math.sin(angle1 + Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 + Math.PI / 6)));\
  1131.    context_curvedarrows2.stroke();\
  1132.    context_curvedarrows2.closePath();\
  1133.   };\
  1134.   return;\
  1135.  };var canvas_curvedarrows2 = create_canvas%d(10%d,xsize,ysize);\
  1136.  var context_curvedarrows2 =  canvas_curvedarrows2.getContext(\"2d\");\
  1137.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  1138.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  1139.  context_curvedarrows2.lineWidth = multilinewidth[%d];\
  1140.  if(multilinewidth[%d]%%2 == 1){ context_curvedarrows2.translate(0.5,0.5);};\
  1141.  context_curvedarrows2.lineCap = \"round\";\
  1142.  context_curvedarrows2.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  1143.  context_curvedarrows2.fillStyle = context_curvedarrows2.strokeStyle;\
  1144.  if(multidash[%d] == 1 ){ if( context_curvedarrows2.setLineDash ){\
  1145.  context_curvedarrows2.setLineDash([2,4]);}else{if(context_curvedarrows2.mozDash){\
  1146.  context_curvedarrows2.mozDash = [2,4]};};};\
  1147.  var curvedarrows2_x = new Array();var curvedarrows2_y = new Array();\
  1148.  var curvedarrows2_snap = multisnaptogrid[%d];",canvas_root_id,u,i,i,i,i,i,i,i,i,i,i,i,i);
  1149.  
  1150.   if( no_controls != 1 ){
  1151.    fprintf(js_include_file,"inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1152.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td><b>(<input type='text' size='5' value='x1 : y1' id='input_curvedarrows2_x' />) -- (<input type='text' size='5' value='x2 : y2' id='input_curvedarrows2_y' />) -- (<input type='text' size='5' value='x3 : y3' id='input_curvedarrows2_r' />)</b></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_curvedarrows2_x,input_curvedarrows2_y,input_curvedarrows2_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  1153.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  1154.   }
  1155.   else
  1156.   {
  1157.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  1158.   }
  1159.   break;
  1160.   case 25 ... 26:
  1161.   fprintf(js_include_file,"function crosshairs(x,y,event_which,num){\
  1162.   if(event_which == 1){ return; };\
  1163.   var xy = multi_snap_check(x,y,crosshairs_snap);\
  1164.   if( num == 0 ){\
  1165.    crosshairs_x[0] = xy[0];\
  1166.    crosshairs_y[0] = xy[1];\
  1167.   }else{\
  1168.    crosshairs_x.push(xy[0]);\
  1169.    crosshairs_y.push(xy[1]);\
  1170.   };\
  1171.   draw_crosshairs();\
  1172.  };\
  1173.  function draw_crosshairs(){\
  1174.   var crosshair_size = %d;\
  1175.   context_crosshairs.clearRect(0,0,xsize,ysize);\
  1176.   var x1,x2,y1,y2;\
  1177.   for(var p = 0 ; p < crosshairs_x.length ; p++ ){\
  1178.    x1 = crosshairs_x[p] - crosshair_size;\
  1179.    x2 = crosshairs_x[p] + crosshair_size;\
  1180.    y1 = crosshairs_y[p] - crosshair_size;\
  1181.    y2 = crosshairs_y[p] + crosshair_size;\
  1182.    context_crosshairs.beginPath();\
  1183.    context_crosshairs.moveTo(x1,y1);\
  1184.    context_crosshairs.lineTo(x2,y2);\
  1185.    context_crosshairs.closePath();\
  1186.    context_crosshairs.stroke();\
  1187.    context_crosshairs.beginPath();\
  1188.    context_crosshairs.moveTo(x2,y1);\
  1189.    context_crosshairs.lineTo(x1,y2);\
  1190.    context_crosshairs.closePath();\
  1191.    context_crosshairs.stroke();\
  1192.   };\
  1193.  };\
  1194.  var canvas_crosshairs = create_canvas%d(100%d,xsize,ysize);var context_crosshairs = canvas_crosshairs.getContext(\"2d\");\
  1195.  if( multistrokeopacity[%d] > 1 ){ multistrokeopacity[%d] = (0.0039215*multistrokeopacity[%d]).toFixed(2); };\
  1196.  if( multifillopacity[%d] > 1 ){ multifillopacity[%d] =  (0.0039215*multifillopacity[%d]).toFixed(2); };\
  1197.  context_crosshairs.strokeStyle = \"rgba(\"+multistrokecolors[%d]+\",\"+multistrokeopacity[%d]+\")\";\
  1198.  context_crosshairs.fillStyle = context_crosshairs.strokeStyle;\
  1199.  context_crosshairs.lineWidth = multilinewidth[%d];if(multilinewidth[%d] %%2 == 1){ context_crosshairs.translate(0.5,0.5);};\
  1200.  var crosshairs_x = new Array();var crosshairs_y = new Array();\
  1201.  var crosshairs_snap = multisnaptogrid[%d];",crosshair_size,canvas_root_id,i,i,i,i,i,i,i,i,i,i,i,i);
  1202.   if( no_controls != 1){
  1203.    fprintf(js_include_file,"\
  1204.   inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1205.   if( multiuserinput[%d] == 1 ){inner_html+=\"<td>(<input type='text' size='5' value='' id='input_crosshairs_x' />:<input type='text' size='5' value='' id='input_crosshairs_y' />)</td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_crosshairs_x,input_crosshairs_y,null);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  1206.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  1207.   }
  1208.   else
  1209.   {
  1210.    fprintf(js_include_file,"userdraw_primitive = %d;",u);
  1211.   }
  1212.   break;
  1213.   case 27:break;
  1214.  
  1215.   /* einde switch */
  1216.   default : break;
  1217.   }
  1218.  } /* end for loop */
  1219.  
  1220.  /* id_z may be used for radius , text etc...e.g. no x-values,y-values, x&y-valuepairs*/
  1221.  fprintf(js_include_file,"update_draw_area%d = function(desc,id_x,id_y,id_z){\
  1222.  if( desc == 20 ){ draw_images();return;};\
  1223.  var x1,x2,x3,y1,y2,y3,z1,r,A,B,C;\
  1224.  x1 = id_x.value;y1 = id_y.value;if(id_z != null){z1 = id_z.value;};\
  1225.  if( (desc > 3 && desc < 12) || desc == 14 || desc == 15 ){A = coord_split(x1);B = coord_split(y1);if(A.length != 2 || B.length != 2){alert('coordinate mismatch');return;};x1 = x2px(safe_eval(A[0]));y1 = y2px(safe_eval(A[1]));x2 = x2px(safe_eval(B[0]));y2 = y2px(safe_eval(B[1]));if(desc == 10 || desc == 11 ){ C = coord_split(z1);x3 = x2px(safe_eval(C[0]));y3 = y2px(safe_eval(C[1]));};};\
  1226.  if( desc < 4 ){x1 = x2px(safe_eval(x1));y1 = y2px( safe_eval(y1));};\
  1227.  if( desc > 20 ){A = coord_split(x1);B = coord_split(y1);C = coord_split(z1);\
  1228.  if(A.length != 2 || B.length != 2 || C.length != 2){ alert('coordinate mismatch');return;};\
  1229.  x1 = x2px(safe_eval(A[0]));y1 = y2px(safe_eval(A[1]));\
  1230.  x2 = x2px(safe_eval(B[0]));y2 = y2px(safe_eval(B[1]));\
  1231.  x3 = x2px(safe_eval(C[0]));y3 = y2px(safe_eval(C[1]));};\
  1232.  switch(desc){",canvas_root_id);
  1233.  for(i=0 ; i < MAX_MULTI_PRIMITIVES ; i++ ){
  1234.   switch(draw_nums[i]){
  1235.    case -1: break;
  1236.    case 0: fprintf(js_include_file,"case 0:points(x1,y1,0,0);break;"); break;
  1237.    case 1: fprintf(js_include_file,"case 1:points(x1,y1,0,1);break;"); break;
  1238.    case 2: fprintf(js_include_file,"case 2:r = scale_x_radius(safe_eval(document.getElementById(id_z.id).value));multi_radius[0] = r;circles_x[0] = x1;circles_y[0] = y1;draw_circles();break;"); break;
  1239.    case 3: fprintf(js_include_file,"case 3:r = scale_x_radius(safe_eval(document.getElementById(id_z.id).value));multi_radius.push(r);circles_x.push(x1);circles_y.push(y1);draw_circles();break;"); break;
  1240.    case 4: fprintf(js_include_file,"case 4:lines_x[0] = x1;lines_x[1] = x2;lines_y[0] = y1;lines_y[1] = y2;calc_lines();draw_lines();break;"); break;
  1241.    case 5: fprintf(js_include_file,"case 5:lines_x.push(x1);lines_x.push(x2);lines_y.push(y1);lines_y.push(y2);calc_lines();draw_lines();break;"); break;
  1242.    case 6: fprintf(js_include_file,"case 6:segments_x[0] = x1;segments_x[1] = x2;segments_y[0] = y1;segments_y[1] = y2;draw_segments();break;"); break;
  1243.    case 7: fprintf(js_include_file,"case 7:segments_x.push(x1);segments_x.push(x2);segments_y.push(y1);segments_y.push(y2);draw_segments();break;"); break;
  1244.    case 8: fprintf(js_include_file,"case 8:arrows_x[0] = x1;arrows_x[1] = x2;arrows_y[0] = y1;arrows_y[1] = y2;draw_arrows();break;"); break;
  1245.    case 9: fprintf(js_include_file,"case 9:arrows_x.push(x1);arrows_x.push(x2);arrows_y.push(y1);arrows_y.push(y2);draw_arrows();break;"); break;
  1246.    case 10: fprintf(js_include_file,"case 10:triangles_x[0] = x1;triangles_x[1] = x2;triangles_x[2] = x3;triangles_y[0] = y1;triangles_y[1] = y2;triangles_y[2] = y3;draw_triangles();break;"); break;
  1247.    case 11: fprintf(js_include_file,"case 11:triangles_x.push(x1);triangles_x.push(x2);triangles_x.push(x3);triangles_y.push(y1);triangles_y.push(y2);triangles_y.push(y3);draw_triangles();break;"); break;
  1248.    case 12: fprintf(js_include_file,"case 12:A = coord_split(x1);B = coord_split(y1);var plus_len = A.length;if( plus_len != B.length){alert('mismatch between the number of x-values and  y-values');return;};for(var p = 0 ; p < plus_len ; p++){x1 = x2px(safe_eval(A[p]));y1 = y2px(safe_eval(B[p]));closedpoly_x.push(x1);closedpoly_y.push(y1);};x1 = x2px(safe_eval(A[0]));y1 = y2px(safe_eval(B[0]));closedpoly_x.push(x1);closedpoly_y.push(y1);draw_closedpoly();break;"); break;
  1249.    case 13: fprintf(js_include_file,"case 13:text_abc.push( document.getElementById(id_z.id).value);text(x2px(safe_eval(x1)),y2px(safe_eval(y1)),0,1);draw_text();break;"); break;
  1250.    case 14: fprintf(js_include_file,"case 14:rects_x[0] = x1;rects_x[1] = x2;rects_y[0] = y1;rects_y[1] = y2;draw_rects();break;"); break;
  1251.    case 15: fprintf(js_include_file,"case 15:rects_x.push(x1);rects_x.push(x2);rects_y.push(y1);rects_y.push(y2);draw_rects();break;"); break;
  1252.    case 16: fprintf(js_include_file,"case 16:polys_x[0] = x1;polys_x[1] = x2;polys_x[2] = x3;polys_y[0] = y1;polys_y[1] = y2;polys_y[2] = y3;draw_polys();break;"); break;
  1253.    case 17: fprintf(js_include_file,"case 17:polys_x.push(x1);polys_x.push(x2);polys_x.push(x3);polys_y.push(y1);polys_y.push(y2);polys_y.push(y3);draw_polys();break;"); break;
  1254.    case 18: fprintf(js_include_file,"case 18:parallelogram_x[0] = x1;parallelogram_x[1] = x2;parallelogram_x[2] = x3;parallelogram_y[0] = y1;parallelogram_y[1] = y2;parallelogram_y[2] = y3;draw_parallelogram();break;"); break;
  1255.    case 19: fprintf(js_include_file,"case 19:parallelogram_x.push(x1);parallelogram_x.push(x2);parallelogram_x.push(x3);parallelogram_y.push(y1);parallelogram_y.push(y2);parallelogram_y.push(y3);draw_parallelogram();break;"); break;
  1256.    case 20: fprintf(js_include_file,"case 20:draw_images();break;"); break;
  1257.    case 21: fprintf(js_include_file,"case 21:curvedarrows_x[0] = x1;curvedarrows_x[1] = x2;curvedarrows_x[2] = x3;curvedarrows_y[0] = y1;curvedarrows_y[1] = y2;curvedarrows_y[2] = y3;draw_curvedarrows();break;"); break;
  1258.    case 22: fprintf(js_include_file,"case 22:curvedarrows_x.push(x1);curvedarrows_x.push(x2);curvedarrows_x.push(x3);curvedarrows_y.push(y1);curvedarrows_y.push(y2);curvedarrows_y.push(y3);draw_curvedarrows();break;"); break;
  1259.    case 23: fprintf(js_include_file,"case 23:curvedarrows2_x[0] = x1;curvedarrows2_x[1] = x2;curvedarrows2_x[2] = x3;curvedarrows2_y[0] = y1;curvedarrows2_y[1] = y2;curvedarrows2_y[2] = y3;draw_curvedarrows2();break;"); break;
  1260.    case 24: fprintf(js_include_file,"case 24:curvedarrows2_x.push(x1);curvedarrows2_x.push(x2);curvedarrows2_x.push(x3);curvedarrows2_y.push(y1);curvedarrows2_y.push(y2);curvedarrows2_y.push(y3);draw_curvedarrows2();break;"); break;
  1261.    case 25: fprintf(js_include_file,"case 25:crosshairs(x1,y1,0,0);break;"); break;
  1262.    case 26: fprintf(js_include_file,"case 26:crosshairs(x1,y1,0,1);break;"); break;
  1263.    default:break;
  1264.   }
  1265.  }
  1266.  fprintf(js_include_file,"default: break;};return;};");
  1267.  
  1268.  /* begin clear_draw_area()*/
  1269.  fprintf(js_include_file,"clear_draw_area%d = function(type){switch(type){",canvas_root_id);
  1270.  for(i=0; i < MAX_MULTI_PRIMITIVES ; i++ ){
  1271.   switch( draw_nums[i] ){
  1272.    case -1: break;
  1273.    case 0: fprintf(js_include_file,"case 0:context_points.clearRect(0,0,xsize,ysize);points_x = [];points_y = [];break;");break;
  1274.    case 1: fprintf(js_include_file,"case 1:points_x.pop();points_y.pop();draw_points();break;");break;
  1275.    case 2: fprintf(js_include_file,"case 2:context_circles.clearRect(0,0,xsize,ysize);circles_x = [];circles_y = []; multi_radius = [];break;");break;
  1276.    case 3: fprintf(js_include_file,"case 3:circles_x.pop();circles_y.pop(); multi_radius.pop();draw_circles();break;");break;
  1277.    case 4: fprintf(js_include_file,"case 4:context_lines.clearRect(0,0,xsize,ysize);lines_x = [];lines_y = [];break;");break;
  1278.    case 5: fprintf(js_include_file,"case 5:lines_x.pop();lines_y.pop();lines_x.pop();lines_y.pop();draw_lines();break;");break;
  1279.    case 6: fprintf(js_include_file,"case 6:context_segments.clearRect(0,0,xsize,ysize);segments_x = [];segments_y = [];break;");break;
  1280.    case 7: fprintf(js_include_file,"case 7:segments_x.pop();segments_y.pop();segments_x.pop();segments_y.pop();draw_segments();break;");break;
  1281.    case 8: fprintf(js_include_file,"case 8:context_arrows.clearRect(0,0,xsize,ysize);arrows_x = [];arrows_y = [];break;");break;
  1282.    case 9: fprintf(js_include_file,"case 9:arrows_x.pop();arrows_y.pop();arrows_x.pop();arrows_y.pop();draw_arrows();break;");break;
  1283.    case 10:fprintf(js_include_file,"case 10:context_triangles.clearRect(0,0,xsize,ysize); triangles_x = [];triangles_y = [];break;");break;
  1284.    case 11:fprintf(js_include_file,"case 11:for(var p=0;p<3;p++){triangles_x.pop();triangles_y.pop();};draw_triangles();break;");break;
  1285.    case 12:fprintf(js_include_file,"case 12:context_closedpoly.clearRect(0,0,xsize,ysize);closedpoly_x = [];closedpoly_y = [];break;");break;
  1286.    case 13:fprintf(js_include_file,"case 13:context_text.clearRect(0,0,xsize,ysize);text_x.pop();text_y.pop();text_abc.pop();draw_text();break;");break;
  1287.    case 14:fprintf(js_include_file,"case 14:context_rects.clearRect(0,0,xsize,ysize);rects_x = [];rects_y = [];break;");break;
  1288.    case 15:fprintf(js_include_file,"case 15:rects_x.pop();rects_y.pop();rects_x.pop();rects_y.pop();draw_rects();break;");break;
  1289.    case 16:fprintf(js_include_file,"case 16:context_polys.clearRect(0,0,xsize,ysize); polys_x = [];polys_y = [];break;");break;
  1290.    case 17:fprintf(js_include_file,"case 17:for(var p=0;p<polynum;p++){polys_x.pop();polys_y.pop();};draw_polys();break;");break;
  1291.    case 18:fprintf(js_include_file,"case 18:context_parallelogram.clearRect(0,0,xsize,ysize); parallelogram_x = [];parallelogram_y = [];break;");break;
  1292.    case 19:fprintf(js_include_file,"case 19:for(var p = 0; p < 4;p++){ parallelogram_x.pop();parallelogram_y.pop();};draw_parallelogram();break;");break;
  1293.    case 20:fprintf(js_include_file,"case 20:context_images.clearRect(0,0,xsize,ysize);var len = images_id.length;if( len == 0 ){return;};var img = document.getElementById(images_id[len-1]);if( img.tagName == 'DIV' ){ img.innerHTML=null;};images_x.pop();images_y.pop();images_id.pop();draw_images();break;");break;
  1294.    case 21:fprintf(js_include_file,"case 21:context_curvedarrows.clearRect(0,0,xsize,ysize);curvedarrows_x = [];curvedarrows_y = [];break;");break;
  1295.    case 22:fprintf(js_include_file,"case 22:curvedarrows_x.pop();curvedarrows_y.pop();curvedarrows_x.pop();curvedarrows_y.pop();curvedarrows_x.pop();curvedarrows_y.pop();draw_curvedarrows();break;");break;
  1296.    case 23:fprintf(js_include_file,"case 23:context_curvedarrows2.clearRect(0,0,xsize,ysize);curvedarrows2_x = [];curvedarrows2_y = [];break;");break;
  1297.    case 24:fprintf(js_include_file,"case 24:curvedarrows2_x.pop();curvedarrows2_y.pop();curvedarrows2_x.pop();curvedarrows2_y.pop();curvedarrows2_x.pop();curvedarrows2_y.pop();draw_curvedarrows2();break;");break;
  1298.    case 25:fprintf(js_include_file,"case 25:context_crosshairs.clearRect(0,0,xsize,ysize);crosshairs_x = [];crosshairs_y = [];break;");break;
  1299.    case 26:fprintf(js_include_file,"case 26:crosshairs_x.pop();crosshairs_y.pop();draw_crosshairs();break;");break;
  1300.    default:break;
  1301.   }
  1302.  }
  1303.  fprintf(js_include_file,"};return;};");
  1304.  /* end clear_draw_area();*/
  1305.  
  1306.  
  1307.  /* add </table> is button controls are needed */
  1308.  if( no_controls != 1 ){fprintf(js_include_file,"inner_html+=\"</table>\";tooltip_div.innerHTML = inner_html;"); }
  1309.  free(str);
  1310.  
  1311. }
  1312. /* end 'void add_js_multidraw()' */
  1313.  
  1314.  
  1315. /*  if( desc >20 ){A = coord_split(x1);B = coord_split(y1);C = coord_split(z1);if(A.length != 2 || B.length != 2 || C.length != 2 ){alert('coordinate mismatch');return;};x1 = x2px(safe_eval(A[0]));y1 = y2px(safe_eval(A[1]));x2 = x2px(safe_eval(B[0]));y2 = y2px(safe_eval(B[1]));x3 = x2px(safe_eval(C[0]));y3 = y2px(safe_eval(C[1]));};};};\
  1316.  
  1317.  
  1318.  
  1319.    inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1320.    if( multiuserinput[%d] == '1' ){inner_html+=\"<td><b>(<input type='text' size='5' value='x1 : y1' id='input_curvedarrows2_x' />) -- (<input type='text' size='5' value='x2 : y2' id='input_curvedarrows2_y' />) -- (<input type='text' size='5' value='x3 : y3' id='input_curvedarrows2_r' />)</b></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_curvedarrows2_x,input_curvedarrows2_y,input_curvedarrows2_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  1321.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  1322.  
  1323.  
  1324.    inner_html+=\"<tr><td><input type='button' onclick='javascript:userdraw_primitive=%d;multidraw_object_cnt = 0;' value='\"+multilabel[%d]+\"' /></td><td><input type='button' onclick='javascript:clear_draw_area%d(%d);' value='delete' /></td>\";\
  1325.    if( multiuserinput[%d] == '1' ){inner_html+=\"<td><b>(<input type='text' size='5' value='x1 : y1' id='input_curvedarrows_x' />) -- (<input type='text' size='5' value='x2 : y2' id='input_curvedarrows_y' />) -- (<input type='text' size='5' value='x3 : y3' id='input_curvedarrows_r' />)</b></td><td><input type='button' id='canvasdraw_ok_button' onclick='javascript:update_draw_area%d(%d,input_curvedarrows_x,input_curvedarrows_y,input_curvedarrows_r);' value='OK' /></td></tr>\";}else{inner_html+=\"</tr>\";};",
  1326.    u,i,canvas_root_id,u,i,canvas_root_id,u);
  1327.  
  1328.  
  1329.  
  1330. */
  1331.  
  1332.