gpt4 book ai didi

javascript - 非常昂贵的 HTML 5 Canvas 剪辑

转载 作者:太空狗 更新时间:2023-10-29 13:41:49 26 4
gpt4 key购买 nike

我在 chrome 中使用 canvas clip() 时遇到了严重的性能问题。

I have made a test case to illustrate .

即使在像这样的简单情况下,红色矩形也会闪烁,好像重绘花费了太多时间,并且 CPU 分析显示 clip() 方法占用了大约 10% 的 CPU。

在我的真实程序中,它达到 16% 并不断增加每一帧,直到 Canvas 几乎卡住浏览器..

我使用clip有问题吗?

感谢您的任何建议,

问候。

最佳答案

原因

插入 beginPath() 作为 rect() 添加到不同于 fillRect()/strokeRect() 。这里发生的是矩形不断累积,最终随着时间的推移减慢了裁剪速度。

这与使用无法与监视器/屏幕刷新同步的 setInterval 相结合,使问题变得更糟。

详细说明后者:

使用 setInterval()/setTimeout() 可能会导致撕裂,当绘图处于其操作的“中间”时未完全完成并发生屏幕刷新时会发生撕裂.

setInterval 只能采用整数值,您需要 16.67 毫秒才能逐帧同步 (@60Hz)。即使 setInterval 可以 采用 float ,它也不会将时间与监视器时间同步,因为计时器机制根本没有绑定(bind)到监视器。

要解决此问题,请始终使用 requestAnimationFrame 将绘图与屏幕更新同步。这直接链接到监视器刷新,并且是比另一个更低级和更高效的实现,并且是为此目的而设计的,因此得名。

嵌入上述两个修复的解决方案

参见 modified bin here .

future 访问者的代码:

function draw() {

context.fillStyle = '#000';
context.fillRect(0, 0, width, height);

context.save();

context.beginPath(); /// add a beginPath here
context.rect(0, 0, 100, 100);
context.clip();

context.fillStyle = '#ff0000';
context.fillRect(0, 0, 200, 200);

context.restore();

requestAnimationFrame(draw); /// use rAF here
}

canvas.width = width;
canvas.height = height;
canvas.style.width = width+'px';
canvas.style.height = height+'px';

requestAnimationFrame(draw); /// start loop

PS:如果您需要停止循环,请在循环内注入(inject)一个条件来运行 rAF,即:

if (isPlaying) requestAnimationFrame(draw);

顺便说一句,不需要closePath(),因为这会隐式为您完成,如the specs .如果需要,您可以添加它,但是调用 clip()(或 fill() 等)将您完成此操作(规范是寻址浏览器实现者):

Open subpaths must be implicitly closed when computing the clipping region

关于javascript - 非常昂贵的 HTML 5 Canvas 剪辑,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21160459/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com