diff options
Diffstat (limited to '')
| -rw-r--r-- | src/input_common/sdl/sdl_impl.cpp | 281 |
1 files changed, 223 insertions, 58 deletions
diff --git a/src/input_common/sdl/sdl_impl.cpp b/src/input_common/sdl/sdl_impl.cpp index 822d0b555..314b0e773 100644 --- a/src/input_common/sdl/sdl_impl.cpp +++ b/src/input_common/sdl/sdl_impl.cpp | |||
| @@ -18,16 +18,6 @@ | |||
| 18 | #include <utility> | 18 | #include <utility> |
| 19 | #include <vector> | 19 | #include <vector> |
| 20 | 20 | ||
| 21 | // Ignore -Wimplicit-fallthrough due to https://github.com/libsdl-org/SDL/issues/4307 | ||
| 22 | #ifdef __clang__ | ||
| 23 | #pragma clang diagnostic push | ||
| 24 | #pragma clang diagnostic ignored "-Wimplicit-fallthrough" | ||
| 25 | #endif | ||
| 26 | #include <SDL.h> | ||
| 27 | #ifdef __clang__ | ||
| 28 | #pragma clang diagnostic pop | ||
| 29 | #endif | ||
| 30 | |||
| 31 | #include "common/logging/log.h" | 21 | #include "common/logging/log.h" |
| 32 | #include "common/math_util.h" | 22 | #include "common/math_util.h" |
| 33 | #include "common/param_package.h" | 23 | #include "common/param_package.h" |
| @@ -214,6 +204,40 @@ public: | |||
| 214 | sdl_controller.reset(controller); | 204 | sdl_controller.reset(controller); |
| 215 | } | 205 | } |
| 216 | 206 | ||
| 207 | bool IsJoyconLeft() const { | ||
| 208 | return std::strstr(GetControllerName().c_str(), "Joy-Con Left") != nullptr; | ||
| 209 | } | ||
| 210 | |||
| 211 | bool IsJoyconRight() const { | ||
| 212 | return std::strstr(GetControllerName().c_str(), "Joy-Con Right") != nullptr; | ||
| 213 | } | ||
| 214 | |||
| 215 | std::string GetControllerName() const { | ||
| 216 | if (sdl_controller) { | ||
| 217 | switch (SDL_GameControllerGetType(sdl_controller.get())) { | ||
| 218 | case SDL_CONTROLLER_TYPE_XBOX360: | ||
| 219 | return "XBox 360 Controller"; | ||
| 220 | case SDL_CONTROLLER_TYPE_XBOXONE: | ||
| 221 | return "XBox One Controller"; | ||
| 222 | default: | ||
| 223 | break; | ||
| 224 | } | ||
| 225 | const auto name = SDL_GameControllerName(sdl_controller.get()); | ||
| 226 | if (name) { | ||
| 227 | return name; | ||
| 228 | } | ||
| 229 | } | ||
| 230 | |||
| 231 | if (sdl_joystick) { | ||
| 232 | const auto name = SDL_JoystickName(sdl_joystick.get()); | ||
| 233 | if (name) { | ||
| 234 | return name; | ||
| 235 | } | ||
| 236 | } | ||
| 237 | |||
| 238 | return "Unknown"; | ||
| 239 | } | ||
| 240 | |||
| 217 | private: | 241 | private: |
| 218 | struct State { | 242 | struct State { |
| 219 | std::unordered_map<int, bool> buttons; | 243 | std::unordered_map<int, bool> buttons; |
| @@ -856,23 +880,42 @@ SDLState::~SDLState() { | |||
| 856 | std::vector<Common::ParamPackage> SDLState::GetInputDevices() { | 880 | std::vector<Common::ParamPackage> SDLState::GetInputDevices() { |
| 857 | std::scoped_lock lock(joystick_map_mutex); | 881 | std::scoped_lock lock(joystick_map_mutex); |
| 858 | std::vector<Common::ParamPackage> devices; | 882 | std::vector<Common::ParamPackage> devices; |
| 883 | std::unordered_map<int, std::shared_ptr<SDLJoystick>> joycon_pairs; | ||
| 884 | for (const auto& [key, value] : joystick_map) { | ||
| 885 | for (const auto& joystick : value) { | ||
| 886 | if (!joystick->GetSDLJoystick()) { | ||
| 887 | continue; | ||
| 888 | } | ||
| 889 | std::string name = | ||
| 890 | fmt::format("{} {}", joystick->GetControllerName(), joystick->GetPort()); | ||
| 891 | devices.emplace_back(Common::ParamPackage{ | ||
| 892 | {"class", "sdl"}, | ||
| 893 | {"display", std::move(name)}, | ||
| 894 | {"guid", joystick->GetGUID()}, | ||
| 895 | {"port", std::to_string(joystick->GetPort())}, | ||
| 896 | }); | ||
| 897 | if (joystick->IsJoyconLeft()) { | ||
| 898 | joycon_pairs.insert_or_assign(joystick->GetPort(), joystick); | ||
| 899 | } | ||
| 900 | } | ||
| 901 | } | ||
| 902 | |||
| 903 | // Add dual controllers | ||
| 859 | for (const auto& [key, value] : joystick_map) { | 904 | for (const auto& [key, value] : joystick_map) { |
| 860 | for (const auto& joystick : value) { | 905 | for (const auto& joystick : value) { |
| 861 | if (auto* const controller = joystick->GetSDLGameController()) { | 906 | if (joystick->IsJoyconRight()) { |
| 907 | if (!joycon_pairs.contains(joystick->GetPort())) { | ||
| 908 | continue; | ||
| 909 | } | ||
| 910 | const auto joystick2 = joycon_pairs.at(joystick->GetPort()); | ||
| 911 | |||
| 862 | std::string name = | 912 | std::string name = |
| 863 | fmt::format("{} {}", GetControllerName(controller), joystick->GetPort()); | 913 | fmt::format("{} {}", "Nintendo Dual Joy-Con", joystick->GetPort()); |
| 864 | devices.emplace_back(Common::ParamPackage{ | ||
| 865 | {"class", "sdl"}, | ||
| 866 | {"display", std::move(name)}, | ||
| 867 | {"guid", joystick->GetGUID()}, | ||
| 868 | {"port", std::to_string(joystick->GetPort())}, | ||
| 869 | }); | ||
| 870 | } else if (auto* const joy = joystick->GetSDLJoystick()) { | ||
| 871 | std::string name = fmt::format("{} {}", SDL_JoystickName(joy), joystick->GetPort()); | ||
| 872 | devices.emplace_back(Common::ParamPackage{ | 914 | devices.emplace_back(Common::ParamPackage{ |
| 873 | {"class", "sdl"}, | 915 | {"class", "sdl"}, |
| 874 | {"display", std::move(name)}, | 916 | {"display", std::move(name)}, |
| 875 | {"guid", joystick->GetGUID()}, | 917 | {"guid", joystick->GetGUID()}, |
| 918 | {"guid2", joystick2->GetGUID()}, | ||
| 876 | {"port", std::to_string(joystick->GetPort())}, | 919 | {"port", std::to_string(joystick->GetPort())}, |
| 877 | }); | 920 | }); |
| 878 | } | 921 | } |
| @@ -881,17 +924,6 @@ std::vector<Common::ParamPackage> SDLState::GetInputDevices() { | |||
| 881 | return devices; | 924 | return devices; |
| 882 | } | 925 | } |
| 883 | 926 | ||
| 884 | std::string SDLState::GetControllerName(SDL_GameController* controller) const { | ||
| 885 | switch (SDL_GameControllerGetType(controller)) { | ||
| 886 | case SDL_CONTROLLER_TYPE_XBOX360: | ||
| 887 | return "XBox 360 Controller"; | ||
| 888 | case SDL_CONTROLLER_TYPE_XBOXONE: | ||
| 889 | return "XBox One Controller"; | ||
| 890 | default: | ||
| 891 | return SDL_GameControllerName(controller); | ||
| 892 | } | ||
| 893 | } | ||
| 894 | |||
| 895 | namespace { | 927 | namespace { |
| 896 | Common::ParamPackage BuildAnalogParamPackageForButton(int port, std::string guid, s32 axis, | 928 | Common::ParamPackage BuildAnalogParamPackageForButton(int port, std::string guid, s32 axis, |
| 897 | float value = 0.1f) { | 929 | float value = 0.1f) { |
| @@ -1071,24 +1103,48 @@ ButtonMapping SDLState::GetButtonMappingForDevice(const Common::ParamPackage& pa | |||
| 1071 | return {}; | 1103 | return {}; |
| 1072 | } | 1104 | } |
| 1073 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); | 1105 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); |
| 1106 | |||
| 1074 | auto* controller = joystick->GetSDLGameController(); | 1107 | auto* controller = joystick->GetSDLGameController(); |
| 1075 | if (controller == nullptr) { | 1108 | if (controller == nullptr) { |
| 1076 | return {}; | 1109 | return {}; |
| 1077 | } | 1110 | } |
| 1078 | 1111 | ||
| 1079 | const bool invert = | ||
| 1080 | SDL_GameControllerGetType(controller) != SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO; | ||
| 1081 | |||
| 1082 | // This list is missing ZL/ZR since those are not considered buttons in SDL GameController. | 1112 | // This list is missing ZL/ZR since those are not considered buttons in SDL GameController. |
| 1083 | // We will add those afterwards | 1113 | // We will add those afterwards |
| 1084 | // This list also excludes Screenshot since theres not really a mapping for that | 1114 | // This list also excludes Screenshot since theres not really a mapping for that |
| 1085 | using ButtonBindings = | 1115 | ButtonBindings switch_to_sdl_button; |
| 1086 | std::array<std::pair<Settings::NativeButton::Values, SDL_GameControllerButton>, 17>; | 1116 | |
| 1087 | const ButtonBindings switch_to_sdl_button{{ | 1117 | if (SDL_GameControllerGetType(controller) == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO) { |
| 1088 | {Settings::NativeButton::A, invert ? SDL_CONTROLLER_BUTTON_B : SDL_CONTROLLER_BUTTON_A}, | 1118 | switch_to_sdl_button = GetNintendoButtonBinding(joystick); |
| 1089 | {Settings::NativeButton::B, invert ? SDL_CONTROLLER_BUTTON_A : SDL_CONTROLLER_BUTTON_B}, | 1119 | } else { |
| 1090 | {Settings::NativeButton::X, invert ? SDL_CONTROLLER_BUTTON_Y : SDL_CONTROLLER_BUTTON_X}, | 1120 | switch_to_sdl_button = GetDefaultButtonBinding(); |
| 1091 | {Settings::NativeButton::Y, invert ? SDL_CONTROLLER_BUTTON_X : SDL_CONTROLLER_BUTTON_Y}, | 1121 | } |
| 1122 | |||
| 1123 | // Add the missing bindings for ZL/ZR | ||
| 1124 | static constexpr ZButtonBindings switch_to_sdl_axis{{ | ||
| 1125 | {Settings::NativeButton::ZL, SDL_CONTROLLER_AXIS_TRIGGERLEFT}, | ||
| 1126 | {Settings::NativeButton::ZR, SDL_CONTROLLER_AXIS_TRIGGERRIGHT}, | ||
| 1127 | }}; | ||
| 1128 | |||
| 1129 | // Parameters contain two joysticks return dual | ||
| 1130 | if (params.Has("guid2")) { | ||
| 1131 | const auto joystick2 = GetSDLJoystickByGUID(params.Get("guid2", ""), params.Get("port", 0)); | ||
| 1132 | |||
| 1133 | if (joystick2->GetSDLGameController() != nullptr) { | ||
| 1134 | return GetDualControllerMapping(joystick, joystick2, switch_to_sdl_button, | ||
| 1135 | switch_to_sdl_axis); | ||
| 1136 | } | ||
| 1137 | } | ||
| 1138 | |||
| 1139 | return GetSingleControllerMapping(joystick, switch_to_sdl_button, switch_to_sdl_axis); | ||
| 1140 | } | ||
| 1141 | |||
| 1142 | ButtonBindings SDLState::GetDefaultButtonBinding() const { | ||
| 1143 | return { | ||
| 1144 | std::pair{Settings::NativeButton::A, SDL_CONTROLLER_BUTTON_B}, | ||
| 1145 | {Settings::NativeButton::B, SDL_CONTROLLER_BUTTON_A}, | ||
| 1146 | {Settings::NativeButton::X, SDL_CONTROLLER_BUTTON_Y}, | ||
| 1147 | {Settings::NativeButton::Y, SDL_CONTROLLER_BUTTON_X}, | ||
| 1092 | {Settings::NativeButton::LStick, SDL_CONTROLLER_BUTTON_LEFTSTICK}, | 1148 | {Settings::NativeButton::LStick, SDL_CONTROLLER_BUTTON_LEFTSTICK}, |
| 1093 | {Settings::NativeButton::RStick, SDL_CONTROLLER_BUTTON_RIGHTSTICK}, | 1149 | {Settings::NativeButton::RStick, SDL_CONTROLLER_BUTTON_RIGHTSTICK}, |
| 1094 | {Settings::NativeButton::L, SDL_CONTROLLER_BUTTON_LEFTSHOULDER}, | 1150 | {Settings::NativeButton::L, SDL_CONTROLLER_BUTTON_LEFTSHOULDER}, |
| @@ -1102,18 +1158,51 @@ ButtonMapping SDLState::GetButtonMappingForDevice(const Common::ParamPackage& pa | |||
| 1102 | {Settings::NativeButton::SL, SDL_CONTROLLER_BUTTON_LEFTSHOULDER}, | 1158 | {Settings::NativeButton::SL, SDL_CONTROLLER_BUTTON_LEFTSHOULDER}, |
| 1103 | {Settings::NativeButton::SR, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER}, | 1159 | {Settings::NativeButton::SR, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER}, |
| 1104 | {Settings::NativeButton::Home, SDL_CONTROLLER_BUTTON_GUIDE}, | 1160 | {Settings::NativeButton::Home, SDL_CONTROLLER_BUTTON_GUIDE}, |
| 1105 | }}; | 1161 | }; |
| 1162 | } | ||
| 1106 | 1163 | ||
| 1107 | // Add the missing bindings for ZL/ZR | 1164 | ButtonBindings SDLState::GetNintendoButtonBinding( |
| 1108 | using ZBindings = | 1165 | const std::shared_ptr<SDLJoystick>& joystick) const { |
| 1109 | std::array<std::pair<Settings::NativeButton::Values, SDL_GameControllerAxis>, 2>; | 1166 | // Default SL/SR mapping for pro controllers |
| 1110 | static constexpr ZBindings switch_to_sdl_axis{{ | 1167 | auto sl_button = SDL_CONTROLLER_BUTTON_LEFTSHOULDER; |
| 1111 | {Settings::NativeButton::ZL, SDL_CONTROLLER_AXIS_TRIGGERLEFT}, | 1168 | auto sr_button = SDL_CONTROLLER_BUTTON_RIGHTSHOULDER; |
| 1112 | {Settings::NativeButton::ZR, SDL_CONTROLLER_AXIS_TRIGGERRIGHT}, | 1169 | |
| 1113 | }}; | 1170 | if (joystick->IsJoyconLeft()) { |
| 1171 | sl_button = SDL_CONTROLLER_BUTTON_PADDLE2; | ||
| 1172 | sr_button = SDL_CONTROLLER_BUTTON_PADDLE4; | ||
| 1173 | } | ||
| 1174 | if (joystick->IsJoyconRight()) { | ||
| 1175 | sl_button = SDL_CONTROLLER_BUTTON_PADDLE3; | ||
| 1176 | sr_button = SDL_CONTROLLER_BUTTON_PADDLE1; | ||
| 1177 | } | ||
| 1114 | 1178 | ||
| 1179 | return { | ||
| 1180 | std::pair{Settings::NativeButton::A, SDL_CONTROLLER_BUTTON_A}, | ||
| 1181 | {Settings::NativeButton::B, SDL_CONTROLLER_BUTTON_B}, | ||
| 1182 | {Settings::NativeButton::X, SDL_CONTROLLER_BUTTON_X}, | ||
| 1183 | {Settings::NativeButton::Y, SDL_CONTROLLER_BUTTON_Y}, | ||
| 1184 | {Settings::NativeButton::LStick, SDL_CONTROLLER_BUTTON_LEFTSTICK}, | ||
| 1185 | {Settings::NativeButton::RStick, SDL_CONTROLLER_BUTTON_RIGHTSTICK}, | ||
| 1186 | {Settings::NativeButton::L, SDL_CONTROLLER_BUTTON_LEFTSHOULDER}, | ||
| 1187 | {Settings::NativeButton::R, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER}, | ||
| 1188 | {Settings::NativeButton::Plus, SDL_CONTROLLER_BUTTON_START}, | ||
| 1189 | {Settings::NativeButton::Minus, SDL_CONTROLLER_BUTTON_BACK}, | ||
| 1190 | {Settings::NativeButton::DLeft, SDL_CONTROLLER_BUTTON_DPAD_LEFT}, | ||
| 1191 | {Settings::NativeButton::DUp, SDL_CONTROLLER_BUTTON_DPAD_UP}, | ||
| 1192 | {Settings::NativeButton::DRight, SDL_CONTROLLER_BUTTON_DPAD_RIGHT}, | ||
| 1193 | {Settings::NativeButton::DDown, SDL_CONTROLLER_BUTTON_DPAD_DOWN}, | ||
| 1194 | {Settings::NativeButton::SL, sl_button}, | ||
| 1195 | {Settings::NativeButton::SR, sr_button}, | ||
| 1196 | {Settings::NativeButton::Home, SDL_CONTROLLER_BUTTON_GUIDE}, | ||
| 1197 | }; | ||
| 1198 | } | ||
| 1199 | |||
| 1200 | ButtonMapping SDLState::GetSingleControllerMapping( | ||
| 1201 | const std::shared_ptr<SDLJoystick>& joystick, const ButtonBindings& switch_to_sdl_button, | ||
| 1202 | const ZButtonBindings& switch_to_sdl_axis) const { | ||
| 1115 | ButtonMapping mapping; | 1203 | ButtonMapping mapping; |
| 1116 | mapping.reserve(switch_to_sdl_button.size() + switch_to_sdl_axis.size()); | 1204 | mapping.reserve(switch_to_sdl_button.size() + switch_to_sdl_axis.size()); |
| 1205 | auto* controller = joystick->GetSDLGameController(); | ||
| 1117 | 1206 | ||
| 1118 | for (const auto& [switch_button, sdl_button] : switch_to_sdl_button) { | 1207 | for (const auto& [switch_button, sdl_button] : switch_to_sdl_button) { |
| 1119 | const auto& binding = SDL_GameControllerGetBindForButton(controller, sdl_button); | 1208 | const auto& binding = SDL_GameControllerGetBindForButton(controller, sdl_button); |
| @@ -1131,11 +1220,68 @@ ButtonMapping SDLState::GetButtonMappingForDevice(const Common::ParamPackage& pa | |||
| 1131 | return mapping; | 1220 | return mapping; |
| 1132 | } | 1221 | } |
| 1133 | 1222 | ||
| 1223 | ButtonMapping SDLState::GetDualControllerMapping(const std::shared_ptr<SDLJoystick>& joystick, | ||
| 1224 | const std::shared_ptr<SDLJoystick>& joystick2, | ||
| 1225 | const ButtonBindings& switch_to_sdl_button, | ||
| 1226 | const ZButtonBindings& switch_to_sdl_axis) const { | ||
| 1227 | ButtonMapping mapping; | ||
| 1228 | mapping.reserve(switch_to_sdl_button.size() + switch_to_sdl_axis.size()); | ||
| 1229 | auto* controller = joystick->GetSDLGameController(); | ||
| 1230 | auto* controller2 = joystick2->GetSDLGameController(); | ||
| 1231 | |||
| 1232 | for (const auto& [switch_button, sdl_button] : switch_to_sdl_button) { | ||
| 1233 | if (IsButtonOnLeftSide(switch_button)) { | ||
| 1234 | const auto& binding = SDL_GameControllerGetBindForButton(controller2, sdl_button); | ||
| 1235 | mapping.insert_or_assign( | ||
| 1236 | switch_button, | ||
| 1237 | BuildParamPackageForBinding(joystick2->GetPort(), joystick2->GetGUID(), binding)); | ||
| 1238 | continue; | ||
| 1239 | } | ||
| 1240 | const auto& binding = SDL_GameControllerGetBindForButton(controller, sdl_button); | ||
| 1241 | mapping.insert_or_assign( | ||
| 1242 | switch_button, | ||
| 1243 | BuildParamPackageForBinding(joystick->GetPort(), joystick->GetGUID(), binding)); | ||
| 1244 | } | ||
| 1245 | for (const auto& [switch_button, sdl_axis] : switch_to_sdl_axis) { | ||
| 1246 | if (IsButtonOnLeftSide(switch_button)) { | ||
| 1247 | const auto& binding = SDL_GameControllerGetBindForAxis(controller2, sdl_axis); | ||
| 1248 | mapping.insert_or_assign( | ||
| 1249 | switch_button, | ||
| 1250 | BuildParamPackageForBinding(joystick2->GetPort(), joystick2->GetGUID(), binding)); | ||
| 1251 | continue; | ||
| 1252 | } | ||
| 1253 | const auto& binding = SDL_GameControllerGetBindForAxis(controller, sdl_axis); | ||
| 1254 | mapping.insert_or_assign( | ||
| 1255 | switch_button, | ||
| 1256 | BuildParamPackageForBinding(joystick->GetPort(), joystick->GetGUID(), binding)); | ||
| 1257 | } | ||
| 1258 | |||
| 1259 | return mapping; | ||
| 1260 | } | ||
| 1261 | |||
| 1262 | bool SDLState::IsButtonOnLeftSide(Settings::NativeButton::Values button) const { | ||
| 1263 | switch (button) { | ||
| 1264 | case Settings::NativeButton::DDown: | ||
| 1265 | case Settings::NativeButton::DLeft: | ||
| 1266 | case Settings::NativeButton::DRight: | ||
| 1267 | case Settings::NativeButton::DUp: | ||
| 1268 | case Settings::NativeButton::L: | ||
| 1269 | case Settings::NativeButton::LStick: | ||
| 1270 | case Settings::NativeButton::Minus: | ||
| 1271 | case Settings::NativeButton::Screenshot: | ||
| 1272 | case Settings::NativeButton::ZL: | ||
| 1273 | return true; | ||
| 1274 | default: | ||
| 1275 | return false; | ||
| 1276 | } | ||
| 1277 | } | ||
| 1278 | |||
| 1134 | AnalogMapping SDLState::GetAnalogMappingForDevice(const Common::ParamPackage& params) { | 1279 | AnalogMapping SDLState::GetAnalogMappingForDevice(const Common::ParamPackage& params) { |
| 1135 | if (!params.Has("guid") || !params.Has("port")) { | 1280 | if (!params.Has("guid") || !params.Has("port")) { |
| 1136 | return {}; | 1281 | return {}; |
| 1137 | } | 1282 | } |
| 1138 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); | 1283 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); |
| 1284 | const auto joystick2 = GetSDLJoystickByGUID(params.Get("guid2", ""), params.Get("port", 0)); | ||
| 1139 | auto* controller = joystick->GetSDLGameController(); | 1285 | auto* controller = joystick->GetSDLGameController(); |
| 1140 | if (controller == nullptr) { | 1286 | if (controller == nullptr) { |
| 1141 | return {}; | 1287 | return {}; |
| @@ -1146,10 +1292,17 @@ AnalogMapping SDLState::GetAnalogMappingForDevice(const Common::ParamPackage& pa | |||
| 1146 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_LEFTX); | 1292 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_LEFTX); |
| 1147 | const auto& binding_left_y = | 1293 | const auto& binding_left_y = |
| 1148 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_LEFTY); | 1294 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_LEFTY); |
| 1149 | mapping.insert_or_assign(Settings::NativeAnalog::LStick, | 1295 | if (params.Has("guid2")) { |
| 1150 | BuildParamPackageForAnalog(joystick->GetPort(), joystick->GetGUID(), | 1296 | mapping.insert_or_assign( |
| 1151 | binding_left_x.value.axis, | 1297 | Settings::NativeAnalog::LStick, |
| 1152 | binding_left_y.value.axis)); | 1298 | BuildParamPackageForAnalog(joystick2->GetPort(), joystick2->GetGUID(), |
| 1299 | binding_left_x.value.axis, binding_left_y.value.axis)); | ||
| 1300 | } else { | ||
| 1301 | mapping.insert_or_assign( | ||
| 1302 | Settings::NativeAnalog::LStick, | ||
| 1303 | BuildParamPackageForAnalog(joystick->GetPort(), joystick->GetGUID(), | ||
| 1304 | binding_left_x.value.axis, binding_left_y.value.axis)); | ||
| 1305 | } | ||
| 1153 | const auto& binding_right_x = | 1306 | const auto& binding_right_x = |
| 1154 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_RIGHTX); | 1307 | SDL_GameControllerGetBindForAxis(controller, SDL_CONTROLLER_AXIS_RIGHTX); |
| 1155 | const auto& binding_right_y = | 1308 | const auto& binding_right_y = |
| @@ -1166,20 +1319,32 @@ MotionMapping SDLState::GetMotionMappingForDevice(const Common::ParamPackage& pa | |||
| 1166 | return {}; | 1319 | return {}; |
| 1167 | } | 1320 | } |
| 1168 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); | 1321 | const auto joystick = GetSDLJoystickByGUID(params.Get("guid", ""), params.Get("port", 0)); |
| 1322 | const auto joystick2 = GetSDLJoystickByGUID(params.Get("guid2", ""), params.Get("port", 0)); | ||
| 1169 | auto* controller = joystick->GetSDLGameController(); | 1323 | auto* controller = joystick->GetSDLGameController(); |
| 1170 | if (controller == nullptr) { | 1324 | if (controller == nullptr) { |
| 1171 | return {}; | 1325 | return {}; |
| 1172 | } | 1326 | } |
| 1173 | 1327 | ||
| 1328 | MotionMapping mapping = {}; | ||
| 1174 | joystick->EnableMotion(); | 1329 | joystick->EnableMotion(); |
| 1175 | 1330 | ||
| 1176 | if (!joystick->HasGyro() && !joystick->HasAccel()) { | 1331 | if (joystick->HasGyro() || joystick->HasAccel()) { |
| 1177 | return {}; | 1332 | mapping.insert_or_assign(Settings::NativeMotion::MotionRight, |
| 1333 | BuildMotionParam(joystick->GetPort(), joystick->GetGUID())); | ||
| 1334 | } | ||
| 1335 | if (params.Has("guid2")) { | ||
| 1336 | joystick2->EnableMotion(); | ||
| 1337 | if (joystick2->HasGyro() || joystick2->HasAccel()) { | ||
| 1338 | mapping.insert_or_assign(Settings::NativeMotion::MotionLeft, | ||
| 1339 | BuildMotionParam(joystick2->GetPort(), joystick2->GetGUID())); | ||
| 1340 | } | ||
| 1341 | } else { | ||
| 1342 | if (joystick->HasGyro() || joystick->HasAccel()) { | ||
| 1343 | mapping.insert_or_assign(Settings::NativeMotion::MotionLeft, | ||
| 1344 | BuildMotionParam(joystick->GetPort(), joystick->GetGUID())); | ||
| 1345 | } | ||
| 1178 | } | 1346 | } |
| 1179 | 1347 | ||
| 1180 | MotionMapping mapping = {}; | ||
| 1181 | mapping.insert_or_assign(Settings::NativeMotion::MotionLeft, | ||
| 1182 | BuildMotionParam(joystick->GetPort(), joystick->GetGUID())); | ||
| 1183 | return mapping; | 1348 | return mapping; |
| 1184 | } | 1349 | } |
| 1185 | namespace Polling { | 1350 | namespace Polling { |