我使用 hidapi lib 做了一些实验来读取控制器/操纵杆数据。目前我在使用 PS4 控制器时遇到问题(使用其他设备也可能出现问题)。
在 Windows 上(我想在 Linux 上也是如此),您可以通过 USB 和蓝牙连接控制器。当使用 hid api lib 枚举设备时,它会检测控制器两次,一次在 USB 总线上,第二次在 BT 总线上。问题是没有办法找出哪个 BT 设备和 USB 设备属于对方。
有人有想法吗?
编辑:
第一个控制器
BT:
path "\\\\?\\HID#{00001124-0000-1000-8000-00805f9b34fb}_VID&0002054c_PID&09cc#8&12e42c53&4&0000#{4d1e55b2-f16f-11cf-88cb-001111000030}"
vendor_id 1356
product_id 2508
serial_number "dc0c2d6f3597"
release_number 0
manufacturer_string "Sony Interactive Entertainment"
product_string "Wireless Controller"
usage_page 1
usage 5
interface_number -1
bus_type HID_API_BUS_BLUETOOTH
USB:
path "\\\\?\\HID#VID_054C&PID_09CC&MI_03#9&2a666ca3&0&0000#{4d1e55b2-f16f-11cf-88cb-001111000030}"
vendor_id 1356
product_id 2508
serial_number ""
release_number 256
manufacturer_string "Sony Interactive Entertainment"
product_string "Wireless Controller"
usage_page 1
usage 5
interface_number 3
bus_type HID_API_BUS_USB
第二个控制器
BT:
path "\\\\?\\HID#{00001124-0000-1000-8000-00805f9b34fb}_VID&0002054c_PID&09cc#8&2e3024ab&1&0000#{4d1e55b2-f16f-11cf-88cb-001111000030}"
vendor_id 1356
product_id 2508
serial_number "dc0c2d6be031"
release_number 0
manufacturer_string "Sony Interactive Entertainment"
product_string "Wireless Controller"
usage_page 1
usage 5
interface_number -1
bus_type HID_API_BUS_BLUETOOTH
USB:
path "\\\\?\\HID#VID_054C&PID_09CC&MI_03#a&150a354e&0&0000#{4d1e55b2-f16f-11cf-88cb-001111000030}"
vendor_id 1356
product_id 2508
serial_number ""
release_number 256
manufacturer_string "Sony Interactive Entertainment"
product_string "Wireless Controller"
usage_page 1
usage 5
interface_number 3
bus_type HID_API_BUS_USB
我找到了解决方案。
有一个唯一的三重供应商 ID、产品 ID 和序列号。如果是同一设备,则具有相同的 id。蓝牙似乎每次都会发送一个序列号(至少对于我测试的所有其他控制器),而 USB 很少设置。对于 DualShock 4,有一份报告可获取类似于序列号的 MAC 地址
struct ReportFeatureInMacAll {
uint8_t ReportID = 0x12; // (0x09 for BT)
uint8_t ClientMac[6];
uint8_t Hard08;
uint8_t Hard25;
uint8_t Hard00;
uint8_t HostMac[6];
}
auto dev = hid_open_path(hidDeviceInfo->path);
ReportFeatureInMacAll report;
hid_get_feature_report(dev, (uint8_t *)&report, sizeof(report));
hid_close(dev);
现在我能够区分它们了。