我为什么要做手动双缓冲?

时间:2010-09-08 15:58:39

标签: c# winforms gdi+ doublebuffered

我正在使用C#进行游戏(2.0或3.5还没有决定)。游戏将在具有六边形网格的地图上播放。我很欣赏这个地图的UI应该使用双缓冲(很多层,所以慢绘图)。我知道我可以通过样式启用双缓冲,或者创建我自己的缓冲区并自己处理它。我在网上找到的大多数建议都是自己处理。我想知道为什么?显然这允许我避免控制双缓冲中固有的假设,但我不知道这些假设是什么。

同样,我不是在寻找代码来解释如何双重缓冲我的控件,而是为什么我自己构建它而不是使用双缓冲样式并允许CLR / Control类来处理它?<​​/ p>

2 个答案:

答案 0 :(得分:4)

来自MSDN

  

对于图形密集型应用程序   比如动画,你有时候可以   通过使用a来提高性能   专用的BufferedGraphicsContext   而不是BufferedGraphicsContext   由...提供   BufferedGraphicsManager。这使得   你要创建和管理图形   单独缓冲,没有   产生性能开销   管理所有其他缓冲   与您的相关的图形   应用程序,虽然记忆   应用程序将使用   大。

编辑:我还发现鲍勃鲍威尔的this文章可能会有所帮助

  

手动双缓冲可能很有用   如果你不想让系统如此制作   对你的假设,如是否   背景是不透明的或   透明或者如果你愿意的话   创建一个更复杂的缓冲   系统。有一些简单的规则   你需要遵循以获得手册   双重缓冲。

     

首先,不要创建新的后台缓冲区   每个抽奖周期。只创建或   在窗口时销毁位图   客户规模变化。第二,仅   创建所需大小的位图。   清除像素需要时间,如果   像素比你需要的多,   你只是在浪费处理器周期。   最后,使用最简单的绘制方法   将位图复制到屏幕。   DrawImageUnscaled是要走的路   这里。

编辑:另一个原因是您可能希望应用程序控制缓冲,而不是控件本身。

来源:Pro .NET 2.0 Windows Forms and custom controls in C#

答案 1 :(得分:3)

在WFA中,双缓冲会降低性能,而不会完全消除自定义图形区域中的闪烁。对于内置的GUI元素,就像创建一个由ImageButtons和Labels构建的游戏一样,内置的双缓冲模式非常适合隐藏重绘控件树。但是,将它用于自定义绘图区域有几个主要问题:

  • 当您设置应用程序以绘制双缓冲时创建的绘制缓冲区用于绘制整个窗口和所有子控件,而不仅仅是您的自定义绘图区域,因此您添加了重绘每个GUI元素的开销。页面翻转前的后台缓冲区。
  • 如果控件无效,则调用Paint方法。当发生这种情况时,您可能无法完成绘图,因此您将向用户显示不完整的图像(实时图形效果不佳)。

通过保持基本窗口GUI单缓冲,但创建一个控制缓冲的区域,这些问题都会被最小化。

双缓冲方法可以像创建一个Bitmap对象作为后台缓冲区一样简单,并在你准备就绪时将其绘制到绘图区域,或者设置一个单独的BufferedGraphicsContext来管理自定义绘图区域的缓冲