2013-10-19 87 views
5

如何在使用HTML5画布时将特定路径保存到JavaScript变量/数组,然后再操作它?以下是我到目前为止所做的:HTML5画布:操纵单个路径

    ctx.beginPath(); 
         ctx.moveTo(lastX,lastY); 
         ctx.lineTo(x,y); 
         ctx.lineWidth = s*2; 
         ctx.stroke(); 
        ctx.closePath(); 

现在,我需要的是有时能够将此路径存储在数组中。然后,我需要能够返回并稍后更改数组中所有路径的颜色。 (显然,我不知道该怎么做。)

+0

可能保存在一个函数的行为?所以你会有一系列的功能。 – Cristy

+0

每当您需要这种功能时,请考虑使用SVG。 – slebetman

回答

0

在画布上,您不能更改画布视图而不清除它并重画它;因此您需要创建一个绘制画布的函数。 在数组中存储行的位置,函数在数组中循环并添加它们。显然你可以随时重画画布;通常你会设置一个事件监听器或定时事件

0

简短的回答:你不能。它在Canvas2D API的下一个草案中(请参阅http://www.w3.org/html/wg/drafts/2dcontext/html5_canvas/#path-objects),但尚未支持。

较长的答案:你不能,但你可以写一个代表路径的对象,并给它一个函数,以便它用自己选择的颜色和填充属性绘制到画布上。例如:

var Path = function() { 
    this.instructions = []; 
} 
Path.prototype = { 
    instructions: [], 
    moveTo: function(x,y) { 
    instructions.push({ 
     type: "moveTo", 
     arguments: [x,y] 
    }); 
    } 
    ... 
    draw: function(canvas) { 
    var ctx = canvas.getContext("2d"); 
    ctx.beginPath(); 
    this.instructions.forEach(function(i) { 
     ctx[i.type].apply(i.arguments); 
    }); 
    ctx.closePath(); 
    } 
} 
+0

这是有效的,我该如何解决它? –

+0

回答编辑回答。 –

+0

只需谨慎地调用对象'Path',因为它是为未来路径保留的。 – K3N

2

可以序列绘制路径成JavaScript对象所需的所有数据

使用JavaScript对象的好处是,你可以进一步序列化对象JSON,如果你需要移动您到不同位置的路径(如回到服务器)。

var path1={ 
    lineWidth:1, 
    stroke:"blue", 
    points:[{x:10,y:10},{x:100,y:50},{x:30,y:200}] 
}; 

然后你就可以使用该对象绘制/重绘路径

function draw(path){ 

     // beginPath 
     ctx.beginPath(); 

     // move to the beginning point of this path 
     ctx.moveTo(path.points[0].x,path.points[0].y); 

     // draw lines to each point on the path 
     for(pt=1;pt<path.points.length;pt++){ 
      var point=path.points[pt]; 
      ctx.lineTo(point.x,point.y); 
     } 

     // set the path styles (color & linewidth) 
     ctx.strokeStyle=path.stroke; 
     ctx.lineWidth=path.lineWidth; 

     // stroke this path 
     ctx.stroke(); 
    } 

要改变路径的颜色,你只需要改变对象的笔触属性和调用draw()再次:

paths[0].stroke="orange"; 
    paths[1].stroke="green"; 
    draw(); 

这里是代码和一个小提琴:http://jsfiddle.net/m1erickson/McZrH/

<!doctype html> 
<html> 
<head> 
<link rel="stylesheet" type="text/css" media="all" href="css/reset.css" /> <!-- reset css --> 
<script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script> 

<style> 
    body{ background-color: ivory; } 
    #canvas{border:1px solid red;} 
</style> 

<script> 
$(function(){ 

    // get references to canvas and context 
    var canvas=document.getElementById("canvas"); 
    var ctx=canvas.getContext("2d"); 

    // serialize paths to a javascript objects 
    var path1={lineWidth:1, stroke:"blue", points:[]}; 
    var path2={lineWidth:4, stroke:"red", points:[]}; 

    // save the paths to an array 
    var paths=[]; 
    paths.push(path1); 
    paths.push(path2); 


    // build test path1 
    newPoint(25,25,path1); 
    newPoint(100,50,path1); 
    newPoint(50,75,path1); 
    newPoint(25,25,path1); 

    // build test path2 
    newPoint(200,100,path2); 
    newPoint(250,100,path2); 
    newPoint(250,200,path2); 
    newPoint(200,200,path2); 
    newPoint(200,100,path2); 

    // draw the paths defined in the paths array 
    draw(); 

    // add a new point to a path 
    function newPoint(x,y,path){ 
     path.points.push({x:x,y:y}); 
    } 


    function draw(){ 

     ctx.clearRect(0,0,canvas.width,canvas.height); 

     for(p=0;p<paths.length;p++){ 

      // get a path definition 
      var path=paths[p]; 

      // beginPath 
      ctx.beginPath(); 

      // move to the beginning point of this path 
      ctx.moveTo(path.points[0].x,path.points[0].y); 

      // draw lines to each point on the path 
      for(pt=1;pt<path.points.length;pt++){ 
       var point=path.points[pt]; 
       ctx.lineTo(point.x,point.y); 
      } 

      // set the path styles (color & linewidth) 
      ctx.strokeStyle=path.stroke; 
      ctx.lineWidth=path.lineWidth; 

      // stroke this path 
      ctx.stroke(); 

     } 

    } 

    // test 
    // change the stroke color on each path 
    $("#recolor").click(function(){ 
     paths[0].stroke="orange"; 
     paths[1].stroke="green"; 
     draw(); 
    }); 

}); // end $(function(){}); 
</script> 

</head> 

<body> 
    <button id="recolor">Recolor</button><br> 
    <canvas id="canvas" width=300 height=300></canvas> 
</body> 
</html> 
2

看起来现在可以使用新的path2D对象。

新的Path2D API(可从Firefox 31+获得)允许您存储路径,这可以简化您的画布绘制代码并使其运行速度更快。构造函数提供了三种方法来创建一个Path2D对象:

new Path2D();  // empty path object 
new Path2D(path); // copy from another path 
new Path2D(d); // path from from SVG path data 

第三个版本,这需要SVG路径数据来构建,尤其方便。现在,您可以重复使用您的SVG路径直接绘制相同的形状,在画布上还有:

var p = new Path2D("M10 10 h 80 v 80 h -80 Z"); 

信息从Mozilla official site拍摄。

+0

谢谢,这个效果非常好! –

0

这可能帮助:

http://www.rgraph.net/blog/2015/september/svg-style-paths-for-canvas-with-the-rgraph-path-function.html

这是一个可以让你使用一个字符串,它由字母和数字,然后由这个函数解释和作用来进行。所以现在你的路径可以是一个字符串 - 就像SVG路径 - 并且它们更容易传递和/或存储在数据库中。

所以绘制一个矩形路径可能是这样的:

B r的5 100 100 F红色

这意味着:

b: beginPath() 
r: rect() 
f: fill()