HTML5 Canvas:重新绘制对象或使用位图更好?
我的项目有一个 HTML5 Canvas,可以在上面重复绘制图形对象。这些物体变化很快。绘制它们需要时间。我怎样才能让它更快?
这些对象并不过分复杂,但包含弧线、渐变、多边形等内容。
对象的外观取决于大约 10 个属性,每个属性都有大约 10 个值之一。这意味着一个物体只有大约 100 种不同的外观。这就是为什么我考虑只绘制每个外观一次,然后缓存位图以供重复使用。
一切都必须在客户端上运行(即我不能使用现成的图像)
- 使用 HTML5 Canvas 执行此操作的最佳方法是什么?
- 这是一个好主意还是使用位图的开销比每次重新绘制对象更大?
My project has an HTML5 Canvas on which graphical objects are drawn repeatedly. These objects change rapidly. Drawing them takes time. How can I make it faster?
The objects are not overly complex but contain things like arcs, gradients, polygons.
The look of an object depends on about 10 properties which each have one of about 10 values. That means that there are only about 100 different appearances than an object can have. That's why I'm thinking about only drawing each appearance once and then caching a bitmap for re-use.
Everything must work on the client (i.e. I cannot use ready-made images)
- What would be the best way to do this with HTML5 Canvas?
- Is it a good idea at all or is the overhead of working with bitmaps greater than re-drawing the objects every time?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
缓存缓存缓存!查看Simon Sarris 撰写的这篇文章,以及我自己的发现。基本上,您在内存中创建一个画布,将内容复制到那里,然后您可以重复使用它们。这样做你会看到性能的巨大提升。
旋转精灵而不缓存
使用缓存旋转精灵(向上走找到僵尸)
您应该会在第二个示例中看到相当大的改进。
编辑
jsfiddle 示例缓存
jsfiddle 示例未缓存
Simon 在评论中发布了此内容,如果您仅通过查看看不到性能提升,这应该会真正清除问题在演示。
Simon Sarris 的 JSperf 研究结果
Cache cache cache! Check out this article by Simon Sarris, and my own findings. Basically you make a canvas in memory copy the contents there and you can reuse them. You will see huge performance increases doing this.
Rotating sprites without caching
Rotating sprites WITH caching (walk upwards to find the zombies)
You should see a pretty big improvement in the 2nd example.
EDIT
jsfiddle example cached
jsfiddle example not cached
Simon posted this in the comments, which should really clear things up if you can't see the performance gains by just looking at the demos.
JSperf findings by Simon Sarris
根据一秒钟内可以改变多少对象,以及因此必须重绘多少对象以及如何重绘 - 在同一秒内,重绘比缓存可能是一个很好的选择。
一般来说,我建议考虑以下决策路径。
您提到您的某个对象可以有 100 种不同的显示方式。
这可以被认为类似于每个对象理论上至少有 99^2 次可能的状态转换。
这些状态转变在形状/大小/颜色上是否引人注目,但它们仍然易于识别、标记和管理?如果是这样,仅缓存一次 100 个不同的外观以供所有对象使用可能会显着提高性能。
相反,如果 - 仅举例来说 - 背景几乎没有变化,并且绘制的部分占据了对象区域不太相关的部分,那么您可以认真考虑每次重新绘制它。
事实上,如果您绘制的对象动态变化,尤其是连续变化,则预渲染图像无法满足您的性能需求,因为预渲染图像需要在每次状态转换时完全绘制,而重新绘制对象可能意味着更少计算负荷。
Depending on how many objects could change in a second, and consequentially how many objects you have to redraw and how - within the same second, redrawing more than caching could be quite an option.
On a general basis I would suggest to consider the following decisional path.
You mentioned that there can be 100 different ways for one of your objects to appear.
This could be considered similar to a minimum of 99^2 theoretically possible status transitions for each of your objects.
Are these status transitions dramatic in shape / size / color, but they're still well-identified, marked and manageable? If so, caching just once 100 different appearances to be used by all of your objects could be a significant performance improvement.
Conversely, if - just for example - the background hardly changes and the drawn part occupies a less relevant part of the object area you could seriously consider redrawing it every time.
In fact, a pre-rendered image could not fit your needs for performance if your drawn object changes dynamically and especially on a continuous basis, as a pre-rendered image needs to be drawn completely at every state transition while redrawing the object could mean less computational load.