您能否请一个look at this演示,让我知道如何在不同坐标的画布中绘制多个圆圈而不重复一串代码?
正如你在Demo和代码中看到的那样
var ctx = $('#canvas')[0].getContext("2d");
ctx.fillStyle = "#00A308";
ctx.beginPath();
ctx.arc(150, 50, 5, 0, Math.PI * 2, true);
ctx.arc(20, 85, 5, 0, Math.PI * 2, true);
ctx.arc(160, 95, 5, 0, Math.PI * 2, true);
ctx.closePath();
ctx.fill();
我试图将它们放在ctx
下,但它不正确,所以我尝试使用for循环来创建50个点,但我有重复和添加代码的问题,如ctx.fill();对于他们所有人。
能告诉我如何解决这个问题吗?
由于
答案 0 :(得分:8)
这是因为您没有关闭路径,使用fill()
或closePath()
将关闭路径,因此它不会尝试连接所有项目。 fill()
填写圈子并关闭路径,以便我们可以使用它。您还需要使用beginPath()
,以便它们彼此分开。这是你的三个圈子:
var coords = [ [150,50], [20,85], [160,95] ];
for(var i = 0; i < coords.length; i++){
ctx.beginPath();
ctx.arc(coords[i][0], coords[i][1], 5, 0, Math.PI * 2, true);
ctx.fill();
}
要不重复大量代码并使用唯一坐标将X
和Y
位置存储在数组中,并使用for
循环来完成它。
<强>更新强>
一种更有效的方法,可以实现相同的效果,即只使用单个路径并使用moveTo()
而不是在绘制每个圆时创建新路径:
ctx.beginPath();
for(var i = 0; i < coords.length; i++){
ctx.moveTo(coords[i][0], coords[i][1]);
ctx.arc(coords[i][0], coords[i][1], 5, 0, Math.PI * 2, true);
}
ctx.fill();
答案 1 :(得分:8)
不断创建和关闭新路径并不是一个好建议。
您应该将所有相同样式的填充/描边一起批处理,并在一次绘制调用中执行它们。随着多边形数量的增加,这些方法之间的性能差异变得非常明显。
解决这个问题的方法是移动笔并为每个圆圈进行路径构建调用;中风/一次填写最后一次。但是,这里有一个怪癖。当您将点移动到中心并绘制圆时,您仍然会看到从圆心到圆周绘制的水平半径线。
为了避免这种假象,我们移动到圆周,而不是移动到中心。这会跳过半径绘图。基本上所有这些命令都用于跟踪路径,没有调用closePath
就无法描述不连续性;通常moveTo
可以做到但HTML5 canvas API却没有。这是一个简单的解决方法来解决这个问题。
const pi2 = Math.PI * 2;
const radius = 5;
ctx.fillStyle = '#00a308';
ctx.beginPath();
for( let i=0, l=coords.length; i < l; i++ )
{
const p = coords[i],
x = p.x,
y = p.y;
ctx.moveTo( x + radius, y ); // This was the line you were looking for
ctx.arc( x, y, radius, 0, pi2 );
}
// Finally, draw outside loop
ctx.stroke();
ctx.fill();
另外值得考虑的是,使用转换,并绘制相对于本地参照系的所有内容。
ctx.fillStyle = '#00a308';
ctx.beginPath();
for( let i=0, l=coords.length; i < l; i++ )
{
const p = coords[i];
ctx.save();
ctx.translate( p.x + radius, p.y );
ctx.moveTo( 0, 0 );
ctx.arc( 0, 0, radius, 0, pi2 );
ctx.restore();
}
ctx.stroke();
ctx.fill();
答案 2 :(得分:1)
ctx.beginPath();
points.forEach(point => {
ctx.moveTo( point.x, point.y );
ctx.arc(point.x,point.y,1,0,Math.PI*2,false);
});
ctx.fill();
答案 3 :(得分:0)
您可以使用for循环轻松创建多个圆圈。你真的只需要绘制一个圆弧并每次填充它。使用你的例子,你可以做这样的事情。
var ctx = $('#canvas')[0].getContext("2d");
ctx.fillStyle = "#00A308";
for (var i = 0; i < 3; i++) {
ctx.arc(50 * (i+1), 50 + 15 * i, 5, 0, Math.PI * 2, true);
ctx.fill();
}
答案 4 :(得分:0)
Example Fiddle在循环中绘制的不同位置的许多圆圈。
var canvas = document.getElementById('canvas');
var ctx = canvas.getContext( '2d' );
var cx = canvas.width/2;
var cy = canvas.height/2;
ctx.fillStyle = "#00A308";
var total_circles = 50;
var radius = 100;
for(i = 0; i < total_circles; i++){
var angle = i * 2 * Math.PI/total_circles;
var x = cx + Math.cos(angle) * radius;
var y = cy + Math.sin(angle) * radius;
ctx.beginPath();
ctx.arc(x, y, 2, 0, Math.PI * 2, true);
ctx.closePath();
ctx.fill();
}