Menu

KBAccel

develop (84)
novice123

内部構造>キーボードアクセラレータについて

キーボードアクセラレータについて

2005年3月12日 (1.5.2.1)

ショートカットキーの処理にキーボードアクセラレータを使用しているが,その使い方が妙.

アクセラレータの作成

キーと機能の割り当てはCKeyBindが配列で管理している.アクセラレータの作成処理はCKeyBind::CreateAccerelator() (スペルミス!)にあるが,これはstatic関数であってCKeyBindはアクセラレータの管理は行わない.

アクセラレータ(オブジェクト)を作成する場所は管理プロセスにある.管理プロセスが作成したアクセラレータハンドルは共有メモリ上に置かれ,全てのエディタプロセスで共有する.

作成 CEditApp::CEditApp()

破棄 CControlProcess::Terminate()

何故か対称になっていない.

アクセラレータではキーとコマンドの組の配列からアクセラレータを生成する.しかし,サクラエディタではコマンドとしてテーブル内のコマンド値を設定していない.代わりにキーコードとシフト状態を組み合わせた値をコマンドとして登録している.

アクセラレータの再構築

設定が変更されるとアクセラレータは再構築される.キーとコードのマッピングは同じだが,機能の登録されていないキーを除外するための処置と思われる.

コマンド受信処理

キーが押されるとTranslateAccelerator()にてキーからコマンドに変換されてWM_COMMANDメッセージとして届く.wParamの上位ワードが0の場合はメニューから送られているのでそのまま下位ワードがコマンドとなるが上位ワードが1の場合はキーコードの組が送られて来るのみである.そこで下位ワードの値を元にCKeyBind::GetFuncCode() で本来のコマンドの値に変換した後にHandleCommand()に送っている.

コマンド変換処理の使用箇所

キーからコマンドを得る処理はエディタ本体以外にCDlgFuncListでも使われている.

謎なところ

  • Translatorを使う理由.WM_KEYDOWNを直接拾えば良いような気がする.
  • 何故コードを直接送るようにしなかったのか.

Related

Wiki: Design