似乎我无法通过所有者绘制控件传递此问题。我已经超级分级了状态控制。我正在尝试自定义但仍保留相同的功能。基本上,我想改变背景和文字。我正在使用Direct2d(或ID2D1DCRenderTarget接口)进行绘图。我使用WM_NCPAINT成功更改了背景;但是,如果需要,可以使用WM_ERASEBKGRND。但是,这两种方法在我的实验中都起到了控制作用,并且仍然发生了闪烁。此外,当SB_SETTEXT的WPARAM
答案 0 :(得分:2)
如果为控制打开双缓冲,则可以避免闪烁。
设置WS_EX_COMPOSITED扩展样式: http://msdn.microsoft.com/en-us/library/windows/desktop/ff700543(v=vs.85).aspx
e.g。处理WM_CREATE时,调用(WTL或MFC):
ModifyStyleEx(0, WS_EX_COMPOSITED);
答案 1 :(得分:1)
**注意:仅在关闭视觉样式的情况下进行测试。 SetWindowTheme(hWndStatus,L“”,L“”); 此外,父窗口必须在窗口创建期间在样式参数中设置WS_CLIPCHILDREN。
1:覆盖WM_SIZE。调用InvalidateRect(m_hWnd,NULL,TRUE)并返回0,除非你想要默认的大小调整;在这种情况下,请调用CallWindowProc。
2:覆盖WM_ERASEBKGND并返回-1。
3:覆盖WM_NCPAINT并将绘图代码放在此处。
处理WM_NCPAINT。人们似乎无法理解如何处理WM_NCPAINT。我就是这样做的。
if (wParam == 1) {
hdc = GetWindowDC(m_hWnd);
} else {
hdc = GetDCEx(m_hWnd, (HRGN) wParam, DCX_WINDOW | DCX_INTERSECTRGN | DCX_CACHE);
}
然后用DC绘图。
4:在父程序(WndProc或其他)中使用状态栏的句柄调用SetWindowPos(...,SWP_DRAWFRAME)。这会调整状态栏的大小。
5:通过SendMessage发送消息(hWndStatusbar,SB_SETPARTS,1,(LPARAM)& parts);
6:通过SendMessage发送消息(hWndStatusbar,SB_SETTEXT,LOBYTE(0)| SBT_OWNERDRAW,L“Ready”)。 WM_DRAWITEM的示例代码:
...
WM_DRAWITEM:
LPDRAWITEMSTRUCT lpDIS = (LPDRAWITEMSTRUCT) lParam;
m_pFramework->m_pD2D1RenderTarget->BindDC(lpDIS->hDC, &lpDIS->rcItem);
m_pFramework->m_pD2D1RenderTarget->BeginDraw();
m_pFramework->m_pD2D1RenderTarget->Clear(D2D1::ColorF(D2D1::ColorF::CadetBlue));
D2D1_RECT_F rf = D2D1::RectF(
PixeltoDipX(lpDIS->rcItem.left),
PixeltoDipY(lpDIS->rcItem.top),
PixeltoDipX(lpDIS->rcItem.right),
PixeltoDipY(lpDIS->rcItem.bottom)
);
m_pFramework->m_pD2D1RenderTarget->DrawText(
(LPCWSTR) lpDIS->itemData,
wcslen((WCHAR*) lpDIS->itemData) + 1,
m_pFramework->m_pTextFormat,
rf,
m_d2dCaptionTextColor
);
m_pFramework->m_pD2D1RenderTarget->EndDraw();
break;
....
这应该停止闪烁。另外,不要在父级的WM_SIZE中调用InvalidateRect(hWndStatus,NULL,TRUE)。这是它闪烁的主要原因。