我需要在画布上每一帧重新绘制所有对象吗?

4
我正在设置一个游戏循环。该循环设置为每秒更新50次。目前,应用程序唯一的操作是在响应触摸事件时绘制屏幕坐标。最初,我将绘图函数设置为仅绘制新的触摸事件。这导致文本闪烁。多个触摸事件会在不同的时间闪烁,这让我认为Canvas在幕后使用多个页面。为了解决这个问题,我列出了发生的每个触摸事件,并在每次绘制调用时重新绘制整个列表。
请纠正我如果我错了,lockCanvas()/unlockCanvasAndPost()调用实质上是一个后备缓冲区交换。阅读锁定和解锁的文档听起来好像必须在调用之间重新绘制整个场景,除非您使用lockCanvas(Rect dirty)。在这种情况下,需要重绘脏矩形区域,而外部区域则被保留。
引用:
表面内容在unlockCanvas()和lockCanvas()之间永远不会被保留,因此,必须写入表面区域内的每个像素。唯一的例外是当指定了脏矩形时,非脏像素将被保留。
我知道这听起来像是我自己回答了我的问题,但根据文档,表面在调用之间永远不会被保留。但是,这并不能解释我的第一个实现的行为,即我轻敲屏幕时文本会开始闪烁。由于我只绘制了文本一次,这意味着闪烁来自于交换到没有得到drawText()调用的“后备缓冲区”,而原始表面没有被销毁,但可能被认为是不可靠的。
所以问题是:我需要在每次绘制调用时重新绘制所有对象吗?如果是这样,我需要“清除”画布,或者至少也要重新绘制背景图像吗?
1个回答

0

是的,除非你正在进行脏重绘,其中你定义了要重新绘制的区域,否则画布上的每个点都会被销毁。


感谢您的回复。是否有更好的文档来说明整个过程是如何工作的?我认为,如果在调用之间Surface被破坏,那么当只有一个drawText()调用时会出现闪烁而不是闪烁文本。因此,要么Surface确实被破坏,但在相同的内存位置重新创建,这样“脏”内存看起来就像没有改变;或者,Surface没有被破坏,但应该被视为不可靠,也许是因为某些其他函数可能会在锁定/解锁调用之间更改它。知道这个工作原理将是很好的。 - Aholio
我不完全确定你试图做什么,但在我所有手动绘图应用程序中,我从未看到过任何闪烁。我相信双缓冲区是自动处理的(我肯定从未必须手动管理它)。每次调用invalidate时,都会调用onDraw回调函数并重新绘制画布。我无法确定Surface *实际上在做什么...我从未查看过底层代码。 - Yevgeny Simkin
目前我只是想更好地理解发生了什么。现在,通过清除画布并重新绘制所有内容,我可以获得无闪烁的动画效果。我只是好奇为什么单个绘图调用会出现闪烁。我的最初假设是画布是持久的,因此在理论上锁定/解锁时我正在处理相同的表面。但事实并非如此,因此锁定/解锁会带来不同的表面。这是我迄今为止收集到的信息。我希望能找到更好的文档来解释这种行为,而不仅仅是依靠自己的观察。再次感谢您的帮助。 - Aholio
传递dirtyRect会破坏性能,因为它必须复制前一个缓冲区的内容。真希望有一种方法可以关闭双缓冲... - jjxtra

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接