キーボード入力の概要

アプリケーションでは、キーボードとマウスからのユーザー入力を受け入れる必要があります。 アプリケーションは、ウィンドウに投稿されたメッセージの形式でキーボード入力を受け取ります。

キーボード入力モデル

システムは、現在のキーボードに適したキーボード デバイス ドライバーをインストールすることで、アプリケーションにデバイスに依存しないキーボード サポートを提供します。 システムは、ユーザーまたはアプリケーションで現在選択されている言語固有のキーボード レイアウトを使用して、言語に依存しないキーボード サポートを提供します。 キーボード デバイス ドライバーは、キーボードからスキャン コードを受け取ります。このコードはキーボード レイアウトに送信され、そこでメッセージに変換され、アプリケーション内の適切なウィンドウに投稿されます。

キーボードの各キーに割り当てられるのは、 スキャン コードと呼ばれる一意の値です。これは、キーボード上のキーのデバイス依存識別子です。 ユーザーがキーを入力すると、キーボードによって 2 つのスキャン コードが生成されます。1 つはユーザーがキーを押したときに、もう 1 つはユーザーがキーを離すときです。

キーボード デバイス ドライバーは、スキャン コードを解釈し、それを 仮想キー コード (キーの目的を識別するシステムによって定義されたデバイスに依存しない値) に変換 (マップ) します。 スキャン コードを翻訳すると、キーボード レイアウトによって、スキャン コード、仮想キー コード、キーストロークに関するその他の情報を含むメッセージが作成され、メッセージがシステム メッセージ キューに配置されます。 システムは、システム・メッセージ待ち行列からメッセージを除去し、それを適切なスレッドのメッセージ待ち行列にポストします。 最終的に、スレッドのメッセージ ループはメッセージを削除し、処理のために適切なウィンドウ プロシージャに渡します。 次の図は、キーボード入力モデルを示しています。

キーボード入力処理モデル

キーボード フォーカスとアクティブ化

システムは、キーボード フォーカスを使用してウィンドウを作成したフォアグラウンド スレッドのメッセージ キューにキーボード メッセージをポストします。 キーボード フォーカスは、ウィンドウの一時的なプロパティです。 システムは、キーボードフォーカスをユーザーの方向に、あるウィンドウから別のウィンドウにシフトすることで、ディスプレイ上のすべてのウィンドウ間でキーボードを共有します。 キーボード フォーカスがあるウィンドウは、フォーカスが別のウィンドウに変わるまで、すべてのキーボード メッセージを (作成したスレッドのメッセージ キューから) 受け取ります。

スレッドは GetFocus 関数を呼び出して、現在キーボード フォーカスを持っているウィンドウ (存在する場合) を決定できます。 スレッドは 、SetFocus 関数を呼び出すことによって、いずれかのウィンドウにキーボード フォーカスを与えることができます。 キーボードフォーカスがウィンドウ間で変化すると、フォーカスを失ったウィンドウに WM_KILLFOCUS メッセージが送信され、フォーカスを取得したウィンドウに WM_SETFOCUS メッセージが送信されます。

キーボード フォーカスの概念は、アクティブ ウィンドウの概念に関連しています。 アクティブ ウィンドウは、ユーザーが現在操作している最上位のウィンドウです。 キーボード フォーカスのあるウィンドウは、アクティブ ウィンドウまたはアクティブ ウィンドウの子ウィンドウです。 ユーザーがアクティブウィンドウを識別できるように、システムはそれをZオーダーの一番上に配置し、タイトルバー(存在する場合)と境界線を強調表示します。

ユーザーは、最上位ウィンドウをクリックするか、Alt + TAB キーまたは Alt + ESC キーの組み合わせを使用して選択するか、タスク リストから選択することで、最上位ウィンドウをアクティブ化できます。 スレッドは 、SetActiveWindow 関数を使用してトップレベル ウィンドウをアクティブ化できます。 作成した最上位ウィンドウがアクティブかどうかを判断するには、 GetActiveWindow 関数を使用します。

1 つのウィンドウが非アクティブ化され、別のウィンドウがアクティブになると、システムは WM_ACTIVATE メッセージを送信します。 ウィンドウが非アクティブ化されている場合は wParam パラメーターの下位ワードは 0、アクティブ化されている場合は 0 以外です。 既定のウィンドウ プロシージャは 、WM_ACTIVATE メッセージを受け取ると、キーボード フォーカスをアクティブ ウィンドウに設定します。

キーボードとマウスの入力イベントがアプリケーションに到達するのをブロックするには、 BlockInput を使用しますBlockInput 関数は、非同期キーボードの入力状態テーブルに干渉しないことに注意してください。 つまり、入力がブロックされている間に SendInput 関数を呼び出すと、非同期キーボードの入力状態テーブルが変更されます。

キーストローク メッセージ

キーを押 すと、キーボード フォーカスがあるウィンドウに接続されている スレッド メッセージ キュー にWM_KEYDOWNメッセージまたはWM_SYSKEYDOWN メッセージが配置されます。 キーを解放すると、 WM_KEYUP または WM_SYSKEYUP メッセージがキューに配置されます。

通常、キーアップメッセージとキーダウンメッセージはペアで行われますが、ユーザーがキーボードの自動繰り返し機能を開始するのに十分な長さのキーを押すと、システムは多数の WM_KEYDOWN またはWM_SYSKEYDOWNメッセージを 1 行に生成します。 その後、ユーザーがキーを解放すると、単一のWM_KEYUPまたはWM_SYSKEYUPメッセージが生成されます。

このセクションは、次のトピックで構成されています。

システムキーストロークと非システムキーストローク

システムは、システムキーストロークと非システムキーストロークを区別します。 システムキーストロークは、システムキーストロークメッセージ、 WM_SYSKEYDOWN および WM_SYSKEYUPを生成します。 非システム キーストロークでは、非システム キーストローク メッセージ、 WM_KEYDOWNWM_KEYUPが生成されます。

ウィンドウ プロシージャでシステム キーストローク メッセージを処理する必要がある場合は、メッセージの処理後に、プロシージャが DefWindowProc 関数に渡すようにします。 それ以外の場合、ウィンドウにキーボード フォーカスがある場合は常に、Alt キーを使用するすべてのシステム操作が無効になります。 つまり、ユーザーはウィンドウのメニューまたはシステム メニューにアクセスしたり、Alt + ESC キーまたは Alt + TAB キーの組み合わせを使用して別のウィンドウをアクティブ化したりすることはできません。

システム キーストローク メッセージは、主にアプリケーションではなくシステムで使用されます。 システムは、それらを使用して、組み込みのキーボード インターフェイスをメニューに提供し、ユーザーがアクティブなウィンドウを制御できるようにします。 システム キーストローク メッセージは、ユーザーが Alt キーと組み合わせてキーを入力したとき、またはユーザーが入力し、ウィンドウにキーボード フォーカスがない場合 (たとえば、アクティブなアプリケーションが最小化されている場合) に生成されます。 この場合、メッセージは、アクティブ ウィンドウに接続されているメッセージ キューにポストされます。

非システム キーストローク メッセージは、アプリケーション ウィンドウで使用されます。 DefWindowProc 関数は、それらに対して何も行いません。 ウィンドウ プロシージャは、不要なシステムキーストロークメッセージを破棄できます。

説明されているVirtual-Key コード

キーストローク メッセージの wParam パラメーターには、押されたか解放されたキーの 仮想キー コード が含まれています。 ウィンドウ プロシージャは、仮想キー コードの値に応じて、キーストローク メッセージを処理または無視します。

一般的なウィンドウ プロシージャでは、受信したキーストローク メッセージの小さなサブセットのみが処理され、残りの部分は無視されます。 たとえば、ウィンドウ プロシージャでは、キーストローク メッセージ WM_KEYDOWN のみを処理し、カーソル移動キー、シフト キー (コントロール キーとも呼ばれます)、およびファンクション キーの仮想キー コードを含むメッセージのみを処理できます。 一般的なウィンドウ プロシージャでは、文字キーからのキーストローク メッセージは処理されません。 代わりに、 TranslateMessage 関数を使用してメッセージを文字メッセージに変換します。 TranslateMessage と文字メッセージの詳細については、「文字メッセージ」を参照してください。

キーストローク メッセージ フラグ

キーストローク メッセージの lParam パラメーターには、メッセージを生成したキーストロークに関する追加情報が含まれています。 この情報には、 繰り返し数スキャン コード拡張キー フラグコンテキスト コード、前の キー状態フラグおよび遷移状態フラグが含まれます。 次の図は、これらのフラグの場所と lParam パラメーターの値を示しています。

キーストローク メッセージの lparam パラメーター内のフラグと値の場所

アプリケーションでは、次の値を使用して 、lParam の上位ワードからキーストローク フラグを取得できます。

説明
KF_EXTENDED
0x0100
拡張キー フラグを操作します。
KF_DLGMODE
0x0800
ダイアログ ボックスがアクティブかどうかを示すダイアログ モード フラグを操作します。
KF_MENUMODE
0x1000
メニューがアクティブかどうかを示すメニュー モード フラグを操作します。
KF_ALTDOWN
0x2000
コンテキスト コード フラグを操作します。
KF_REPEAT
0x4000
前のキー状態フラグを操作します。
KF_UP
0x8000
遷移状態フラグを操作します。

コード例:

case WM_KEYDOWN:
case WM_KEYUP:
case WM_SYSKEYDOWN:
case WM_SYSKEYUP:
{
    WORD vkCode = LOWORD(wParam);                                 // virtual-key code
    
    WORD keyFlags = HIWORD(lParam);

    WORD scanCode = LOBYTE(keyFlags);                             // scan code
    BOOL isExtendedKey = (keyFlags & KF_EXTENDED) == KF_EXTENDED; // extended-key flag, 1 if scancode has 0xE0 prefix
    
    if (isExtendedKey)
        scanCode = MAKEWORD(scanCode, 0xE0);

    BOOL wasKeyDown = (keyFlags & KF_REPEAT) == KF_REPEAT;        // previous key-state flag, 1 on autorepeat
    WORD repeatCount = LOWORD(lParam);                            // repeat count, > 0 if several keydown messages was combined into one message

    BOOL isKeyReleased = (keyFlags & KF_UP) == KF_UP;             // transition-state flag, 1 on keyup

    // if we want to distinguish these keys:
    switch (vkCode)
    {
    case VK_SHIFT:   // converts to VK_LSHIFT or VK_RSHIFT
    case VK_CONTROL: // converts to VK_LCONTROL or VK_RCONTROL
    case VK_MENU:    // converts to VK_LMENU or VK_RMENU
        vkCode = LOWORD(MapVirtualKeyW(scanCode, MAPVK_VSC_TO_VK_EX));
        break;
    }

    // ...
}
break;

繰り返し回数

繰り返し数を確認して、キーストローク メッセージが複数のキーストロークを表しているかどうかを判断できます。 システムは、キーボードがメッセージをWM_KEYDOWNまたはWM_SYSKEYDOWNメッセージを生成するときに、アプリケーションで処理できる時間よりも速くカウントをインクリメントします。 これは多くの場合、ユーザーがキーボードの自動繰り返し機能を開始するのに十分な長さにキーを押したままにすると発生します。 システム メッセージ キューに結果のキーダウン メッセージを入力する代わりに、システムはメッセージを 1 つのキーダウン メッセージに結合し、繰り返し数を増やします。 キーを解放しても自動繰り返し機能を開始できないため、 WM_KEYUP メッセージと WM_SYSKEYUP メッセージの繰り返し数は常に 1 に設定されます。

スキャン コード

各キーのキー位置を持つ Type 4 キーボードの図。

スキャン コードは、ユーザーがキーを押したときにシステムによって生成される値です。 これは、キーで表される文字ではなく、アクティブな キーボード レイアウトに関係なく押されたキーを識別する値です。 通常、アプリケーションはスキャン コードを無視します。 代わりに、仮想キー コードを使用してキーストローク メッセージを解釈します。

最新のキーボードでは、コンピューターと通信するために ヒューマン インターフェイス デバイス (HID) 仕様が使用されています。 キーボード ドライバーは 、報告された HID 使用状況の値をキーボードから送信して сode をスキャンし、アプリケーションに渡します。

Note

通常、仮想キー コードはデスクトップ アプリケーションの方が便利ですが、現在の キーボード レイアウトに関係なく押されているキーを知る必要がある場合、特定のケースでスキャン コードが必要になる場合があります。 たとえば、WASD (W が上、A が左、S がダウン、D が右) のゲームのキー バインドを使用します。これにより、 US QWERTY または フランス語の AZERTY キーボード レイアウト全体で一貫したキーの形成が保証されます。

次の表に、Windows で現在認識されているスキャン コードのセットを示します。 HID の使用状況ページ/HID の使用状況 ID/HID 使用法名の 値は、 HID 使用法テーブルドキュメントを 参照します。 キーの場所の値は、前のキーボード イメージを参照します。

Scan 1 Make コードは、メッセージWM_KEYDOWN WM_KEYUP/WM_SYSKEYDOWN/WM_SYSKEYUP/およびWM_INPUTメッセージで配信されます。

HID の使用状況ページ HID 使用法の ID HID 使用法の名前 キーの場所 スキャン 1 Make
07 01 ErrorRollOver FF
07 02 POSTFail FC
07 04 キーボード A 31 1E
07 05 キーボード B 50 30
07 06 キーボード C 48 2e
07 07 キーボード D 33 20
07 08 キーボード E 19 12
07 09 キーボード F 34 21
07 0A キーボード G 35 22
07 0B キーボード H 36 23
07 0C キーボード I 24 17
07 0D キーボード J 37 24
07 0E キーボード K 38 25
07 0F キーボード L 39 26
07 10 キーボード M 52 32
07 11 キーボード N 51 31
07 12 キーボード O 25 18
07 13 キーボード P 26 19
07 14 キーボード Q 17 10
07 15 キーボード R 20 13
07 16 キーボード S 32 1F
07 17 キーボード T 21 14
07 18 キーボード U 23 16
07 19 キーボード V 49 2F
07 1A キーボード W 18 11
07 1B キーボード X 47 2D
07 1C キーボード Y 22 15
07 1D キーボード Z 46 2C
07 1E キーボード 1 と Bang 2 02
07 1F キーボード 2 と At 3 03
07 20 キーボード 3 とハッシュ 4 04
07 21 キーボード 4 とドル 5 05
07 22 キーボード 5 とパーセント 6 06
07 23 キーボード 6 とキャレット 7 07
07 24 キーボード 7 とアンパサンド 8 08
07 25 キーボード 8 と星 9 09
07 26 キーボード 9 と左角かっこ 10 0A
07 27 キーボード 0 と右角かっこ 11 0B
07 28 キーボード 戻り値 Enter 43 1C
07 29 キーボード エスケープ 110 01
07 2A キーボードの削除 15 0E
07 2B [キーボード] タブ 16 0F
07 2C キーボードの Space キー 61 39
07 2D キーボードダッシュとアンダースコア 12 0C
07 2e キーボードが等しいとプラス 13 0D
07 2F キーボード左中かっこ 27 1A
07 30 キーボード右中かっこ 28 1B
07 31 キーボード パイプとスラッシュ 29 2B
07 32 キーボード (米国以外) 42 2B
07 33 キーボード SemiColon とコロン 40 27
07 34 キーボード左アポスとダブル 41 28
07 35 キーボード グレーブ アクセントとチルダ 1 29
07 36 キーボード コンマ 53 33
07 37 キーボードのピリオド 54 34
07 38 キーボードの QuestionMark 55 35
07 39 キーボードキャップロック 30 3A
07 3A キーボード F1 112 3B
07 3B キーボード F2 113 3C
07 3C キーボード F3 114 3D
07 3D キーボード F4 115 3e
07 3e キーボード F5 116 3階
07 3階 キーボード F6 117 40
07 40 キーボード F7 118 41
07 41 キーボード F8 119 42
07 42 キーボード F9 120 43
07 43 キーボード F10 121 44
07 44 キーボード F11 122 57
07 45 キーボード F12 123 58
07 46 キーボードの PrintScreen 124 E0 37
54 *注 1
07 47 キーボード スクロール ロック 125 46
07 48 キーボードの一時停止 126 E1 1D
E0 46 *注 2
45 *注 3
07 49 キーボードの挿入 75 E0 52
07 4A キーボード ホーム 80 E0 47
07 4B キーボード の PageUp 85 E0 49
07 4C キーボードの前方削除 76 E0 53
07 4D キーボードの終了 81 E0 4F
07 4E キーボード の PageDown 86 E0 51
07 4f キーボード RightArrow 89 E0 4D
07 50 キーボード LeftArrow 79 E0 4B
07 51 キーボード DownArrow 84 E0 50
07 52 キーボードの UpArrow 83 E0 48
07 53 キーパッドの番号ロックとクリア 90 45
E0 45 *注 3
07 54 キーパッドスラッシュ 95 E0 35
07 55 キーパッドの星 100 37
07 56 キーパッドダッシュ 105 4A
07 57 キーパッドプラス 106 4E
07 58 キーパッド ENTER 108 E0 1C
07 59 キーパッド 1 と終了 93 4f
07 5A キーパッド 2 と下矢印 98 50
07 5B キーパッド 3 と PageDn 103 51
07 5C キーパッド 4 と左矢印 92 4B
07 5D キーパッド 5 97 4C
07 5E キーパッド 6 と右矢印 102 4D
07 5f キーパッド 7 とホーム 91 47
07 60 キーパッド 8 と上矢印 96 48
07 61 キーパッド 9 と PageUp 101 49
07 62 キーパッド 0 と挿入 99 52
07 63 キーパッドの期間 104 53
07 64 キーボードの米国以外のスラッシュ バー 45 56
07 65 キーボード アプリケーション 129 E0 5D
07 67 キーパッドが等しい 59
07 85 キーパッドコンマ 107*注 4 7E
07 87 キーボードインターナショナル1 56*注 4、5 73
07 88 キーボード インターナショナル 2 133*注 5 70
07 89 キーボード インターナショナル 3 14*注 5 7D
07 8A キーボードインターナショナル4 132*注 5 79
07 8B キーボードインターナショナル5 131*注 5 7b
07 8C キーボードインターナショナル6 5C
07 90 キーボード LANG1 72
07 91 キーボード LANG2 71
07 92 キーボード LANG3 78
07 93 キーボード LANG4 77
07 94 キーボード LANG5 76
07 E0 キーボード LeftControl 58 1D
07 E1 キーボード LeftShift 44 2A
07 E2 キーボード LeftAlt 60 38
07 E3 キーボードの左 GUI 127 E0 5B
07 E4 キーボード RightControl 64 E0 1D
07 E5 キーボード RightShift 57 36
07 E6 キーボード RightAlt 62 E0 38
07 E7 キーボードの右 GUI 128 E0 5C
01 81 システムの電源を切る E0 5E
01 82 システム スリープ E0 5F
01 83 システムウェイクアップ E0 63
0C 00B5 次のトラックをスキャンする E0 19
0C 00B6 前のトラックをスキャンする E0 10
0C 00B7 Stop E0 24
0C 00CD 再生/一時停止 E0 22
0C 00E2 Mute E0 20
0C 00E9 ボリュームの増分 E0 30
0C 00EA ボリュームデクリメント E0 2E
0C 0183 AL コンシューマー制御の構成 E0 6D
0C 018A AL Email リーダー E0 6C
0C 0192 AL 電卓 E0 21
0C 0194 AL ローカル コンピューター ブラウザー E0 6B
0C 0221 AC 検索 E0 65
0C 0223 AC ホーム E0 32
0C 0224 AC Back E0 6A
0C 0225 AC 転送 E0 69
0C 0226 AC 停止 E0 68
0C 0227 AC 更新 E0 67
0C 022A AC Previous Link E0 66

メモ:

  1. SysRq キー スキャン コードが Alt + Print 画面 のキーストロークに入力されている
  2. 中断 キー スキャン コードが Control キーと一時停止 キーストロークで送信される
  3. 従来のキーボード メッセージで見られるように
  4. キーはブラジルのキーボードに存在します
  5. キーは日本語キーボードに存在します

Extended-Key フラグ

拡張キー フラグは、キーストローク メッセージが Enhanced 101/102 キー キーボードの追加キーの 1 つから送信されたかどうかを示します。 拡張キーは、キーボードの右側にある Alt キーと Ctrl キーで構成されます。テンキーの左側にあるクラスター内の INS、DEL、HOME、END、PAGE UP、PAGE DOWN、および方向キー。NUM LOCK キー。BREAK (Ctrl + PAUSE) キー。PRINT SCRN キー。とテンキーの除算 (/) キーと ENTER キー。 右側の Shift キーは拡張キーとは見なされず、代わりに別のスキャン コードがあります。

指定した場合、スキャン コードは 2 バイトのシーケンスで構成され、最初のバイトの値は 0xE0。

コンテキスト コード

コンテキスト コードは、キーストローク メッセージが生成されたときに Alt キーがダウンしたかどうかを示します。 Alt キーがダウンしている場合は 1、アップしている場合は 0 です。

前のKey-State フラグ

前のキー状態フラグは、キーストローク メッセージを生成したキーが以前にアップまたはダウンしたかどうかを示します。 キーが以前にダウンしていた場合は 1、キーが以前にアップしていた場合は 0 です。 このフラグを使用すると、キーボードの自動繰り返し機能によって生成されたキーストローク メッセージを識別できます。 このフラグは、自動繰り返し機能によって生成された WM_KEYDOWN および WM_SYSKEYDOWN キーストローク メッセージの場合は 1 に設定されます。 メッセージの WM_KEYUPWM_SYSKEYUP は常に 1 に設定されます。

Transition-State フラグ

遷移状態フラグは、キーを押すか、キーを解放してキーストローク メッセージを生成したかを示します。 このフラグは、メッセージのWM_KEYDOWNWM_SYSKEYDOWNの場合は常に 0 に設定されます。メッセージのWM_KEYUPとWM_SYSKEYUPの場合は、常に 1 に設定されます。

文字メッセージ

キーストローク メッセージはキーストロークに関する多くの情報を提供しますが、文字キーストロークの文字コードは提供しません。 文字コードを取得するには、アプリケーションのスレッド メッセージ ループに TranslateMessage 関数を含める必要があります。 TranslateMessage はWM_KEYDOWN または WM_SYSKEYDOWN メッセージをキーボード レイアウトに渡します。 レイアウトはメッセージの仮想キー コードを調べ、文字キーに対応する場合は、(Shift キーと CAPS LOCK キーの状態を考慮して) 同等の文字コードを提供します。 次に、文字コードを含む文字メッセージを生成し、メッセージキューの先頭にメッセージを配置します。 メッセージ ループの次の繰り返しでは、キューから文字メッセージを削除し、メッセージを適切なウィンドウ プロシージャにディスパッチします。

このセクションは、次のトピックで構成されています。

非システム文字メッセージ

ウィンドウ プロシージャは、WM_CHAR、WM_DEADCHAR、WM_SYSCHARWM_SYSDEADCHAR、WM_UNICHARの文字メッセージを受け取ることができます。 TranslateMessage 関数は、WM_KEYDOWN メッセージを処理するときに、WM_CHARまたはWM_DEADCHARメッセージを生成します。 同様に、 WM_SYSKEYDOWN メッセージを処理すると 、WM_SYSCHARまたはWM_SYSDEADCHAR メッセージ 生成されます。

キーボード入力を処理するアプリケーションでは、通常、 WM_CHAR メッセージと WM_UNICHAR メッセージ以外のすべてのメッセージが無視され、その他のメッセージが DefWindowProc 関数に渡されます。 WM_CHARでは UTF-16 (16 ビット Unicode 変換形式) または ANSI 文字セットが使用されますが、WM_UNICHARでは常に UTF-32 (32 ビット Unicode 変換形式) が使用されることに注意してください。 システムは、 WM_SYSCHAR メッセージと WM_SYSDEADCHAR メッセージを使用してメニューニーモニックを実装します。

すべての文字メッセージの wParam パラメーターには、押された文字キーの文字コードが含まれています。 文字コードの値は、メッセージを受信するウィンドウのウィンドウ クラスによって異なります。 RegisterClass 関数の Unicode バージョンを使用してウィンドウ クラスを登録した場合、システムはそのクラスのすべてのウィンドウに Unicode 文字を提供します。 それ以外の場合、システムは ANSI 文字コードを提供します。 詳細については、「 ウィンドウ クラスの登録 」および「 Windows アプリで UTF-8 コード ページを使用する」を参照してください。

文字メッセージの lParam パラメーターの内容は、文字メッセージを生成するために変換されたキーダウン メッセージの lParam パラメーターの内容と同じです。 詳細については、「 キーストローク メッセージ フラグ」を参照してください。

メッセージのDead-Character

一部の英語以外のキーボードには、それ自体で文字を生成することが想定されていない文字キーが含まれています。 代わりに、後続のキーストロークによって生成される文字に分音記号を追加するために使用されます。 これらのキーは 、"デッド キー" と呼ばれます。 ドイツ語キーボードの circumflex キーは、デッド キーの例です。 "o" で構成される文字を circumflex で入力するには、ドイツのユーザーが circumflex キーを入力し、その後に "o" キーを入力します。 キーボード フォーカスのあるウィンドウには、次の一連のメッセージが表示されます。

  1. Wm_keydown
  2. WM_DEADCHAR
  3. Wm_keyup
  4. Wm_keydown
  5. Wm_char
  6. Wm_keyup

TranslateMessage は、配信不能キーから WM_KEYDOWN メッセージを処理するときに 、WM_DEADCHAR メッセージを生成します。 WM_DEADCHAR メッセージの wParam パラメーターには、配信不能キーの分音記号の文字コードが含まれていますが、通常、アプリケーションはメッセージを無視します。 代わりに、後続のキーストロークによって生成された WM_CHAR メッセージを処理します。 WM_CHAR メッセージの wParam パラメーターには、分音記号を含む文字コードが含まれています。 後続のキーストロークで分音記号と組み合わせることができない文字が生成された場合、システムは 2 つの WM_CHAR メッセージを生成します。 最初の の wParam パラメーターには、分音記号の文字コードが含まれています。2 番目の の wParam パラメーターには、後続の文字キーの文字コードが含まれています。

TranslateMessage 関数は、システムの配信不能キー (Alt キーと組み合わせて押されたデッド キー) からWM_SYSKEYDOWN メッセージを処理するときに、WM_SYSDEADCHAR メッセージを生成します。 アプリケーションは通常、 WM_SYSDEADCHAR メッセージを無視します。

キーの状態

キーボード メッセージの処理中に、アプリケーションでは、現在のメッセージを生成したキー以外の別のキーの状態を確認する必要がある場合があります。 たとえば、ユーザーが Shift キーを押しながら END キーを押してテキスト ブロックを選択できるようにするワープロ アプリケーションでは、END キーからキーストローク メッセージを受信するたびに Shift キーの状態を確認する必要があります。 アプリケーションでは 、GetKeyState 関数を使用して、現在のメッセージが生成された時点の仮想キーの状態を確認できます。 GetAsyncKeyState 関数を使用して、仮想キーの現在の状態を取得できます。

キーボード レイアウトでは、名前の一覧が保持されます。 1 つの文字を生成するキーの名前は、キーによって生成される文字と同じです。 TAB や ENTER などの文字以外のキーの名前は、文字列として格納されます。 アプリケーションは 、GetKeyNameText 関数を呼び出すことによって、デバイス ドライバーから任意のキーの名前を取得できます。

キーストロークと文字変換

このシステムには、さまざまなキーストローク メッセージによって提供されるスキャン コード、文字コード、仮想キー コードを変換するいくつかの特殊な目的機能が含まれています。 これらの関数には、 MapVirtualKeyToAsciiToUnicodeVkKeyScan が含まれます

さらに、Microsoft Rich Edit 3.0 では HexToUnicode IME がサポートされています。これにより、ユーザーはホット キーを使用して 16 進文字と Unicode 文字を変換できます。 つまり、Microsoft Rich Edit 3.0 をアプリケーションに組み込むと、アプリケーションは HexToUnicode IME の機能を継承します。

Hot-Key サポート

ホット キーは、WM_HOTKEY メッセージを生成するキーの組み合わせで、システムがスレッドのメッセージ キューの先頭に配置し、キュー内の既存のメッセージをバイパスします。 アプリケーションでは、ホット キーを使用して、ユーザーから優先度の高いキーボード入力を取得します。 たとえば、Ctrl + C キーの組み合わせで構成されるホット キーを定義することで、アプリケーションでは、ユーザーが長い操作を取り消すことができます。

ホット キーを定義するために、アプリケーションは RegisterHotKey 関数を呼び出し、 WM_HOTKEY メッセージを生成するキーの組み合わせ、メッセージを受信するウィンドウへのハンドル、ホット キーの識別子を指定します。 ユーザーがホット キーを押すと、ウィンドウを作成したスレッドのメッセージ キューに WM_HOTKEY メッセージが配置されます。 メッセージの wParam パラメーターには、ホット キーの識別子が含まれています。 アプリケーションはスレッドに対して複数のホット キーを定義できますが、スレッド内の各ホット キーには一意の識別子が必要です。 アプリケーションが終了する前に、 UnregisterHotKey 関数を使用してホット キーを破棄する必要があります。

アプリケーションでは、ホット キー コントロールを使用して、ユーザーがホット キーを簡単に選択できるようにすることができます。 ホット キー コントロールは、通常、ウィンドウをアクティブにするホット キーを定義するために使用されます。 RegisterHotKey 関数と UnregisterHotKey 関数は 使用されません。 代わりに、ホット キー コントロールを使用するアプリケーションは、通常、ホット キーを設定するために WM_SETHOTKEY メッセージを送信します。 ユーザーがホット キーを押すたびに、システムは SC_HOTKEY を指定する WM_SYSCOMMAND メッセージを送信します。 ホット キー コントロールの詳細については、「ホット キー コントロールの使用」を参照してください。

ブラウズやその他の機能用のキーボード キー

Windows では、ブラウザー機能、メディア機能、アプリケーション起動、電源管理用の特別なキーを備えたキーボードがサポートされています。 WM_APPCOMMANDでは、追加のキーボード キーがサポートされます。 さらに、 ShellProc 関数は、追加のキーボード キーをサポートするように変更されています。

コンポーネント アプリケーションの子ウィンドウで、これらの追加のキーボード キーのコマンドを直接実装できる可能性はほとんどありません。 そのため、これらのキーのいずれかが押されると、 DefWindowProcウィンドウにWM_APPCOMMAND メッセージを送信します。 DefWindowProc は、 WM_APPCOMMAND メッセージを親ウィンドウにバブルします。 これは、右マウス ボタンを使用してコンテキスト メニューを呼び出す方法と似ています。 つまり、DefWindowProc は右ボタン クリック でWM_CONTEXTMENU メッセージを送信し、親にバブルします。 さらに、 DefWindowProc がトップレベル ウィンドウの WM_APPCOMMAND メッセージを受信すると、コード HSHELL_APPCOMMANDを含むシェル フックが呼び出されます。

Windows では、5 つのボタンを持つマウスである Microsoft IntelliMouse Explorer もサポートされています。 2 つの追加ボタンは、前方および後方のブラウザー ナビゲーションをサポートします。 詳細については、「 XBUTTON」を参照してください。

入力のシミュレート

中断されない一連のユーザー入力イベントをシミュレートするには、 SendInput 関数を使用します。 関数は、3 つのパラメーターを受け取ります。 最初のパラメーター cInputs は、シミュレートされる入力イベントの数を示します。 2 番目のパラメーター rgInputsINPUT 構造体の配列であり、それぞれが入力イベントの種類とそのイベントに関する追加情報を記述します。 最後のパラメーター cbSize は、 INPUT 構造体のサイズをバイト単位で受け入れます。

SendInput 関数は、シミュレートされた一連の入力イベントをデバイスの入力ストリームに挿入することによって機能します。 この効果は、 keybd_event または mouse_event 関数を繰り返し呼び出すことと似ていますが、システムは、シミュレートされたイベントと他の入力イベントが混在しないようにします。 呼び出しが完了すると、戻り値は、正常に再生された入力イベントの数を示します。 この値が 0 の場合、入力はブロックされました。

SendInput 関数は、キーボードの現在の状態をリセットしません。 したがって、この関数を呼び出すときにユーザーがキーを押すと、この関数が生成するイベントに干渉する可能性があります。 干渉の可能性が心配な場合は、 GetAsyncKeyState 関数を使用してキーボードの状態を確認し、必要に応じて修正します。

言語、ロケール、キーボード レイアウト

言語は、英語、フランス語、日本語などの自然言語です。 サブ言語は、英国で話される英語のサブ言語や米国など、特定の地理的地域で話される自然言語の変種です。 アプリケーションでは、 言語識別子と呼ばれる値を使用して、言語とサブ言語を一意に識別します。

通常、アプリケーションでは ロケールを 使用して、入力と出力を処理する言語を設定します。 たとえば、キーボードのロケールを設定すると、キーボードによって生成される文字値に影響します。 ディスプレイまたはプリンターのロケールを設定すると、表示または印刷されるグリフに影響します。 アプリケーションでは、キーボード レイアウトを読み込んで使用して、キーボードのロケールを設定します。 指定したロケールをサポートするフォントを選択して、ディスプレイまたはプリンターのロケールを設定します。

キーボード レイアウトは、キーボード上のキーの物理的な位置を指定するだけでなく、それらのキーを押すことによって生成される文字値も決定します。 各レイアウトは、現在の入力言語を識別し、どのキーとキーの組み合わせによって生成される文字値を決定します。

すべてのキーボード レイアウトには、レイアウトと言語を識別する対応するハンドルがあります。 ハンドルのロー ワードは言語識別子です。 高い単語は、物理レイアウトを指定するデバイス ハンドル、または既定の物理レイアウトを示す 0 です。 ユーザーは、任意の入力言語を物理レイアウトに関連付けることができます。 たとえば、非常に頻繁にフランス語で作業する英語を話すユーザーは、キーボードの物理的なレイアウトを変更せずに、キーボードの入力言語をフランス語に設定できます。 つまり、ユーザーは使い慣れた英語レイアウトを使用してフランス語でテキストを入力できます。

通常、アプリケーションは入力言語を直接操作することは想定されていません。 代わりに、ユーザーは言語とレイアウトの組み合わせを設定し、それらの間で切り替えます。 ユーザーが別の言語でマークされたテキストをクリックすると、アプリケーションは ActivateKeyboardLayout 関数を呼び出して、その言語のユーザーの既定のレイアウトをアクティブにします。 ユーザーが作業中のリストにない言語でテキストを編集した場合、アプリケーションは言語を使用して LoadKeyboardLayout 関数を呼び出して、その言語に基づくレイアウトを取得できます。

ActivateKeyboardLayout 関数は、現在のタスクの入力言語を設定します。 hkl パラメーターには、キーボード レイアウトへのハンドルまたはゼロ拡張言語識別子を指定できます。 キーボード レイアウト ハンドルは、 LoadKeyboardLayout 関数または GetKeyboardLayoutList 関数から取得できます。 HKL_NEXTHKL_PREVの値を使用して、次または前のキーボードを選択することもできます。

GetKeyboardLayoutName 関数は、呼び出し元スレッドのアクティブなキーボード レイアウトの名前を取得します。 アプリケーションが LoadKeyboardLayout 関数を使用してアクティブなレイアウトを作成する場合、 GetKeyboardLayoutName はレイアウトの作成に使用されたのと同じ文字列を取得します。 それ以外の場合、文字列はアクティブレイアウトのロケールに対応する第一言語識別子です。 つまり、関数は必ずしも同じ主言語を持つ異なるレイアウト間で区別できるとは限らないため、入力言語に関する特定の情報を返すことはできません。 ただし、 GetKeyboardLayout 関数を使用して入力言語を決定できます。

LoadKeyboardLayout 関数は、キーボード レイアウトを読み込み、ユーザーがレイアウトを使用できるようにします。 アプリケーションでは、 KLF_ACTIVATE 値を使用して、現在のスレッドのレイアウトをすぐにアクティブにすることができます。 アプリケーションでは、 KLF_REORDER 値を使用して、 KLF_ACTIVATE 値も指定せずにレイアウトを並べ替えることができます。 アプリケーションでは、キーボード レイアウトを読み込むときに 常に KLF_SUBSTITUTE_OK 値を使用して、ユーザーの設定 (ある場合) が選択されていることを確認する必要があります。

多言語サポートの場合、 LoadKeyboardLayout 関数は 、KLF_REPLACELANG フラグと KLF_NOTELLSHELL フラグを提供します。 KLF_REPLACELANG フラグは、言語を変更せずに既存のキーボード レイアウトを置き換える関数を指示します。 同じ言語識別子を使用し、 KLF_REPLACELANG を指定せずに既存のレイアウトを置き換えようとすると、エラーになります。 KLF_NOTELLSHELL フラグを指定すると、キーボード レイアウトが追加または置き換えられたときに、関数がシェルに通知できなくなります。 これは、連続する一連の呼び出しで複数のレイアウトを追加するアプリケーションに役立ちます。 このフラグは、最後の呼び出し以外のすべての呼び出しで使用する必要があります。

UnloadKeyboardLayout 関数は、システムの既定の入力言語をアンロードできないという点で制限されています。 これにより、シェルおよびファイル システムで使用されるのと同じ文字セットを使用して、ユーザーが入力テキストに使用できるレイアウトが常に 1 つ確保されます。