10

我有一个调整大小的对话框。它还有一个自定义背景,我绘制它以响应 WM_ERASEBKGND 调用(当前是对 FillSolidRect 的简单调用)。

调整对话框大小时,会出现巨大的闪烁。为了尝试减少闪烁,我枚举了所有子窗口并将它们添加到剪切区域。这似乎有点帮助——现在闪烁在所有子控件中最明显,因为它们重新绘制。

如何在调整大小时使对话框无闪烁?我怀疑双缓冲必须发挥作用,但我不确定如何通过带有子控件的对话框来做到这一点(而不是让所有子控件都由所有者绘制或类似的东西)。

我应该注意,我使用的是 C++(不是 .NET)和 MFC,尽管欢迎纯基于 Win32 的解决方案 :)

注意:我尝试过但不起作用的一件事(不知道为什么)是:

CDC memDC;
memDC.CreateCompatibleDC(pDC);
memDC.FillSolidRect(rect, backgroundColor);

pDC->BitBlt(0, 0, rect.Width(), rect.Height(), &memDC, 0, 0, SRCCOPY);
4

6 回答 6

10

假设“FillSolidRect”是背景的擦除,然后从 WM_ERASEBKGND 返回 TRUE。

要执行几乎在代码片段中执行的双缓冲,您需要使用 CreateCompatibleBitmap 并将其选择到您的 memDC 中。

于 2008-10-19T09:47:47.477 回答
6

尝试将以下行添加到您的 OnInitDialog 函数:

    ModifyStyle(0, WS_CLIPCHILDREN, 0);
于 2008-10-02T23:04:24.250 回答
5

在 WM_ERASEBKGND 处理中什么也不做,并将擦除作为主 WM_PAINT 的一部分。您可以更智能地绘制,以便仅重绘无效区域,或者更轻松地对绘图进行双重缓冲。

通过在擦除背景中不做任何事情,您可以将所有绘图代码放在一个位置,这应该使其他人更容易遵循和维护。

于 2008-10-02T22:01:05.153 回答
5

如果您的目标是 WinXP 或更高版本,您还可以使用 WS_EX_COMPOSITED 样式为具有此样式的顶级窗口默认启用双缓冲。请记住,这有其自身的一组限制——特别是,不再使用 GetDC 等从 OnPaint 循环中抽出。

于 2008-12-31T20:00:59.563 回答
4

您可以将调用 InvalidateRect 方法的参数设置为 false。这将阻止您在窗口重绘时发送 WM_ERASEBKGND。

于 2013-02-12T09:55:13.273 回答
3

双缓冲确实是完成这项工作的唯一方法。

只要您确定,子控件就会自行处理CLIPCHILDREN

于 2008-10-02T21:49:56.897 回答