キーイベントの流れ
何は、ともあれ、顧客の要請である。
ウィンドウシステムのデフォルト動作を殺すため、
キーイベントの流れを追う事になった。
これが、また、随分と複雑である。
更に言えば、Windows と SWT の両方が絡むので、厄介だ。
とりあえず、SWT の Display クラスから追い始める。
Display クラスの readAndDispatch メソッドが、
SWT のメッセージループにおける要である。
で、中を覗いてみると、何の事はない。
Windows のメッセージループ、その物である。
if (OS.PeekMessage (msg, 0, 0, 0, OS.PM_REMOVE)) { if (!filterMessage (msg)) { OS.TranslateMessage (msg); OS.DispatchMessage (msg); } runDeferredEvents (); return true; }
filterMessage が、何をしているかというと...
boolean filterMessage (MSG msg) { int message = msg.message; if (OS.WM_KEYFIRST <= message && message <= OS.WM_KEYLAST) { Control control = findControl (msg.hwnd); if (control != null) { if (translateAccelerator (msg, control) || translateMnemonic (msg, control) || translateTraversal (msg, control)) { lastAscii = lastKey = 0; lastVirtual = lastNull = lastDead = false; return true; } } } return false; }
対象となるイベントは、以下の通り。
public static final int WM_KEYFIRST = 0x100; public static final int WM_KEYDOWN = 0x100; public static final int WM_KEYUP = 0x101; public static final int WM_CHAR = 0x102; public static final int WM_DEADCHAR = 0x103; public static final int WM_SYSKEYDOWN = 0x104; public static final int WM_SYSKEYUP = 0x105; public static final int WM_SYSCHAR = 0x106; public static final int WM_KEYLAST = 0x108;
0x107(WM_SYSDEADCHAR)は、SWT では、未定義の模様。
ちなみに、Windows 側では、0x109(WM_UNICHAR)が追加されている模様。
これを加えた場合は、WM_KEYLAST も 0x109 になるようだ。
まぁ、この辺は、今回の作業に、直接の関係はないだろうから、軽く流して...
結局、何をやっているのかというと...
キー関連のイベントで、かつ、メッセージの宛先コントロールが null ではなく、
translateAccelerator か translateMnemonic か translateTraversal で処理されたら ture を返す。
って感じかな?
translateAccelerator は、TranslateAccelerator に対応して、主にメニューなどのアクセラレータキー処理、
translateMnemonic は、内部で mnemonicMatch や traverse を呼び出しているけど、
どうも具体的な処理は、それぞれの派生クラスでオーバーライドするのか?
これは、改めて、派生クラス毎に確認する必要がありそうだな。
translateTraversal は、基本的に、フォーカス制御キーの処理。
ここでも traverse が呼び出されているので、translateMnemonic で呼び出される場合との違いを調べる必要があるか?