mirror of
https://github.com/libsdl-org/SDL.git
synced 2026-06-04 06:12:04 +08:00
Correct the sensor axis ordering with the Linux Nintendo driver
Fixes https://github.com/libsdl-org/SDL/issues/14552
Manual cherry-pick of 5e9163592f by Sam Lantinga <slouken@libsdl.org>
This commit is contained in:
committed by
Sam Lantinga
parent
07bf82e39e
commit
57462dad9c
@@ -154,6 +154,8 @@ typedef struct SDL_joylist_item
|
|||||||
{
|
{
|
||||||
SDL_JoystickID device_instance;
|
SDL_JoystickID device_instance;
|
||||||
char *path; /* "/dev/input/event2" or whatever */
|
char *path; /* "/dev/input/event2" or whatever */
|
||||||
|
Uint16 vendor;
|
||||||
|
Uint16 product;
|
||||||
char *name; /* "SideWinder 3D Pro" or whatever */
|
char *name; /* "SideWinder 3D Pro" or whatever */
|
||||||
SDL_JoystickGUID guid;
|
SDL_JoystickGUID guid;
|
||||||
dev_t devnum;
|
dev_t devnum;
|
||||||
@@ -483,6 +485,8 @@ static void MaybeAddDevice(const char *path)
|
|||||||
item->devnum = sb.st_rdev;
|
item->devnum = sb.st_rdev;
|
||||||
item->steam_virtual_gamepad_slot = -1;
|
item->steam_virtual_gamepad_slot = -1;
|
||||||
item->path = SDL_strdup(path);
|
item->path = SDL_strdup(path);
|
||||||
|
item->vendor = vendor;
|
||||||
|
item->product = product;
|
||||||
item->name = name;
|
item->name = name;
|
||||||
item->guid = guid;
|
item->guid = guid;
|
||||||
|
|
||||||
@@ -1932,6 +1936,20 @@ static void PollAllValues(SDL_Joystick *joystick)
|
|||||||
/* Joyballs are relative input, so there's no poll state. Events only! */
|
/* Joyballs are relative input, so there's no poll state. Events only! */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void CorrectSensorData(struct joystick_hwdata *hwdata, float *values, float *data)
|
||||||
|
{
|
||||||
|
if (hwdata->item->vendor == USB_VENDOR_NINTENDO) {
|
||||||
|
// The Nintendo driver uses a different axis order than SDL
|
||||||
|
data[0] = -values[1];
|
||||||
|
data[1] = values[2];
|
||||||
|
data[2] = -values[0];
|
||||||
|
} else {
|
||||||
|
data[0] = values[0];
|
||||||
|
data[1] = values[1];
|
||||||
|
data[2] = values[2];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void PollAllSensors(SDL_Joystick *joystick)
|
static void PollAllSensors(SDL_Joystick *joystick)
|
||||||
{
|
{
|
||||||
struct input_absinfo absinfo;
|
struct input_absinfo absinfo;
|
||||||
@@ -1942,27 +1960,31 @@ static void PollAllSensors(SDL_Joystick *joystick)
|
|||||||
SDL_assert(joystick->hwdata->fd_sensor >= 0);
|
SDL_assert(joystick->hwdata->fd_sensor >= 0);
|
||||||
|
|
||||||
if (joystick->hwdata->has_gyro) {
|
if (joystick->hwdata->has_gyro) {
|
||||||
float data[3] = {0.0f, 0.0f, 0.0f};
|
float values[3] = {0.0f, 0.0f, 0.0f};
|
||||||
|
float data[3];
|
||||||
for (i = 0; i < 3; i++) {
|
for (i = 0; i < 3; i++) {
|
||||||
if (ioctl(joystick->hwdata->fd_sensor, EVIOCGABS(ABS_RX + i), &absinfo) >= 0) {
|
if (ioctl(joystick->hwdata->fd_sensor, EVIOCGABS(ABS_RX + i), &absinfo) >= 0) {
|
||||||
data[i] = absinfo.value * (M_PI / 180.f) / joystick->hwdata->gyro_scale[i];
|
values[i] = absinfo.value * (M_PI / 180.f) / joystick->hwdata->gyro_scale[i];
|
||||||
#ifdef DEBUG_INPUT_EVENTS
|
#ifdef DEBUG_INPUT_EVENTS
|
||||||
SDL_Log("Joystick : Re-read Gyro (axis %d) val= %f\n", i, data[i]);
|
SDL_Log("Joystick : Re-read Gyro (axis %d) val= %f\n", i, data[i]);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
CorrectSensorData(joystick->hwdata, values, data);
|
||||||
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_GYRO, joystick->hwdata->sensor_tick, data, 3);
|
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_GYRO, joystick->hwdata->sensor_tick, data, 3);
|
||||||
}
|
}
|
||||||
if (joystick->hwdata->has_accelerometer) {
|
if (joystick->hwdata->has_accelerometer) {
|
||||||
float data[3] = {0.0f, 0.0f, 0.0f};
|
float values[3] = {0.0f, 0.0f, 0.0f};
|
||||||
|
float data[3];
|
||||||
for (i = 0; i < 3; i++) {
|
for (i = 0; i < 3; i++) {
|
||||||
if (ioctl(joystick->hwdata->fd_sensor, EVIOCGABS(ABS_X + i), &absinfo) >= 0) {
|
if (ioctl(joystick->hwdata->fd_sensor, EVIOCGABS(ABS_X + i), &absinfo) >= 0) {
|
||||||
data[i] = absinfo.value * SDL_STANDARD_GRAVITY / joystick->hwdata->accelerometer_scale[i];
|
values[i] = absinfo.value * SDL_STANDARD_GRAVITY / joystick->hwdata->accelerometer_scale[i];
|
||||||
#ifdef DEBUG_INPUT_EVENTS
|
#ifdef DEBUG_INPUT_EVENTS
|
||||||
SDL_Log("Joystick : Re-read Accelerometer (axis %d) val= %f\n", i, data[i]);
|
SDL_Log("Joystick : Re-read Accelerometer (axis %d) val= %f\n", i, data[i]);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
CorrectSensorData(joystick->hwdata, values, data);
|
||||||
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL, joystick->hwdata->sensor_tick, data, 3);
|
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL, joystick->hwdata->sensor_tick, data, 3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2132,12 +2154,15 @@ static void HandleInputEvents(SDL_Joystick *joystick)
|
|||||||
joystick->hwdata->recovering_from_dropped_sensor = SDL_FALSE;
|
joystick->hwdata->recovering_from_dropped_sensor = SDL_FALSE;
|
||||||
PollAllSensors(joystick); /* try to sync up to current state now */
|
PollAllSensors(joystick); /* try to sync up to current state now */
|
||||||
} else {
|
} else {
|
||||||
|
float data[3];
|
||||||
|
CorrectSensorData(joystick->hwdata, joystick->hwdata->gyro_data, data);
|
||||||
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_GYRO,
|
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_GYRO,
|
||||||
joystick->hwdata->sensor_tick,
|
joystick->hwdata->sensor_tick,
|
||||||
joystick->hwdata->gyro_data, 3);
|
data, 3);
|
||||||
|
CorrectSensorData(joystick->hwdata, joystick->hwdata->accel_data, data);
|
||||||
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL,
|
SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL,
|
||||||
joystick->hwdata->sensor_tick,
|
joystick->hwdata->sensor_tick,
|
||||||
joystick->hwdata->accel_data, 3);
|
data, 3);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|||||||
Reference in New Issue
Block a user