Gamepad feedback force (vibration) on windows using original input

I am currently writing a cross platform library in C that includes gamepad support. Gamepad communication in windows is handled by both raw input and xinput, depending on the specific gamepad.

While xinput simplifies feedback strength feedback on xbox360 controllers, I haven't found a way to do this using raw input. I have some gamepads that can give force feedback, but I can't seem to find a way to do this with raw input. Is there a way to do this?

I prefer not to use the directinput api as it is deprecated and not recommended by Microsoft.

Edit:

Since I've implemented gamepads for the most part, maybe I can narrow the question down a bit. I suspect the number of thunder motors in a gamepad can be found by reading the NumberOutputValueCaps of the HIDP_CAPS structure. This gives the correct result for all of my test gamepads.

I am using funtcion HidP_GetUsageValue to read axis values, which works great. Now I suspect that the call to HidP_SetUsageValue should allow me to change this output value by turning on the rumble motor. However, the call to this function fails. Should this function work with motors?

+3


source to share


1 answer


HidP_SetUsageValue () only modifies the report buffer - you need to first prepare a buffer of the appropriate size (this may be the reason for the function to fail, input reports and output reports will not necessarily be the same size) and then send it to the device before it has any Effect. MSDN suggests you use HidD_SetOutputReport () for this purpose, but I had some luck with WriteFile () following the sample code: https://code.msdn.microsoft.com/windowshardware/HClient-HID-Sample-4ec99697/sourcecode?fileId=51262&pathId = 340791466

This snippet (based on Linux driver) allows me to control motors and LEDs on a DualShock 4:



const char *path = /* from GetRawInputDeviceInfo(RIDI_DEVICENAME) */;
HANDLE hid_device = CreateFile(path, GENERIC_READ | GENERIC_WRITE,
                               FILE_SHARE_READ | FILE_SHARE_WRITE, NULL,
                               OPEN_EXISTING, 0, NULL);
assert(hid_device != INVALID_HANDLE_VALUE);
uint8_t buf[32];
memset(buf, 0, sizeof(buf));
buf[0] = 0x05;
buf[1] = 0xFF;
buf[4] = right_motor_strength;  // 0-255
buf[5] = left_motor_strength;   // 0-255
buf[6] = led_red_level;         // 0-255
buf[7] = led_green_level;       // 0-255
buf[8] = led_blue_level;        // 0-255
DWORD bytes_written;
assert(WriteFile(hid_device, buf, sizeof(buf), &bytes_written, NULL));
assert(bytes_written == 32);

      

(EDIT: fixed buffer offsets)

+5


source







All Articles