diff --git a/include/SDL_sensor.h b/include/SDL_sensor.h index a2f30e0f8f..6b07183ead 100644 --- a/include/SDL_sensor.h +++ b/include/SDL_sensor.h @@ -71,7 +71,11 @@ typedef enum SDL_SENSOR_INVALID = -1, /**< Returned for an invalid sensor */ SDL_SENSOR_UNKNOWN, /**< Unknown sensor type */ SDL_SENSOR_ACCEL, /**< Accelerometer */ - SDL_SENSOR_GYRO /**< Gyroscope */ + SDL_SENSOR_GYRO, /**< Gyroscope */ + SDL_SENSOR_ACCEL_L, /**< Accelerometer for left Joy-Con controller and Wii nunchuk */ + SDL_SENSOR_GYRO_L, /**< Gyroscope for left Joy-Con controller */ + SDL_SENSOR_ACCEL_R, /**< Accelerometer for right Joy-Con controller */ + SDL_SENSOR_GYRO_R /**< Gyroscope for right Joy-Con controller */ } SDL_SensorType; /** diff --git a/src/joystick/hidapi/SDL_hidapi_switch.c b/src/joystick/hidapi/SDL_hidapi_switch.c index 799dbb1cf5..727b59ce1a 100644 --- a/src/joystick/hidapi/SDL_hidapi_switch.c +++ b/src/joystick/hidapi/SDL_hidapi_switch.c @@ -254,7 +254,6 @@ typedef struct { SDL_bool m_bRumblePending; SDL_bool m_bRumbleZeroPending; Uint32 m_unRumblePending; - SDL_bool m_bHasSensors; SDL_bool m_bReportSensors; SDL_bool m_bHasSensorData; Uint32 m_unLastInput; @@ -1351,7 +1350,16 @@ HIDAPI_DriverSwitch_OpenJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joysti ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConRight) { SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_GYRO, 200.0f); SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL, 200.0f); - ctx->m_bHasSensors = SDL_TRUE; + } + if (device->parent && + ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConLeft) { + SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_GYRO_L, 200.0f); + SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL_L, 200.0f); + } + if (device->parent && + ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConRight) { + SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_GYRO_R, 200.0f); + SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL_R, 200.0f); } } @@ -1610,10 +1618,6 @@ HIDAPI_DriverSwitch_SetJoystickSensorsEnabled(SDL_HIDAPI_Device *device, SDL_Joy { SDL_DriverSwitch_Context* ctx = (SDL_DriverSwitch_Context*)device->context; - if (!ctx->m_bHasSensors) { - return SDL_Unsupported(); - } - SetIMUEnabled(ctx, enabled); ctx->m_bReportSensors = enabled; @@ -1816,7 +1820,7 @@ static void SendSensorUpdate(SDL_Joystick *joystick, SDL_DriverSwitch_Context *c * since that's our de facto standard from already supporting those controllers, and * users will want consistent axis mappings across devices. */ - if (type == SDL_SENSOR_GYRO) { + if (type == SDL_SENSOR_GYRO || type == SDL_SENSOR_GYRO_L || type == SDL_SENSOR_GYRO_R ) { data[0] = -(ctx->m_IMUScaleData.fGyroScaleY * (float)values[1]); data[1] = ctx->m_IMUScaleData.fGyroScaleZ * (float)values[2]; data[2] = -(ctx->m_IMUScaleData.fGyroScaleX * (float)values[0]); @@ -2068,13 +2072,37 @@ static void HandleFullControllerState(SDL_Joystick *joystick, SDL_DriverSwitch_C if (bHasSensorData) { ctx->m_bHasSensorData = SDL_TRUE; - SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[2].sGyroX); - SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[1].sGyroX); - SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[0].sGyroX); + if (!ctx->device->parent || + ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConRight) { + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[2].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[1].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO, &packet->imuState[0].sGyroX); - SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[2].sAccelX); - SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[1].sAccelX); - SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[0].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[2].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[1].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL, &packet->imuState[0].sAccelX); + } + + if (ctx->device->parent && + ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConLeft) { + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_L, &packet->imuState[2].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_L, &packet->imuState[1].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_L, &packet->imuState[0].sGyroX); + + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_L, &packet->imuState[2].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_L, &packet->imuState[1].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_L, &packet->imuState[0].sAccelX); + } + if (ctx->device->parent && + ctx->m_eControllerType == k_eSwitchDeviceInfoControllerType_JoyConRight) { + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_R, &packet->imuState[2].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_R, &packet->imuState[1].sGyroX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_GYRO_R, &packet->imuState[0].sGyroX); + + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_R, &packet->imuState[2].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_R, &packet->imuState[1].sAccelX); + SendSensorUpdate(joystick, ctx, SDL_SENSOR_ACCEL_R, &packet->imuState[0].sAccelX); + } } else if (ctx->m_bHasSensorData) { /* Uh oh, someone turned off the IMU? */ diff --git a/src/joystick/hidapi/SDL_hidapi_wii.c b/src/joystick/hidapi/SDL_hidapi_wii.c index b000a036f9..0b9922fad6 100644 --- a/src/joystick/hidapi/SDL_hidapi_wii.c +++ b/src/joystick/hidapi/SDL_hidapi_wii.c @@ -809,6 +809,9 @@ HIDAPI_DriverWii_OpenJoystick(SDL_HIDAPI_Device *device, SDL_Joystick *joystick) if (ctx->m_eExtensionControllerType == k_eWiiExtensionControllerType_None || ctx->m_eExtensionControllerType == k_eWiiExtensionControllerType_Nunchuk) { SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL, 100.0f); + if (ctx->m_eExtensionControllerType == k_eWiiExtensionControllerType_Nunchuk) { + SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL_L, 100.0f); + } if (ctx->m_bMotionPlusPresent) { SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_GYRO, 100.0f); @@ -1162,7 +1165,6 @@ static void HandleNunchuckButtonData(SDL_DriverWii_Context *ctx, SDL_Joystick *j PostStickCalibrated(joystick, &ctx->m_StickCalibrationData[0], SDL_CONTROLLER_AXIS_LEFTX, data->rgucExtension[0]); PostStickCalibrated(joystick, &ctx->m_StickCalibrationData[1], SDL_CONTROLLER_AXIS_LEFTY, data->rgucExtension[1]); -#if 0 /* We'll report this when we have the concept of right/left sensors */ if (ctx->m_bReportSensors) { const float ACCEL_RES_PER_G = 200.0f; Sint16 x, y, z; @@ -1190,9 +1192,8 @@ static void HandleNunchuckButtonData(SDL_DriverWii_Context *ctx, SDL_Joystick *j values[0] = -((float)x / ACCEL_RES_PER_G) * SDL_STANDARD_GRAVITY; values[1] = ((float)z / ACCEL_RES_PER_G) * SDL_STANDARD_GRAVITY; values[2] = ((float)y / ACCEL_RES_PER_G) * SDL_STANDARD_GRAVITY; - SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL, values, 3); + SDL_PrivateJoystickSensor(joystick, SDL_SENSOR_ACCEL_L, values, 3); } -#endif } static void HandleMotionPlusData(SDL_DriverWii_Context *ctx, SDL_Joystick *joystick, const WiiButtonData *data) diff --git a/test/testgamecontroller.c b/test/testgamecontroller.c index 7e51bcbfce..2dc32d60e1 100644 --- a/test/testgamecontroller.c +++ b/test/testgamecontroller.c @@ -127,6 +127,26 @@ static void UpdateWindowTitle() } } +static const char *GetSensorName(SDL_SensorType sensor) +{ + switch (sensor) { + case SDL_SENSOR_ACCEL: + return "accelerometer"; + case SDL_SENSOR_GYRO: + return "gyro"; + case SDL_SENSOR_ACCEL_L: + return "accelerometer (L)"; + case SDL_SENSOR_GYRO_L: + return "gyro (L)"; + case SDL_SENSOR_ACCEL_R: + return "accelerometer (R)"; + case SDL_SENSOR_GYRO_R: + return "gyro (R)"; + default: + return "UNKNOWN"; + } +} + static int FindController(SDL_JoystickID controller_id) { int i; @@ -145,6 +165,15 @@ static void AddController(int device_index, SDL_bool verbose) SDL_GameController *controller; SDL_GameController **controllers; Uint16 firmware_version; + SDL_SensorType sensors[] = { + SDL_SENSOR_ACCEL, + SDL_SENSOR_GYRO, + SDL_SENSOR_ACCEL_L, + SDL_SENSOR_GYRO_L, + SDL_SENSOR_ACCEL_R, + SDL_SENSOR_GYRO_R + }; + unsigned int i; controller_id = SDL_JoystickGetDeviceInstanceID(device_index); if (controller_id < 0) { @@ -187,18 +216,15 @@ static void AddController(int device_index, SDL_bool verbose) } } - if (SDL_GameControllerHasSensor(gamecontroller, SDL_SENSOR_ACCEL)) { - if (verbose) { - SDL_Log("Enabling accelerometer at %.2f Hz\n", SDL_GameControllerGetSensorDataRate(gamecontroller, SDL_SENSOR_ACCEL)); - } - SDL_GameControllerSetSensorEnabled(gamecontroller, SDL_SENSOR_ACCEL, SDL_TRUE); - } + for (i = 0; i < SDL_arraysize(sensors); ++i) { + SDL_SensorType sensor = sensors[i]; - if (SDL_GameControllerHasSensor(gamecontroller, SDL_SENSOR_GYRO)) { - if (verbose) { - SDL_Log("Enabling gyro at %.2f Hz\n", SDL_GameControllerGetSensorDataRate(gamecontroller, SDL_SENSOR_GYRO)); + if (SDL_GameControllerHasSensor(gamecontroller, sensor)) { + if (verbose) { + SDL_Log("Enabling %s at %.2f Hz\n", GetSensorName(sensor), SDL_GameControllerGetSensorDataRate(gamecontroller, sensor)); + } + SDL_GameControllerSetSensorEnabled(gamecontroller, sensor, SDL_TRUE); } - SDL_GameControllerSetSensorEnabled(gamecontroller, SDL_SENSOR_GYRO, SDL_TRUE); } if (SDL_GameControllerHasRumble(gamecontroller)) { @@ -565,8 +591,7 @@ loop(void *arg) case SDL_CONTROLLERSENSORUPDATE: SDL_Log("Controller %d sensor %s: %.2f, %.2f, %.2f\n", event.csensor.which, - event.csensor.sensor == SDL_SENSOR_ACCEL ? "accelerometer" : - event.csensor.sensor == SDL_SENSOR_GYRO ? "gyro" : "unknown", + GetSensorName((SDL_SensorType)event.csensor.sensor), event.csensor.data[0], event.csensor.data[1], event.csensor.data[2]);