これがWindowsおよびWin32API内にあると仮定すると、1つのオプションは、メインGetMessage
のTranslateMessage
、、DispatchMessage
ループでメッセージを探すことです。対象のウィンドウに関係なく、このループ内の任意のメッセージを特殊なケースにすることができます。
おそらくIsChild
、メッセージがメインウィンドウのコントロールを対象としていることを確認するために使用する必要があります(個別に表示されるダイアログボックスやメッセージボックスとは対照的です)。ロジックを正しく理解するのも面倒です。コントロールがフォーカスを失ったことがわかっている場合にのみメッセージを傍受し、必要な正確なメッセージのみを傍受するのが最善です。
数年前、私はこれをたくさん組み込んだライブラリメッセージループを作成しました。自分の小さなウィンドウクラスのインスタンスへのポインタを保持する単純なマネージャクラスがありました。ループは、ダイアログと通常のウィンドウの違いを認識し、各ウィンドウクラスにその子メッセージをスパイする機会を与えました。これを直接実行することはできず、規則は少し奇妙ですが、これは便利だと思うかもしれません...
int c_Window_List::Message_Loop (void)
{
MSG msg;
bool l_Handled;
while (GetMessage (&msg, NULL, 0, 0))
{
l_Handled = false;
c_Windows::c_Cursor l_Cursor;
bool ok;
for (ok = l_Cursor.Find_First (g_Windows); ok; ok = l_Cursor.Step_Next ())
{
if (IsChild (l_Cursor.Key (), msg.hwnd))
{
if (l_Cursor.Data ().f_Accelerators != NULL)
{
l_Handled = TranslateAccelerator (l_Cursor.Key (), l_Cursor.Data ().f_Accelerators, &msg);
if (l_Handled) break;
}
if (l_Cursor.Data ().f_Manager != 0)
{
l_Handled = l_Cursor.Data ().f_Manager->Spy_Msg (l_Cursor.Key (), msg);
}
if (l_Handled) break;
if (l_Cursor.Data ().f_Is_Dialog)
{
l_Handled = IsDialogMessage (l_Cursor.Key (), &msg);
if (l_Handled) break;
}
}
}
if (!l_Handled)
{
TranslateMessage (&msg);
DispatchMessage (&msg);
}
if (g_Windows.Size () == 0)
{
// When all windows have closed, exit
PostQuitMessage (0);
}
}
return msg.wParam;
}
接頭辞はf_
フィールドを意味します-後で規則を取り上げましたm_
が、このコードは非常に長い間再検討されていません。特に私のクラスf_Manager
のインスタンスを指しています。クラスは一種のイテレータであり、変数に格納されているすべてのウィンドウ(実際にはグローバルではなく静的クラスメンバー)をステップスルーするために使用されc_Window_Base
ます。c_Cursor
g_Windows