使用Win32 / MFC关闭和等待子框架窗口的最佳方法

时间:2009-06-11 13:04:40

标签: winapi mfc

这里有一些选项可能,但您认为最安全的方法是做什么:

我有一个带有父= NULL的子CFrameWnd(这样它可以与主应用程序分开生活,而应用程序正在运行,至少)。我已将所有这些窗口存储在列表中。当主应用程序关闭(MainFrame获取OnClose)时,我将遍历数组并向所有人发出PostMessage(WM_CLOSE)。然而,问题是他们每个人都必须在关闭之前做一些事情。所以,我需要等待他们。但是我们都在同一个线程上...那么,我怎么能等待孩子们关闭,而不会在单线程应用程序中阻止他们自己的处理呢?

或者我应该启动一个工作线程来处理它?会更容易吗?

提前致谢!

2 个答案:

答案 0 :(得分:3)

使用SendMessage()而不是PostMessage()。

编辑:另一个选项可能是在您的子窗口中简单地处理WM_DESTROY(当然,这取决于您的代码)。

答案 1 :(得分:1)

嗯,你当然不能等待他们关闭,你至少需要pump messages才能收到并处理WM_CLOSE。我猜你是怎么做到的。但我看到你在做PostMessage。为什么不改为SendMessage - 这将在窗口的窗口过程中同步运行关闭。或者您是否想要退出应用程序?然后你应该使用PostQuitMessage然后以正常方式抽取消息,直到GetMessage返回0.有很多选项。

抽取消息意味着在代码中有一个如下所示的循环。您不必调用AfxPumpMessages,但这可能会做类似的事情。实际上有许多不同的方法可以根据您的需要来提取消息。此外,还有很多功能可以为您提供信息。

BOOL bRet;

// note that GetMessage returns 0 when WM_QUIT is received - this is how PostQuitMessage
// would work to get us to shut down
// We are passing NULL for the hWnd parameter - this means receive all window and
// thread messages for this thread
while( (bRet = GetMessage( &msg, NULL /* hWnd */, 0, 0 )) != 0)
{ 
    if (bRet == -1)
    {
        // handle the error and possibly exit
    }
    else
    {
        TranslateMessage(&msg); 
        DispatchMessage(&msg); 
    }
}

如果您将消息发布到窗口或窗口,则需要提取消息。发生的事情是消息进入与该窗口相关联的线程的队列(该线程) - 消息泵将它们提取出来并将它们分派到正确的窗口过程。

如果您已发送消息而不是发布消息,则直接调用窗口的窗口过程 - 而不是进入队列。您不需要抽取消息,因为一旦SendMessage返回,消息就会被完全处理。

PostQuitMessage works的方式是在消息队列上设置一个标志,指示应用程序应该退出。 WM_QUIT消息实际上不是您要发送的窗口消息 - 会发生的是GetMessage将在处理完所有其他发布的窗口消息后检查此标志,如果已设置则返回0。这将导致所有窗口正确关闭,您无需将其自身发送到窗口。