Microsoft DirectX 8.0 (C++)

データ出力

ヒューマン インターフェイス デバイスは、入力の生成と同様に出力を認知することができる。IDirectInputDevice8::SendDeviceData メソッドは、データのパケットをそれらのデバイスに送る。

SendDeviceData は、反対に IDirectInputDevice8::GetDeviceData として表示することができる。SendDeviceData メソッドと同様、GetDeviceData メソッドは、データの基本単位として DIDEVICEOBJECTDATA 構造体を使用する。この場合、dwOfs メンバに含まれるのは、デバイスのデータ形式のオフセットではなく、データに関連付けられたデバイス オブジェクトのインスタンス ID である(オフセット識別子は、選択されたデータ形式での入力を提供するデバイス オブジェクトのためだけに存在するので、出力しか認めないオブジェクトは、オフセットを持つことすらない)。dwData メンバには、そのオブジェクトに適したデータが含まれる。dwTimeStamp および dwSequence メンバは使用しない。これらのメンバは、ゼロに設定しなければならない。

デバイスにデータを送るには、最初に DIDEVICEOBJECTDATA 構造体の配列を設定し、要求された数の要素をデータで埋めてから、使用されるアドレスと要素数を SendDeviceData に渡す。異なるデバイス オブジェクトのデータは、デバイスに送られる単一パケットに結合される。

データ パケットの形式は、パケット内の使用されないフィールドの処理方法と同じで、デバイスによって異なる。デバイスによっては、フィールドをオプションとして扱う。つまり、データが提供されない場合、オブジェクトの状態は前と同じである。一般的には、特にデータがフィールドに提供されない場合であっても、すべてのフィールドは重要である。たとえば、単一のキーボード LED にデータを送ると、ほかの 2 つの LED のデータはゼロで、それらの LED はオフであると仮定される。ただし、DISDD_CONTINUE フラグを使用してこの動作を無効にすることができる。この場合は、ほかの 2 つの LED のデータは、最後に送信した値となる。

デバイス オブジェクトの型の識別子は、HID 使用ページと使用コードを IDirectInputDevice8::GetObjectInfo に渡した後で DIDEVICEOBJECTINSTANCE 構造体 の dwType メンバから取得する。たとえば Scroll Lock LED の型識別子は、以下のコードを使って取得する。このコードで、pdev はキーボードを表す IDirectInputDevice8 インターフェイス ポインタである。

DIDEVICEOBJECTINSTANCE didoi;
DWORD NumLockID;
 
HRESULT hr = pdev->GetObjectInfo(&didoi, 
        DIMAKEUSAGEDWORD(0x07,0x53), DIPH_BYUSAGE);
NumLockID = didoi.dwType;
 

次の例では、コードが繰り返し実行される場合、キーボード上の LED は繰り返し点滅する。LED の状態は、データ バイトの上位ビットにより決定されるものとする。DWORDNumLockIDCapsLockID、および ScrollLockID は、すべてこの方法で取得する。

#define ARRAYSIZE 4
void FlashLEDs(void)
    {
    static int         rgiBits[] = { 1, 2, 4, 2 };
    static int         iLooper = 0; 
    DWORD              cdod = 3;                  // 項目数。
    DIDEVICEOBJECTDATA rgdod[ARRAYSIZE-1];
    HRESULT            hres;
 
    // dwTimeStamp および dwSequence を消去する必要がある。
    ZeroMemory(rgdod, sizeof(rgdod));
 
    rgdod[0].dwOfs = NumLockID; 
    rgdod[1].dwOfs = CapsLockID; 
    rgdod[2].dwOfs = ScrollLockID;
 
    rgdod[0].dwData = (rgiBits[iLooper] & 1) ? 0x80 : 0; 
                                           // NumLock ライトのオン/オフ
    rgdod[1].dwData = (rgiBits[iLooper] & 2) ? 0x80 : 0; 
                                           // CapsLock ライトのオン/オフ
    rgdod[2].dwData = (rgiBits[iLooper] & 4) ? 0x80 : 0; 
                                           // ScrollLock ライトのオン/オフ
 
    iLooper = (iLooper + 1) % ARRAYSIZE; // 0 から 3 までループする。
 
    hres = pdev->SendDeviceData(sizeof(DIDEVICEOBJECTDATA), 
            rgdod, &cdod, 0);
    }