OpenGL的Win32主消息循环

时间:2017-01-25 21:00:35

标签: c++ winapi opengl waitformultipleobjects

Win32 OpenGL应用程序中的主要消息循环如下所示:

// Inside wWinMain
bool bQuit = false;
while( bQuit == false )
{
    DWORD dwReturn = ::MsgWaitForMultipleObjects( 0, NULL, FALSE, 12, QS_ALLINPUT );

    if( dwReturn == WAIT_OBJECT_0 )
    {
        MSG msg;
        BOOL bReturn = ::PeekMessage( &msg, NULL, 0, 0, PM_REMOVE );
        if( bReturn != FALSE )
        {
            if( msg.message == WM_QUIT )
                bQuit = true;
            ::TranslateMessage( &msg );
            ::DispatchMessage( &msg );
        }
    }

    if( dwReturn == WAIT_OBJECT_0 || dwReturn == WAIT_TIMEOUT )
    {
        RenderFrame();
        ::SwapBuffers( hDc );
    }
}

它工作得很好,我只有一个问题:如果我按Alt + F4关闭窗口,它在我释放键后不会立即退出,但是,如果我将鼠标悬停在窗口上,它会立即退出

A)这是为什么?我应该如何修改我的循环?

B)我发现的原始代码没有使用MsgWaitForMultipleObjects,而是连续调用RenderFrame。我认为这样会浪费太多的CPU时间来重绘屏幕。我对吗?什么是通常的方式,你是否将所有多余的能力用于绘图?

1 个答案:

答案 0 :(得分:3)

您的错误是PeekMessage每次WAIT_OBJECT_0 ,但您需要在循环while (::PeekMessage( &msg, NULL, 0, 0, PM_REMOVE ))中运行它,因为我们可以在此处输入多条消息。并且更好地使用MsgWaitForMultipleObjectsEx - 尝试此代码:

bool bQuit = false;
while( !bQuit )// for (;;)
{
    MSG msg;

    switch(::MsgWaitForMultipleObjectsEx( 0, NULL, 12, QS_ALLINPUT, 0))
    {
    case WAIT_OBJECT_0:
        while (::PeekMessage( &msg, NULL, 0, 0, PM_REMOVE ))
        {
            if( msg.message == WM_QUIT )
                bQuit = true;// return;
            ::TranslateMessage( &msg );
            ::DispatchMessage( &msg );
        }
    case WAIT_TIMEOUT:
        RenderFrame();
        ::SwapBuffers( hDc );
    }
}
  

如果我按Alt + F4关闭窗口,它就不会在我之后立即退出   释放钥匙

当您按Alt+F4MsgWaitForMultipleObjects返回时,会向您的帖子队列发布几条消息,但您处理的是并非全部,但仅一个 < / p>

  

但是,如果我将鼠标悬停在窗口上,它会立即退出

新消息(WM_MOUSEMOVE)已放置,但主MsgWaitForMultipleObjects再次返回,并且您最后处理与关闭流程相关的所有消息