if (isMSIE) {
	var vectorModel = new VectorModel();
}

function InitDrawler(par, name) {

	function Surface(canvas, name) {
		this.drawler = new Drawler(canvas, name);
		this.archive = {};
	};

	Surface.prototype.DrawPoly = function(array) {
		this.drawler.redraw(array, true);
	};

	function Drawler(edit, name) {
		name = name || 'canvas';

		if (isMSIE) this.vectorModel = vectorModel;
		this.objects = new Array();
		this.edit = edit;

		if (!isMSIE/* || MSIEVersion > 7*/) {
			this.canvas = document.createElement('div');
			this.canvas.style.position = "absolute";
			this.canvas.style.left = '0px';
			this.canvas.style.top = '0px';
			this.canvas.id = name;

			edit.appendChild(this.canvas);
		} else {
			this.canvas1 = document.createElementNS("http://www.w3.org/2000/svg", "svg");
			this.canvas1.style.position = 'absolute';
			this.canvas1.style.left = 0
			this.canvas1.style.top = 0;
			this.canvas1.id = name;
			edit.appendChild(this.canvas1);
			this.canvas = this.canvas1;
		};
	}

	Drawler.prototype.clear = function() {
		this.canvas.innerHTML = "";
		this.objects = new Array();
	}

	Drawler.prototype.delPoly = function(poly) {
		if (!poly.visible) return false;
		this.canvas.removeChild(poly.line);
		if (poly.outline) this.canvas.removeChild(poly.outline);
		poly.visible = false;
	}

	Drawler.prototype.SetBox = function(x, y, box) {
		if (!box) {
			box = {x1: x, y1: y, x2: x, y2: y};
		} else {;
		if (x<box.x1) box.x1 = x;
		if (y<box.y1) box.y1 = y;
		if (x>box.x2) box.x2 = x;
		if (y>box.y2) box.y2 = y;
		};
		return box;
	};

	Drawler.prototype.draw_all_arrows = function(pts, arr, attributes, dir, scale) {
		//		if (!arr||(!dir&&(dir!=0))) return pts;
		if (!arr||(!attributes&&(attributes!==0))) return pts;
		var arrow, control=0, counter=0;
		//	var lett = (isMSIE)? "m" : "M";
		//	if (this.zoom!=undefined) d('this.zoom: '+this.zoom);
		if (attributes[0].zoom) control = counter = this.zoom;
		for (var i=(arr.length-1); i>=0; i--) {
			if (attributes[arr[i].attr]) {
				arrow = attributes[arr[i].attr];
				if (counter==control) {
					counter=0;
					if (arrow.angle==1000) {
						if (typeof(pts)!='string') {
							if (!(dir<0)) {
								if (arr[i-1]) this.drawArrow(pts, scale, (i-1), (i), arr);
							};
							if (!(dir>0)) {
								if (arr[i+1]) this.drawArrow(pts, scale, (i+1), (i), arr);
							};
						} else {
							//	pts += " "+lett+Math.round(arr[i].x)+","+Math.round(arr[i].y);
							if (!(dir<0)) {
								if (arr[i-1]) pts = this.drawArrow(pts, scale, (i-1), (i), arr);
							};
							if (!(dir>0)) {
								if (arr[i+1]) pts = this.drawArrow(pts, scale, (i+1), (i), arr);
							};
						};
					} else {
						if (typeof(pts)!='string') this.drawArrow(pts, scale, false, false, arr, arrow.angle, arr[i]);
						else  pts = this.drawArrow(pts, scale, false, false, arr, arrow.angle, arr[i]);
					};
				} else counter++;
			};
		};

		return pts;
	}

	Drawler.prototype.drawArrow = function(pts, scale, n1, n2, arr, angle, p2) {
		if (!scale) return pts;
		//var cords = [{x:0,y:2.5,a:90}, {x:5,y:0,a:0}, {x:0,y:-2.5,a:-90}, {x:0,y:0,a:0}];
		var cords = [{x:0,y:scale,a:90}, {x:(2*scale),y:0,a:0}, {x:0,y:-scale,a:-90}, {x:0,y:0,a:0}];
		var x, y, gep, startP;
		if (!p2) {
			var p1 = arr[n1];
			p2 = arr[n2];
			var j = (n1<n2)? 1 : -1;
			while ((Math.sqrt((p2.x-p1.x)*(p2.x-p1.x)+(p2.y-p1.y)*(p2.y-p1.y))<3)&&(arr[n1-j])) {
				p1 = arr[n1-j];
				n1 -= j;
			};
			angle = this.getAngle(p1, p2);
		};

		if (typeof(pts)!='string') pts.moveTo(p2.x,p2.y);
		else pts += " "+((isMSIE)? 'm' : 'M')+Math.round(p2.x)+","+Math.round(p2.y);

		for (var i=0; i<4; i++) {
			if (cords[i].x) {
				gep = Math.abs(cords[i].x);
			} else {
				gep = Math.abs(cords[i].y);
			};
			cords[i].y = gep*Math.sin((angle+cords[i].a)*Math.PI/180);
			cords[i].x = gep*Math.cos((angle+cords[i].a)*Math.PI/180);

			if (typeof(pts)!='string') {
				pts.lineTo(Math.round(cords[i].x+p2.x), Math.round(cords[i].y+p2.y));
			} else {
				if (isMSIE) {
					pts += " l"+Math.round(cords[i].x+p2.x)+","+Math.round(cords[i].y+p2.y);
				} else  pts += " L"+Math.round(cords[i].x+p2.x)+","+Math.round(cords[i].y+p2.y);
			};
		};
		return pts;
	};

	Drawler.prototype.polyline2 = function(line, style, arrow, dir) {
		var points="m", pointsArr = new Array();
		var ps, remove = false, polybox = false;
		poly = {line: new Array(),  visible: false};
		if (line.length<2) return poly;
		if (!style) style = {};

		for (var i=0; i<line.length-1; i++) {
			polybox = this.SetBox(line[i].x, line[i].y, polybox);
			if (line[i]&&line.length>1) {
				points += Math.round(line[i].x)+","+Math.round(line[i].y)+" l";
				if (points.length>500) {
					pointsArr.push(points);
					points = "";
				};
			};
		};

		if (points.length>0) pointsArr.push(points);
		if (line[0]&&line.length>1) pointsArr[pointsArr.length-1] += Math.round(line[line.length-1].x)+","+Math.round(line[line.length-1].y);
		polybox = this.SetBox(line[line.length-1].x, line[line.length-1].y, polybox);

		if (pointsArr[0]=="m"||pointsArr[0]=="") {
			this.delPoly(poly);
		} else {
			points = "";
			/*if (dir||dir===0) {
			if (!(dir>0)) pointsArr[0] = pointsArr[0].slice(0, pointsArr[0].indexOf(" l"))+this.drawArrow("", 1, 0, line)+pointsArr[0].slice(pointsArr[0].indexOf(" l"));
			if (!(dir<0)) points = this.drawArrow(points, (line.length-2), (line.length-1), line);
			};*/
			points = this.draw_all_arrows(points, line, arrow, dir, (style.arrowscale || 2.5));
			pointsArr.push(points);

			var box = {l: polybox.x1, t: polybox.y1, w: Math.round(Math.abs(polybox.x2-polybox.x1)), h: Math.round(Math.abs(polybox.y2-polybox.y1))};

			var obj = poly.line;

			obj.push('<div style="position: absolute; left:0; top:0">');

			if (style.outline) {
				obj.push('<');
				obj.push('v:shape ');
				obj.push('style="position: absolute; width: '+(box.w+30)+'px; height: '+(box.h+30)+'px;" ');
				obj.push('coordsize="'+(box.w+30)+','+(box.h+30)+'" filled="f" ');
				obj.push('path="');
				for (var i=0; i<pointsArr.length; i++) {
					obj.push(pointsArr[i]);
				};
				obj.push(' e">');

				obj.push('<');
				obj.push('v:stroke color="'+((style.outline.color)? style.outline.color : 'rgb(0,0,0)')+'" ');
				obj.push('endcap="round"');
				obj.push('joinstyle="'+((style.join)? style.join : 'miter')+'"');
				obj.push('weight="'+((style.outline.width)? (2*style.outline.width + ((style.width)? style.width : 3)) : (((style.width)? style.width : 3)+1))+'px">');
				obj.push('<');
				obj.push('/v:stroke>');
				obj.push('<');
				obj.push('/v:shape>');
			};

			obj.push('<');
			obj.push('v:shape ');
			obj.push('style="position: absolute; width: '+(box.w+30)+'px; height: '+(box.h+30)+'px;" ');
			obj.push('coordsize="'+(box.w+30)+','+(box.h+30)+'" filled="f" ');
			obj.push('path="');
			for (var i=0; i<pointsArr.length; i++) {
				obj.push(pointsArr[i]);
			};
			obj.push(' e">');

			obj.push('<');
			obj.push('v:stroke color="'+((style.color)? style.color : 'rgb(200,0,0)')+'" ');
			obj.push('endcap="round"');
			obj.push('joinstyle="'+((style.join)? style.join : 'miter')+'"');
			obj.push('weight="'+((style.width)? style.width : 3)+'px">');
			obj.push('<');
			obj.push('/v:stroke>');
			obj.push('<');
			obj.push('/v:shape>');
			obj.push('</div>');

			poly.visible = true;
		};
		return poly;
	};
	Drawler.prototype.polyline = function(line, style, arrow, dir, poly) {
		var points="M";
		var ps, remove = false, polybox = false;
		//	if (!poly) {
		poly = {line: document.createElementNS("http://www.w3.org/2000/svg", "svg"), visible: false};
		poly.line.style.position = 'absolute';
		//	};
		if (line.length<2) return poly;
		if (!style) style = {};
		for (var i=0; i<line.length-1; i++) {
			polybox = this.SetBox(line[i].x, line[i].y, polybox);
			if (line[i]&&line.length>1) {

				if (style.good) {
					if (i==0) points += Math.round(line[0].x)+","+Math.round(line[0].y)+" L"+Math.round(line[0].x+(line[1].x-line[0].x)/2)+","+Math.round(line[0].y+(line[1].y-line[0].y)/2);
					else points += " C"+Math.round(line[i].x)+","+Math.round(line[i].y)+" "+Math.round(line[i].x)+","+Math.round(line[i].y)+" "+Math.round(line[i].x+(line[i+1].x-line[i].x)/2)+","+Math.round(line[i].y+(line[i+1].y-line[i].y)/2);
				} else points += Math.round(line[i].x)+","+Math.round(line[i].y)+" L";
			};
		};
		if (style.good) points += " L";
		if (line[0]&&line.length>1) points += Math.round(line[line.length-1].x)+","+Math.round(line[line.length-1].y);

		polybox = this.SetBox(line[line.length-1].x, line[line.length-1].y, polybox);

		var box = {l: polybox.x1, t: polybox.y1, w: Math.round(Math.abs(polybox.x2-polybox.x1)), h: Math.round(Math.abs(polybox.y2-polybox.y1))};

		if (points=="M") {
			this.delPoly(poly);
		} else {

			poly.line.style.left = box.l-15+'px';
			poly.line.style.top = box.t-15+'px';

			poly.line.setAttribute("width", (box.w+30)+"px");
			poly.line.setAttribute("height", (box.h+30)+"px");
			poly.line.setAttributeNS(null,"viewBox", (box.l-15)+" "+(box.t-15)+" "+(box.w+30)+" "+(box.h+30));
			/*if (dir||dir===0) {
			if (!(dir>0)) points = points.slice(0, points.indexOf(" L"))+this.drawArrow("", 1, 0, line)+points.slice(points.indexOf(" L"));
			if (!(dir<0)) points = this.drawArrow(points, (line.length-2), (line.length-1), line);
			};*/
			points = this.draw_all_arrows(points, line, arrow, dir, (style.arrowscale || 2.5));

			if (style.outline) {
				var obj = (poly.line.childNodes.length==0)? poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path") : poly.line.firstChild;

				obj.setAttribute("d", points);

				obj.setAttribute("fill", "none");
				obj.setAttribute("stroke", ((style.outline.color)? style.outline.color : "rgb(0,0,0)"));
				obj.setAttribute("stroke-linecap", "round");
				obj.setAttribute("stroke-linejoin",  ((style.join)? style.join : "miter"));
				obj.setAttribute("stroke-width", ((style.outline.width)? (2*style.outline.width+((style.width)? style.width : 3)) : (((style.width)? style.width : 3)+1))+'px');
				if (poly.line.childNodes.length==0) poly.line.appendChild(obj);
			};

			var obj2 = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");

			obj2.setAttribute("d", points);

			obj2.setAttribute("fill", "none");
			obj2.setAttribute("stroke", ((style.color)? style.color : "rgb(200,0,0)"));
			obj2.setAttribute("stroke-linecap", "round");
			obj2.setAttribute("stroke-linejoin",  ((style.join)? style.join : "miter"));
			obj2.setAttribute("stroke-width", ((style.width)? style.width : 3)+'px');

			poly.line.appendChild(obj2);

			if (!poly.visible) {
				this.canvas.appendChild(poly.line);
			};

			poly.visible = true;
		};
		return poly;
	}


	Drawler.prototype.polyline3 = function(line, style, arrow, dir, parent, poly) {
		var polybox = false;
		//if (!poly) {
		poly = {line: document.createElement('canvas'), visible: false};
		poly.line.style.position = 'absolute';
		//};

		if (line.length<2) return poly;
		if (!style) style = {};
		if (!parent) parent = this.canvas;

		for (var i=0; i<line.length; i++) {
			polybox = this.SetBox(line[i].x, line[i].y, polybox);
		};

		var box = {l: polybox.x1, t: polybox.y1, w: Math.round(Math.abs(polybox.x2-polybox.x1)), h: Math.round(Math.abs(polybox.y2-polybox.y1))};

		if ((box.w>10000)||(box.h>10000)) {
			return this.polyline(line, style, arrow, dir, parent, poly);
			/*poly = {line: document.createElement('div'), visible: false};
			poly.line.style.position = 'absolute';
			poly.line.style.left = '0px';
			poly.line.style.top = '0px';
			parent.appendChild(poly.line);
			poly.visible = true;
			var l = Math.round(line.length/2);
			var obj;
			var line1 = new Array();
			var line2 = new Array();
			for (var i=0; i<line.length; i++) {
			if (i<=l) line1.push(line[i]);
			else line2.push(line[i]);
			};
			obj = this.polyline3(line1,style,arrow,dir,poly.line);
			obj = this.polyline3(line2,style,arrow,dir,poly.line);

			return poly;*/
		};

		parent.appendChild(poly.line);
		poly.visible = true;

		poly.line.style.left = (box.l-15)+'px';
		poly.line.style.top = (box.t-15)+'px';

		poly.line.style.width = (box.w+30)+"px";
		poly.line.width = (box.w+30);
		poly.line.style.height = (box.h+30)+"px";
		poly.line.height = (box.h+30);

		var ctx = poly.line.getContext('2d');

		if (line.length>1) {

			if (style.outline) {
				ctx.save();
				ctx.translate(-(box.l-15), -(box.t-15));
				ctx.strokeStyle = ((style.outline.color)? style.outline.color : "rgb(0,0,0)");
				ctx.lineWidth = ((style.outline.width)? (2*style.outline.width+((style.width)? style.width : 3)) : (((style.width)? style.width : 3)+1));
				ctx.lineJoin = ((style.join)? style.join : "miter");
				ctx.lineCap = "round";
				ctx.beginPath();

				ctx.moveTo(line[0].x, line[0].y);
				for (var i=1; i<line.length; i++) {
					if (line[i]) ctx.lineTo(line[i].x, line[i].y);
				};

				/*if (dir||dir===0) {
				if (!(dir>0)) this.drawArrow(ctx, 1, 0, line);
				if (!(dir<0)) this.drawArrow(ctx, (line.length-2), (line.length-1), line);
				};*/
				this.draw_all_arrows(ctx, line, arrow, dir, (style.arrowscale || 2.5));

				ctx.stroke();
				ctx.closePath();
				ctx.restore();
			};

			ctx.save();
			ctx.translate(-(box.l-15), -(box.t-15));
			ctx.strokeStyle = ((style.color)? style.color : "rgb(200,0,0)");
			ctx.lineWidth = ((style.width)? style.width : 3.0);
			ctx.lineJoin =  ((style.join)? style.join : "miter");
			ctx.lineCap = "round";
			ctx.beginPath();

			ctx.moveTo(line[0].x, line[0].y);
			for (var i=1; i<line.length; i++) {
				if (line[i]) ctx.lineTo(line[i].x, line[i].y);
			};

			/*if (dir||dir===0) {
			if (!(dir>0)) this.drawArrow(ctx, 1, 0, line);
			if (!(dir<0)) this.drawArrow(ctx, (line.length-2), (line.length-1), line);
			};*/
			this.draw_all_arrows(ctx, line, arrow, dir, (style.arrowscale || 2.5));

			ctx.stroke();
			ctx.closePath();
			ctx.restore();
		};

		return poly;
	}

	Drawler.prototype.drawPoint = function (x,y,Inobj,shadow,events,group,object) {
		var Div, params;
		if (object.tagName) {
			Div = object;
			while (Div.childNodes.length>0) {
				Div.removeChild(Div.firstChild);
			};
			if (!Div.id)  Div.id = this.canvas.id+'_point'+x+''+y+''+Math.round(10000*Math.random());
		} else {
			Div = document.createElement('div');
			Div.id = this.canvas.id+'_point'+x+''+y+''+Math.round(10000*Math.random());
			for (var i in object) {
				Div[i] = object[i];
			};
		};
		params = Div.point_properties;
		if (!params) params = {};

		var poly = {line: document.createElementNS("http://www.w3.org/2000/svg", "svg"), visible: false};

		x = Math.round(x);
		y = Math.round(y);

		Div.style.position = 'absolute';
		Div.style.left = x+'px';
		Div.style.top = y+'px';

		if (!document.getElementById(Div.id)) {
			this.canvas.appendChild(Div);
		};

		poly.line.style.position = 'absolute';
		if (!events) events = {};

		if (!Inobj||typeof(Inobj)=='string') {
			var text = (Inobj)? Inobj : "";
			Inobj = document.createElement("div");
			Inobj.innerHTML = text;
		};

		Inobj.style.position = "absolute";
		Inobj.style.left = (x)+'px';
		Inobj.style.top = (y)+'px';

		if (params.events) events = params.events;
		else params.events = events;


		Div.onmouseoverF = (!events.onmouseover)? function() {Div.style.zIndex = '1'} : events.onmouseover;
		Div.onmouseoutF = (!events.onmouseout)? function() {Div.style.zIndex = ''} : events.onmouseout;

		Div.onremoveF = events.onremove;

		Div.removeself = function() {
			if (Div.onremoveF) Div.onremoveF();
			if (this.parentNode) this.parentNode.removeChild(this);
		};

		Inobj.onmouseover = function(e) {
			Div.onmouseoverF(e);
		};

		//Div.onmouseover = function(e) {
		// Div.onmouseoverF(e);
		//};

		Div.onmouseout = function(e) {
			Div.onmouseoutF(e);
		};
		
		Div.appendChild(Inobj);

		var h = (Inobj.style.height)? parseInt(Inobj.style.height) : Inobj.offsetHeight;
		var w = (Inobj.style.width)? parseInt(Inobj.style.width) : Inobj.offsetWidth;

		var bord = params.border = (params.border)? params.border : 3;
		var r = params.radius = (params.radius)? params.radius : 15;
		var L = params.arrow_length = (params.arrow_length)? params.arrow_length : 20;
		var W = 20;
		var bordercolor = params.bordercolor = (params.bordercolor)? params.bordercolor : 'rgb(0,0,0)';
		var fillcolor = params.fillcolor = (params.fillcolor)? params.fillcolor : 'rgb(200,150,100)';
		var opacity = params.opacity = (params.opacity)? params.opacity : 0.7;
		var close = params.closebutton;
		var style = params.style = (params.style)? params.style : 'svg';
		var position = params.position = (params.position)? params.position : {x: Math.round(-w/2), y: Math.round(-h/2)};
		var svgposition = params.svgposition = (params.svgposition)? params.svgposition : {x: 0, y: 0};
		var buttons = params.buttons = (params.buttons)? params.buttons : [];
		var L_tan = params.arrow_width = (params.arrow_width)? params.arrow_width : 4;
		var L_x = params.arrow_top = (params.arrow_top)? params.arrow_top : 0;
		shadow = (params.noshadow)? !params.noshadow : shadow;

		Div.point_properties = params;

		
		var L_alph = -5;

		r = 2*Math.round(r/2);
		L = 2*Math.round(L/2);

		var inbord = (r<15)? r : r/2;

		if (Inobj.innerHTML.length==0) {
			inbord = 0;
			h = 0;
			w = 0;
			style = 'svg';
		};

		if ((style=='svg')||(style=='svg2')) {
			Inobj.style.height = h+'px';
			Inobj.style.width = w+'px';
			if (style=='svg2') {
				if (W<5) W = 5;
				W = Math.round(W);
				L_tan = (L_tan==4)? 17 : L_tan;
				L_tan = 2*Math.round(L_tan/2);

				if (close) w += 5+inbord;

				if (buttons.length>0) {
					for (var i=0; i<buttons.length; i++) {
						if (buttons[i]) w += 5+inbord;
					};
				};

				h += (2*inbord+bord);
				w += (2*inbord+bord);
				if (w<(2*r)) w=2*r;
				if (h<(2*r)) h=2*r;
				if ((Inobj.innerHTML.length==0)&&(h<w)) h=w-2;

				L_x = L_x||10;
				//if ((r+L_x)>20) L_x = 20-r;
				if (L_x<0) L_x = 0;

				if (h<(L_tan+2*r+L_x)) L_tan = h-2*r-L_x;

				Div.style.left = (x)+'px';
				Div.style.top = (y-(L+L_x+r+Math.round(bord/2)+2))+'px';
				x = W+Math.round(W*bord/L_tan);
				y = r+bord+L_x+L;
				w += x;
				Inobj.style.left = (x+inbord+svgposition.x)+'px';
				Inobj.style.top = (inbord+svgposition.y)+'px';

				poly.line.style.left = svgposition.x+'px';
				poly.line.style.top = svgposition.y+'px';


				poly.line.setAttribute("width", (w+(Math.tan(Math.PI/4)*((h)/2)-3)+bord)+"px");
				poly.line.setAttribute("height", (h+15)+"px");

				var obj = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");
				var points = ("M"+(Math.round(W*bord/L_tan))+","+(L_x+L+r+Math.round(bord/2))+" l"+W+","+(-L)+" l0,"+(-L_x)+" q0,"+(-r)+" "+(r)+","+(-r)+" l"+(w-x-2*r)+",0 q"+(r)+",0 "+(r)+","+(r)+" l0,"+(h-2*r)+" q0,"+(r)+" "+(-r)+","+(r)+" l"+(-w+x+2*r)+",0 q"+(-r)+",0 "+(-r)+","+(-r)+" l0,"+(-h+2*r+L_x+L_tan)+" Z");
			} else if (style=='svg') {
				if (W<(L_tan+L_alph+4)) W = L_tan+L_alph+4;
				W = Math.round(W);
				L_tan = 2*Math.round(L_tan/2);

				if (close) w += 5+inbord;

				if (buttons.length>0) {
					for (var i=0; i<buttons.length; i++) {
						if (buttons[i]) w += 5+inbord;
					};
				};

				h += (2*inbord+bord);
				w += (2*inbord+bord);
				if (w<(2*r)) w=2*r;
				if (w<(W+L_x+r)) w=W+L_x+r;
				if (h<(2*r)) h=2*r;
				if ((Inobj.innerHTML.length==0)&&(h<w)) h=w-2;

				Div.style.left = (x)+'px';
				Div.style.top = (y-(h+L+(L*bord/L_tan)))+'px';

				x = 0;
				y = (h+L+(L*bord/L_tan));

				Inobj.style.left = (x+inbord)+'px';
				Inobj.style.top = (y-(h+L+(L*bord/L_tan))+inbord)+'px';

				poly.line.style.left = 0+'px';
				poly.line.style.top = 0+'px';

				poly.line.setAttribute("width", (w+(Math.tan(Math.PI/4)*((h+L)/2)-3)+bord)+"px");
				poly.line.setAttribute("height", (h+L+(L*bord/L_tan))+"px");

				var obj = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");
				var points = ("M"+(Math.round(bord/2)+r)+","+(Math.round(bord/2))+" q"+(-r)+",0 "+(-r)+","+(r)+" l0,"+(h-2*r+r+L)+" l"+(L_tan/2)+","+(-L/2)+" q"+(L_tan/2)+","+(-L/2)+" "+(W-L_tan)+","+(-L/2)+" l"+(w-W-r)+",0 q"+(r)+",0 "+(r)+","+(-r)+" l0,"+(-h+2*r)+" q0,"+(-r)+" "+(-r)+","+(-r)+" Z");//L"+(Math.round(bord/2)+r)+","+(Math.round(bord/2));//Z";
			};

			obj.setAttribute("d", points);

			obj.setAttribute("fill", fillcolor);
			obj.setAttribute("fill-opacity", opacity);
			obj.setAttribute("stroke", bordercolor);
			obj.setAttribute("stroke-linecap", "round");
			obj.setAttribute("stroke-linejoin", "miter");
			obj.setAttribute("stroke-miterlimit", 10000);
			obj.setAttribute("stroke-opacity", (opacity+0.2));
			obj.setAttribute("stroke-width", bord+"px");

			obj.onmouseover = function() {
				Div.onmouseoverF();
			};

			poly.line.div = obj.div = Inobj.div = Div.div = Div;

			poly.line.onmousedownF = obj.onmousedownF = Inobj.onmousedownF = Div.onmousedownF = events.onmousedown;
			poly.line.ondragF = obj.ondragF = Inobj.ondragF = Div.ondragF = events.ondrag;
			poly.line.onmouseupF = obj.onmouseupF = Inobj.onmouseupF = Div.onmouseupF = events.onmouseup;

			obj.group = Inobj.group = group;

			if (shadow) {
				if (!isMSIE) {
					var Shadow = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "g");
					var obj1 = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");
					if (params.shadow==2) {
						Shadow.setAttribute("transform", "translate(5,5)");
						/*var Defs = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "defs");
						var Filter = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "filter");
						Filter.id = "Gaussian_Blur";
						var Blur =  poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "feGaussianBlur");
						Blur.setAttribute("in","SourceGraphic");
						Blur.setAttribute("stdDeviation","1");
						Filter.appendChild(Blur);
						Defs.appendChild(Filter);
						poly.line.appendChild(Defs);
						obj1.setAttribute("filter", "url(#Gaussian_Blur)");*/
					} else Shadow.setAttribute("transform", "translate("+Math.round(Math.tan(Math.PI/4)*(h+L)/2-3)+","+Math.round((h+L)/2+(L*bord/L_tan))+") skewX(-45) scale(1,0.5)");
					
					obj1.setAttribute("d", points);
					obj1.setAttribute("stroke-linejoin", "miter");
					obj1.setAttribute("stroke-miterlimit", (L*bord/L_tan));
					obj1.setAttribute("fill", "black");
					obj1.setAttribute("fill-opacity", 0.3);

					Shadow.appendChild(obj1);
					poly.line.appendChild(Shadow);
				} else {
					if (params.shadow==2) {
						//Inobj.style.left = (Inobj.offsetLeft-3)+'px';

						//poly.line.style.left = (parseInt(poly.line.style.left)-3)+'px';

						obj.style.width = w+bord;
						obj.style.height = h+bord+L;
						obj.coordsize= (w+bord)+" "+( h+bord+L);

						obj.setAttribute("shadow", "single");
						obj.setAttribute("shadow-color", "black");
						obj.setAttribute("shadow-obscured", true);
						obj.setAttribute("shadow-opacity", "0.2");
						obj.setAttribute("shadow-offset", "5pt,5pt");
					} else {
						Inobj.style.left = (Inobj.offsetLeft-3)+'px';

						poly.line.style.left = (parseInt(poly.line.style.left)-3)+'px';

						obj.style.width = w+bord;
						obj.style.height = h+bord+L;
						obj.coordsize= (w+bord)+" "+( h+bord+L);

						obj.setAttribute("shadow", "perspective");
						obj.setAttribute("shadow-color", "black");
						obj.setAttribute("shadow-obscured", true);
						obj.setAttribute("shadow-opacity", "0.3");
						obj.setAttribute("shadow-offset", (Math.round(Math.tan(Math.PI/4)*(h+L)/5-4)+"pt,"+Math.round((h+L)/5+(L*(bord-1)/L_tan))+"pt"));
						obj.setAttribute("shadow-matrix", "1,-0.5,0,0.5,0,0");
					}
				};
			};

			poly.line.appendChild(obj);

			if (close) {
				if (!inbord) inbord = r/4;
				if (inbord<3) inbord = 3;
				obj = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");
				obj.setAttribute("d", "M"+(w-inbord-5)+","+inbord+" q5,0 5,5 q0,5 -5,5 q-5,0 -5,-5 q0,-5 5,-5 Z m-4,1 l8,8 m0,-8 l-8,8");
				obj.setAttribute("fill", "red");
				obj.setAttribute("stroke", "black");
				obj.setAttribute("stroke-width", "1px");
				obj.onclick = function() {Div.removeself()};
				obj.style.cursor = 'pointer';
				obj.onmouseover = function(e) {
					Div.onmouseoverF(e);
				};
				poly.line.appendChild(obj);
			};

			if (buttons.length>0) {
				var butstep = (close)? (inbord+5) : 0;
				var butcolor;
				if (!inbord) inbord = r/4;
				if (inbord<3) inbord = 3;
				for (var i=0; i<buttons.length; i++) {
					if (buttons[i]) {
						if (buttons[i].object) {
							obj = buttons[i].object;
							obj.style.position = 'absolute';
							obj.style.left = (svgposition.x+w-inbord-5-butstep-(parseInt(obj.style.width)/2))+'px';
							obj.style.top = (svgposition.y+inbord)+'px';
							Div.appendChild(obj);
						} else {
							butcolor = buttons[i].color || 'red';
							obj = poly.line.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "path");
							obj.setAttribute("d", "M"+(w-inbord-5-butstep)+","+inbord+" q5,0 5,5 q0,5 -5,5 q-5,0 -5,-5 q0,-5 5,-5 Z");
							obj.setAttribute("fill", butcolor);
							obj.setAttribute("stroke", "black");
							obj.setAttribute("stroke-width", "1px");
							poly.line.appendChild(obj);
						};
						obj.onclick = buttons[i].func || function() {};
						obj.style.cursor = 'pointer';
						obj.onmouseover = function(e) {
							Div.onmouseoverF(e);
						};
						butstep += (inbord+5);
					};
				};
			};

			if (!poly.visible) {
				Div.insertBefore(poly.line, Inobj);
			};
		} else if (style=='div') {
			Div.style.left = (x+position.x)+'px';
			Div.style.top = (y+position.y)+'px';
			Inobj.style.left = '0px';
			Inobj.style.top = '0px';
			Inobj.style.height = h+'px';
			Inobj.style.width = w+'px';
			Inobj.div = Div.div = Div;

			Inobj.onmousedownF = Div.onmousedownF = events.onmousedown;
			Inobj.ondragF = Div.ondragF = events.ondrag;
			Inobj.onmouseupF = Div.onmouseupF = events.onmouseup;

			Inobj.group = group;
		};

		for (var i=0; i<Inobj.childNodes.length; i++) {
			if (Inobj.childNodes[i].nodeName=='#text') continue;
			Inobj.childNodes[i].onmousedownF = events.onmousedown;
			Inobj.childNodes[i].ondragF = events.ondrag;
			Inobj.childNodes[i].onmouseupF = events.onmouseup;
			Inobj.childNodes[i].div = Div;
			Inobj.childNodes[i].group = group;
		};

		poly.visible = true;
		poly.line = Div;

		return poly;
	}
	Drawler.prototype.drawCircle = function(center, radius, color) {
		var svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
		svg.style.position = 'absolute';
		svg.style.left = (center.x-radius-2)+'px';
		svg.style.top = (center.y-radius-2)+'px';
		svg.setAttribute("width", (2*radius+4)+"px");
		svg.setAttribute("height", (2*radius+4)+"px");
		var circ = svg.ownerDocument.createElementNS("http://www.w3.org/2000/svg", "circle");
		circ.setAttribute('cx', (radius+2));
		circ.setAttribute('cy', (radius+2));
		circ.setAttribute('r', (radius));
		circ.setAttribute('fill', color);
		svg.appendChild(circ);
		this.canvas.appendChild(svg);
	};

	Drawler.prototype.getAngle = function (p0,p1) {
		var Lin = {x: (p1.x-p0.x), y: (p1.y-p0.y)};
		var factor = (p1.x<p0.x)? -1 : 1;
		var pi = (factor>0)? 0 : Math.PI;
		var Len = Math.sqrt(Lin.x*Lin.x+Lin.y*Lin.y);
		if (Len<1) return 0;
		return (factor*Math.asin(Lin.y/Len)+pi)*180/Math.PI;
	};

	Drawler.prototype.drawL = function(objs, clear, stat, allprop, zoom) {
		this.LObj = false;
		if (objs) {
			this.zoom = zoom;
			if (clear) this.clear();
			var Style;
			if (!allprop) allprop = {};
			this.Lobjs = {objs: objs, allprop: allprop};
			if (isMSIE) {
				var old_objs = new Array();
				for (var i=0; i<this.canvas.childNodes.length; i++) {
					old_objs.push(this.canvas.childNodes[i]);
				};
				for (var i=0; i<objs.length; i++) {
					Style = {color: (objs[i].color || allprop.color), width: (objs[i].width || allprop.width), outline: (objs[i].outline || allprop.outline), join: (objs[i].join || allprop.join), arrowscale: (objs[i].arrowscale || allprop.arrowscale)};
					this.LObj = this.polyline2(objs[i].line, Style, objs[i].attributes, objs[i].dir);
					this.objects = this.objects.concat(((this.LObj.visible)? this.LObj.line : ""));
				};
				this.canvas.innerHTML = this.objects.join('');
				this.LObj = new Array();
				for (var i=0; i<this.canvas.childNodes.length; i++) {
					this.LObj.push({line: this.canvas.childNodes[i], visible: true});
				};
				for (var i=0; i<old_objs.length; i++) {
					this.canvas.insertBefore(old_objs[i], this.canvas.firstChild);
				};
			} else {
				this.LObj = new Array();
				var func = (stat)? 'polyline3' : 'polyline';
				//func = 'polyline3';
				for (var i=0; i<objs.length; i++) {
					Style = {color: (objs[i].color || allprop.color), width: (objs[i].width || allprop.width), outline: (objs[i].outline || allprop.outline), join: (objs[i].join || allprop.join), good: (objs[i].good || allprop.good), arrowscale: (objs[i].arrowscale || allprop.arrowscale)};
					this.LObj.push(this[func](objs[i].line, Style, objs[i].attributes, objs[i].dir));
				};
			};
			this.zoom = undefined;
			return this.LObj;
		};
	};

	Drawler.prototype.drawP = function(objs, clear, stat, allprop) {
		this.PObj = false;
		if (!allprop) allprop = {};
		this.Pobjs = {objs: objs, allprop: allprop};
		if (objs) {
			if (clear) this.clear();

			var Obj = new Array();
			var func = 'drawPoint';
			for (var i=0; i<objs.length; i++) {
				Obj.push(this[func](objs[i].coords.x, objs[i].coords.y, objs[i].content, (allprop.shadow || objs[i].shadow), (allprop.events || objs[i].events), (allprop.group || objs[i].group), objs[i]));
			};
			return Obj;
		};
	};

	//-------------------------------------------------------------------------



	var surf = new Surface(par, name);
	return surf;
}
