antenn-a
company profile

MFC航海日記 六十日目(ダイアログ上でのキーボードショートカット取得)


以前、こういったアプリを作った時ダイアログ好きな私が、何故か普通にMDIアプリにしたのを覚えている。
なぜだろう・・・。と、ふと、思い出してしまったのだよ。
そう、ダイアログではKeyDownとか取れないという事実に。
ワーオ。マジかよ。
さーてどうすっぺ。複数選択させる手段を考えて居たのになぁ。
で、しょうがないので、せめてキーボードからのショートカットを幾つか受け入れる事で妥協する事に。

prev


さて、ショートカットと言えば、アクセラレータキーでしょって事で、リソースエディタ開く。
で、アクセラレータを作る、もしくは追加する。

このアクセラレータキーの名前を仮に IDR_MAINDIALOG とした。
この中にキーを作って行くのだが、取り合えず 今回の場合は IDR_MAINFRAME とバッティングしない Ctrl + F とかを作ってみたりする。
作ったら、そのCtrl+FのショートカットのIDを ID_MAINDLG_CTRL_F と付けてみる。
実験実験。
アクセラレータを追加したら、今度は使いたいダイアログのヘッダーファイルを開き、
HACCEL m_hAccKey;
をメンバに加える。このハンドルは IDR 1個と対になるので、通常は1個で良いはず。
1つのアクセラレータファイルに複数登録出来るから。
これを複数持つケースとして考えられるのは、内部の状態遷移に拠って同じショートカットの飛び先の関数を変えたり、そういう事をしたい時は二つ以上宣言することも有るには有るが、普通は無いかなぁ。
更にヘッダーファイルにイベント発生時の関数を宣言しておく。
afx_msg void OnShortCutCtrlF();
さて、次はCPPファイルを開き、OnInitDialog内で、
m_hAccKey = ::LoadAccelerators( AfxGetInstanceHandle(), MAKEINTRESOURCE( IDR_MAINDIALOG ) );
を追加する。
更に、PreTranslateMessages をオーバライドする。オーバライドして出来た関数内で、
BOOL EDialog::PreTranslateMessage(MSG* pMsg)
{
    if ( m_hAccKey != NULL ){
        if ( ::TranslateAccelerator( this->m_hWnd, m_hAccKey, pMsg ) )
            return TRUE;
    }

	return CDialog::PreTranslateMessage(pMsg);
}
						
という感じに書く。
更に、実際にイベントをフックする部分を同CPPファイルに追加する
BEGIN_MESSAGE_MAP(EDialog, CDialog)
	ON_COMMAND(ID_MAINDLG_CTRL_F, OnShortCutCtrlF)
END_MESSAGE_MAP()
						
ここで書いた ID_MAINDLG_CTRL_F とは、アクセラレータキーの登録時に Ctrl+F のショートカットのIDです。
で、右側が先にヘッダーファイルに書いたイベント発生時に呼ばれるべき関数名です。
これを実装します。
void EDialog::OnShortCutCtrlF()
{
}
						

こんな感じで、OKなはず。これでダイアログ上で Ctrl+Fを押すとこの関数に飛んでくるですよ。
今回のサンプルはここからダウンロードしてください。


antenn-a

prev next


antenn-a