【发布时间】:2016-07-29 19:53:32
【问题描述】:
我有两个窗口,一个是由 D3D11 渲染的父窗口,另一个是我想在父窗口上移动的子窗口。
这是我如何创建窗口的代码:
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = 0;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = LoadIcon(NULL,IDI_APPLICATION);
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)0;
wcex.lpszMenuName = 0;
wcex.lpszClassName = L"Parent";
wcex.hIconSm = LoadIcon(NULL,IDI_APPLICATION);
if(!RegisterClassEx(&wcex)){
return E_FAIL;
}
if(!(hWnd = CreateWindowEx(WS_EX_COMPOSITED,L"Parent",L"WINDOW",
WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN |
WS_VISIBLE,
CW_USEDEFAULT,CW_USEDEFAULT,
WIDTH,HEIGHT,
NULL,NULL,
hInstance,NULL))){
return E_FAIL;
}
和子窗口
wcex2.cbSize = sizeof(WNDCLASSEX);
wcex2.style = 0;
wcex2.lpfnWndProc = WndProc2;
wcex2.cbClsExtra = 0;
wcex2.cbWndExtra = 0;
wcex2.hInstance = hInstance;
wcex2.hIcon = LoadIcon(NULL,IDI_APPLICATION);
wcex2.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex2.hbrBackground = (HBRUSH)0;
wcex2.lpszMenuName = 0;
wcex2.lpszClassName = L"Child";
wcex2.hIconSm = LoadIcon(NULL,IDI_APPLICATION);
if(!RegisterClassEx(&wcex2)){
return E_FAIL;
}
if(!(chilWnd = CreateWindowEx(0, wcex2.lpszClassName, NULL,
WS_CHILD|WS_CLIPSIBLINGS,
0,0,
200, 100,
hWnd,NULL,
hInstance,0)))
{
return FALSE;
}
这是子窗口的 WndProc
case WM_LBUTTONDOWN:
dragWindow = true;
SetCapture(hWnd);
break;
case WM_LBUTTONUP:
ReleaseCapture();
dragWindow = false;
break;
case WM_MOUSEMOVE:
if (dragWindow == true)
{
RECT mainWindowRect;
POINT pos;
int windowWidth, windowHeight;
pos.x = (int)(short) LOWORD(lp);
pos.y = (int)(short) HIWORD(lp);
GetWindowRect(hWnd,&mainWindowRect);
windowHeight = mainWindowRect.bottom - mainWindowRect.top;
windowWidth = mainWindowRect.right - mainWindowRect.left;
ClientToScreen(hWnd, &pos);
HDWP hdwp = BeginDeferWindowPos(1);
DeferWindowPos(hdwp,
hWnd,
HWND_TOP,
pos.x,
pos.y,
windowWidth,
windowHeight,
SWP_NOZORDER);
EndDeferWindowPos(hdwp);
LockWindowUpdate(hWnd);
RedrawWindow(hWnd, 0, 0, RDW_UPDATENOW);
LockWindowUpdate(NULL);
....
case WM_PAINT:
hdc = BeginPaint(hWnd, &Ps);
FillRect( hdc, &r, (HBRUSH)GetStockObject(GRAY_BRUSH));
EndPaint(hWnd, &Ps);
如果没有 LockWindowUpdate() 函数,我在移动它时会有子窗口跟踪。 所以最终结果是我移动它时子窗口是黑色的。我还能做什么? 我尝试了 GDI 双缓冲,即在 WM_MOUSEMOVE 事件上绘制屏幕外缓冲区 并在 WM_PAINT 事件的窗口上绘制,但结果相同。
【问题讨论】:
-
在子进程中你可以添加
case WM_NCHITTEST: return HTCAPTION;这将移动窗口(删除WM_MOUSEMOVE/LBUTTONUP/DOWN)也尝试将WS_EX_COMPOSITED更改为零 -
我添加了
case WM_NCHITTEST: return HTCAPTION;并删除了WM_MOUSEMOVE/LBUTTONUP/DOWN,但是当我移动它时,我有子窗口的痕迹,就像旧位置一样。 -
不应有任何尾随行。更新您的问题以显示您在做什么。