SDL  2.0
SDL_xinputjoystick.c
Go to the documentation of this file.
1 /*
2  Simple DirectMedia Layer
3  Copyright (C) 1997-2017 Sam Lantinga <slouken@libsdl.org>
4 
5  This software is provided 'as-is', without any express or implied
6  warranty. In no event will the authors be held liable for any damages
7  arising from the use of this software.
8 
9  Permission is granted to anyone to use this software for any purpose,
10  including commercial applications, and to alter it and redistribute it
11  freely, subject to the following restrictions:
12 
13  1. The origin of this software must not be misrepresented; you must not
14  claim that you wrote the original software. If you use this software
15  in a product, an acknowledgment in the product documentation would be
16  appreciated but is not required.
17  2. Altered source versions must be plainly marked as such, and must not be
18  misrepresented as being the original software.
19  3. This notice may not be removed or altered from any source distribution.
20 */
21 #include "../../SDL_internal.h"
22 
23 #include "../SDL_sysjoystick.h"
24 
25 #if SDL_JOYSTICK_XINPUT
26 
27 #include "SDL_assert.h"
28 #include "SDL_hints.h"
29 #include "SDL_windowsjoystick_c.h"
30 #include "SDL_xinputjoystick_c.h"
31 
32 /*
33  * Internal stuff.
34  */
35 static SDL_bool s_bXInputEnabled = SDL_TRUE;
36 static char *s_arrXInputDevicePath[XUSER_MAX_COUNT];
37 
38 
39 static SDL_bool
40 SDL_XInputUseOldJoystickMapping()
41 {
42 #ifdef __WINRT__
43  /* TODO: remove this __WINRT__ block, but only after integrating with UWP/WinRT's HID API */
44  return SDL_TRUE;
45 #else
46  static int s_XInputUseOldJoystickMapping = -1;
47  if (s_XInputUseOldJoystickMapping < 0) {
49  }
50  return (s_XInputUseOldJoystickMapping > 0);
51 #endif
52 }
53 
55 {
56  return s_bXInputEnabled;
57 }
58 
59 int
61 {
63 
64  if (s_bXInputEnabled && WIN_LoadXInputDLL() < 0) {
65  s_bXInputEnabled = SDL_FALSE; /* oh well. */
66  }
67  return 0;
68 }
69 
70 static char *
71 GetXInputName(const Uint8 userid, BYTE SubType)
72 {
73  char name[32];
74 
75  if (SDL_XInputUseOldJoystickMapping()) {
76  SDL_snprintf(name, sizeof(name), "X360 Controller #%u", 1 + userid);
77  } else {
78  switch (SubType) {
79  case XINPUT_DEVSUBTYPE_GAMEPAD:
80  SDL_snprintf(name, sizeof(name), "XInput Controller #%u", 1 + userid);
81  break;
82  case XINPUT_DEVSUBTYPE_WHEEL:
83  SDL_snprintf(name, sizeof(name), "XInput Wheel #%u", 1 + userid);
84  break;
85  case XINPUT_DEVSUBTYPE_ARCADE_STICK:
86  SDL_snprintf(name, sizeof(name), "XInput ArcadeStick #%u", 1 + userid);
87  break;
88  case XINPUT_DEVSUBTYPE_FLIGHT_STICK:
89  SDL_snprintf(name, sizeof(name), "XInput FlightStick #%u", 1 + userid);
90  break;
91  case XINPUT_DEVSUBTYPE_DANCE_PAD:
92  SDL_snprintf(name, sizeof(name), "XInput DancePad #%u", 1 + userid);
93  break;
94  case XINPUT_DEVSUBTYPE_GUITAR:
95  case XINPUT_DEVSUBTYPE_GUITAR_ALTERNATE:
96  case XINPUT_DEVSUBTYPE_GUITAR_BASS:
97  SDL_snprintf(name, sizeof(name), "XInput Guitar #%u", 1 + userid);
98  break;
99  case XINPUT_DEVSUBTYPE_DRUM_KIT:
100  SDL_snprintf(name, sizeof(name), "XInput DrumKit #%u", 1 + userid);
101  break;
102  case XINPUT_DEVSUBTYPE_ARCADE_PAD:
103  SDL_snprintf(name, sizeof(name), "XInput ArcadePad #%u", 1 + userid);
104  break;
105  default:
106  SDL_snprintf(name, sizeof(name), "XInput Device #%u", 1 + userid);
107  break;
108  }
109  }
110  return SDL_strdup(name);
111 }
112 
113 /* We can't really tell what device is being used for XInput, but we can guess
114  and we'll be correct for the case where only one device is connected.
115  */
116 static void
117 GuessXInputDevice(Uint8 userid, Uint16 *pVID, Uint16 *pPID, Uint16 *pVersion)
118 {
119 #ifndef __WINRT__ /* TODO: remove this ifndef __WINRT__ block, but only after integrating with UWP/WinRT's HID API */
120 
121  PRAWINPUTDEVICELIST devices = NULL;
122  UINT i, j, device_count = 0;
123 
124  if ((GetRawInputDeviceList(NULL, &device_count, sizeof(RAWINPUTDEVICELIST)) == -1) || (!device_count)) {
125  return; /* oh well. */
126  }
127 
128  devices = (PRAWINPUTDEVICELIST)SDL_malloc(sizeof(RAWINPUTDEVICELIST) * device_count);
129  if (devices == NULL) {
130  return;
131  }
132 
133  if (GetRawInputDeviceList(devices, &device_count, sizeof(RAWINPUTDEVICELIST)) == -1) {
134  SDL_free(devices);
135  return; /* oh well. */
136  }
137 
138  for (i = 0; i < device_count; i++) {
139  RID_DEVICE_INFO rdi;
140  char devName[128];
141  UINT rdiSize = sizeof(rdi);
142  UINT nameSize = SDL_arraysize(devName);
143 
144  rdi.cbSize = sizeof(rdi);
145  if ((devices[i].dwType == RIM_TYPEHID) &&
146  (GetRawInputDeviceInfoA(devices[i].hDevice, RIDI_DEVICEINFO, &rdi, &rdiSize) != ((UINT)-1)) &&
147  (GetRawInputDeviceInfoA(devices[i].hDevice, RIDI_DEVICENAME, devName, &nameSize) != ((UINT)-1)) &&
148  (SDL_strstr(devName, "IG_") != NULL)) {
149  SDL_bool found = SDL_FALSE;
150  for (j = 0; j < SDL_arraysize(s_arrXInputDevicePath); ++j) {
151  if (j == userid) {
152  continue;
153  }
154  if (!s_arrXInputDevicePath[j]) {
155  continue;
156  }
157  if (SDL_strcmp(devName, s_arrXInputDevicePath[j]) == 0) {
158  found = SDL_TRUE;
159  break;
160  }
161  }
162  if (found) {
163  /* We already have this device in our XInput device list */
164  continue;
165  }
166 
167  /* We don't actually know if this is the right device for this
168  * userid, but we'll record it so we'll at least be consistent
169  * when the raw device list changes.
170  */
171  *pVID = (Uint16)rdi.hid.dwVendorId;
172  *pPID = (Uint16)rdi.hid.dwProductId;
173  *pVersion = (Uint16)rdi.hid.dwVersionNumber;
174  if (s_arrXInputDevicePath[userid]) {
175  SDL_free(s_arrXInputDevicePath[userid]);
176  }
177  s_arrXInputDevicePath[userid] = SDL_strdup(devName);
178  break;
179  }
180  }
181  SDL_free(devices);
182 #endif /* ifndef __WINRT__ */
183 }
184 
185 static void
186 AddXInputDevice(Uint8 userid, BYTE SubType, JoyStick_DeviceData **pContext)
187 {
188  JoyStick_DeviceData *pPrevJoystick = NULL;
189  JoyStick_DeviceData *pNewJoystick = *pContext;
190 
191  if (SDL_XInputUseOldJoystickMapping() && SubType != XINPUT_DEVSUBTYPE_GAMEPAD)
192  return;
193 
194  if (SubType == XINPUT_DEVSUBTYPE_UNKNOWN)
195  return;
196 
197  while (pNewJoystick) {
198  if (pNewJoystick->bXInputDevice && (pNewJoystick->XInputUserId == userid) && (pNewJoystick->SubType == SubType)) {
199  /* if we are replacing the front of the list then update it */
200  if (pNewJoystick == *pContext) {
201  *pContext = pNewJoystick->pNext;
202  } else if (pPrevJoystick) {
203  pPrevJoystick->pNext = pNewJoystick->pNext;
204  }
205 
206  pNewJoystick->pNext = SYS_Joystick;
207  SYS_Joystick = pNewJoystick;
208  return; /* already in the list. */
209  }
210 
211  pPrevJoystick = pNewJoystick;
212  pNewJoystick = pNewJoystick->pNext;
213  }
214 
215  pNewJoystick = (JoyStick_DeviceData *)SDL_malloc(sizeof(JoyStick_DeviceData));
216  if (!pNewJoystick) {
217  return; /* better luck next time? */
218  }
219  SDL_zerop(pNewJoystick);
220 
221  pNewJoystick->joystickname = GetXInputName(userid, SubType);
222  if (!pNewJoystick->joystickname) {
223  SDL_free(pNewJoystick);
224  return; /* better luck next time? */
225  }
226 
227  pNewJoystick->bXInputDevice = SDL_TRUE;
228  if (SDL_XInputUseOldJoystickMapping()) {
229  SDL_zero(pNewJoystick->guid);
230  } else {
231  const Uint16 BUS_USB = 0x03;
232  Uint16 vendor = 0;
233  Uint16 product = 0;
234  Uint16 version = 0;
235  Uint16 *guid16 = (Uint16 *)pNewJoystick->guid.data;
236 
237  GuessXInputDevice(userid, &vendor, &product, &version);
238 
239  *guid16++ = SDL_SwapLE16(BUS_USB);
240  *guid16++ = 0;
241  *guid16++ = SDL_SwapLE16(vendor);
242  *guid16++ = 0;
243  *guid16++ = SDL_SwapLE16(product);
244  *guid16++ = 0;
245  *guid16++ = SDL_SwapLE16(version);
246  *guid16++ = 0;
247 
248  /* Note that this is an XInput device and what subtype it is */
249  pNewJoystick->guid.data[14] = 'x';
250  pNewJoystick->guid.data[15] = SubType;
251  }
252  pNewJoystick->SubType = SubType;
253  pNewJoystick->XInputUserId = userid;
254 
255  if (SDL_ShouldIgnoreGameController(pNewJoystick->joystickname, pNewJoystick->guid)) {
256  SDL_free(pNewJoystick);
257  return;
258  }
259 
260  SDL_SYS_AddJoystickDevice(pNewJoystick);
261 }
262 
263 void
265 {
266  int iuserid;
267 
268  if (!s_bXInputEnabled) {
269  return;
270  }
271 
272  /* iterate in reverse, so these are in the final list in ascending numeric order. */
273  for (iuserid = XUSER_MAX_COUNT - 1; iuserid >= 0; iuserid--) {
274  const Uint8 userid = (Uint8)iuserid;
275  XINPUT_CAPABILITIES capabilities;
276  if (XINPUTGETCAPABILITIES(userid, XINPUT_FLAG_GAMEPAD, &capabilities) == ERROR_SUCCESS) {
277  AddXInputDevice(userid, capabilities.SubType, pContext);
278  }
279  }
280 }
281 
282 int
283 SDL_XINPUT_JoystickOpen(SDL_Joystick * joystick, JoyStick_DeviceData *joystickdevice)
284 {
285  const Uint8 userId = joystickdevice->XInputUserId;
286  XINPUT_CAPABILITIES capabilities;
287  XINPUT_VIBRATION state;
288 
289  SDL_assert(s_bXInputEnabled);
290  SDL_assert(XINPUTGETCAPABILITIES);
291  SDL_assert(XINPUTSETSTATE);
292  SDL_assert(userId < XUSER_MAX_COUNT);
293 
294  joystick->hwdata->bXInputDevice = SDL_TRUE;
295 
296  if (XINPUTGETCAPABILITIES(userId, XINPUT_FLAG_GAMEPAD, &capabilities) != ERROR_SUCCESS) {
297  SDL_free(joystick->hwdata);
298  joystick->hwdata = NULL;
299  return SDL_SetError("Failed to obtain XInput device capabilities. Device disconnected?");
300  }
301  SDL_zero(state);
302  joystick->hwdata->bXInputHaptic = (XINPUTSETSTATE(userId, &state) == ERROR_SUCCESS);
303  joystick->hwdata->userid = userId;
304 
305  /* The XInput API has a hard coded button/axis mapping, so we just match it */
306  if (SDL_XInputUseOldJoystickMapping()) {
307  joystick->naxes = 6;
308  joystick->nbuttons = 15;
309  } else {
310  joystick->naxes = 6;
311  joystick->nbuttons = 11;
312  joystick->nhats = 1;
313  }
314  return 0;
315 }
316 
317 static void
318 UpdateXInputJoystickBatteryInformation(SDL_Joystick * joystick, XINPUT_BATTERY_INFORMATION_EX *pBatteryInformation)
319 {
320  if (pBatteryInformation->BatteryType != BATTERY_TYPE_UNKNOWN) {
322  if (pBatteryInformation->BatteryType == BATTERY_TYPE_WIRED) {
323  ePowerLevel = SDL_JOYSTICK_POWER_WIRED;
324  } else {
325  switch (pBatteryInformation->BatteryLevel) {
326  case BATTERY_LEVEL_EMPTY:
327  ePowerLevel = SDL_JOYSTICK_POWER_EMPTY;
328  break;
329  case BATTERY_LEVEL_LOW:
330  ePowerLevel = SDL_JOYSTICK_POWER_LOW;
331  break;
332  case BATTERY_LEVEL_MEDIUM:
333  ePowerLevel = SDL_JOYSTICK_POWER_MEDIUM;
334  break;
335  default:
336  case BATTERY_LEVEL_FULL:
337  ePowerLevel = SDL_JOYSTICK_POWER_FULL;
338  break;
339  }
340  }
341 
342  SDL_PrivateJoystickBatteryLevel(joystick, ePowerLevel);
343  }
344 }
345 
346 static void
347 UpdateXInputJoystickState_OLD(SDL_Joystick * joystick, XINPUT_STATE_EX *pXInputState, XINPUT_BATTERY_INFORMATION_EX *pBatteryInformation)
348 {
349  static WORD s_XInputButtons[] = {
350  XINPUT_GAMEPAD_DPAD_UP, XINPUT_GAMEPAD_DPAD_DOWN, XINPUT_GAMEPAD_DPAD_LEFT, XINPUT_GAMEPAD_DPAD_RIGHT,
351  XINPUT_GAMEPAD_START, XINPUT_GAMEPAD_BACK, XINPUT_GAMEPAD_LEFT_THUMB, XINPUT_GAMEPAD_RIGHT_THUMB,
352  XINPUT_GAMEPAD_LEFT_SHOULDER, XINPUT_GAMEPAD_RIGHT_SHOULDER,
353  XINPUT_GAMEPAD_A, XINPUT_GAMEPAD_B, XINPUT_GAMEPAD_X, XINPUT_GAMEPAD_Y,
354  XINPUT_GAMEPAD_GUIDE
355  };
356  WORD wButtons = pXInputState->Gamepad.wButtons;
357  Uint8 button;
358 
359  SDL_PrivateJoystickAxis(joystick, 0, (Sint16)pXInputState->Gamepad.sThumbLX);
360  SDL_PrivateJoystickAxis(joystick, 1, (Sint16)(-SDL_max(-32767, pXInputState->Gamepad.sThumbLY)));
361  SDL_PrivateJoystickAxis(joystick, 2, (Sint16)pXInputState->Gamepad.sThumbRX);
362  SDL_PrivateJoystickAxis(joystick, 3, (Sint16)(-SDL_max(-32767, pXInputState->Gamepad.sThumbRY)));
363  SDL_PrivateJoystickAxis(joystick, 4, (Sint16)(((int)pXInputState->Gamepad.bLeftTrigger * 65535 / 255) - 32768));
364  SDL_PrivateJoystickAxis(joystick, 5, (Sint16)(((int)pXInputState->Gamepad.bRightTrigger * 65535 / 255) - 32768));
365 
366  for (button = 0; button < SDL_arraysize(s_XInputButtons); ++button) {
367  SDL_PrivateJoystickButton(joystick, button, (wButtons & s_XInputButtons[button]) ? SDL_PRESSED : SDL_RELEASED);
368  }
369 
370  UpdateXInputJoystickBatteryInformation(joystick, pBatteryInformation);
371 }
372 
373 static void
374 UpdateXInputJoystickState(SDL_Joystick * joystick, XINPUT_STATE_EX *pXInputState, XINPUT_BATTERY_INFORMATION_EX *pBatteryInformation)
375 {
376  static WORD s_XInputButtons[] = {
377  XINPUT_GAMEPAD_A, XINPUT_GAMEPAD_B, XINPUT_GAMEPAD_X, XINPUT_GAMEPAD_Y,
378  XINPUT_GAMEPAD_LEFT_SHOULDER, XINPUT_GAMEPAD_RIGHT_SHOULDER, XINPUT_GAMEPAD_BACK, XINPUT_GAMEPAD_START,
379  XINPUT_GAMEPAD_LEFT_THUMB, XINPUT_GAMEPAD_RIGHT_THUMB,
380  XINPUT_GAMEPAD_GUIDE
381  };
382  WORD wButtons = pXInputState->Gamepad.wButtons;
383  Uint8 button;
384  Uint8 hat = SDL_HAT_CENTERED;
385 
386  SDL_PrivateJoystickAxis(joystick, 0, (Sint16)pXInputState->Gamepad.sThumbLX);
387  SDL_PrivateJoystickAxis(joystick, 1, (Sint16)(-SDL_max(-32767, pXInputState->Gamepad.sThumbLY)));
388  SDL_PrivateJoystickAxis(joystick, 2, (Sint16)(((int)pXInputState->Gamepad.bLeftTrigger * 65535 / 255) - 32768));
389  SDL_PrivateJoystickAxis(joystick, 3, (Sint16)pXInputState->Gamepad.sThumbRX);
390  SDL_PrivateJoystickAxis(joystick, 4, (Sint16)(-SDL_max(-32767, pXInputState->Gamepad.sThumbRY)));
391  SDL_PrivateJoystickAxis(joystick, 5, (Sint16)(((int)pXInputState->Gamepad.bRightTrigger * 65535 / 255) - 32768));
392 
393  for (button = 0; button < SDL_arraysize(s_XInputButtons); ++button) {
394  SDL_PrivateJoystickButton(joystick, button, (wButtons & s_XInputButtons[button]) ? SDL_PRESSED : SDL_RELEASED);
395  }
396 
397  if (wButtons & XINPUT_GAMEPAD_DPAD_UP) {
398  hat |= SDL_HAT_UP;
399  }
400  if (wButtons & XINPUT_GAMEPAD_DPAD_DOWN) {
401  hat |= SDL_HAT_DOWN;
402  }
403  if (wButtons & XINPUT_GAMEPAD_DPAD_LEFT) {
404  hat |= SDL_HAT_LEFT;
405  }
406  if (wButtons & XINPUT_GAMEPAD_DPAD_RIGHT) {
407  hat |= SDL_HAT_RIGHT;
408  }
409  SDL_PrivateJoystickHat(joystick, 0, hat);
410 
411  UpdateXInputJoystickBatteryInformation(joystick, pBatteryInformation);
412 }
413 
414 void
415 SDL_XINPUT_JoystickUpdate(SDL_Joystick * joystick)
416 {
417  HRESULT result;
418  XINPUT_STATE_EX XInputState;
419  XINPUT_BATTERY_INFORMATION_EX XBatteryInformation;
420 
421  if (!XINPUTGETSTATE)
422  return;
423 
424  result = XINPUTGETSTATE(joystick->hwdata->userid, &XInputState);
425  if (result == ERROR_DEVICE_NOT_CONNECTED) {
426  Uint8 userid = joystick->hwdata->userid;
427 
428  joystick->hwdata->send_remove_event = SDL_TRUE;
429  joystick->hwdata->removed = SDL_TRUE;
430  if (s_arrXInputDevicePath[userid]) {
431  SDL_free(s_arrXInputDevicePath[userid]);
432  s_arrXInputDevicePath[userid] = NULL;
433  }
434  return;
435  }
436 
437  SDL_zero(XBatteryInformation);
438  if (XINPUTGETBATTERYINFORMATION) {
439  result = XINPUTGETBATTERYINFORMATION(joystick->hwdata->userid, BATTERY_DEVTYPE_GAMEPAD, &XBatteryInformation);
440  }
441 
442  /* only fire events if the data changed from last time */
443  if (XInputState.dwPacketNumber && XInputState.dwPacketNumber != joystick->hwdata->dwPacketNumber) {
444  if (SDL_XInputUseOldJoystickMapping()) {
445  UpdateXInputJoystickState_OLD(joystick, &XInputState, &XBatteryInformation);
446  } else {
447  UpdateXInputJoystickState(joystick, &XInputState, &XBatteryInformation);
448  }
449  joystick->hwdata->dwPacketNumber = XInputState.dwPacketNumber;
450  }
451 }
452 
453 void
454 SDL_XINPUT_JoystickClose(SDL_Joystick * joystick)
455 {
456 }
457 
458 void
460 {
461  if (s_bXInputEnabled) {
462  WIN_UnloadXInputDLL();
463  }
464 }
465 
466 SDL_bool
467 SDL_SYS_IsXInputGamepad_DeviceIndex(int device_index)
468 {
470  int index;
471 
472  for (index = device_index; index > 0; index--)
473  device = device->pNext;
474 
475  return device->bXInputDevice;
476 }
477 
478 #else /* !SDL_JOYSTICK_XINPUT */
479 
481 
483 {
484  return SDL_FALSE;
485 }
486 
487 int
489 {
490  return 0;
491 }
492 
493 void
495 {
496 }
497 
498 int
499 SDL_XINPUT_JoystickOpen(SDL_Joystick * joystick, JoyStick_DeviceData *joystickdevice)
500 {
501  return SDL_Unsupported();
502 }
503 
504 void
505 SDL_XINPUT_JoystickUpdate(SDL_Joystick * joystick)
506 {
507 }
508 
509 void
510 SDL_XINPUT_JoystickClose(SDL_Joystick * joystick)
511 {
512 }
513 
514 void
516 {
517 }
518 
519 #endif /* SDL_JOYSTICK_XINPUT */
520 
521 /* vi: set ts=4 sw=4 expandtab: */
JoyStick_DeviceData * SYS_Joystick
SDL_Texture * button
GLuint64EXT * result
int SDL_PrivateJoystickHat(SDL_Joystick *joystick, Uint8 hat, Uint8 value)
Definition: SDL_joystick.c:712
struct JoyStick_DeviceData * pNext
void SDL_SYS_AddJoystickDevice(JoyStick_DeviceData *device)
struct xkb_state * state
int SDL_PrivateJoystickButton(SDL_Joystick *joystick, Uint8 button, Uint8 state)
Definition: SDL_joystick.c:788
int SDL_XINPUT_JoystickOpen(SDL_Joystick *joystick, JoyStick_DeviceData *joystickdevice)
Uint8 data[16]
Definition: SDL_joystick.h:71
#define SDL_zerop(x)
Definition: SDL_stdinc.h:417
void SDL_XINPUT_JoystickClose(SDL_Joystick *joystick)
#define SDL_max(x, y)
Definition: SDL_stdinc.h:407
int SDL_PrivateJoystickAxis(SDL_Joystick *joystick, Uint8 axis, Sint16 value)
Definition: SDL_joystick.c:655
GLuint const GLchar * name
#define SDL_GetHintBoolean
#define SDL_HINT_XINPUT_ENABLED
A variable that lets you disable the detection and use of Xinput gamepad devices. ...
Definition: SDL_hints.h:375
static SDL_AudioDeviceID device
Definition: loopwave.c:37
#define SDL_HAT_RIGHT
Definition: SDL_joystick.h:318
#define SDL_HAT_LEFT
Definition: SDL_joystick.h:320
uint8_t Uint8
Definition: SDL_stdinc.h:157
#define SDL_free
return Display return Display Bool Bool int int int return Display XEvent Bool(*) XPointer return Display return Display Drawable _Xconst char unsigned int unsigned int return Display Pixmap Pixmap XColor XColor unsigned int unsigned int return Display _Xconst char char int char return Display Visual unsigned int int int char unsigned int unsigned int int in j)
Definition: SDL_x11sym.h:50
SDL_bool SDL_ShouldIgnoreGameController(const char *name, SDL_JoystickGUID guid)
SDL_bool SDL_XINPUT_Enabled(void)
#define SDL_zero(x)
Definition: SDL_stdinc.h:416
SDL_JoystickPowerLevel
Definition: SDL_joystick.h:97
GLuint index
int SDL_XINPUT_JoystickInit(void)
return Display return Display Bool Bool int int int return Display XEvent Bool(*) XPointer return Display return Display Drawable _Xconst char unsigned int unsigned int return Display Pixmap Pixmap XColor XColor unsigned int unsigned int return Display _Xconst char char int char return Display Visual unsigned int int int char unsigned int unsigned int in i)
Definition: SDL_x11sym.h:50
#define SDL_assert(condition)
Definition: SDL_assert.h:169
#define NULL
Definition: begin_code.h:164
SDL_bool
Definition: SDL_stdinc.h:139
#define SDL_SetError
void SDL_XINPUT_JoystickQuit(void)
#define SDL_HINT_XINPUT_USE_OLD_JOYSTICK_MAPPING
A variable that causes SDL to use the old axis and button mapping for XInput devices.
Definition: SDL_hints.h:384
#define SDL_strdup
void SDL_PrivateJoystickBatteryLevel(SDL_Joystick *joystick, SDL_JoystickPowerLevel ePowerLevel)
uint16_t Uint16
Definition: SDL_stdinc.h:169
#define SDL_snprintf
void SDL_XINPUT_JoystickUpdate(SDL_Joystick *joystick)
#define SDL_arraysize(array)
Definition: SDL_stdinc.h:93
#define SDL_malloc
#define SDL_strcmp
#define SDL_PRESSED
Definition: SDL_events.h:50
#define SDL_HAT_CENTERED
Definition: SDL_joystick.h:316
#define SDL_SwapLE16(X)
Definition: SDL_endian.h:232
#define SDL_RELEASED
Definition: SDL_events.h:49
#define SDL_HAT_UP
Definition: SDL_joystick.h:317
EGLDeviceEXT * devices
Definition: eglext.h:621
#define SDL_HAT_DOWN
Definition: SDL_joystick.h:319
#define SDL_Unsupported()
Definition: SDL_error.h:53
void SDL_XINPUT_JoystickDetect(JoyStick_DeviceData **pContext)
int16_t Sint16
Definition: SDL_stdinc.h:163
#define SDL_strstr