【问题标题】:Win32 Message Loops: Quitting after window closes with GetMessage(&msg, NULL, 0, 0)?Win32 消息循环:使用 GetMessage(&msg, NULL, 0, 0) 关闭窗口后退出?
【发布时间】:2011-06-21 01:36:52
【问题描述】:

如果我有以下代码,如何检测窗口何时关闭,以便退出? r 似乎永远不会得到值 -1 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);
}

【问题讨论】:

    标签: c winapi window message-loop


    【解决方案1】:

    我找到了解决方案: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 会不间断地检索 WM_NULL 消息(第一个提示),IsWindow 可以检查窗口(确认)。

    【讨论】:

      【解决方案2】:

      等待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?

      【讨论】:

      • 对不起,我完全忘记了r == -1 不是关闭条件。但它不也应该以r == 0 退出吗?它怎么不这样做? (顺便说一句,我WM_QUIT 永远不会被发送到循环中。)
      • @Mehrdad:是的,我的回答指出WM_QUIT 永远不会发送到消息循环。如果GetMessage 检索到WM_QUIT,它返回值0。大概问题是您从未发送 WM_QUIT 消息。需要在窗口关闭时处理这种情况,并使用PostQuitMessage function 指示循环应该退出。
      • 哦,等等……所以如果我需要发送它,并且我打开了多个窗口,并且彼此之间有许多控件,我怎么知道我是否是最后一个打开的窗口,以及是否我应该从 WndProc 发送它吗?跟踪它不是变得很丑陋吗?
      • @Mehrdad:大多数应用程序都有一个“主”窗口,它在关闭时退出程序,而不管其他窗口是否打开。如果您确实有对等窗口,只需将计数保存在全局变量中即可。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-10-14
      • 2017-06-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-05-26
      相关资源
      最近更新 更多