カスタム コントローラ デバイス マッピングの追加

ゲーム コントローラ ライブラリは、コントローラ デバイスの内部データベースを保持しています。このデータベースは、ボタン、モーション軸のレイアウト、認識されたコントローラのマッピング、不明なコントローラのデフォルト マッピングの構成に使用されます。データベースには一般的なコントローラが多数含まれていますが、特定のゲームに関連するすべてのデバイスが含まれているとは限りません。ゲーム コントローラ ライブラリでは、次の機能を備えた関数のカスタマイズがサポートされています。

  • 現在のマッピング データベースを取得する。
  • 既存のデータベースにエントリを追加する。
  • 既存のデータベース エントリを置き換える。
  • 現在のデータベース全体を新しいデータベースに置き換える。

デバイスの識別

コントローラ デバイスは productIdvendorId の値で識別されます。認識された各コントローラ デバイスには、データベース内に productIdvendorId が一致するエントリが 1 つ以上あります。コントローラのマッピング構造体には、そのエントリに対して対応する Android API の範囲の最小と最大を指定するフィールドがあります。同じ最小と最大 API 範囲が一意である限り、同じ productIdvendorId を持つ複数のエントリがデータベースに存在できます。

現在の再マップデータを読み取る

Paddleboat_getControllerRemapTableData 関数を使用して、現在の再マップデータを取得します。

int32_t Paddleboat_getControllerRemapTableData(
   const int32_t destRemapTableEntryCount,
   Paddleboat_Controller_Mapping_Data* mappingData)

Paddleboat_getControllerRemapTableData は、内部データベースに存在する再マップエントリの総数を返します。

パラメータ 説明
destRemapTableEntryCount mappingData パラメータで渡された Paddleboat_Controller_Mapping_Data 要素の配列サイズ。
mappingData Paddleboat_Controller_Mapping_Data 要素の配列へのポインタ。

destRemapTableEntryCount が再マッピング エントリの合計数よりも少ない場合、destRemapTableEntryCount で指定されたエントリ数のみが mappingData にコピーされます。

再マップデータの追加または置換

Paddleboat_addControllerRemapData 関数を使用して、再マップエントリの追加、または現在の再マップ データベースの置き換えを行います。

void Paddleboat_addControllerRemapData(
   const Paddleboat_Remap_Addition_Mode addMode,
   const int32_t remapTableEntryCount,
   const Paddleboat_Controller_Mapping_Data* mappingData)
パラメータ 説明
addMode この操作に使用される追加ルール。有効な値は PADDLEBOAT_REMAP_ADD_MODE_DEFAULTPADDLEBOAT_REMAP_ADD_MODE_REPLACE_ALL です。
remapTableEntryCount mappingData パラメータで渡された Paddleboat_Controller_Mapping_Data 要素の配列サイズ。
mappingData Paddleboat_Controller_Mapping_Data 要素の配列へのポインタ。

追加モード

addModePADDLEBOAT_REMAP_ADD_MODE_REPLACE_ALL が指定されている場合、既存のデータベースは削除され、新しい配列の内容に置き換えられます。

addModePADDLEBOAT_REMAP_ADD_MODE_DEFAULT が指定されている場合、mappingData で渡された配列の各要素に次の条件が適用されます。

  • Paddleboat_getControllerRemapTableData が固有のものである場合(つまり、vendorIdproductId が存在しないか、存在していても minApi または maxApi の範囲が重なっていない場合)、エントリが内部データベースに追加されます。
  • Paddleboat_getControllerRemapTableData が固有のものでない場合(vendorIdproductId が存在し、minApi または maxApi が重なっている場合)、内部データベース内の既存のエントリを置き換えます

Paddleboat_Controller_Mapping_Data 構造体は以下のとおりです。

typedef struct Paddleboat_Controller_Mapping_Data {
    int16_t minimumEffectiveApiLevel; /** Min. API level for this entry */
    int16_t maximumEffectiveApiLevel; /** Max. API level, 0 = no max */
    int32_t vendorId; /** VendorID of the controller device for this entry */
    int32_t productId; /** ProductID of the controller device for this entry */
    int32_t flags; /** Flag bits, will be ORed with
                     * Paddleboat_Controller_Info.controllerFlags */

    /** AMOTION_EVENT_AXIS value for the corresponding Paddleboat control axis,
     *  or PADDLEBOAT_AXIS_IGNORED if unsupported. */
    uint16_t axisMapping[PADDLEBOAT_MAPPING_AXIS_COUNT];
    /** Button to set on positive or negative axis value,
     *  PADDLEBOAT_AXIS_BUTTON_IGNORED if none. */
    uint8_t axisPositiveButtonMapping[PADDLEBOAT_MAPPING_AXIS_COUNT];
    uint8_t axisNegativeButtonMapping[PADDLEBOAT_MAPPING_AXIS_COUNT];
    /** AKEYCODE_ value corresponding with the corresponding Paddleboat button.
     *  PADDLEBOAT_BUTTON_IGNORED if unsupported. */
    uint16_t buttonMapping[PADDLEBOAT_BUTTON_COUNT];
} Paddleboat_Controller_Mapping_Data;

マッピングの例

以下に、Google Stadia コントローラを表す Paddleboat_Controller_Mapping_Data を示します。

#define PADDLEBOAT_AXIS_BUTTON_DPAD_UP 0
#define PADDLEBOAT_AXIS_BUTTON_DPAD_LEFT 1
#define PADDLEBOAT_AXIS_BUTTON_DPAD_DOWN 2
#define PADDLEBOAT_AXIS_BUTTON_DPAD_RIGHT 3
#define PADDLEBOAT_AXIS_BUTTON_L2 9
#define PADDLEBOAT_AXIS_BUTTON_R2 12

static const Paddleboat_Controller_Mapping_Data stadia_controller_map[] = {
    16, 0, 0x18d1, 0x9400, PADDLEBOAT_CONTROLLER_LAYOUT_STANDARD,
    {
        /* LX */ AMOTION_EVENT_AXIS_X,
        /* LY */ AMOTION_EVENT_AXIS_Y,
        /* RX */ AMOTION_EVENT_AXIS_Z,
        /* RY */ AMOTION_EVENT_AXIS_RZ,
        /* L1 */ PADDLEBOAT_AXIS_IGNORED,
        /* L2 */ AMOTION_EVENT_AXIS_BRAKE,
        /* R1 */ PADDLEBOAT_AXIS_IGNORED,
        /* R2 */ AMOTION_EVENT_AXIS_GAS,
        /* HX */ AMOTION_EVENT_AXIS_HAT_X,
        /* HY */ AMOTION_EVENT_AXIS_HAT_Y,
    },
    {
        /* LX */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* LY */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* RX */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* RY */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* L1 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* L2 */ PADDLEBOAT_AXIS_BUTTON_L2,
        /* R1 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* R2 */ PADDLEBOAT_AXIS_BUTTON_R2,
        /* HX */ PADDLEBOAT_AXIS_BUTTON_DPAD_RIGHT,
        /* HY */ PADDLEBOAT_AXIS_BUTTON_DPAD_DOWN,
    },
    {
        /* LX */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* LY */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* RX */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* RY */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* L1 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* L2 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* R1 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* R2 */ PADDLEBOAT_AXIS_BUTTON_IGNORED,
        /* HX */ PADDLEBOAT_AXIS_BUTTON_DPAD_LEFT,
        /* HY */ PADDLEBOAT_AXIS_BUTTON_DPAD_UP,
    },
    {
        /* UP     */ AKEYCODE_DPAD_UP,
        /* LEFT   */ AKEYCODE_DPAD_LEFT,
        /* DOWN   */ AKEYCODE_DPAD_DOWN,
        /* RIGHT  */ AKEYCODE_DPAD_RIGHT,
        /* A      */ AKEYCODE_BUTTON_A,
        /* B      */ AKEYCODE_BUTTON_B,
        /* X      */ AKEYCODE_BUTTON_X,
        /* Y      */ AKEYCODE_BUTTON_Y,
        /* L1     */ AKEYCODE_BUTTON_L1,
        /* L2     */ AKEYCODE_BUTTON_L2,
        /* L3     */ AKEYCODE_BUTTON_THUMBL,
        /* R1     */ AKEYCODE_BUTTON_R1,
        /* R2     */ AKEYCODE_BUTTON_R2,
        /* R3     */ AKEYCODE_BUTTON_THUMBR,
        /* SELECT */ AKEYCODE_BUTTON_SELECT,
        /* START  */ AKEYCODE_BUTTON_START,
        /* SYSTEM */ AKEYCODE_BUTTON_MODE,
        /* TOUCHP */ PADDLEBOAT_BUTTON_IGNORED,
        /* AUX1   */ PADDLEBOAT_BUTTON_IGNORED,
        /* AUX2   */ PADDLEBOAT_BUTTON_IGNORED,
        /* AUX3   */ PADDLEBOAT_BUTTON_IGNORED,
        /* AUX4   */ PADDLEBOAT_BUTTON_IGNORED
    }
};