2011-02-04 148 views
1

如果我有下面的代码,我该如何检测窗口关闭的时间,以便我可以退出? r似乎从来没有得到的值 -1 0,我需要为整个线程处理消息,而不仅仅是当前窗口。Win32消息循环:使用GetMessage(&msg,NULL,0,0)关闭窗口后退出?

HWND hWnd = CreateWindowExW(0, L"Edit", L"My Window", WS_OVERLAPPEDWINDOW, 
    CW_USEDEFAULT, CW_USEDEFAULT, 300, 200, NULL, NULL, NULL, NULL); 
ShowWindow(hWnd, SW_SHOWDEFAULT); 
MSG msg; 
BOOL r; 
while ((r = GetMessageW(&msg, NULL, 0, 0)) != 0) 
{ 
    if (r == -1) { break; } 
    TranslateMessage(&msg); 
    DispatchMessageW(&msg); 
} 

回答

3

等待r = -1不是您检测到窗口关闭的方式。 -1的返回值不是正常情况:它表示消息循环中发生错误。

documentation

返回值

类型:BOOL

如果函数检索比WM_QUIT其它的消息,则返回值为非零。

如果函数检索到WM_QUIT消息,则返回值为零。

如果有错误,则返回值为-1。例如,如果hWnd是无效窗口句柄或lpMsg是无效指针,则该函数失败。要获得更多的错误信息,请致电GetLastError

GetMessage从队列检索一个WM_QUIT消息,它会返回一个0值,你应该结束循环。

如果您只是想知道窗口何时关闭,您可能需要处理WM_CLOSEWM_DESTROY消息。有关这些消息的讨论,请参阅此问题的答案:What is the difference between WM_QUIT, WM_CLOSE, and WM_DESTROY in a windows program?

+1

对不起,我完全忘了'r == -1'不是关闭条件。但是它不是应该用`r == 0`退出吗?它怎么没有这样做? (顺便说一句,我`WM_QUIT`永远不会发送到循环中。) – Mehrdad 2011-02-04 00:46:14

0

我找到了解决方案:WM_NULL
消息循环可以自行独立处理事情的WndProc

// written in C# 
MSG msg = new MSG(); 
while (GetMessage(out msg, window, 0, 0)) 
{ 
    if ((msg.message == WM_NULL) && !IsWindow(window)) 
     break; 
    TranslateMessage(ref msg); 
    DispatchMessage(ref msg); 
} 
Console.WriteLine("yeah, out of loop ^^"); 

从我的观察:当窗口被破坏GetMessage没有停顿(1提示)检索WM_NULL消息和IsWindow可以检查窗口(肯定)。