#include "canvasdraw.h"
 
 
 
void add_js_userdraw(char *draw_type,char *stroke_color,double stroke_opacity,int crosshair_size,int arrow_head,int use_offset, char *css_class,int use_snap,int canvas_type,int use_filled,char * fill_color,double fill_opacity,int line_width,char *font_family){
 
 
 
#define MAX_USERDRAW_PRIMITIVES 59
 
static char userdraw_primitives[MAX_USERDRAW_PRIMITIVES][32] = {
 
"point","points", /* 0,1 */
 
"crosshair","crosshairs",/* 2,3 */
 
"circle","circles",/* 4,5 */
 
"segment","segments", /* 6,7 */
 
"demiline","halfline","demilines","halflines", /* 8,9,10,11 */
 
"line","lines", /* 12,13 */
 
"hline","hlines", /* 14,15 */
 
"vline","vlines", /* 16,17 */
 
"arrow","arrows", /* 18,19 */
 
"arrow2","arrows2", /* 20,21 */
 
"curvedarrow","curvedarrows",/* 22,23 */
 
"curvedarrow2","curvedarrows2", /* 24,25 */
 
"freehandline","path","freehandlines","paths", /* 26,27,28,29 */
 
"poly","polys",/*poly[3]...polys[9] */ /* 30,31 */
 
"polygon","polygons", /* 32,33 */
 
"polyline","polylines", /* 34,35 */
 
"triangle","triangles", /* 36,37 */
 
"rect","rects",/* 38,39 */
 
"roundrect","roundrects", /* 40,41*/
 
"arc","arcs", /* 42,43 */
 
"text", /* 44 */
 
"image","images", /* 45 46*/
 
"input","inputs", /* 47,48*/
 
"clickfill","gridfill","diamondfill","dotfill","hatchfill","textfill",/* 49,50,51,52,53,54 */
 
"parallelogram","parallelograms",/* 55,56 */
 
"function","functions" /* 57,58 is the same as command "userinput function"*/
 
};
 
 
 
/*1+strlen() of words "point","points",... == 6,7,..*/
 
//static int userdraw_primitives_length[MAX_USERDRAW_PRIMITIVES] = {6,7,10,11,7,8,8,9,9,9,10,10,5,6,6,7,6,7,6,7,7,8,12,13,13,14,13,5,14,6,5,6,8,9,9,10,9,10,5,6,10,11,4,5,5,6,7,6,7,19,12,8,10,9,14,15};
 
 
 
static int userdraw_primitives_length[MAX_USERDRAW_PRIMITIVES] = {6,7,10,11,7,8,8,9,9,9,10,10,5,6,6,7,6,7,6,7,7,8,12,13,13,14,13,5,14,6,5,6,8,9,9,10,9,10,5,6,10,11,4,5,5,6,7,6,7,10,9,12,8,10,9,14,15,9,10};
 
int p,n;
 
int found = 0;
 
int draw_num = -1;
 
int equal = -1;;
 
int polynum = -1;
 
 
 
 
 
if(strncmp(draw_type
,"functions",9) == 0){  
 draw_num = 58; polynum = (int) (draw_type[9]-'0');found = 1;
 
// fprintf(stdout,"found polys%d<br>",polynum);
 
}
 
else
 
{
 
if(strncmp(draw_type
,"polys",5) == 0){  
 draw_num = 31; polynum = (int) (draw_type[5]-'0');found = 1;
 
// fprintf(stdout,"found polys%d<br>",polynum);
 
}
 
else
 
{
 
 if( strncmp(draw_type
,"poly",4)  == 0 && ( strstr(draw_type
,"polygon") == NULL 
&& strstr(draw_type
,"polyline") == NULL 
) ){  
  draw_num = 30; polynum = (int) (draw_type[4]-'0');found = 1;
 
//  fprintf(stdout,"found poly%d<br>",polynum);
 
 }
 
 else
 
 {
 
  for( p = 0; p < MAX_USERDRAW_PRIMITIVES ; p++ ){
 
   equal 
= strncmp(userdraw_primitives
[p
],draw_type
,userdraw_primitives_length
[p
]); 
/* remake array:  static int userdraw_primitives_length[MAX_USERDRAW_PRIMITIVES]*/
 
/* fprintf(stdout,"%d,",1+strlen(userdraw_primitives[p]));*/
 
   if( equal == 0 ){
 
/*    fprintf(stdout,"found %s p=%d<br>",userdraw_primitives[p],p);*/
 
    draw_num= p;found=1; break;
 
   }
 
  }
 
 }
 
}
 
}
 
if( found == 0 ){canvas_error("unknown userdraw primitive found...typo?");}
 
 
 
/* begin user_draw() */
 
 
 
/* touchend routine for touch devices */
 
function user_drawstop(evt){\
 
 if(!user_is_dragging){user_drag(evt);return;};\
 
 if(user_is_dragging){user_draw(evt);return;};\
 
};");
 
 
 
fprintf(js_include_file
,"function user_draw(evt){\  
if(evt.button == 2){remove_last();return;};\
 
var mouse = getMouse(evt,canvas_userdraw);\
 
var xy = multisnap_check(mouse.x,mouse.y,use_snap);\
 
user_is_dragging = false;\
 
var x = xy[0];var y = xy[1];\
 
if(x>forbidden_zone[0] && y>forbidden_zone[1]){console.log('drawing in zoom area...');return;};\
 
");
 
int temp_reply_format = 22;
 
switch( draw_num ){
 
 default: break;
 
 case 0:temp_reply_format 
= 8;fprintf(js_include_file
,"points(x,y,0,0);");break;  
 case 1:temp_reply_format 
= 8;fprintf(js_include_file
,"points(x,y,0,1);");break;  
 case 2:temp_reply_format 
= 8;fprintf(js_include_file
,"crosshairs(x,y,0,0);");break;  
 case 3:temp_reply_format 
= 8;fprintf(js_include_file
,"crosshairs(x,y,0,1);");break;  
 case 4:temp_reply_format 
= 10;fprintf(js_include_file
,"circles(x,y,0,0);");break;  
 case 5:temp_reply_format 
= 10;fprintf(js_include_file
,"circles(x,y,0,1);");break;  
 case 6:temp_reply_format 
= 11;fprintf(js_include_file
,"segments(x,y,0,0);");break;  
 case 7:temp_reply_format 
= 11;fprintf(js_include_file
,"segments(x,y,0,1);");break;  
 case 8 ... 
9:temp_reply_format 
= 11;fprintf(js_include_file
,"demilines(x,y,0,0);");break;  
 case 10 ... 
11:temp_reply_format 
= 11;fprintf(js_include_file
,"demilines(x,y,0,1);");break;  
 case 12:temp_reply_format 
= 11;fprintf(js_include_file
,"lines(x,y,0,0);");break;  
 case 13:temp_reply_format 
= 11;fprintf(js_include_file
,"lines(x,y,0,1);");break;  
 case 14:temp_reply_format 
= 11;fprintf(js_include_file
,"hlines(x,y,0,0);");break;  
 case 15:temp_reply_format 
= 11;fprintf(js_include_file
,"hlines(x,y,0,1);");break;  
 case 16:temp_reply_format 
= 11;fprintf(js_include_file
,"vlines(x,y,0,0);");break;  
 case 17:temp_reply_format 
= 11;fprintf(js_include_file
,"vlines(x,y,0,1);");break;  
 case 18:temp_reply_format 
= 11;fprintf(js_include_file
,"arrows(x,y,0,0);");break;  
 case 19:temp_reply_format 
= 11;fprintf(js_include_file
,"arrows(x,y,0,1);");break;  
 case 20:temp_reply_format 
= 11;fprintf(js_include_file
,"arrows2(x,y,0,0);");break;  
 case 21:temp_reply_format 
= 11;fprintf(js_include_file
,"arrows2(x,y,0,1);");break;  
 case 22:temp_reply_format 
= 2;fprintf(js_include_file
,"curvedarrows(x,y,0,0);");break;  
 case 23:temp_reply_format 
= 2;fprintf(js_include_file
,"curvedarrows(x,y,0,1);");break;  
 case 24:temp_reply_format 
= 2;fprintf(js_include_file
,"curvedarrows2(x,y,0,0);");break;  
 case 25:temp_reply_format 
= 2;fprintf(js_include_file
,"curvedarrows2(x,y,0,1);");break;  
 case 26 ... 
27:temp_reply_format 
= 6;fprintf(js_include_file
,"paths(x,y,0,0);");break;  
 case 28 ... 
29:temp_reply_format 
= 6;fprintf(js_include_file
,"paths(x,y,0,0);");break;  
 case 30:temp_reply_format 
= 2;fprintf(js_include_file
,"polys(x,y,0,0);");break;  
 case 31:temp_reply_format 
= 2;fprintf(js_include_file
,"polys(x,y,0,1);");break;  
 case 32:temp_reply_format 
= 2;fprintf(js_include_file
,"polygon(x,y,0,0);");break;  
 case 33:temp_reply_format 
= 2;fprintf(js_include_file
,"polygon(x,y,0,1);");break;  
 case 34:temp_reply_format 
= 23;fprintf(js_include_file
,"polylines(x,y,0,1);");break;  
 case 35:temp_reply_format 
= 23;fprintf(js_include_file
,"polylines(x,y,0,1);");break;  
 case 36:temp_reply_format 
= 2;fprintf(js_include_file
,"triangles(x,y,0,0);");break;  
 case 37:temp_reply_format 
= 2;fprintf(js_include_file
,"triangles(x,y,0,1);");break;  
 case 38:temp_reply_format 
= 2;fprintf(js_include_file
,"rects(x,y,0,0);");break;  
 case 39:temp_reply_format 
= 2;fprintf(js_include_file
,"rects(x,y,0,1);");break;  
 case 40:temp_reply_format 
= 2;fprintf(js_include_file
,"roundrects(x,y,0,0);");break;  
 case 41:temp_reply_format 
= 2;fprintf(js_include_file
,"roundrects(x,y,0,1);");break;  
 case 42:temp_reply_format 
= 25;js_function
[JS_FIND_ANGLE
] = 1; fprintf(js_include_file
,"arcs(x,y,0,0);");break;  
 case 43:temp_reply_format 
= 25;js_function
[JS_FIND_ANGLE
] = 1; fprintf(js_include_file
,"arcs(x,y,0,1);");break;  
 case 44:temp_reply_format 
= 17;js_function
[DRAW_SUBSUP
] = 1;fprintf(js_include_file
,"text(x,y,0,1);");break;  
 case 45:temp_reply_format 
= 17;fprintf(js_include_file
,"images(x,y,0,0);");break;  
 case 46:temp_reply_format 
= 17;fprintf(js_include_file
,"images(x,y,0,1);");break;  
 case 47:temp_reply_format 
= 27;fprintf(js_include_file
,"inputs(x,y,0,0);");break;  
 case 48:temp_reply_format 
= 27;fprintf(js_include_file
,"inputs(x,y,0,1);");break;  
 case 49 ... 54 :
 
 /*
 
 "clickfill 49","gridfill 50","diamondfill 51","dotfill 52","hatchfill 53","textfill 54", 49,50,51,52,53,54
 
use_filled ...  0:no fill, 1:fill,2=grid?,3=hatch?,4=diamond?,5=dot?,6=image ?
 
 */
 
 temp_reply_format = 10;
 
 fprintf(js_include_file
,"clickfill(x,y,0,1);");  
 if( draw_num == 49 ){ use_filled = 1;}
 
 else{
 
 if( draw_num == 50 ){js_function[DRAW_GRIDFILL] = 1;use_filled = 2;}
 
 else{
 
 if( draw_num == 51 ){js_function[DRAW_DIAMONDFILL] = 1;use_filled = 4;}
 
 else{
 
 if( draw_num == 52 ){js_function[DRAW_DOTFILL] = 1;use_filled = 5;}
 
 else{
 
 if( draw_num == 53 ){js_function[DRAW_HATCHFILL] = 1;use_filled = 3;}
 
 else{
 
 if( draw_num == 54 ){js_function[DRAW_TEXTFILL] = 1;use_filled = 7;}}}}}}
 
 break;
 
 
 
 case 55:temp_reply_format 
= 2;fprintf(js_include_file
,"parallelograms(x,y,0,0);");break;  
 case 56:temp_reply_format 
= 2;fprintf(js_include_file
,"parallelograms(x,y,0,1);");break;  
 case 57 ... 58:
 
 fprintf(stdout
,"functions num = %d;",(int) (draw_type
[9]-'0')); /* functions4 == 9*/  
 if(reply_format == 0 || reply_format != -1){reply_format = 24;}
 
 break;
 
 
 
}
 
fprintf(js_include_file
," return;};");  
 
 
if( reply_format == 0 ){reply_format = temp_reply_format;}
 
 
 
/* begin user_drag()  */
 
fprintf(js_include_file
,"function user_drag(evt){\  
var mouse = getMouse(evt,canvas_userdraw);\
 
if(isTouch){var xy = multisnap_check(mouse.x,mouse.y,use_snap);};\
 
var x = mouse.x;var y = mouse.y;\
 
user_is_dragging = true;\
 
if(x>forbidden_zone[0] && y>forbidden_zone[1]){return;};");
 
switch( draw_num ){
 
 case 0:fprintf(js_include_file
,"return;");break;  
 case 1:fprintf(js_include_file
,"return;");break;  
 case 2:fprintf(js_include_file
,"return;");break;  
 case 3:fprintf(js_include_file
,"return;");break;  
 case 4:fprintf(js_include_file
,"circles(x,y,1,0);return;");break;  
 case 5:fprintf(js_include_file
,"circles(x,y,1,1);return;");break;  
 case 6:fprintf(js_include_file
,"segments(x,y,1,0);");break;  
 case 7:fprintf(js_include_file
,"segments(x,y,1,1);return;");break;  
 case 8 ... 
9:fprintf(js_include_file
,"demilines(x,y,1,0);return;");break;  
 case 10 ... 
11:fprintf(js_include_file
,"demilines(x,y,1,1);return;");break;  
 case 12:fprintf(js_include_file
,"lines(x,y,1,0);return;");break;  
 case 13:fprintf(js_include_file
,"lines(x,y,1,1);return;");break;  
 case 14:fprintf(js_include_file
,"hlines(x,y,1,0);return;");break;  
 case 15:fprintf(js_include_file
,"hlines(x,y,1,1);return;");break;  
 case 16:fprintf(js_include_file
,"vlines(x,y,1,0);return;");break;  
 case 17:fprintf(js_include_file
,"vlines(x,y,1,1);return;");break;  
 case 18:fprintf(js_include_file
,"arrows(x,y,1,0);return;");break;  
 case 19:fprintf(js_include_file
,"arrows(x,y,1,1);return;");break;  
 case 20:fprintf(js_include_file
,"arrows2(x,y,1,0);return;");break;  
 case 21:fprintf(js_include_file
,"arrows2(x,y,1,1);return;");break;  
 case 22:fprintf(js_include_file
,"curvedarrows(x,y,1,0);return;");break;  
 case 23:fprintf(js_include_file
,"curvedarrows(x,y,1,1);return;");break;  
 case 24:fprintf(js_include_file
,"curvedarrows2(x,y,1,0);return;");break;  
 case 25:fprintf(js_include_file
,"curvedarrows2(x,y,1,1);return;");break;  
 case 26 ... 
27:fprintf(js_include_file
,"paths(x,y,1,0);return;");break;  
 case 28 ... 
29:fprintf(js_include_file
,"paths(x,y,1,0);return;");break;  
 case 30:fprintf(js_include_file
,"polys(x,y,1,0);return;");break;  
 case 31:fprintf(js_include_file
,"polys(x,y,1,1);return;");break;  
 case 32:fprintf(js_include_file
,"polygon(x,y,1,0);return;");break;  
 case 33:fprintf(js_include_file
,"polygon(x,y,1,1);return;");break;  
 case 34:fprintf(js_include_file
,"polylines(x,y,1,1);return;");break;  
 case 35:fprintf(js_include_file
,"polylines(x,y,1,1);return;");break;  
 case 36:fprintf(js_include_file
,"triangles(x,y,1,0);return;");break;  
 case 37:fprintf(js_include_file
,"triangles(x,y,1,1);return;");break;  
 case 38:fprintf(js_include_file
,"rects(x,y,1,0);return;");break;  
 case 39:fprintf(js_include_file
,"rects(x,y,1,1);return;");break;  
 case 40:fprintf(js_include_file
,"roundrects(x,y,1,0);return;");break;  
 case 41:fprintf(js_include_file
,"roundrects(x,y,1,1);return;");break;  
 case 42:fprintf(js_include_file
,"arcs(x,y,1,0);return;");break;  
 case 43:fprintf(js_include_file
,"arcs(x,y,1,1);return;");break;  
 case 44:fprintf(js_include_file
,"return;");break;  
 case 45:fprintf(js_include_file
,"return;");break;  
 case 46:fprintf(js_include_file
,"return;");break;  
 case 47:fprintf(js_include_file
,"return;");break;  
 case 48:fprintf(js_include_file
,"return;");break;  
 case 49:fprintf(js_include_file
,"return;");break;  
 case 50:fprintf(js_include_file
,"return;");break;  
 case 51:fprintf(js_include_file
,"return;");break;  
 case 52:fprintf(js_include_file
,"return;");break;  
 case 53:fprintf(js_include_file
,"return;");break;  
 case 54:fprintf(js_include_file
,"return;");break;  
 case 55:fprintf(js_include_file
,"parallelograms(x,y,1,0);return;");break;  
 case 56:fprintf(js_include_file
,"parallelograms(x,y,1,1);return;");break;  
 case 57 ... 58: break;
 
}
 
 
 
 
 
/* add all stuff needed to draw the selected primitives... */
 
switch( draw_num ){
 
/* point/points */
 
 case -1 : break;
 
 case 0 ... 1:
 
context_userdraw.fillStyle = \"rgba(%s,%.2f)\";\
 
function redraw_userdraw(){draw_points();}\
 
function remove_last(){if( userdraw_x.length > 0 ){userdraw_x.pop();userdraw_y.pop();draw_points();};return;};\
 
function points(x,y,event_which,num){\
 
 if(event_which == 1){ return; };\
 
 if( num == 0 ){\
 
  userdraw_x[0] = x;\
 
  userdraw_y[0] = y;\
 
 }else{\
 
  userdraw_x.push(x);\
 
  userdraw_y.push(y);\
 
 };\
 
 draw_points();\
 
};\
 
function draw_points(){\
 
 var len = userdraw_x.length;\
 
 var radius = 2*(context_userdraw.lineWidth);\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 var r = 2*Math.PI;\
 
 for(var p = 0 ; p < len ; p++ ){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.arc(userdraw_x[p],userdraw_y[p],radius,0,r,false);\
 
  context_userdraw.closePath();context_userdraw.fill();\
 
 };\
 
};",stroke_color,stroke_opacity);
 
 break;
 
  /* crosshair /crosshairs */
 
 case 2 ... 3:
 
function redraw_userdraw(){draw_crosshairs();};\
 
function remove_last(){if( userdraw_x.length > 0 ){userdraw_x.pop();userdraw_y.pop();draw_crosshairs();};return;};\
 
function crosshairs(x,y,event_which,num){\
 
 if(event_which == 1){ return; };\
 
 if( num == 0 ){\
 
  userdraw_x[0] = x;\
 
  userdraw_y[0] = y;\
 
 }else{\
 
  userdraw_x.push(x);\
 
  userdraw_y.push(y);\
 
 };\
 
 draw_crosshairs();\
 
};\
 
function draw_crosshairs(){\
 
 var crosshair_size = %d;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 var x1,x2,y1,y2;\
 
 var len = userdraw_x.length;\
 
 for(var p = 0 ; p < len ; p++ ){\
 
  x1 = userdraw_x[p] - crosshair_size;\
 
  x2 = userdraw_x[p] + crosshair_size;\
 
  y1 = userdraw_y[p] - crosshair_size;\
 
  y2 = userdraw_y[p] + crosshair_size;\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(x1,y1);\
 
  context_userdraw.lineTo(x2,y2);\
 
  context_userdraw.closePath();\
 
  context_userdraw.stroke();\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(x2,y1);\
 
  context_userdraw.lineTo(x1,y2);\
 
  context_userdraw.closePath();\
 
  context_userdraw.stroke();\
 
 };\
 
};",crosshair_size);
 
 break;
 
 /* circle/circles */
 
 case 4 ... 5 :
 
function redraw_userdraw(){draw_circles();};\
 
function remove_last(){if( userdraw_x.length > 0 ){userdraw_x.pop();userdraw_y.pop();userdraw_radius.pop();draw_circles();};return;};\
 
function circles(x,y,event_which,num){\
 
 var last = userdraw_x.length - 1;\
 
 var xc = userdraw_x[last];\
 
 var yc = userdraw_y[last];\
 
 if(event_which == 0){\
 
  if( xy_cnt == 0 ){\
 
   if( num  == 0 ){\
 
    userdraw_x[0]=x;userdraw_y[0]=y;userdraw_radius[0]=4;\
 
   }\
 
   else\
 
   {\
 
    userdraw_x.push(x);userdraw_y.push(y);userdraw_radius.push(4);\
 
   };\
 
  };\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_radius[last] = parseInt(Math.sqrt( (x - xc)*(x - xc) + (y - yc)*(y - yc) ));\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  if( num == 0 ){\
 
   userdraw_x = [];userdraw_y = [];\
 
   userdraw_x[0] = xc;userdraw_y[0] = yc;\
 
  };\
 
 };\
 
 draw_circles();\
 
};\
 
function draw_circles(){\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 var len = userdraw_x.length;\
 
 var r = 2*Math.PI;\
 
 for(var p = 0 ; p < len ; p++ ){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.arc(userdraw_x[p],userdraw_y[p],userdraw_radius[p],0,r,false);\
 
  context_userdraw.closePath();\
 
  if(use_filled!=0){context_userdraw.fill();};\
 
  context_userdraw.stroke();\
 
 };\
 
 return;\
 
};");
 
 break;
 
 
 
  /* segment/segments */
 
 case 6 ... 7 :
 
function redraw_userdraw(){draw_segments();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_segments();};return;};\
 
function segments(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_segments();\
 
    userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_segments();\
 
 };\
 
};\
 
function draw_segments(){\
 
 var len = userdraw_x.length;\
 
 if( len%%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
   context_userdraw.lineTo(userdraw_x[p+1],userdraw_y[p+1]);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};");
 
 
 
 /* "demiline","demilines","halfline","halflines"  8,9,10,11 */
 
 case 8 ... 11 :
 
function redraw_userdraw(){draw_demilines();};\
 
function find_inf_point(x1,y1,x2,y2){\
 
 if(x1<x2+2 && x1>x2-2){if(y1<y2){return [x1,y1,x1,ysize];}else{return [x1,0,x1,y1];};};\
 
 var rc = (y2 - y1)/(x2 - x1);var q = y1 - (x1)*rc;\
 
 if( x1 < x2 ){ return [x1,y1,xsize,rc*xsize+q];}else{return [x1,y1,0,q];};\
 
};\
 
function calc_lines(){\
 
 var len = userdraw_x.length;\
 
 var points = find_inf_point(userdraw_x[len-2],userdraw_y[len-2],userdraw_x[len-1],userdraw_y[len-1]);\
 
 userdraw_x[len-2] = points[0];\
 
 userdraw_y[len-2] = points[1];\
 
 userdraw_x[len-1] = points[2];\
 
 userdraw_y[len-1] = points[3];\
 
};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_demilines();};return;};\
 
function demilines(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_demilines();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  calc_lines();\
 
  draw_demilines();\
 
 };\
 
};\
 
function draw_demilines(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
   context_userdraw.lineTo(userdraw_x[p+1],userdraw_y[p+1]);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};");
 
 break;
 
  /* line/lines */
 
 case 12 ... 13 :
 
function redraw_userdraw(){calc_lines();draw_lines();};\
 
function calc_lines(){\
 
 var marge = 2;var len = userdraw_x.length;\
 
 var tmp_x = new Array(len);\
 
 var tmp_y = new Array(len);\
 
 var pp;\
 
 for(var p = 0 ; p < len ;p = p+2){\
 
  pp = p+1;\
 
  if(userdraw_x[p] < userdraw_x[pp]+marge && userdraw_x[p] > userdraw_x[pp]-marge){\
 
   tmp_x[p] = userdraw_x[p];tmp_x[pp] = userdraw_x[pp];\
 
   tmp_y[p] = 0;tmp_y[pp] = ysize;\
 
  }\
 
  else\
 
  {\
 
   if(userdraw_y[p] < userdraw_y[pp]+marge && userdraw_y[p] > userdraw_y[pp]-marge){\
 
    tmp_x[p] = 0;tmp_x[pp] = xsize;\
 
    tmp_y[p] = userdraw_y[p];tmp_y[pp] = userdraw_y[pp];\
 
   }\
 
   else\
 
   {\
 
    tmp_x[p] = 0;tmp_x[pp] = xsize;\
 
    tmp_y[p] = userdraw_y[p] - (userdraw_x[p])*(userdraw_y[pp] - userdraw_y[p])/(userdraw_x[pp] - userdraw_x[p]);\
 
    tmp_y[pp] = userdraw_y[p] + (xsize - userdraw_x[p])*(userdraw_y[pp] - userdraw_y[p])/(userdraw_x[pp] - userdraw_x[p]);\
 
   };\
 
  };\
 
 };\
 
 return {x:tmp_x,y:tmp_y};\
 
};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_lines();};return;};\
 
function lines(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_lines();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_lines();\
 
 };\
 
};\
 
function draw_lines(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  var xy = calc_lines();\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(xy.x[p],xy.y[p]);\
 
   context_userdraw.lineTo(xy.x[p+1],xy.y[p+1]);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};");
 
 break;
 
 /* hline/hlines 14,15 */
 
 case 14 ... 15:
 
function redraw_userdraw(){draw_hlines();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_hlines();};return;};\
 
function hlines(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(0);userdraw_y.push(y);\
 
  userdraw_x.push(xsize);userdraw_y.push(y);\
 
  draw_hlines();\
 
 };\
 
};\
 
function draw_hlines(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
   context_userdraw.lineTo(userdraw_x[p+1],userdraw_y[p+1]);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};");
 
 
 
 break;
 
 /* vline,vlines  16,17 */
 
 case 16 ... 17:
 
function redraw_userdraw(){draw_vlines();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_vlines();};return;};\
 
function vlines(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(0);\
 
  userdraw_x.push(x);userdraw_y.push(ysize);\
 
  draw_vlines();\
 
 };\
 
};\
 
function draw_vlines(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
   context_userdraw.lineTo(userdraw_x[p+1],userdraw_y[p+1]);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;};");
 
 
 
 break;
 
 /* arrow/arrows */
 
 case 18 ... 19 :
 
function redraw_userdraw(){draw_arrows();};\
 
context_userdraw.fillStyle = \"rgba(%s,%.2f)\";\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_arrows();};return;};\
 
function arrows(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_arrows();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_arrows();\
 
 };\
 
};\
 
function draw_arrows(){\
 
 var arrow_head = %d;\
 
 var len = userdraw_x.length;\
 
 var x1,y1,x2,y2,dx,dy,h;\
 
 if( len%%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   x1 = userdraw_x[p];y1 = userdraw_y[p];x2 = userdraw_x[p+1];y2 = userdraw_y[p+1];dx = x2 - x1;dy = y2 - y1;\
 
   context_userdraw.save();\
 
   context_userdraw.setLineDash([]);\
 
   context_userdraw.translate(x2,y2);\
 
   context_userdraw.rotate(Math.atan2(dy,dx));\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(0,0);\
 
   context_userdraw.lineTo(-1*arrow_head,-0.5*arrow_head);\
 
   context_userdraw.lineTo(-1*arrow_head, 0.5*arrow_head);\
 
   context_userdraw.closePath();\
 
   context_userdraw.fill();\
 
   context_userdraw.stroke();\
 
   context_userdraw.restore();\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(x1,y1);\
 
   context_userdraw.lineTo(x2,y2);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};",stroke_color,stroke_opacity,arrow_head);
 
 break;
 
 /* arrow/arrows */
 
 case 20 ... 21 :
 
function redraw_userdraw(){draw_arrows2();};\
 
context_userdraw.fillStyle = \"rgba(%s,%.2f)\";\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_arrows();};return;};\
 
function arrows2(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_arrows2();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_arrows2();\
 
 };\
 
};\
 
function draw_arrows2(){\
 
 var arrow_head = %d;\
 
 var len = userdraw_x.length;\
 
 var x1,y1,x2,y2,dx,dy,h;\
 
 if( len%%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.save();\
 
   x1 = userdraw_x[p];y1 = userdraw_y[p];x2 = userdraw_x[p+1];y2 = userdraw_y[p+1];dx = x2 - x1;dy = y2 - y1;\
 
   context_userdraw.save();\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(x1,y1);\
 
   context_userdraw.lineTo(x2,y2);\
 
   context_userdraw.closePath();\
 
   context_userdraw.stroke();\
 
   context_userdraw.translate(x2,y2);\
 
   context_userdraw.rotate(Math.atan2(dy,dx));\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(0,0);\
 
   context_userdraw.lineTo(-1*arrow_head,-0.5*arrow_head);\
 
   context_userdraw.lineTo(-1*arrow_head, 0.5*arrow_head);\
 
   context_userdraw.closePath();\
 
   context_userdraw.fill();\
 
   context_userdraw.stroke();\
 
   context_userdraw.restore();\
 
   context_userdraw.translate(x1,y1);\
 
   context_userdraw.rotate(Math.atan2(-dy,-dx));\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(0,0);\
 
   context_userdraw.lineTo(-1*arrow_head,-0.5*arrow_head);\
 
   context_userdraw.lineTo(-1*arrow_head, 0.5*arrow_head);\
 
   context_userdraw.closePath();\
 
   context_userdraw.fill();\
 
   context_userdraw.stroke();\
 
   context_userdraw.restore();\
 
  };\
 
 };\
 
 return;\
 
};",stroke_color,stroke_opacity,arrow_head);
 
 break;
 
 /* curvedarrow/curvedarrows */
 
 case 22 ... 23:
 
function redraw_userdraw(){draw_curvedarrows();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<3;p++){userdraw_x.pop();userdraw_y.pop();};draw_curvedarrows();};return;};\
 
function curvedarrows(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 0){\
 
   userdraw_x = [];userdraw_y = [];userdraw_x[0] = x;userdraw_y[0] = y;\
 
  }\
 
  else\
 
  {\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
  };\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt < 3 ){userdraw_x.push(x);userdraw_y.push(y);draw_curvedarrows();userdraw_x.pop();userdraw_y.pop();};\
 
  if( xy_cnt == 3 ){userdraw_x.pop();userdraw_y.pop();userdraw_x.push(x);userdraw_y.push(y);xy_cnt = 0;draw_curvedarrows();};\
 
 };\
 
};\
 
var arrow_head = %d;\
 
function draw_curvedarrows(){\
 
 var len = userdraw_x.length;var x1,y1,x2,y2,x3,y3;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p = p+3){\
 
  x1 = userdraw_x[p];x2 = userdraw_x[p+1];x3 = userdraw_x[p+2];y1 = userdraw_y[p];y2 = userdraw_y[p+1];y3 = userdraw_y[p+2];\
 
  var angle1 = Math.atan2(x3 - x2,y3 - y2) + Math.PI;\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(x1,y1);\
 
  context_userdraw.quadraticCurveTo(x3,y3,x2,y2);\
 
  context_userdraw.moveTo(x2 - (arrow_head * Math.sin(angle1 - Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 - Math.PI / 6)));\
 
  context_userdraw.lineTo(x2, y2);\
 
  context_userdraw.lineTo(x2 - (arrow_head * Math.sin(angle1 + Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 + Math.PI / 6)));\
 
  context_userdraw.stroke();\
 
  context_userdraw.closePath();\
 
 };\
 
 return;};",arrow_head);
 
 break;
 
 /* curvedarrow2/curvedarrows2 */
 
 case 24 ... 25:
 
function redraw_userdraw(){draw_curvedarrows2();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<3;p++){userdraw_x.pop();userdraw_y.pop();};draw_curvedarrows2();};return;};\
 
function curvedarrows2(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 0){userdraw_x = [];userdraw_y = [];userdraw_x[0] = x;userdraw_y[0] = y;}else{userdraw_x.push(x);userdraw_y.push(y);};xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt < 3 ){userdraw_x.push(x);userdraw_y.push(y);draw_curvedarrows2();userdraw_x.pop();userdraw_y.pop();};\
 
  if( xy_cnt == 3 ){userdraw_x.pop();userdraw_y.pop();userdraw_x.push(x);userdraw_y.push(y);xy_cnt = 0;draw_curvedarrows2();};\
 
 };\
 
};\
 
var arrow_head = %d;\
 
function draw_curvedarrows2(){\
 
 var len = userdraw_x.length;var x1,y1,x2,y2,x3,y3;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p = p+3){\
 
  x1 = userdraw_x[p];x2 = userdraw_x[p+1];x3 = userdraw_x[p+2];y1 = userdraw_y[p];y2 = userdraw_y[p+1];y3 = userdraw_y[p+2];\
 
  var angle1 = Math.atan2(x3 - x2,y3 - y2) + Math.PI;\
 
  var angle2 = Math.atan2(x3 - x1,y3 - y1) + Math.PI;\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(x1,y1);\
 
  context_userdraw.moveTo(x1 - (arrow_head * Math.sin(angle2 - Math.PI / 6)),y1 - (arrow_head * Math.cos(angle2 - Math.PI / 6)));\
 
  context_userdraw.lineTo(x1, y1);\
 
  context_userdraw.lineTo(x1 - (arrow_head * Math.sin(angle2 + Math.PI / 6)),y1 - (arrow_head * Math.cos(angle2 + Math.PI / 6)));\
 
  context_userdraw.moveTo(x1,y1);\
 
  context_userdraw.quadraticCurveTo(x3,y3,x2,y2);\
 
  context_userdraw.moveTo(x2 - (arrow_head * Math.sin(angle1 - Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 - Math.PI / 6)));\
 
  context_userdraw.lineTo(x2, y2);\
 
  context_userdraw.lineTo(x2 - (arrow_head * Math.sin(angle1 + Math.PI / 6)),y2 - (arrow_head * Math.cos(angle1 + Math.PI / 6)));\
 
  context_userdraw.stroke();\
 
  context_userdraw.closePath();\
 
 };\
 
 return;\
 
};",arrow_head);
 
 break;
 
 
 
 /* freehandline/freehandlines/path/paths 0,1  26,27,28,29  */
 
 case 26 ... 29:
 
 var stop = 1;\
 
function remove_last(){userdraw_x = [];userdraw_y = []; context_userdraw.clearRect(0,0,xsize,ysize);return;};\
 
function paths(x,y,event_which,num){\
 
 if(event_which == 0 && stop == 0 ){stop = 1;return;};\
 
 if(event_which == 1 && stop == 1 ){return;}; \
 
 if(event_which == 0 && stop == 1 ){\
 
 stop = 0;userdraw_x = [];userdraw_y = [];return;};\
 
 userdraw_x.push(x);userdraw_y.push(y);\
 
 draw_paths();\
 
};\
 
function draw_paths(){\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 var len = userdraw_x.length ;\
 
 context_userdraw.beginPath();\
 
 context_userdraw.moveTo(userdraw_x[0],userdraw_y[0]);\
 
 for(var p = 1 ; p < len ; p++ ){\
 
  context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);\
 
 };\
 
 if(use_filled!=0){context_userdraw.fill();};\
 
 context_userdraw.stroke();\
 
 return;\
 
};");
 
 
 
 break;
 
 
 
 /* poly/polys poly[3]...polys[9] 30,31 */
 
 case 30 ... 31:
 
var polynum = %d;\
 
function redraw_userdraw(){draw_polys();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<polynum;p++){userdraw_x.pop();userdraw_y.pop();};draw_polys();};return;};\
 
function polys(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 0){\
 
   userdraw_x = [];userdraw_y = [];\
 
   userdraw_x[0] = x;userdraw_y[0] = y;\
 
  }\
 
  else\
 
  {\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
  };\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt < polynum ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_polys();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == polynum ){\
 
  userdraw_x.pop();userdraw_y.pop();\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt = 0;\
 
  draw_polys();\
 
 };\
 
};\
 
function draw_polys(){\
 
 var len = userdraw_x.length;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p = p+polynum){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
  for( var m = p+1 ;m < p+polynum ; m++){\
 
  if(typeof(userdraw_x[m]) !== 'undefined' ){context_userdraw.lineTo(userdraw_x[m],userdraw_y[m]);};};\
 
  context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);\
 
  context_userdraw.stroke();\
 
  context_userdraw.closePath();\
 
  if(use_filled!=0){context_userdraw.fill();};\
 
 };\
 
 return;\
 
};",polynum);
 
 break;
 
 case 32 ... 33:
 
 /* polygon/polygon  32,33 */
 
 /* multiple polygons are now working as expected : no problems with duplicated/closing points*/
 
var poly_closed = [];\
 
var do_not_pop = 0;\
 
function redraw_userdraw(){do_not_pop = 1;draw_polygon();};\
 
function remove_last(){var len = poly_closed.length;if(len > 1 ){var last = poly_closed[len-1]-poly_closed[len-2];for(var p=0;p<last-1;p++){userdraw_x.pop();userdraw_y.pop();};poly_closed.pop();}else{poly_closed = [];userdraw_x = [];userdraw_y = [];};draw_polygon();return;};\
 
function check_closed(x1,y1,X,Y){\
 
 var marge=10;\
 
 var len = X.length-1;\
 
 for(var p = 0 ; p < len ; p++){\
 
  if(x1 < X[p] + marge && x1 > X[p] - marge ){\
 
   if(y1 < Y[p] + marge && y1 > Y[p] - marge ){\
 
    return 1;\
 
   };\
 
  };\
 
 };\
 
 return 0;\
 
};\
 
\
 
function polygon(x,y,event_which,num){\
 
 do_not_pop = 0;\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 0){\
 
   userdraw_x = [];userdraw_y = [];\
 
   userdraw_x[0] = x;userdraw_y[0] = y;\
 
  }\
 
  else\
 
  {\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
  };\
 
  xy_cnt++;\
 
  if( xy_cnt > 2 ){\
 
   if( check_closed(x,y,userdraw_x,userdraw_y) == 1){\
 
    poly_closed.push(userdraw_x.length - 1);\
 
    draw_polygon();\
 
    xy_cnt = 0;\
 
   };\
 
  };\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt > 0 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_polygon();\
 
  };\
 
 };\
 
};\
 
function draw_polygon(){\
 
 var len = userdraw_x.length;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 context_userdraw.beginPath();\
 
 var begin = 0;\
 
 context_userdraw.moveTo(userdraw_x[0],userdraw_y[0]);\
 
 for( var p = 0 ; p < len ; p++){\
 
  if( poly_closed.indexOf(p) != -1 ){\
 
   context_userdraw.lineTo(userdraw_x[begin],userdraw_y[begin]);\
 
   begin = p;\
 
   context_userdraw.closePath();\
 
   if(use_filled!=0){context_userdraw.fill();};\
 
   context_userdraw.stroke();\
 
   context_userdraw.beginPath();\
 
  }else{ context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);};\
 
 };\
 
 context_userdraw.lineTo(userdraw_x[begin],userdraw_y[begin]);\
 
 context_userdraw.closePath();\
 
 if(use_filled!=0){context_userdraw.fill();};\
 
 context_userdraw.stroke();\
 
 if(do_not_pop == 0){ userdraw_x.pop();userdraw_y.pop();};\
 
 return;\
 
};");
 
 break;
 
 
 
 /*
 
 polyline/brokenline 34,35
 
 there is just a single polyline/brokenline possible !
 
 */
 
 case 34 ... 35:
 
function redraw_userdraw(){draw_polylines();};\
 
function remove_last(){if( userdraw_x.length > 0 ){userdraw_x.pop();userdraw_y.pop();draw_polylines();};return;};\
 
function polylines(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if(num == 0  && xy_cnt == 0 ){ userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){xy_cnt = 0;};\
 
 draw_polylines();\
 
};\
 
var full_circle = 2*Math.PI;\
 
function draw_polylines(){\
 
 var len = userdraw_x.length;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 context_userdraw.beginPath();\
 
 context_userdraw.moveTo(userdraw_x[0],userdraw_y[0]);\
 
 for( var p = 0 ; p < len ; p++){\
 
  context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);\
 
  context_userdraw.arc(userdraw_x[p],userdraw_y[p],2,0,full_circle,false);\
 
 };\
 
  context_userdraw.stroke();\
 
 context_userdraw.closePath();\
 
 if(use_filled != 0 ){if(use_filled!=0){context_userdraw.fill();};};\
 
 return;\
 
};");
 
 break;
 
 
 
 /* triangle/triangles 36,37 */
 
 case 36 ... 37:
 
function redraw_userdraw(){draw_triangles();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<3;p++){userdraw_x.pop();userdraw_y.pop();};draw_triangles();};return;};\
 
function triangles(x,y,event_which,num){\
 
 var last = userdraw_x.length - 1;\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 0){\
 
   userdraw_x = [];userdraw_y = [];userdraw_x[0] = x;userdraw_y[0] = y;\
 
  }\
 
  else\
 
  {\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
  };\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt < 3 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_triangles();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
   return;\
 
  };\
 
 };\
 
 if( xy_cnt == 3 ){\
 
  userdraw_x.pop();userdraw_y.pop();\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt = 0;\
 
  draw_triangles();\
 
 };\
 
};\
 
function draw_triangles(){\
 
 var len = userdraw_x.length - 1;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p = p+3){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
  for( var m = p+1 ;m < p+3 ; m++){\
 
   context_userdraw.lineTo(userdraw_x[m],userdraw_y[m]);\
 
  };\
 
  context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);\
 
  context_userdraw.closePath();\
 
  if(use_filled!=0){context_userdraw.fill();};\
 
  context_userdraw.stroke();\
 
 };\
 
 return;\
 
};");
 
 break;
 
 
 
 /* rect/rects 38,39 : NOT USING A PATH !!*/
 
 case 38 ... 39 :
 
function redraw_userdraw(){draw_rects();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_rects();};return;};\
 
function rects(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_rects();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_rects();\
 
 };\
 
};\
 
function draw_rects(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  for(var p = 0 ; p < len ; p = p+2 ){\
 
   context_userdraw.beginPath();\
 
   context_userdraw.rect(userdraw_x[p],userdraw_y[p],userdraw_x[p+1]-userdraw_x[p],userdraw_y[p+1]-userdraw_y[p]);\
 
   context_userdraw.closePath();\
 
   if(use_filled!=0){context_userdraw.fill();};\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
 return;\
 
};");
 
 break;
 
 /* roundrect/roundrects 40,41  : NOT USING A PATH !!*/
 
 case 40 ... 41:
 
function redraw_userdraw(){draw_roundrects();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<2;p++){userdraw_x.pop();userdraw_y.pop();};draw_roundrects();};return;};\
 
function roundrects(x,y,event_which,num){\
 
 if(event_which == 0){\
 
  if( num == 0 && xy_cnt == 0 ){userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if( xy_cnt == 1 ){\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   draw_roundrects();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  };\
 
 };\
 
 if( xy_cnt == 2 ){\
 
  xy_cnt = 0;\
 
  draw_roundrects();\
 
 };\
 
};\
 
function draw_roundrects(){\
 
 var len = userdraw_x.length;\
 
 if( len %%2 == 0 ){\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  var x,y,w,h,r;\
 
  for(var p = 0; p < len; p = p+2){\
 
   x = userdraw_x[p];y = userdraw_y[p];w = userdraw_x[p+1] - x;h = userdraw_y[p+1] - y;r = parseInt(0.1*w);\
 
   context_userdraw.beginPath();\
 
   context_userdraw.moveTo(x + r, y);\
 
   context_userdraw.lineTo(x + w - r, y);\
 
   context_userdraw.quadraticCurveTo(x + w, y, x + w, y + r);\
 
   context_userdraw.lineTo(x + w, y + h - r);\
 
   context_userdraw.quadraticCurveTo(x + w, y + h, x + w - r, y + h);\
 
   context_userdraw.lineTo(x + r, y + h);\
 
   context_userdraw.quadraticCurveTo(x, y + h, x, y + h - r);\
 
   context_userdraw.lineTo(x, y + r);\
 
   context_userdraw.quadraticCurveTo(x, y, x + r, y);\
 
   context_userdraw.closePath();\
 
   if(use_filled!=0){context_userdraw.fill();};\
 
   context_userdraw.stroke();\
 
  };\
 
 };\
 
return;\
 
};");
 
 break;
 
 /* arc/arcs  42,43 */
 
 case 42 ... 43:
 
function redraw_userdraw(){draw_arcs();};\
 
var temp_point_x = new Array(3);\
 
var temp_point_y = new Array(3);\
 
context_userdraw.fillStyle = context_userdraw.strokeStyle;\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<3;p++){userdraw_x.pop();userdraw_y.pop();userdraw_radius.pop();temp_point_x = [];temp_point_y = [];};draw_arcs();};return;};\
 
function arcs(x,y,event_which,num){\
 
 var last = userdraw_x.length - 1;\
 
 var xc = userdraw_x[last];\
 
 var yc = userdraw_y[last];\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 3 ){xy_cnt = 0;userdraw_x = [];userdraw_y = [];};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  temp_point_x.push(x);\
 
  temp_point_y.push(y);\
 
  draw_points();\
 
  xy_cnt++;\
 
 };\
 
 if( xy_cnt%%3 == 0 ){ draw_arcs();temp_point_x = [];temp_point_y = [];};\
 
 return;\
 
};\
 
function draw_points(){\
 
 var len = temp_point_x.length;\
 
 var radius = 4*(context_userdraw.lineWidth);\
 
 var r = 2*Math.PI;\
 
 for(var p = 0 ; p < len ; p++ ){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.arc(temp_point_x[p],temp_point_y[p],radius,0,r,false);\
 
  context_userdraw.closePath();\
 
  context_userdraw.fill();\
 
 };\
 
 return;\
 
};\
 
function draw_arcs(){\
 
 var xc,x1,x2,yc,y1,y2,radius,end,start,direction,p1,p2;\
 
 var len = userdraw_x.length;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 var idx = 0;\
 
 for(var p=0; p< len;p = p+3){\
 
  p1=p+1;p2=p+2;\
 
  xc = userdraw_x[p1];x1 = userdraw_x[p];x2 = userdraw_x[p2];yc = userdraw_y[p1];y1 = userdraw_y[p];y2 = userdraw_y[p2];\
 
  radius = distance(x1,y1,xc,yc);\
 
  start = Math.atan2(y1-yc, x1-xc);\
 
  end = Math.atan2(y2-yc, x2-xc);\
 
  direction = ( start > end);\
 
  userdraw_radius[idx] = Math.abs( end - start );idx++;\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(xc,yc);\
 
  context_userdraw.arc(xc, yc,radius,start,end,direction);\
 
  context_userdraw.closePath();\
 
  context_userdraw.stroke();\
 
  if(use_filled!=0){context_userdraw.fill();};\
 
 };\
 
 return;\
 
};");
 
 break;
 
 /* text : 44 always uses user input field !! */
 
 case 44:
 
function redraw_userdraw(){draw_text();};\
 
var userdraw_text = new Array();\
 
var tooltip_div = document.getElementById(\"tooltip_placeholder_div%d\");\
 
var inner_html = tooltip_div.innerHTML;\
 
tooltip_div.innerHTML = inner_html + \"<input class='%s' type='text' size='4' value='' id='userdraw_text_abc' />\";\
 
context_userdraw.fillStyle = \"rgba(%s,%f)\";\
 
var userdraw_textheight = 0.3 * (context_userdraw.measureText('M').width);\
 
function remove_last(){if(userdraw_x.length > 0 ){userdraw_x.pop();userdraw_y.pop();userdraw_text.pop();draw_text();return;};};\
 
function text(x,y,event_which,num){\
 
 if(event_which == 1){ return; };\
 
 if( num == 0 ){\
 
  userdraw_x[0] = x;\
 
  userdraw_y[0] = y;\
 
 }else{\
 
  userdraw_x.push(x);\
 
  userdraw_y.push(y);\
 
 };\
 
 var txt = document.getElementById('userdraw_text_abc').value;\
 
 if( ! txt ){userdraw_x.pop();userdraw_y.pop();userdraw_text.pop();return;};\
 
 txt = conv_to_unicode(txt);userdraw_text.push(txt.replace(/\\\\/g,' '));\
 
 draw_text();\
 
};\
 
function conv_to_unicode(str){return str.replace(/\\u[\\dA-F]{4}/gi,function(match){return String.fromCharCode(parseInt(match.replace(/\\u/g,''), 16));});};\
 
function draw_text(){\
 
 var len = userdraw_x.length;\
 
 var half = 0;\
 
 var txt;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p++ ){\
 
   txt = userdraw_text[p];\
 
   if(txt.indexOf('_') > 0 || txt.indexOf('^') > 0 ){draw_subsup(context_userdraw,userdraw_x[p],userdraw_y[p],txt,4);}else{half = 0.5*( context_userdraw.measureText(txt).width );context_userdraw.fillText(txt,userdraw_x[p] - half,userdraw_y[p] + userdraw_textheight);};\
 
 };\
 
};",canvas_root_id,css_class,stroke_color,stroke_opacity);
 
 break;
 
 /* images 45,46  replyformat is same as 'userdraw text,color' e.g. 17 === x,y,image_id  */
 
 case 45 ... 46:
 
 function redraw_userdraw(){draw_images(0);};\
 
var userdraw_text = new Array();\
 
var current_id = null;var external_div_cnt=0;\
 
function remove_last(){draw_images(1);return;};\
 
function image_adjust(image,x,y){\
 
 var centered = %d;\
 
 var w = parseInt(image.width);var h = parseInt(image.height);\
 
 switch(centered){\
 
  case 0: return [x,y];break;\
 
  case 1: return [x,parseInt(y-0.5*h)];break;\
 
  case 2: return [parseInt(x+0.5*h),y];break;\
 
  case 3: return [parseInt(x+0.5*h),parseInt(y-0.5*h)];break;\
 
  case 4: return [parseInt(x-0.5*w),parseInt(y-0.5*h)];break;\
 
  default: return [x,y];break;\
 
 };\
 
};\
 
place_image_on_canvas = function(id){\
 
 var thing = document.getElementById(id);\
 
 var tag = thing.tagName;\
 
 if(tag == 'SVG'){draw_mathml_svg(thing,id);return;};\
 
 if(tag == 'DIV' || tag == 'SPAN' || tag == 'P' || tag == 'TD' || tag == 'TH' ){draw_mathml_div(thing,id);return;};\
 
 var src = thing.src;\
 
 var image = new Image();\
 
 image.src = src;\
 
 image.id = 'placed_'+id;\
 
 image.width = thing.width;\
 
 image.height = thing.height;\
 
 image.onload = function(){ current_id = id; };\
 
 return;\
 
};\
 
function draw_mathml_div(thing,id){\
 
 var fix_div = document.createElement('DIV');\
 
 var new_id='placed_'+external_div_cnt+'_'+id;\
 
 fix_div.setAttribute('id',new_id);\
 
 var w = parseInt(thing.clientWidth);\
 
 var h = parseInt(thing.clientHeight);\
 
 fix_div.innerHTML = thing.innerHTML;\
 
 fix_div.setAttribute('style','display:none;position;absolute;width:'+w+'px;height:'+h+'px');\
 
 fix_div.width = w;fix_div.height = h;\
 
 canvas_div.appendChild(fix_div);\
 
 current_id = new_id;\
 
 external_div_cnt++;\
 
 return;\
 
};\
 
function draw_mathml_svg(thing,id){\
 
 var fix_div = document.createElement('DIV');\
 
 fix_div.setAttribute('style','display:none;position;relative');\
 
 canvas_div.appendChild(fix_div);\
 
 var image = new Image();\
 
 var svg_string = new XMLSerializer().serializeToString(thing);\
 
 var dom = self.URL || self.webkitURL || self;\
 
 var svg = new Blob([svg_string], {type: \"image/svg+xml;charset=utf-8\"});\
 
 var url = dom.createObjectURL(svg);\
 
 image.src= url;\
 
 image.id = 'placed_'+id;\
 
 image.onload = function(){\
 
  current_id = image.id;\
 
  fix_div.innerHTML='<img src='+image.src+' id='+image.id+' alt=\"this should not happen today...!\"/>';\
 
 };\
 
 return;\
 
};\
 
function images(x,y,event_which,num){\
 
 if(event_which == 1){ return;};\
 
 if( current_id ){\
 
  if(num == 0 ){ \
 
   userdraw_x[0] = x;\
 
   userdraw_y[0] = y;\
 
   userdraw_text[0] = current_id;\
 
   external_div_cnt = 0;\
 
  }else{\
 
   userdraw_x.push(x);\
 
   userdraw_y.push(y);\
 
   userdraw_text.push(current_id);\
 
  };\
 
  current_id = null;\
 
  draw_images(0);\
 
 };\
 
};\
 
function draw_images(remove){\
 
 var last = userdraw_x.length - 1;\
 
 if(last < 0 ){return;};\
 
 var x = userdraw_x[last];\
 
 var y = userdraw_y[last];\
 
 var id =  userdraw_text[last];\
 
 var img = document.getElementById(id);\
 
 var tag = img.tagName;\
 
 var xy = image_adjust(img,x,y);\
 
 if( tag == 'DIV' || tag == 'SPAN' || tag == 'P' || tag == 'TD' || tag == 'TH'){\
 
  if( remove == 1 ){\
 
   img.setAttribute('style','display:none');\
 
   userdraw_x.pop();userdraw_y.pop();userdraw_text.pop();external_div_cnt--;\
 
  }\
 
  else\
 
  {\
 
   img.setAttribute('style','display:inline-block;position:absolute;top:'+xy[1]+'px;left:'+xy[0]+'px;');\
 
  };\
 
  return;\
 
 }else{\
 
  context_userdraw.clearRect(0,0,xsize,ysize);\
 
  if(remove == 1){\
 
   userdraw_x.pop();userdraw_y.pop();userdraw_text.pop();\
 
  };\
 
  var len = userdraw_x.length;\
 
  for(var p = 0 ; p < len; p++){\
 
   if( userdraw_text[p] ){\
 
    img = document.getElementById(userdraw_text[p]);\
 
    tag = img.tagName;\
 
    xy = image_adjust(img,userdraw_x[p],userdraw_y[p]);\
 
    if( tag == 'IMG' || tag == 'SVG' ){\
 
     context_userdraw.drawImage(img,xy[0],xy[1],img.width,img.height);\
 
    };\
 
   };\
 
  };\
 
 };\
 
};",use_offset);
 
 break;
 
 /* input/inputs" 46,47
 
 if(use_offset != 0 ){ center_input('canvas_input'+input_cnt,x,y,style);};\
 
  inp.addEventListener(\"touchstart\", function(e){this.focus();},false);\
 
  if( wims_status == \"done\" ){ inp.setAttribute(\"readonly\",\"readonly\");};
 
 */
 
 case 47 ... 48:
 
 /*
 
 input_cnt keeps track of all inputfields INCLUDING static inputfields
 
 xy_cnt keeps track of the dynamically added userdraw inputfields
 
 */
 
var current_id = null;\
 
var current_obj = null;\
 
var inputs_width = 16;\
 
var inputs_height = 8;\
 
function redraw_userdraw(){console.log('userdraw inputs not zooming...');};\
 
if(typeof(input_cnt) !== 'undefined'){var input_cnt = 0;};\
 
function remove_last(){console.log('input_cnt ='+input_cnt);\
 
var input = document.getElementById('canvas_input'+input_cnt);try{ canvas_div.removeChild(input);userdraw_x.pop();userdraw_y.pop();xy_cnt--;input_cnt--;}catch(e){console.log('removal failed...'+e);};};\
 
function check_overlap(x,y,obj){\
 
 var inputs;var xi,yi;\
 
 for(var p = 0 ; p < xy_cnt ; p++ ){\
 
  xi = userdraw_x[p];yi = userdraw_y[p];\
 
  if( x > xi - 5 && x < xi + inputs_width &&  y > yi-5 && y < yi + inputs_height){\
 
   try{canvas_div.removeChild(obj);\
 
    current_obj = null;userdraw_x.pop();userdraw_y.pop();xy_cnt--;input_cnt--;\
 
   }catch(e){console.log('failed removing overlap: '+e);};\
 
   return;\
 
  };\
 
 };\
 
 return;\
 
};\
 
function inputs(x,y,event_which,num){\
 
 if( document.getElementById('canvas_input0')){\
 
  var inputs = document.getElementById('canvas_input0');\
 
  inputs_width = 5+parseInt(inputs.clientWidth);\
 
  inputs_height = 5+ parseInt(inputs.clientHeight);\
 
 };\
 
 if(event_which == 0){\
 
  if(num == 0 && xy_cnt == 1 ){try{ canvas_div.removeChild(document.getElementById('canvas_input0'));\
 
  userdraw_x = [];userdraw_y = [];xy_cnt=0;}catch(e){console.log('removal first input failed...'+e);};};\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  current_id = 'canvas_input'+input_cnt;\
 
  current_obj = document.getElementById(current_id);\
 
  draw_inputs(x,y);\
 
  if(input_cnt > 0){check_overlap(x,y,current_obj);};\
 
  input_cnt++;\
 
  xy_cnt++;\
 
  if(isTouch){current_obj.addEventListener(\"touchstart\", function(e){this.focus();},false);}else{\
 
  current_obj.autofocus = true;};\
 
 };\
 
 return;\
 
};\
 
function draw_inputs(x,y){\
 
 var input_size = parseInt(context_userdraw.lineWidth);\
 
 current_obj = document.createElement(\"input\");\
 
 current_obj.setAttribute(\"id\",current_id);\
 
 current_obj.setAttribute(\"size\",input_size);\
 
 var xx = x - 0.5*inputs_width;\
 
 var yy = y - 0.5*inputs_height;\
 
 current_obj.setAttribute(\"style\",\"position:absolute;left:\"+xx+\"px;top:\"+yy+\"px;\");\
 
 canvas_div.appendChild(current_obj);\
 
 return;\
 
};");
 
 break;
 
// current_obj.setAttribute(\"class\",\"%s\");
 
 
 
 // input.setAttribute(\"style\",\"position:absolute;left:\"+userdraw_x[p]+\"px;top:\"+userdraw_y[p]+\"px;%s\");
 
 /* gridfill/diamondfill/dotfill/hatchfill/textfill  48,49,50,51,52
 
  0:no fill, 1:fill,2=grid?,3=hatch?,4=diamond?,5=dot?,6=image?
 
 if( draw_num == 50 ){js_function[DRAW_GRIDFILL] = 1;use_filled = 2;}
 
 else{
 
 if( draw_num == 51 ){js_function[DRAW_DIAMONDFILL] = 1;use_filled = 4;}
 
 else{
 
 if( draw_num == 52 ){js_function[DRAW_DOTFILL] = 1;use_filled = 5;}
 
 else{
 
 if( draw_num == 53 ){js_function[DRAW_HATCHFILL] = 1;use_filled = 3;}
 
 else{
 
 if( draw_num == 54 ){js_function[DRAW_TEXTFILL] = 1;use_filled = 7;}
 
 else{ use_filled = 1;}}}}}
 
 
 
 
 
 
 
 */
 
 case 49 ... 54:
 
/* handling rare case of clickfill using a pattern in stead of a single color...*/
 
 add_js_filltoborder(canvas_type);
 
 /*fprintf(stdout,"USE_FILLED = %d<br>",use_filled);*/
 
 switch(use_filled){
 
 case 1:
 
  p 
= 1 + snprintf(NULL
,0,"var use_pattern_ctx = false;"); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,  "var use_pattern_ctx = false;");  
  break;
 
 case 2:
 
  p 
= 1 + snprintf(NULL
,0,"draw_gridfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = grid_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215)); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,  "draw_gridfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = grid_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215));  
  break;
 
 case 3:
 
  p 
= 1 + snprintf(NULL
,0,"draw_hatchfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = hatch_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215)); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,"draw_hatchfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = hatch_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215));  
  break;
 
 case 4:
 
  p 
= 1 + snprintf(NULL
,0,"draw_diamondfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = diamond_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215)); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,"draw_diamondfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = diamond_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215));  
  break;
 
 case 5:
 
  p 
= 1 + snprintf(NULL
,0,"draw_dotfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = dot_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215)); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,"draw_dotfill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = dot_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215));  
  break;
 
 case 6:
 
   p 
= 1 + snprintf(NULL
,0,"draw_imagefill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = image_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215)); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,"draw_imagefill(%d,0,0,%d,%d,%d,'%s',%d,xsize,ysize,1);var use_pattern_ctx = true;var pattern_ctx = image_fill_pattern;",CLICKFILL_CANVAS
,5*line_width
,5*line_width
,line_width
,fill_color
,(int) (fill_opacity
/0.0039215));  
  break;
 
  case 7:
 
/*var draw_textfill = function(canvas_type,x0,y0,color,fontfamily,xsize,ysize,txt,use_userdraw)*/
 
  p 
= 1 + snprintf(NULL
,0,"draw_textfill(%d,0,0,'%s','%s',xsize,ysize,userdraw_text_string,1);var use_pattern_ctx = true;var pattern_ctx = text_fill_pattern;",CLICKFILL_CANVAS
,stroke_color
,font_family
); 
  check_string_length(p);
 
  tmp_buffer = my_newmem(p);
 
  snprintf(tmp_buffer
,p
,"draw_textfill(%d,0,0,'%s','%s',xsize,ysize,userdraw_text_string,1);var use_pattern_ctx = true;var pattern_ctx = text_fill_pattern;",CLICKFILL_CANVAS
,stroke_color
,font_family
);  
  break;
 
 }
 
  add_to_buffer(tmp_buffer);
 
 
 
fprintf(js_include_file
,"function redraw_userdraw(){console.log('userdraw fill not zooming...');return;};\  
function remove_last(){var last = fill_canvas_no;\
 
console.log('last = '+last);\
 
if(last > %d){\
 
var last_canvas = document.getElementById('wims_canvas%d'+last);\
 
if( last_canvas == null ){fill_canvas_no--;return;};\
 
var last_ctx = last_canvas.getContext('2d');\
 
last_ctx.clearRect(0,0,xsize,ysize);\
 
canvas_div.removeChild(last_canvas);\
 
userdraw_x.pop();userdraw_y.pop();\
 
fill_canvas_no--;\
 
};return;};\
 
if( typeof(fill_canvas_no) === 'undefined' ){ var fill_canvas_no = %d; };\
 
function clickfill(x,y,event_which,num){\
 
 var color = [%s,255];\
 
 if( typeof(multifillcolors) === 'object'){\
 
  var numx = userdraw_x.length;\
 
  var numc = multifillcolors.length-1;var num = numx%%numc;\
 
  if( ! multifillcolors[num] ){alert('first select a colour...');return;};\
 
  var tc = (multifillcolors[num]).split(',');\
 
  color = [ tc[0],tc[1],tc[2],255 ];\
 
  if( typeof( palettecolors ) === 'object'){\
 
   var idx = palettecolors.indexOf( multifillcolors[num]);\
 
   userdraw_radius.push(idx);\
 
  }else{ userdraw_radius.push(num);};\
 
 }\
 
 else\
 
 {\
 
  userdraw_radius.push(0);\
 
 };\
 
 document.body.style.cursor = 'wait';\
 
 if( use_pattern_ctx ){\
 
  setTimeout(function(){ filltoborder( px2x(x),px2y(y),color,color,fill_canvas_no,true,pattern_ctx);},500);\
 
 }\
 
 else\
 
 {\
 
  setTimeout(function(){ filltoborder(px2x(x),px2y(y),color,color,fill_canvas_no,false,null);},500);\
 
 };\
 
 userdraw_x.push(x);\
 
 userdraw_y.push(y);\
 
 fill_canvas_no++;\
 
 document.body.style.cursor = 'default';\
 
 return;\
 
};",CLICKFILL_CANVAS,canvas_root_id,CLICKFILL_CANVAS,stroke_color);
 
/*(int) (stroke_opacity/0.0039215),(int) (stroke_opacity/0.0039215) */
 
 break;
 
 /* parallelogram/parallelograms */
 
 case 55 ... 56:
 
function redraw_userdraw(){draw_parallelograms();};\
 
function remove_last(){if( userdraw_x.length > 0 ){for(var p=0;p<4;p++){userdraw_x.pop();userdraw_y.pop();};draw_parallelograms();};return;};\
 
function parallelograms(x,y,event_which,num){\
 
 var l2 = userdraw_x.length;\
 
 var l1 = l2 - 1;var l0 = l2 - 2;\
 
 var xxyy;\
 
 if(event_which == 0){\
 
  if(xy_cnt == 0){\
 
   if(num == 0){userdraw_x = [];userdraw_y = [];};\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
  }\
 
  else\
 
  {\
 
   userdraw_x.push(x);userdraw_y.push(y);\
 
   if(xy_cnt == 2){\
 
    var xy = multisnap_check(userdraw_x[l2] - userdraw_x[l1] + userdraw_x[l0],userdraw_y[l2] - userdraw_y[l1] + userdraw_y[l0],use_snap);\
 
    userdraw_x.push(xy[0]);\
 
    userdraw_y.push(xy[1]);\
 
   };\
 
  };\
 
  xy_cnt++;\
 
 }\
 
 else\
 
 {\
 
  if(xy_cnt == 1){\
 
   var xxyy = multisnap_check(userdraw_x[l1],userdraw_y[l1],use_snap);\
 
   userdraw_x.push(xxyy[0]);\
 
   userdraw_y.push(xxyy[1]);\
 
   userdraw_x.push(x);\
 
   userdraw_y.push(y);\
 
   draw_parallelograms();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
   userdraw_x.pop();userdraw_y.pop();\
 
  }\
 
  else\
 
  {\
 
   if(xy_cnt == 2){\
 
    xxyy = multisnap_check(userdraw_x[l2]-userdraw_x[l1] + userdraw_x[l0],userdraw_y[l2]-userdraw_y[l1] + userdraw_y[l0],use_snap);\
 
    userdraw_x.push(x);userdraw_y.push(y);\
 
    userdraw_x.push(xxyy[0]);\
 
    userdraw_y.push(xxyy[1]);\
 
    draw_parallelograms();\
 
    userdraw_x.pop();userdraw_y.pop();\
 
    userdraw_x.pop();userdraw_y.pop();\
 
   };\
 
  };\
 
 };\
 
 if( xy_cnt == 3 ){\
 
  userdraw_x.pop();userdraw_y.pop();\
 
  xxyy = multisnap_check(userdraw_x[l2]-userdraw_x[l1] + userdraw_x[l0],userdraw_y[l2]-userdraw_y[l1] + userdraw_y[l0],use_snap);\
 
  userdraw_x.push(xxyy[0]);userdraw_y.push(xxyy[1]);\
 
  userdraw_x.push(x);userdraw_y.push(y);\
 
  userdraw_x.pop();userdraw_y.pop();\
 
  xy_cnt = 0;\
 
  draw_parallelograms();\
 
 };\
 
};\
 
function draw_parallelograms(){\
 
 var len = userdraw_x.length-1;\
 
 context_userdraw.clearRect(0,0,xsize,ysize);\
 
 for(var p = 0 ; p < len ; p = p+4){\
 
  context_userdraw.beginPath();\
 
  context_userdraw.moveTo(userdraw_x[p],userdraw_y[p]);\
 
  for( var m = p+1 ;m < p+4 ; m++){\
 
   context_userdraw.lineTo(userdraw_x[m],userdraw_y[m]);\
 
  };\
 
  context_userdraw.lineTo(userdraw_x[p],userdraw_y[p]);\
 
  context_userdraw.closePath();\
 
  if(use_filled!=0){context_userdraw.fill();};\
 
  context_userdraw.stroke();\
 
 };\
 
 return;};");
 
 break;
 
 
 
  case 57 ... 58:
 
   if( js_function[DRAW_JSFUNCTION] != 1 ){
 
    js_function[JS_RAWMATH] = 1;js_function[DRAW_JSFUNCTION] = 1;
 
    js_function[JS_MATH] = 1;js_function[JS_PLOT] = 1;
 
    if(reply_format == 0 || reply_format != -1){reply_format = 24;}/* read canvas_input values */
 
    if(polynum == -1 ){polynum = 1; } /* functions5 --> polynum = 5 */
 
    for(n=0;n<polynum;n++){
 
     add_input_jsfunction(css_class,function_label,input_cnt,stroke_color,stroke_opacity,
 
     line_width,use_dashed,dashtype[0],dashtype[1],font_size);
 
     input_cnt++;
 
     jsplot_cnt++;
 
    }
 
   }
 
  fprintf(js_include_file
,"if(typeof(all_jsplots) !== 'number'){var all_jsplots;};all_jsplots = %d;function redraw_userdraw(){redraw_jsplot();return;};",jsplot_cnt
);  
 
 
 break;
 
 
 
 default:canvas_error("unknown drawtype?? this should not happen...");break;
 
}/* einde switch */
 
 
 
 
 
}/* einde add_js_userdraw */