web-dev-qa-db-ja.com

EnterキーとEscapeキーでMFCダイアログが閉じないようにするにはどうすればよいですか?

MFCダイアログが閉じられないようにする方法の1つを知っています。 Enter または Esc キーが押されましたが、プロセスの詳細とそうするためのすべての一般的な代替方法を知りたいのですが。

助けてくれてありがとう。

22
Laxman Sahni

ユーザーがダイアログでEnterキーを押すと、次の2つのことが起こります。

  1. ダイアログにはデフォルトのコントロールがあります(CDialog::SetDefID()を参照)。次に、このコントロールのIDを持つWM_COMMANDがダイアログに送信されます。
  2. ダイアログにはデフォルトのコントロールがありません。次に、ID = IDOKのWM_COMMANDがダイアログに送信されます。

最初のオプションでは、デフォルトのコントロールのIDがIDOKに等しい場合があります。その後、結果は2番目のオプションと同じになります。

デフォルトでは、クラスCDialogには、仮想関数であるWM_COMMAND(IDOK)を呼び出すCDialog::OnOk()のハンドラーがあり、デフォルトではEndDialog(IDOK)ダイアログを閉じます。

したがって、ダイアログが閉じないようにする場合は、次のいずれかを実行します。

  1. デフォルトのコントロールをIDOK以外に設定します。
  2. WM_COMMAND(IDOK)を呼び出さないハンドラをEndDialog()に設定します。
  3. CDialog::OnOk()をオーバーライドし、基本実装を呼び出さない。

IDCANCELについても同様ですが、同等のSetDefID()はなく、ESCキーはハードコーディングされています。ダイアログが閉じられるのを防ぐには:

  1. WM_COMMAND(IDCANCEL)を呼び出さないハンドラをEndDialog()に設定します。
  2. CDialog::OnCancel()をオーバーライドし、基本実装を呼び出さない。
33
rodrigo

前の回答に代わる方法があります。これは、[OK]ボタンと[閉じる]ボタンを引き続き使用する場合に役立ちます。 PreTranslateMessage関数をオーバーライドすると、次のようにVK_ESCAPE/VK_RETURNの使用をキャッチできます。

BOOL MyCtrl::PreTranslateMessage(MSG* pMsg)
{
    if( pMsg->message == WM_KEYDOWN )
    {
        if(pMsg->wParam == VK_RETURN || pMsg->wParam == VK_ESCAPE)
        {
            return TRUE;                // Do not process further
        }
    }

    return CWnd::PreTranslateMessage(pMsg);
}

OnOkイベントをオーバーライドし、メッセージを親ダイアログに渡す代わりに、何もしません。
基本的にはそうするのと同じくらい簡単です:

void OnOk() override { /*CDialog::OnOK();*/ }

これにより、Enter/Enterキーを押したときにダイアログが閉じないようにする必要があります。

0
user7867434

しないでください#define CUSTOM_ID 2理由は2はエスケープ用にすでに定義されており、1はEnterに対して定義されていますか?私が間違っている場合は私を修正してください。

0
Kazem Sami