2017-03-02 13 views
2

DestroyWindow()ドキュメントは言う以下:DestroyWindow()は、メッセージキューからウィンドウのメッセージを削除しますか?

機能も、ウィンドウのメニューを破棄スレッド メッセージキューをフラッシュし、

をいそれがすることを意味し、「スレッドのメッセージキューがフラッシュ」破棄したいウィンドウのメッセージキューからメッセージを削除しますか?

+0

このマニュアルページでは、「関連付けられた子ウィンドウまたは所有ウィンドウが破壊される」と言っているため、メッセージキューも破棄されます。しかし、OSが他のすべてのプロセスを調べて、メッセージキューを探し出して再編成するのは不合理なことです。それはボールを投げて、ああ、忘れて、それを忘れて言っているようなものです。 –

+1

良い質問ですが、ドキュメントによって明確にされていません。私の推測では、それはそのウィンドウとその子に投稿されたメッセージのキューだけをフラッシュします。 –

+2

@WeatherVane、メッセージキューは*スレッド*に属し、*ウィンドウではありません* - 単一スレッドは複数のウィンドウを作成することができます。また、特定のウィンドウを破棄することで、スレッドのメッセージキューも同様です。 –

答えて

3

ドキュメントは明示的ではありませんが、提案どおりに動作します。破棄されたウィンドウに投稿されたメッセージはフラッシュされ、他のウィンドウのメッセージ(またはスレッドに投稿されたメッセージ)はスレッドのキューに残ります。

次のサンプルプログラムはこれを実証しています - あなたの提案が真であれば、アサーションは発動すべきではなく(私のテストではそうしない)、

@HarryJohnstonがコメントで指摘しているように、スレッドによって1つのウィンドウを破壊しても、スレッドが所有する他のウィンドウは破壊されません(破壊されたウィンドウの子ウィンドウと所有ウィンドウは除きます)。彼らの投稿されたメッセージは効果的に削除されました。

#include <windows.h> 
#include <assert.h> 

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) 
{ 
    assert(message != WM_APP + 1); 
    return DefWindowProc(hWnd, message, wParam, lParam); 
} 

int APIENTRY wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow) 
{ 
    WNDCLASSEXW wcex{}; 
    wcex.cbSize = sizeof(WNDCLASSEX); 
    wcex.lpfnWndProc = WndProc; 
    wcex.hInstance = hInstance; 
    wcex.lpszClassName = L"msgflushtest"; 
    assert(RegisterClassExW(&wcex)); 

    HWND hWnd = CreateWindowEx(0, L"msgflushtest", nullptr, WS_POPUP, 0, 0, CW_USEDEFAULT, CW_USEDEFAULT, 
     HWND_DESKTOP, nullptr, hInstance, nullptr); 
    assert(hWnd); 

    assert(PostMessage(hWnd, WM_APP + 1, 0, 0)); // should be flushed 
    assert(PostThreadMessage(GetCurrentThreadId(), WM_APP + 2, 0, 0)); // should not be flushed 

    DestroyWindow(hWnd); 

    MSG msg; 
    assert(!PeekMessage(&msg, nullptr, WM_APP + 1, WM_APP + 1, PM_REMOVE)); 
    assert(PeekMessage(&msg, nullptr, WM_APP + 2, WM_APP + 2, PM_REMOVE)); 

    return 0; 
} 
+0

これを単純に拡張して(2番目のウィンドウで)、その場合の動作が同じであることを示します。破棄されていないウィンドウのメッセージは、ディスパッチもキューからも削除されません。 –

+0

( 'wcex {}'はタイプミスか、それとも私が追いついていない新しい構文ですか?VS2010はそれを拒否します)。 –

+0

@HarryJohnston - typoではありません。新しい構文。古い 'CL'コンパイラはそれを理解していません。 'WNDCLASSEXW wcex = {};'と書くことができます。これは正常に動作します。ほとんどの場合、 'WNDCLASSEXW wcex = {0};'しかし、ここでは '0'を余分に書きます。' = {} 'をCLで、{}バージョン – RbMm

関連する問題