
Android 入力サブシステムは、名目上、システムの複数のレイヤーを横断するイベント パイプラインで構成されています。
入力パイプライン
最下層の物理入力デバイスは、キーの押下やタッチ接触ポイントなどの状態変化を表す信号を生成します。デバイスのファームウェアは、USB HID レポートをシステムに送信したり、I2C バスで割り込みを生成したりするなど、何らかの方法でこれらの信号をエンコードして送信します。
その後、信号は Linux カーネルのデバイス ドライバーによってデコードされます。 Linux カーネルは、多くの標準周辺機器、特に HID プロトコルに準拠する周辺機器用のドライバーを提供します。ただし、OEM は多くの場合、タッチ スクリーンなどの低レベルでシステムに緊密に統合されている組み込みデバイス用のカスタム ドライバーを提供する必要があります。
入力デバイス ドライバーは、Linux 入力プロトコルを介して、デバイス固有の信号を標準の入力イベント形式に変換する役割を果たします。 Linux 入力プロトコルは、 linux/input.h
カーネル ヘッダー ファイルでイベント タイプとコードの標準セットを定義します。このように、カーネル外部のコンポーネントは、物理スキャン コード、HID の使用法、I2C メッセージ、GPIO ピンなどの詳細を気にする必要がありません。
次に、Android EventHub
コンポーネントは、各入力デバイスに関連付けられたevdev
ドライバーを開いて、カーネルから入力イベントを読み取ります。次に、Android InputReader コンポーネントは、デバイス クラスに従って入力イベントをデコードし、Android 入力イベントのストリームを生成します。このプロセスの一環として、Linux 入力プロトコル イベント コードは、入力デバイスの構成、キーボード レイアウト ファイル、およびさまざまなマッピング テーブルに従って、Android イベント コードに変換されます。
最後に、 InputReader
は入力イベントを InputDispatcher に送信し、InputDispatcher はそれらを適切なウィンドウに転送します。
コントロール ポイント
入力パイプラインには、入力デバイスの動作を制御するステージがいくつかあります。
ドライバーとファームウェアの構成
入力デバイス ドライバーは、レジスタにパラメーターを設定したり、ファームウェア自体をアップロードしたりすることによって、入力デバイスの動作を構成することがよくあります。これは特に、タッチ スクリーンなどの組み込みデバイスの場合に当てはまります。これらのキャリブレーション プロセスの大部分は、これらのパラメータの調整やファームウェアの修正を行って、目的の精度と応答性を実現し、ノイズを抑制します。
ドライバー構成オプションは、多くの場合、カーネル ボード サポート パッケージ (BSP) のモジュール パラメーターとして指定されるため、同じドライバーで複数の異なるハードウェア実装をサポートできます。
このドキュメントでは、ドライバーまたはファームウェアの構成について説明しようとしていますが、デバイスのキャリブレーション全般に関するガイダンスを提供しています。
ボード構成プロパティ
カーネル ボード サポート パッケージ (BSP) は、タッチ スクリーン上の仮想キーの配置など、Android InputReader コンポーネントによって使用される SysFS を介してボード構成プロパティをエクスポートする場合があります。
さまざまなデバイスがボード構成プロパティを使用する方法の詳細については、デバイス クラスのセクションを参照してください。
リソース オーバーレイ
ふたスイッチの操作など、いくつかの入力動作は、 config.xml
のリソース オーバーレイを介して構成されます。
以下にいくつかの例を示します。
config_lidKeyboardAccessibility
: ハードウェア キーボードがアクセス可能か非表示かについて、蓋スイッチの効果を指定します。config_lidNavigationAccessibility
: トラックパッドがアクセス可能か非表示かについて、蓋スイッチの効果を指定します。config_longPressOnPowerBehavior
: ユーザーが電源ボタンを押したままにするとどうなるかを指定します。config_lidOpenRotation
: 画面の向きに対するふたのスイッチの効果を指定します。
各構成オプションの詳細については、 frameworks/base/core/res/res/values/config.xml
内のドキュメントを参照してください。
キーマップ
キー マップは、キー、ジョイスティック ボタン、およびジョイスティック軸の Linux イベント コードから Android イベント コードへのマッピングを構成するために、Android EventHub
およびInputReader
コンポーネントによって使用されます。マッピングは、デバイスまたは言語に依存する場合があります。
さまざまなデバイスがキー マップを使用する方法の詳細については、デバイス クラスのセクションを参照してください。
入力デバイス構成ファイル
入力デバイス構成ファイルは、Android EventHub
およびInputReader
コンポーネントによって使用され、タッチ サイズ情報の報告方法などの特別なデバイス特性を構成します。
さまざまなデバイスが入力デバイス構成マップを使用する方法の詳細については、デバイス クラスのセクションを参照してください。
HID の使用法とイベント コードについて
多くの場合、キーボードの特定のキー、ゲーム コントローラーのボタン、ジョイスティックの軸、またはその他のコントロールを参照するために、いくつかの異なる識別子が使用されます。これらの識別子間の関係は常に同じではありません: それらは一連のマッピング テーブルに依存しており、一部は固定されており、一部はデバイスの特性、デバイス ドライバー、現在のロケール、システム構成に基づいて異なります。ユーザーの好みやその他の要因。
- 物理スキャンコード
物理スキャン コードは、各キー、ボタン、またはその他のコントロールに関連付けられているデバイス固有の識別子です。物理スキャン コードはデバイスごとに異なることが多いため、ファームウェアまたはデバイス ドライバーは、それらを HID 使用法や Linux キー コードなどの標準識別子にマッピングする必要があります。
スキャン コードは、主にキーボードに関係します。他のデバイスは通常、GPIO ピン、I2C メッセージ、またはその他の手段を使用して低レベルで通信します。その結果、ソフトウェア スタックの上位レイヤーはデバイス ドライバーに依存して、何が起こっているのかを理解します。
- HID の使用
HID の使用法は、キーボード キー、ジョイスティック軸、マウス ボタン、またはタッチ接点などのコントロールの状態を報告するために使用される標準の識別子です。ほとんどの USB および Bluetooth 入力デバイスは HID 仕様に準拠しているため、システムはそれらと統一された方法でインターフェイスできます。
Android フレームワークは、Linux カーネル HID ドライバーに依存して、HID 使用コードを Linux キー コードおよびその他の識別子に変換します。したがって、HID の使用法は主に周辺機器メーカーの関心事です。
- Linux キーコード
Linux キー コードは、キーまたはボタンの標準的な識別子です。 Linux キー コードは、プレフィックス
KEY_
またはBTN_
で始まる定数を使用して、linux/input.h
ヘッダー ファイルで定義されます。 Linux カーネル入力ドライバーは、物理スキャン コード、HID の使用、およびその他のデバイス固有の信号を Linux キー コードに変換し、それらに関する情報をEV_KEY
イベントの一部として配信する役割を果たします。Android API では、キーに関連付けられた Linux キー コードを「スキャン コード」と呼ぶことがあります。これは技術的には正しくありませんが、API で Linux キー コードと Android キー コードを区別するのに役立ちます。
- Linux の相対または絶対軸コード
Linux の相対または絶対軸コードは、X 軸に沿ったマウスの相対移動や X 軸に沿ったジョイスティックの絶対位置など、軸に沿った相対移動または絶対位置を報告するための標準的な識別子です。 Linux 軸コードは、プレフィックス
REL_
またはABS_
で始まる定数を使用して、linux/input.h
ヘッダー ファイルで定義されます。 Linux カーネル入力ドライバーは、HID の使用法やその他のデバイス固有の信号を Linux 軸コードに変換し、それらに関する情報をEV_REL
およびEV_ABS
イベントの一部として配信する役割を果たします。- Linux スイッチ コード
Linux スイッチ コードは、蓋のスイッチなど、デバイスのスイッチの状態を報告するための標準的な識別子です。 Linux スイッチ コードは、プレフィックス
SW_
で始まる定数を使用して、linux/input.h
ヘッダー ファイルで定義されます。 Linux カーネル入力ドライバーは、スイッチ状態の変化をEV_SW
イベントとして報告します。通常、Android アプリケーションはスイッチからイベントを受信しませんが、システムはそれらを内部で使用して、さまざまなデバイス固有の機能を制御する場合があります。
- Android キーコード
Android キー コードは、「HOME」などの特定のキーを示すために Android API で定義されている標準の識別子です。 Android キー コードは、接頭辞
KEYCODE_
で始まる定数としてandroid.view.KeyEvent
クラスによって定義されます。キー レイアウトは、Linux キー コードを Android キー コードにマッピングする方法を指定します。キーボードのモデル、言語、国、レイアウト、または特殊機能に応じて、異なるキー レイアウトが使用される場合があります。
Android キー コードの組み合わせは、デバイスおよびロケール固有のキー文字マップを使用して文字コードに変換されます。たとえば、
KEYCODE_SHIFT
とKEYCODE_A
として識別されるキーが両方とも同時に押されると、システムはキー文字マップで組み合わせを検索し、大文字の「A」を見つけて、現在フォーカスされているテキスト ウィジェットに挿入します。- Android 軸コード
Android 軸コードは、特定のデバイス軸を示すために Android API で定義されている標準の識別子です。 Android の軸コードは、接頭辞
AXIS_
で始まる定数としてandroid.view.MotionEvent
クラスによって定義されます。キー レイアウトは、Linux 軸コードが Android 軸コードにどのようにマップされるかを指定します。デバイスのモデル、言語、国、レイアウト、または特殊機能に応じて、異なるキー レイアウトが使用される場合があります。
- Android のメタ状態
Android メタ状態は、どの修飾キーが押されたかを示すために Android API で定義された標準の識別子です。 Android のメタ ステートは、接頭辞
META_
で始まる定数としてandroid.view.KeyEvent
クラスによって定義されます。現在のメタ状態は、
KEYCODE_SHIFT_LEFT
などの修飾キーが押された/離されたときを監視し、適切なメタ状態フラグを設定/リセットする Android InputReader コンポーネントによって決定されます。修飾キーとメタ状態の関係はハードコーディングされていますが、キー レイアウトによって修飾キー自体のマッピング方法が変更され、メタ状態に影響を与える可能性があります。
- Android ボタンの状態
Android ボタンの状態は、(マウスまたはスタイラスの) どのボタンが押されているかを示すために Android API で定義されている標準の識別子です。 Android ボタンの状態は、接頭辞
BUTTON_
で始まる定数としてandroid.view.MotionEvent
クラスによって定義されます。現在のボタンの状態は、Android InputReader コンポーネントによって決定されます。このコンポーネントは、(マウスまたはスタイラスの) ボタンが押された/離されたときを監視し、適切なボタン状態フラグを設定/リセットします。
ボタンとボタンの状態の関係はハードコーディングされています。