2013-10-19 89 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()