スポンサーサイト

--.--.--.--.--:--
上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

Windows8.1でJoystickの状態を取得する 2

2013.09.12.Thu.01:19
久しぶりに余裕ができたので、すごい広島第17回に行ってきました。

(あれ、この書き出し、前回もやったぞ…)

さて、今回もJoystickの状態を取得する方法の調査です。
前回はボタンの現在の押下状態などをバイト列から推定しましたが、ボタンの数などが分かっていないと、いろいろなコントローラに対応できません。できれば、何もわからない状態からボタンの数などを取得したいので、その方法について調べました。

□ レポートディスクリプタを取得する


デバイスのボタンの数などを取得する方法ですが、HIDデバイスではレポートディスクリプタによってデバイスが持っている機能を表しているそうなので、このレポートディスクリプタを取得する方法を探してみます。

まず、HID APIを眺めてみます。
HidDeviceクラスを見てみると、GetBooleanControlDescriptions関数とGetNumericControlDescriptions関数があります。名前から考えるとこのあたりが怪しいです。


□ GetNumericControlDescriptionsで方向キーの対応を確認する


前回の調査で、方向キーはX軸とY軸がそれぞれ0~255であらわされていることが確認できました。これはNumericControlだと思われるので、GetNumericControlDescriptionsで取得できるはずです。
GetNumericControlDescriptions関数の引数を見てみると、

GetNumericControlDescriptions(
HidReportType reportType,
ushort usagePage,
ushort usageId
)


となっています。

reportTypeはInputReportで間違いないでしょう。
問題はusagePageとusageIdです。JoystickのUsagePage(0x01),UsageId(0x04)を指定してみましたが、nullが返ってきます。HID Usage Tablesを確認してみると、"Table 6:Generic Desktop Page"の表の中にX,Y,Zの文字があります。あやしいです。


var numericControl = device.GetNumericControlDescriptions(
HidReportType.InputReport,
0x01,
0x30);


こんな感じで取得すると、numericControl.LogicalMaximumが255とか、それらしい値が取得できます。

ただ、あくまでUsageIdを指定して取得することしかできないため、どの軸に対応しているかは取得してみてnullじゃなかったら…みたいな処理になると思われます。つまり、ある程度、対象デバイスについて知っておく必要があります。
まぁ、デバイスの列挙時にUsagePageとUsageIdでJoystickに制限していますので、大して問題ないでしょう。

□ GetBooleanControlDescriptionsでボタンが何個ついているか確認する


ここにたどり着くのに少し時間がかかりました。
ボタンが何個ついているかは、GetBooleanControlDescriptions関数で調べられそうです。

関数の引数は先ほどと同様です。
問題はまたもusagePageとusageIdです。JoystickのUsageIdにはそれらしい値がありません。
先ほどのHID Usage Tablesをずーっと見ていくと、UsagePage(0x09)にButtonという項目があります。あやしいです。

UsageIdが0x01から順番にボタン番号となるようなので、10個ボタンのあるコントローラーなら、UsageIdが0x01~0x0AまでHidBooleanControlDescriptionが取得できるはずです。


□ まとめ


GetNumericControlDescriptions関数とGetBooleanControlDescriptions関数を使えば、コントローラーのボタン数などは推定できそうだということが分かりました。
次回は、コントローラーについているスティックとボタンの数を推定し、画面に表示できるよう実装します。
スポンサーサイト
コメント

管理者のみに表示
上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。