点生线,线生面,然后生亿万种图形。
<body><div id='canvas'></div></body>
<script type='text/javascript'>
function Graphics(canvas)//coordinate
{
this.canvas = typeof(canvas)=="string"?document.getElementById(canvas):canvas;
this.color = '#000000';
this.stroke=2
this.documentRoot = document.createElement("div");
}
Graphics.prototype = {
paint : function()
{
this.canvas.appendChild(this.documentRoot);
},
clear : function()
{
if(this.documentRoot)this.documentRoot.innerHTML='';
if (this.canvas) this.canvas.innerHTML = '';
},
drawDiv : function(x, y, w, h)
{
var elem = document.createElement("div");
var style0 = elem.style,style1={'position':'absolute','overflow':'hidden','left':x,'top':y,'width':w,'height':h,'backgroundColor':this.color}
for(var p in style1){style0[p]=style1[p]}
this.documentRoot.appendChild(elem);
delete style1;
},
/*2D画线(Bresenham算法)*/
drawLine2D : function(x1, y1, x2, y2)
{
if (x1 > x2)
{
var _x2 = x2;
var _y2 = y2;
x2 = x1;
y2 = y1;
x1 = _x2;
y1 = _y2;
}
var dx = x2-x1, dy = Math.abs(y2-y1),
x = x1, y = y1,
yIncr = (y1 > y2)? -1 : 1;
var s = this.stroke;
if (dx >= dy)
{
if (dx > 0 && s-3 > 0)
{
var _s = (s*dx*Math.sqrt(1+dy*dy/(dx*dx))-dx-(s>>1)*dy) / dx;
_s = (!(s-4)? Math.ceil(_s) : Math.round(_s)) + 1;
}
else var _s = s;
var ad = Math.ceil(s/2);
var pr = dy<<1,
pru = pr - (dx<<1),
p = pr-dx,
ox = x;
while ((dx--) > 0)
{
++x;
if (p > 0)
{
this.drawDiv(ox, y, x-ox+ad, _s);
y += yIncr;
p += pru;
ox = x;
}
else p += pr;
}
this.drawDiv(ox, y, x2-ox+ad+1, _s);
}else{
if (s-3 > 0)
{
var _s = (s*dy*Math.sqrt(1+dx*dx/(dy*dy))-(s>>1)*dx-dy) / dy;
_s = (!(s-4)? Math.ceil(_s) : Math.round(_s)) + 1;
}
else var _s = s;
var ad = Math.round(s/2);
var pr = dx<<1,
pru = pr - (dy<<1),
p = pr-dy,
oy = y;
if (y2 <= y1)
{
++ad;
while ((dy--) > 0)
{
if (p > 0)
{
this.drawDiv(x++, y, _s, oy-y+ad);
y += yIncr;
p += pru;
oy = y;
}
else
{
y += yIncr;
p += pr;
}
}
this.drawDiv(x2, y2, _s, oy-y2+ad);
}
else
{
while ((dy--) > 0)
{
y += yIncr;
if (p > 0)
{
this.drawDiv(x++, oy, _s, y-oy+ad);
p += pru;
oy = y;
}
else p += pr;
}
this.drawDiv(x2, oy, _s, y2-oy+ad+1);
}
}
},
/*绘制箭头*/
drawArrow : function(x1, y1, x2, y2){
this.drawLine2D(x1, y1, x2, y2);
var arrow = 60; //箭头转角
var lenth = 10; //箭头宽度
var angle = 0;
if (Math.abs(x2 - x1) < 0.1 && y2 < y1)
angle = -90;
else if (Math.abs(x2 - x1) < 0.1 && y2 > y1)
angle = 90;
else if(x1 == x2)
angle = 180;
else{
angle = Math.atan(parseFloat(y1 - y2) / (x1 - x2)) * 180 / Math.PI;
}
if (x1 > x2)angle = 180 + angle;
var left = 270 - angle - arrow / 2;
var right = 270 - angle + arrow / 2;
var rx = lenth * Math.sin(right * Math.PI / 180);
var ry = lenth * Math.cos(right * Math.PI / 180);
var lx = lenth * Math.sin(left * Math.PI / 180);
var ly = lenth * Math.cos(left * Math.PI / 180);
this.drawLine2D(x1, y1, x2, y2);
this.drawLine2D(x2, y2, x2 + parseInt(lx),y2 + parseInt(ly));
this.drawLine2D(x2, y2, x2 + parseInt(rx),y2 + parseInt(ry));
}
};
var gc = new Graphics('canvas');
gc.color='#0000FF';//设置颜色
gc.paint();
var tempX=0;
var tempY=0;
function drawA(event){
var event = window.event||event;
var x = event.pageX||event.x
var y = event.pageY||event.y
if(Math.abs(x-tempX)>2||Math.abs(y-tempY)>2){
gc.clear();
//gc.drawLine2D(100,100,x,y);
gc.drawArrow(100,100,x,y);
gc.paint();
tempX=x;
tempY=y;
}
}
window.οnmοusemοve=drawA;//FF
document.body.οnmοusemοve=drawA;//IE
</script>
备注:这个是用纯HTMLElement绘图,效率很差。 实际应用可以用VML&SVG绘图。