3

尝试绘制画布并稍后将其重新绘制到同一画布上会产生意想不到的行为。例如,请参阅Jsfiddle

逻辑相当简单:

  • 给定画布上的图像,并平移到中心(我使用矩形来演示)。
  • 剪掉图像的一部分。我只是在示例中复制整个“图像”。
  • 可能会进行操纵。
  • 清除后粘贴回同一画布。要点是将原始图像的一部分剪辑到具有宽度/高度的给定点,然后稍后将其粘贴并进行修改。

var c=document.getElementById("cvs1"),
    ctx = c.getContext("2d"),
    bufferCvs = document.createElement('canvas'),
    bufferCtx = bufferCvs.getContext('2d');


bufferCvs.width = c.width;
bufferCvs.height = c.height;

ctx.translate( c.width/2, c.height/2 );
ctx.fillStyle="#FF0000";
ctx.fillRect( -75, -50 ,150,100);

//Image data experiment
//Set the buffer width / height same size as rectangle
bufferCvs.width = 150;
bufferCvs.height = 100;
//Draw the "image" from the first context to the buffer by clipping the first, and pasting to 0,0 width the same "image" dimensions.
bufferCtx.drawImage( c, -75, -50, 150, 100, 0, 0, 150, 100 );
//clear out old canvas drawing
ctx.save()
ctx.setTransform(1,0,0,1,0,0,1,0,0);
ctx.clearRect(0, 0, c.width, c.height);
ctx.restore();

ctx.drawImage( bufferCvs, -75, -50, 150, 100 );

由于我保持完全相同的坐标/尺寸,因此预期的输出将是最初在画布上的内容。但是,仅绘制了左上角的一部分(参见小提琴)。出于效率原因,我使用 drawImage ,但我使用 get/putImageData 的结果相同。宽度和高度都被定义为修复其他奇怪的行为

您将如何确保绘制存储在缓冲区画布中的所有内容,而不仅仅是顶角?

编辑:为了帮助解决我的问题以及我认为正在发生的行为,我将发布一些屏幕。

步骤 1:将上下文 1 平移到中心,并绘制一个矩形来表示图像。

ctx.translate( c.width/2, c.height/2 );
ctx.fillStyle="#FF0000";
ctx.fillRect( -75, -50 ,150,100);

翻译/添加矩形

第 2 步:使用 drawImage 从 -75、-50 点“剪裁”并使用宽度 150、100 仅剪切矩形。这应该绘制到画布缓冲区上,但不是

bufferCvs.width = 150;
bufferCvs.height = 100;
//Draw the "image" from the first context to the buffer by clipping the first at -75, -50 (the start of the image), and pasting to 0,0 width the same "image" dimensions.
bufferCtx.drawImage( c, -75, -50, 150, 100, 0, 0, 150, 100 );

我希望缓冲区画布看起来像这样(不是):

预期的缓冲画布

但是,如果我将 drawImage 更改为

bufferCtx.drawImage( c, 0, 0, 150, 100, 0, 0, 150, 100 );

我在缓冲区上获得了预期数量的空白(最后一个 drawImage 回到上下文没有问题)

第 3 步:从第一个上下文中清除旧的“图像”。这不应该改变翻译,因为我在执行清除后恢复了上下文状态。(这按预期工作)

ctx.save()
ctx.setTransform(1,0,0,1,0,0,1,0,0);
ctx.clearRect(0, 0, c.width, c.height);
ctx.restore();

第 4 步:只需将缓冲区画布中的内容绘制到它开始返回的原始上下文中:

翻译/添加矩形

这个想法是更多地“剪切”原始区域,清除旧图像,并将新剪切的区域粘贴回原始上下文中。我查看了MDN 的示例,但 drawImage 的剪辑部分没有按我预期的那样执行。

4

1 回答 1

0

主要问题是在 上绘制的第一个画布bufferCvs没有绘制在您期望的位置。证明这一点的最简单方法是添加bufferCvs到 DOM 树:http: //jsfiddle.net/CdWn6/4/

我想这就是你要找的东西:http: //jsfiddle.net/CdWn6/6/

var c=document.getElementById("cvs1"),
    c2 = document.getElementById("cvs2"),
    bufferCvs = document.createElement('canvas'),
    bufferCtx = bufferCvs.getContext('2d'),
    ctx = c.getContext("2d"),
    ctx2 = c2.getContext("2d");

bufferCvs.width = c.width;
bufferCvs.height = c.height;

ctx.translate( c.width/2, c.height/2 );
ctx.fillStyle="#FF0000";
ctx2.translate( c.width/2, c.height/2 );
ctx2.fillStyle="#FF0000";

bufferCtx.translate( c.width/2, c.height/2 );

ctx.fillRect( -75, -50 ,150,100);
ctx2.fillRect( -75, -50 ,150,100);

//Image data experiment
bufferCtx.drawImage( c, -135, -110, 270, 220);

ctx.save()
ctx.setTransform(1,0,0,1,0,0,1,0,0);
ctx.clearRect(0, 0, c.width, c.height);
ctx.restore();

//Draw background to demonstrate coordinates still work
ctx.fillStyle="#00FF00";
//ctx.fillRect( -75, -50 ,150,100);

ctx.drawImage( bufferCvs, -75, -50, 150, 100 );
于 2013-03-23T09:12:02.017 回答