Skip to content

Latest commit

 

History

History
526 lines (454 loc) · 17 KB

SDL_hidapi_ps4.c

File metadata and controls

526 lines (454 loc) · 17 KB
 
1
2
/*
Simple DirectMedia Layer
Jan 17, 2020
Jan 17, 2020
3
Copyright (C) 1997-2020 Sam Lantinga <slouken@libsdl.org>
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
Aug 9, 2018
Aug 9, 2018
21
22
23
/* This driver supports both simplified reports and the extended input reports enabled by Steam.
Code and logic contributed by Valve Corporation under the SDL zlib license.
*/
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
#include "../../SDL_internal.h"
#ifdef SDL_JOYSTICK_HIDAPI
#include "SDL_hints.h"
#include "SDL_log.h"
#include "SDL_events.h"
#include "SDL_timer.h"
#include "SDL_joystick.h"
#include "SDL_gamecontroller.h"
#include "../SDL_sysjoystick.h"
#include "SDL_hidapijoystick_c.h"
#ifdef SDL_JOYSTICK_HIDAPI_PS4
#define SONY_USB_VID 0x054C
#define SONY_DS4_PID 0x05C4
#define SONY_DS4_DONGLE_PID 0x0BA0
#define SONY_DS4_SLIM_PID 0x09CC
Sep 5, 2018
Sep 5, 2018
45
46
#define RAZER_USB_VID 0x1532
#define RAZER_PANTHERA_PID 0X0401
Sep 5, 2018
Sep 5, 2018
47
#define RAZER_PANTHERA_EVO_PID 0x1008
Sep 5, 2018
Sep 5, 2018
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
#define USB_PACKET_LENGTH 64
typedef enum
{
k_EPS4ReportIdUsbState = 1,
k_EPS4ReportIdUsbEffects = 5,
k_EPS4ReportIdBluetoothState = 17,
k_EPS4ReportIdBluetoothEffects = 17,
k_EPS4ReportIdDisconnectMessage = 226,
} EPS4ReportId;
typedef enum
{
k_ePS4FeatureReportIdGyroCalibration_USB = 0x02,
k_ePS4FeatureReportIdGyroCalibration_BT = 0x05,
k_ePS4FeatureReportIdSerialNumber = 0x12,
} EPS4FeatureReportID;
typedef struct
{
Uint8 ucLeftJoystickX;
Uint8 ucLeftJoystickY;
Uint8 ucRightJoystickX;
Uint8 ucRightJoystickY;
Uint8 rgucButtonsHatAndCounter[ 3 ];
Uint8 ucTriggerLeft;
Uint8 ucTriggerRight;
Uint8 _rgucPad0[ 3 ];
Sint16 sGyroX;
Sint16 sGyroY;
Sint16 sGyroZ;
Sint16 sAccelX;
Sint16 sAccelY;
Sint16 sAccelZ;
Uint8 _rgucPad1[ 5 ];
Uint8 ucBatteryLevel;
Uint8 _rgucPad2[ 4 ];
Uint8 ucTrackpadCounter1;
Uint8 rgucTrackpadData1[ 3 ];
Uint8 ucTrackpadCounter2;
Uint8 rgucTrackpadData2[ 3 ];
} PS4StatePacket_t;
typedef struct
{
Uint8 ucRumbleRight;
Uint8 ucRumbleLeft;
Uint8 ucLedRed;
Uint8 ucLedGreen;
Uint8 ucLedBlue;
Uint8 ucLedDelayOn;
Uint8 ucLedDelayOff;
Uint8 _rgucPad0[ 8 ];
Uint8 ucVolumeLeft;
Uint8 ucVolumeRight;
Uint8 ucVolumeMic;
Uint8 ucVolumeSpeaker;
} DS4EffectsState_t;
typedef struct {
SDL_bool is_dongle;
SDL_bool is_bluetooth;
SDL_bool audio_supported;
Aug 30, 2018
Aug 30, 2018
112
SDL_bool rumble_supported;
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
Uint8 volume;
Uint32 last_volume_check;
Uint32 rumble_expiration;
PS4StatePacket_t last_state;
} SDL_DriverPS4_Context;
/* Public domain CRC implementation adapted from:
http://home.thep.lu.se/~bjorn/crc/crc32_simple.c
*/
static Uint32 crc32_for_byte(Uint32 r)
{
int i;
for(i = 0; i < 8; ++i) {
r = (r & 1? 0: (Uint32)0xEDB88320L) ^ r >> 1;
}
return r ^ (Uint32)0xFF000000L;
}
static Uint32 crc32(Uint32 crc, const void *data, int count)
{
int i;
for(i = 0; i < count; ++i) {
crc = crc32_for_byte((Uint8)crc ^ ((const Uint8*)data)[i]) ^ crc >> 8;
}
return crc;
}
static SDL_bool
Oct 22, 2019
Oct 22, 2019
142
HIDAPI_DriverPS4_IsSupportedDevice(Uint16 vendor_id, Uint16 product_id, Uint16 version, int interface_number, const char *name)
Nov 22, 2019
Nov 22, 2019
144
return (SDL_GetJoystickGameControllerType(vendor_id, product_id, name) == SDL_CONTROLLER_TYPE_PS4);
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
}
static const char *
HIDAPI_DriverPS4_GetDeviceName(Uint16 vendor_id, Uint16 product_id)
{
if (vendor_id == SONY_USB_VID) {
return "PS4 Controller";
}
return NULL;
}
static SDL_bool ReadFeatureReport(hid_device *dev, Uint8 report_id, Uint8 *data, size_t size)
{
Uint8 report[USB_PACKET_LENGTH + 1];
SDL_memset(report, 0, sizeof(report));
report[0] = report_id;
if (hid_get_feature_report(dev, report, sizeof(report)) < 0) {
return SDL_FALSE;
}
SDL_memcpy(data, report, SDL_min(size, sizeof(report)));
return SDL_TRUE;
}
static SDL_bool CheckUSBConnected(hid_device *dev)
{
int i;
Uint8 data[16];
/* This will fail if we're on Bluetooth */
if (ReadFeatureReport(dev, k_ePS4FeatureReportIdSerialNumber, data, sizeof(data))) {
for (i = 0; i < sizeof(data); ++i) {
if (data[i] != 0x00) {
return SDL_TRUE;
}
}
/* Maybe the dongle without a connected controller? */
}
return SDL_FALSE;
}
Sep 5, 2018
Sep 5, 2018
186
187
188
static SDL_bool HIDAPI_DriverPS4_CanRumble(Uint16 vendor_id, Uint16 product_id)
{
/* The Razer Panthera fight stick hangs when trying to rumble */
Sep 5, 2018
Sep 5, 2018
189
190
if (vendor_id == RAZER_USB_VID &&
(product_id == RAZER_PANTHERA_PID || product_id == RAZER_PANTHERA_EVO_PID)) {
Sep 5, 2018
Sep 5, 2018
191
192
193
194
195
return SDL_FALSE;
}
return SDL_TRUE;
}
Dec 19, 2019
Dec 19, 2019
196
197
198
199
200
201
static SDL_bool
HIDAPI_DriverPS4_InitDevice(SDL_HIDAPI_Device *device)
{
return HIDAPI_JoystickConnected(device, NULL);
}
Dec 21, 2019
Dec 21, 2019
202
203
204
205
206
207
208
209
210
211
212
static int
HIDAPI_DriverPS4_GetDevicePlayerIndex(SDL_HIDAPI_Device *device, SDL_JoystickID instance_id)
{
return -1;
}
static void
HIDAPI_DriverPS4_SetDevicePlayerIndex(SDL_HIDAPI_Device *device, SDL_JoystickID instance_id, int player_index)
{
}
Dec 19, 2019
Dec 19, 2019
213
static int HIDAPI_DriverPS4_RumbleJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joystick, Uint16 low_frequency_rumble, Uint16 high_frequency_rumble, Uint32 duration_ms);
Jun 19, 2019
Jun 19, 2019
214
Dec 19, 2019
Dec 19, 2019
216
HIDAPI_DriverPS4_OpenJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joystick)
217
218
219
220
221
222
223
224
{
SDL_DriverPS4_Context *ctx;
ctx = (SDL_DriverPS4_Context *)SDL_calloc(1, sizeof(*ctx));
if (!ctx) {
SDL_OutOfMemory();
return SDL_FALSE;
}
Dec 19, 2019
Dec 19, 2019
225
226
227
228
229
230
231
232
device->dev = hid_open_path(device->path, 0);
if (!device->dev) {
SDL_free(ctx);
SDL_SetError("Couldn't open %s", device->path);
return SDL_FALSE;
}
device->context = ctx;
233
234
/* Check for type of connection */
Dec 19, 2019
Dec 19, 2019
235
ctx->is_dongle = (device->vendor_id == SONY_USB_VID && device->product_id == SONY_DS4_DONGLE_PID);
236
237
if (ctx->is_dongle) {
ctx->is_bluetooth = SDL_FALSE;
Dec 19, 2019
Dec 19, 2019
238
239
} else if (device->vendor_id == SONY_USB_VID) {
ctx->is_bluetooth = !CheckUSBConnected(device->dev);
240
241
242
243
244
245
246
247
248
} else {
/* Third party controllers appear to all be wired */
ctx->is_bluetooth = SDL_FALSE;
}
#ifdef DEBUG_PS4
SDL_Log("PS4 dongle = %s, bluetooth = %s\n", ctx->is_dongle ? "TRUE" : "FALSE", ctx->is_bluetooth ? "TRUE" : "FALSE");
#endif
/* Check to see if audio is supported */
Dec 19, 2019
Dec 19, 2019
249
250
if (device->vendor_id == SONY_USB_VID &&
(device->product_id == SONY_DS4_SLIM_PID || device->product_id == SONY_DS4_DONGLE_PID )) {
251
252
253
ctx->audio_supported = SDL_TRUE;
}
Dec 19, 2019
Dec 19, 2019
254
if (HIDAPI_DriverPS4_CanRumble(device->vendor_id, device->product_id)) {
Sep 5, 2018
Sep 5, 2018
255
256
257
258
259
if (ctx->is_bluetooth) {
ctx->rumble_supported = SDL_GetHintBoolean(SDL_HINT_JOYSTICK_HIDAPI_PS4_RUMBLE, SDL_FALSE);
} else {
ctx->rumble_supported = SDL_TRUE;
}
Aug 30, 2018
Aug 30, 2018
260
261
}
262
/* Initialize LED and effect state */
Dec 19, 2019
Dec 19, 2019
263
HIDAPI_DriverPS4_RumbleJoystick(device, joystick, 0, 0, 0);
264
265
/* Initialize the joystick capabilities */
Jun 8, 2019
Jun 8, 2019
266
joystick->nbuttons = 16;
267
268
269
270
271
272
273
joystick->naxes = SDL_CONTROLLER_AXIS_MAX;
joystick->epowerlevel = SDL_JOYSTICK_POWER_WIRED;
return SDL_TRUE;
}
static int
Dec 19, 2019
Dec 19, 2019
274
HIDAPI_DriverPS4_RumbleJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joystick, Uint16 low_frequency_rumble, Uint16 high_frequency_rumble, Uint32 duration_ms)
Dec 19, 2019
Dec 19, 2019
276
SDL_DriverPS4_Context *ctx = (SDL_DriverPS4_Context *)device->context;
277
278
279
280
DS4EffectsState_t *effects;
Uint8 data[78];
int report_size, offset;
Aug 30, 2018
Aug 30, 2018
281
282
283
284
if (!ctx->rumble_supported) {
return SDL_Unsupported();
}
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
/* In order to send rumble, we have to send a complete effect packet */
SDL_memset(data, 0, sizeof(data));
if (ctx->is_bluetooth) {
data[0] = k_EPS4ReportIdBluetoothEffects;
data[1] = 0xC0 | 0x04; /* Magic value HID + CRC, also sets interval to 4ms for samples */
data[3] = 0x03; /* 0x1 is rumble, 0x2 is lightbar, 0x4 is the blink interval */
report_size = 78;
offset = 6;
} else {
data[0] = k_EPS4ReportIdUsbEffects;
data[1] = 0x07; /* Magic value */
report_size = 32;
offset = 4;
}
effects = (DS4EffectsState_t *)&data[offset];
effects->ucRumbleLeft = (low_frequency_rumble >> 8);
effects->ucRumbleRight = (high_frequency_rumble >> 8);
effects->ucLedRed = 0;
effects->ucLedGreen = 0;
effects->ucLedBlue = 80;
if (ctx->is_bluetooth) {
/* Bluetooth reports need a CRC at the end of the packet (at least on Linux) */
Uint8 ubHdr = 0xA2; /* hidp header is part of the CRC calculation */
Uint32 unCRC;
unCRC = crc32(0, &ubHdr, 1);
unCRC = crc32(unCRC, data, (Uint32)(report_size - sizeof(unCRC)));
SDL_memcpy(&data[report_size - sizeof(unCRC)], &unCRC, sizeof(unCRC));
}
Dec 19, 2019
Dec 19, 2019
320
if (hid_write(device->dev, data, report_size) != report_size) {
321
322
323
324
return SDL_SetError("Couldn't send rumble packet");
}
if ((low_frequency_rumble || high_frequency_rumble) && duration_ms) {
Dec 16, 2019
Dec 16, 2019
325
ctx->rumble_expiration = SDL_GetTicks() + SDL_min(duration_ms, SDL_MAX_RUMBLE_DURATION_MS);
Dec 20, 2019
Dec 20, 2019
326
327
328
if (!ctx->rumble_expiration) {
ctx->rumble_expiration = 1;
}
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
} else {
ctx->rumble_expiration = 0;
}
return 0;
}
static void
HIDAPI_DriverPS4_HandleStatePacket(SDL_Joystick *joystick, hid_device *dev, SDL_DriverPS4_Context *ctx, PS4StatePacket_t *packet)
{
Sint16 axis;
if (ctx->last_state.rgucButtonsHatAndCounter[0] != packet->rgucButtonsHatAndCounter[0]) {
{
Uint8 data = (packet->rgucButtonsHatAndCounter[0] >> 4);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_X, (data & 0x01) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_A, (data & 0x02) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_B, (data & 0x04) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_Y, (data & 0x08) ? SDL_PRESSED : SDL_RELEASED);
}
{
Uint8 data = (packet->rgucButtonsHatAndCounter[0] & 0x0F);
SDL_bool dpad_up = SDL_FALSE;
SDL_bool dpad_down = SDL_FALSE;
SDL_bool dpad_left = SDL_FALSE;
SDL_bool dpad_right = SDL_FALSE;
switch (data) {
case 0:
dpad_up = SDL_TRUE;
break;
case 1:
dpad_up = SDL_TRUE;
dpad_right = SDL_TRUE;
break;
case 2:
dpad_right = SDL_TRUE;
break;
case 3:
dpad_right = SDL_TRUE;
dpad_down = SDL_TRUE;
break;
case 4:
dpad_down = SDL_TRUE;
break;
case 5:
dpad_left = SDL_TRUE;
dpad_down = SDL_TRUE;
break;
case 6:
dpad_left = SDL_TRUE;
break;
case 7:
dpad_up = SDL_TRUE;
dpad_left = SDL_TRUE;
break;
default:
break;
}
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_DPAD_DOWN, dpad_down);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_DPAD_UP, dpad_up);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_DPAD_RIGHT, dpad_right);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_DPAD_LEFT, dpad_left);
}
}
if (ctx->last_state.rgucButtonsHatAndCounter[1] != packet->rgucButtonsHatAndCounter[1]) {
Uint8 data = packet->rgucButtonsHatAndCounter[1];
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_LEFTSHOULDER, (data & 0x01) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER, (data & 0x02) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_BACK, (data & 0x10) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_START, (data & 0x20) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_LEFTSTICK, (data & 0x40) ? SDL_PRESSED : SDL_RELEASED);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_RIGHTSTICK, (data & 0x80) ? SDL_PRESSED : SDL_RELEASED);
}
if (ctx->last_state.rgucButtonsHatAndCounter[2] != packet->rgucButtonsHatAndCounter[2]) {
Uint8 data = (packet->rgucButtonsHatAndCounter[2] & 0x03);
SDL_PrivateJoystickButton(joystick, SDL_CONTROLLER_BUTTON_GUIDE, (data & 0x01) ? SDL_PRESSED : SDL_RELEASED);
Jun 8, 2019
Jun 8, 2019
410
SDL_PrivateJoystickButton(joystick, 15, (data & 0x02) ? SDL_PRESSED : SDL_RELEASED);
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
}
axis = ((int)packet->ucTriggerLeft * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_TRIGGERLEFT, axis);
axis = ((int)packet->ucTriggerRight * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_TRIGGERRIGHT, axis);
axis = ((int)packet->ucLeftJoystickX * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_LEFTX, axis);
axis = ((int)packet->ucLeftJoystickY * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_LEFTY, axis);
axis = ((int)packet->ucRightJoystickX * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_RIGHTX, axis);
axis = ((int)packet->ucRightJoystickY * 257) - 32768;
SDL_PrivateJoystickAxis(joystick, SDL_CONTROLLER_AXIS_RIGHTY, axis);
if (packet->ucBatteryLevel & 0x10) {
joystick->epowerlevel = SDL_JOYSTICK_POWER_WIRED;
} else {
/* Battery level ranges from 0 to 10 */
int level = (packet->ucBatteryLevel & 0xF);
if (level == 0) {
joystick->epowerlevel = SDL_JOYSTICK_POWER_EMPTY;
} else if (level <= 2) {
joystick->epowerlevel = SDL_JOYSTICK_POWER_LOW;
} else if (level <= 7) {
joystick->epowerlevel = SDL_JOYSTICK_POWER_MEDIUM;
} else {
joystick->epowerlevel = SDL_JOYSTICK_POWER_FULL;
}
}
SDL_memcpy(&ctx->last_state, packet, sizeof(ctx->last_state));
}
Aug 16, 2018
Aug 16, 2018
445
static SDL_bool
Dec 19, 2019
Dec 19, 2019
446
HIDAPI_DriverPS4_UpdateDevice(SDL_HIDAPI_Device *device)
Dec 19, 2019
Dec 19, 2019
448
449
SDL_DriverPS4_Context *ctx = (SDL_DriverPS4_Context *)device->context;
SDL_Joystick *joystick = NULL;
450
451
452
Uint8 data[USB_PACKET_LENGTH];
int size;
Dec 19, 2019
Dec 19, 2019
453
454
455
456
457
458
459
460
if (device->num_joysticks > 0) {
joystick = SDL_JoystickFromInstanceID(device->joysticks[0]);
}
if (!joystick) {
return SDL_FALSE;
}
while ((size = hid_read_timeout(device->dev, data, sizeof(data), 0)) > 0) {
461
462
switch (data[0]) {
case k_EPS4ReportIdUsbState:
Dec 19, 2019
Dec 19, 2019
463
HIDAPI_DriverPS4_HandleStatePacket(joystick, device->dev, ctx, (PS4StatePacket_t *)&data[1]);
464
465
466
break;
case k_EPS4ReportIdBluetoothState:
/* Bluetooth state packets have two additional bytes at the beginning */
Dec 19, 2019
Dec 19, 2019
467
HIDAPI_DriverPS4_HandleStatePacket(joystick, device->dev, ctx, (PS4StatePacket_t *)&data[3]);
468
469
470
471
472
473
474
475
476
477
478
479
break;
default:
#ifdef DEBUG_JOYSTICK
SDL_Log("Unknown PS4 packet: 0x%.2x\n", data[0]);
#endif
break;
}
}
if (ctx->rumble_expiration) {
Uint32 now = SDL_GetTicks();
if (SDL_TICKS_PASSED(now, ctx->rumble_expiration)) {
Dec 19, 2019
Dec 19, 2019
480
HIDAPI_DriverPS4_RumbleJoystick(device, joystick, 0, 0, 0);
Aug 16, 2018
Aug 16, 2018
483
Dec 19, 2019
Dec 19, 2019
484
485
486
487
if (size < 0) {
/* Read error, device is disconnected */
HIDAPI_JoystickDisconnected(device, joystick->instance_id);
}
Aug 30, 2018
Aug 30, 2018
488
return (size >= 0);
Jun 19, 2019
Jun 19, 2019
491
static void
Dec 19, 2019
Dec 19, 2019
492
493
494
495
496
497
498
499
500
501
502
HIDAPI_DriverPS4_CloseJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joystick)
{
hid_close(device->dev);
device->dev = NULL;
SDL_free(device->context);
device->context = NULL;
}
static void
HIDAPI_DriverPS4_FreeDevice(SDL_HIDAPI_Device *device)
Jun 19, 2019
Jun 19, 2019
503
504
505
{
}
506
507
508
509
510
511
SDL_HIDAPI_DeviceDriver SDL_HIDAPI_DriverPS4 =
{
SDL_HINT_JOYSTICK_HIDAPI_PS4,
SDL_TRUE,
HIDAPI_DriverPS4_IsSupportedDevice,
HIDAPI_DriverPS4_GetDeviceName,
Dec 19, 2019
Dec 19, 2019
512
HIDAPI_DriverPS4_InitDevice,
Dec 21, 2019
Dec 21, 2019
513
514
HIDAPI_DriverPS4_GetDevicePlayerIndex,
HIDAPI_DriverPS4_SetDevicePlayerIndex,
Dec 19, 2019
Dec 19, 2019
515
516
517
518
519
HIDAPI_DriverPS4_UpdateDevice,
HIDAPI_DriverPS4_OpenJoystick,
HIDAPI_DriverPS4_RumbleJoystick,
HIDAPI_DriverPS4_CloseJoystick,
HIDAPI_DriverPS4_FreeDevice
520
521
522
523
524
525
526
};
#endif /* SDL_JOYSTICK_HIDAPI_PS4 */
#endif /* SDL_JOYSTICK_HIDAPI */
/* vi: set ts=4 sw=4 expandtab: */