diff options
Diffstat (limited to 'src/input_common/drivers')
| -rw-r--r-- | src/input_common/drivers/mouse.cpp | 99 | ||||
| -rw-r--r-- | src/input_common/drivers/mouse.h | 2 | ||||
| -rw-r--r-- | src/input_common/drivers/sdl_driver.cpp | 32 |
3 files changed, 73 insertions, 60 deletions
diff --git a/src/input_common/drivers/mouse.cpp b/src/input_common/drivers/mouse.cpp index 0c9f642bb..f07cf8a0e 100644 --- a/src/input_common/drivers/mouse.cpp +++ b/src/input_common/drivers/mouse.cpp | |||
| @@ -76,9 +76,6 @@ void Mouse::UpdateThread(std::stop_token stop_token) { | |||
| 76 | UpdateStickInput(); | 76 | UpdateStickInput(); |
| 77 | UpdateMotionInput(); | 77 | UpdateMotionInput(); |
| 78 | 78 | ||
| 79 | if (mouse_panning_timeout++ > 20) { | ||
| 80 | StopPanning(); | ||
| 81 | } | ||
| 82 | std::this_thread::sleep_for(std::chrono::milliseconds(update_time)); | 79 | std::this_thread::sleep_for(std::chrono::milliseconds(update_time)); |
| 83 | } | 80 | } |
| 84 | } | 81 | } |
| @@ -88,18 +85,45 @@ void Mouse::UpdateStickInput() { | |||
| 88 | return; | 85 | return; |
| 89 | } | 86 | } |
| 90 | 87 | ||
| 91 | const float sensitivity = | 88 | const float length = last_mouse_change.Length(); |
| 92 | Settings::values.mouse_panning_sensitivity.GetValue() * default_stick_sensitivity; | ||
| 93 | 89 | ||
| 94 | // Slow movement by 4% | 90 | // Prevent input from exceeding the max range (1.0f) too much, |
| 95 | last_mouse_change *= 0.96f; | 91 | // but allow some room to make it easier to sustain |
| 96 | SetAxis(identifier, mouse_axis_x, last_mouse_change.x * sensitivity); | 92 | if (length > 1.2f) { |
| 97 | SetAxis(identifier, mouse_axis_y, -last_mouse_change.y * sensitivity); | 93 | last_mouse_change /= length; |
| 94 | last_mouse_change *= 1.2f; | ||
| 95 | } | ||
| 96 | |||
| 97 | auto mouse_change = last_mouse_change; | ||
| 98 | |||
| 99 | // Bind the mouse change to [0 <= deadzone_counterweight <= 1,1] | ||
| 100 | if (length < 1.0f) { | ||
| 101 | const float deadzone_h_counterweight = | ||
| 102 | Settings::values.mouse_panning_deadzone_x_counterweight.GetValue(); | ||
| 103 | const float deadzone_v_counterweight = | ||
| 104 | Settings::values.mouse_panning_deadzone_y_counterweight.GetValue(); | ||
| 105 | mouse_change /= length; | ||
| 106 | mouse_change.x *= length + (1 - length) * deadzone_h_counterweight * 0.01f; | ||
| 107 | mouse_change.y *= length + (1 - length) * deadzone_v_counterweight * 0.01f; | ||
| 108 | } | ||
| 109 | |||
| 110 | SetAxis(identifier, mouse_axis_x, mouse_change.x); | ||
| 111 | SetAxis(identifier, mouse_axis_y, -mouse_change.y); | ||
| 112 | |||
| 113 | // Decay input over time | ||
| 114 | const float clamped_length = std::min(1.0f, length); | ||
| 115 | const float decay_strength = Settings::values.mouse_panning_decay_strength.GetValue(); | ||
| 116 | const float decay = 1 - clamped_length * clamped_length * decay_strength * 0.01f; | ||
| 117 | const float min_decay = Settings::values.mouse_panning_min_decay.GetValue(); | ||
| 118 | const float clamped_decay = std::min(1 - min_decay / 100.0f, decay); | ||
| 119 | last_mouse_change *= clamped_decay; | ||
| 98 | } | 120 | } |
| 99 | 121 | ||
| 100 | void Mouse::UpdateMotionInput() { | 122 | void Mouse::UpdateMotionInput() { |
| 101 | const float sensitivity = | 123 | // This may need its own sensitivity instead of using the average |
| 102 | Settings::values.mouse_panning_sensitivity.GetValue() * default_motion_sensitivity; | 124 | const float sensitivity = (Settings::values.mouse_panning_x_sensitivity.GetValue() + |
| 125 | Settings::values.mouse_panning_y_sensitivity.GetValue()) / | ||
| 126 | 2.0f * default_motion_sensitivity; | ||
| 103 | 127 | ||
| 104 | const float rotation_velocity = std::sqrt(last_motion_change.x * last_motion_change.x + | 128 | const float rotation_velocity = std::sqrt(last_motion_change.x * last_motion_change.x + |
| 105 | last_motion_change.y * last_motion_change.y); | 129 | last_motion_change.y * last_motion_change.y); |
| @@ -131,49 +155,28 @@ void Mouse::UpdateMotionInput() { | |||
| 131 | 155 | ||
| 132 | void Mouse::Move(int x, int y, int center_x, int center_y) { | 156 | void Mouse::Move(int x, int y, int center_x, int center_y) { |
| 133 | if (Settings::values.mouse_panning) { | 157 | if (Settings::values.mouse_panning) { |
| 134 | mouse_panning_timeout = 0; | 158 | const auto mouse_change = |
| 135 | |||
| 136 | auto mouse_change = | ||
| 137 | (Common::MakeVec(x, y) - Common::MakeVec(center_x, center_y)).Cast<float>(); | 159 | (Common::MakeVec(x, y) - Common::MakeVec(center_x, center_y)).Cast<float>(); |
| 138 | last_motion_change += {-mouse_change.y, -mouse_change.x, 0}; | 160 | const float x_sensitivity = |
| 139 | 161 | Settings::values.mouse_panning_x_sensitivity.GetValue() * default_stick_sensitivity; | |
| 140 | const auto move_distance = mouse_change.Length(); | 162 | const float y_sensitivity = |
| 141 | if (move_distance == 0) { | 163 | Settings::values.mouse_panning_y_sensitivity.GetValue() * default_stick_sensitivity; |
| 142 | return; | ||
| 143 | } | ||
| 144 | 164 | ||
| 145 | // Make slow movements at least 3 units on length | 165 | last_motion_change += {-mouse_change.y, -mouse_change.x, 0}; |
| 146 | if (move_distance < 3.0f) { | 166 | last_mouse_change.x += mouse_change.x * x_sensitivity * 0.09f; |
| 147 | // Normalize value | 167 | last_mouse_change.y += mouse_change.y * y_sensitivity * 0.09f; |
| 148 | mouse_change /= move_distance; | ||
| 149 | mouse_change *= 3.0f; | ||
| 150 | } | ||
| 151 | |||
| 152 | // Average mouse movements | ||
| 153 | last_mouse_change = (last_mouse_change * 0.91f) + (mouse_change * 0.09f); | ||
| 154 | |||
| 155 | const auto last_move_distance = last_mouse_change.Length(); | ||
| 156 | |||
| 157 | // Make fast movements clamp to 8 units on length | ||
| 158 | if (last_move_distance > 8.0f) { | ||
| 159 | // Normalize value | ||
| 160 | last_mouse_change /= last_move_distance; | ||
| 161 | last_mouse_change *= 8.0f; | ||
| 162 | } | ||
| 163 | |||
| 164 | // Ignore average if it's less than 1 unit and use current movement value | ||
| 165 | if (last_move_distance < 1.0f) { | ||
| 166 | last_mouse_change = mouse_change / mouse_change.Length(); | ||
| 167 | } | ||
| 168 | 168 | ||
| 169 | return; | 169 | return; |
| 170 | } | 170 | } |
| 171 | 171 | ||
| 172 | if (button_pressed) { | 172 | if (button_pressed) { |
| 173 | const auto mouse_move = Common::MakeVec<int>(x, y) - mouse_origin; | 173 | const auto mouse_move = Common::MakeVec<int>(x, y) - mouse_origin; |
| 174 | const float sensitivity = Settings::values.mouse_panning_sensitivity.GetValue() * 0.0012f; | 174 | const float x_sensitivity = Settings::values.mouse_panning_x_sensitivity.GetValue(); |
| 175 | SetAxis(identifier, mouse_axis_x, static_cast<float>(mouse_move.x) * sensitivity); | 175 | const float y_sensitivity = Settings::values.mouse_panning_y_sensitivity.GetValue(); |
| 176 | SetAxis(identifier, mouse_axis_y, static_cast<float>(-mouse_move.y) * sensitivity); | 176 | SetAxis(identifier, mouse_axis_x, |
| 177 | static_cast<float>(mouse_move.x) * x_sensitivity * 0.0012f); | ||
| 178 | SetAxis(identifier, mouse_axis_y, | ||
| 179 | static_cast<float>(-mouse_move.y) * y_sensitivity * 0.0012f); | ||
| 177 | 180 | ||
| 178 | last_motion_change = { | 181 | last_motion_change = { |
| 179 | static_cast<float>(-mouse_move.y) / 50.0f, | 182 | static_cast<float>(-mouse_move.y) / 50.0f, |
| @@ -241,10 +244,6 @@ void Mouse::ReleaseAllButtons() { | |||
| 241 | button_pressed = false; | 244 | button_pressed = false; |
| 242 | } | 245 | } |
| 243 | 246 | ||
| 244 | void Mouse::StopPanning() { | ||
| 245 | last_mouse_change = {}; | ||
| 246 | } | ||
| 247 | |||
| 248 | std::vector<Common::ParamPackage> Mouse::GetInputDevices() const { | 247 | std::vector<Common::ParamPackage> Mouse::GetInputDevices() const { |
| 249 | std::vector<Common::ParamPackage> devices; | 248 | std::vector<Common::ParamPackage> devices; |
| 250 | devices.emplace_back(Common::ParamPackage{ | 249 | devices.emplace_back(Common::ParamPackage{ |
diff --git a/src/input_common/drivers/mouse.h b/src/input_common/drivers/mouse.h index b872c7a0f..0e8edcce1 100644 --- a/src/input_common/drivers/mouse.h +++ b/src/input_common/drivers/mouse.h | |||
| @@ -98,7 +98,6 @@ private: | |||
| 98 | void UpdateThread(std::stop_token stop_token); | 98 | void UpdateThread(std::stop_token stop_token); |
| 99 | void UpdateStickInput(); | 99 | void UpdateStickInput(); |
| 100 | void UpdateMotionInput(); | 100 | void UpdateMotionInput(); |
| 101 | void StopPanning(); | ||
| 102 | 101 | ||
| 103 | Common::Input::ButtonNames GetUIButtonName(const Common::ParamPackage& params) const; | 102 | Common::Input::ButtonNames GetUIButtonName(const Common::ParamPackage& params) const; |
| 104 | 103 | ||
| @@ -108,7 +107,6 @@ private: | |||
| 108 | Common::Vec3<float> last_motion_change; | 107 | Common::Vec3<float> last_motion_change; |
| 109 | Common::Vec2<int> wheel_position; | 108 | Common::Vec2<int> wheel_position; |
| 110 | bool button_pressed; | 109 | bool button_pressed; |
| 111 | int mouse_panning_timeout{}; | ||
| 112 | std::jthread update_thread; | 110 | std::jthread update_thread; |
| 113 | }; | 111 | }; |
| 114 | 112 | ||
diff --git a/src/input_common/drivers/sdl_driver.cpp b/src/input_common/drivers/sdl_driver.cpp index 9a0439bb5..9f26392b1 100644 --- a/src/input_common/drivers/sdl_driver.cpp +++ b/src/input_common/drivers/sdl_driver.cpp | |||
| @@ -150,6 +150,8 @@ public: | |||
| 150 | if (sdl_controller) { | 150 | if (sdl_controller) { |
| 151 | const auto type = SDL_GameControllerGetType(sdl_controller.get()); | 151 | const auto type = SDL_GameControllerGetType(sdl_controller.get()); |
| 152 | return (type == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO) || | 152 | return (type == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO) || |
| 153 | (type == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_JOYCON_LEFT) || | ||
| 154 | (type == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_JOYCON_RIGHT) || | ||
| 153 | (type == SDL_CONTROLLER_TYPE_PS5); | 155 | (type == SDL_CONTROLLER_TYPE_PS5); |
| 154 | } | 156 | } |
| 155 | return false; | 157 | return false; |
| @@ -228,9 +230,8 @@ public: | |||
| 228 | return false; | 230 | return false; |
| 229 | } | 231 | } |
| 230 | 232 | ||
| 231 | Common::Input::BatteryLevel GetBatteryLevel() { | 233 | Common::Input::BatteryLevel GetBatteryLevel(SDL_JoystickPowerLevel battery_level) { |
| 232 | const auto level = SDL_JoystickCurrentPowerLevel(sdl_joystick.get()); | 234 | switch (battery_level) { |
| 233 | switch (level) { | ||
| 234 | case SDL_JOYSTICK_POWER_EMPTY: | 235 | case SDL_JOYSTICK_POWER_EMPTY: |
| 235 | return Common::Input::BatteryLevel::Empty; | 236 | return Common::Input::BatteryLevel::Empty; |
| 236 | case SDL_JOYSTICK_POWER_LOW: | 237 | case SDL_JOYSTICK_POWER_LOW: |
| @@ -378,7 +379,6 @@ void SDLDriver::InitJoystick(int joystick_index) { | |||
| 378 | if (joystick_map.find(guid) == joystick_map.end()) { | 379 | if (joystick_map.find(guid) == joystick_map.end()) { |
| 379 | auto joystick = std::make_shared<SDLJoystick>(guid, 0, sdl_joystick, sdl_gamecontroller); | 380 | auto joystick = std::make_shared<SDLJoystick>(guid, 0, sdl_joystick, sdl_gamecontroller); |
| 380 | PreSetController(joystick->GetPadIdentifier()); | 381 | PreSetController(joystick->GetPadIdentifier()); |
| 381 | SetBattery(joystick->GetPadIdentifier(), joystick->GetBatteryLevel()); | ||
| 382 | joystick->EnableMotion(); | 382 | joystick->EnableMotion(); |
| 383 | joystick_map[guid].emplace_back(std::move(joystick)); | 383 | joystick_map[guid].emplace_back(std::move(joystick)); |
| 384 | return; | 384 | return; |
| @@ -398,7 +398,6 @@ void SDLDriver::InitJoystick(int joystick_index) { | |||
| 398 | const int port = static_cast<int>(joystick_guid_list.size()); | 398 | const int port = static_cast<int>(joystick_guid_list.size()); |
| 399 | auto joystick = std::make_shared<SDLJoystick>(guid, port, sdl_joystick, sdl_gamecontroller); | 399 | auto joystick = std::make_shared<SDLJoystick>(guid, port, sdl_joystick, sdl_gamecontroller); |
| 400 | PreSetController(joystick->GetPadIdentifier()); | 400 | PreSetController(joystick->GetPadIdentifier()); |
| 401 | SetBattery(joystick->GetPadIdentifier(), joystick->GetBatteryLevel()); | ||
| 402 | joystick->EnableMotion(); | 401 | joystick->EnableMotion(); |
| 403 | joystick_guid_list.emplace_back(std::move(joystick)); | 402 | joystick_guid_list.emplace_back(std::move(joystick)); |
| 404 | } | 403 | } |
| @@ -438,8 +437,6 @@ void SDLDriver::HandleGameControllerEvent(const SDL_Event& event) { | |||
| 438 | if (const auto joystick = GetSDLJoystickBySDLID(event.jbutton.which)) { | 437 | if (const auto joystick = GetSDLJoystickBySDLID(event.jbutton.which)) { |
| 439 | const PadIdentifier identifier = joystick->GetPadIdentifier(); | 438 | const PadIdentifier identifier = joystick->GetPadIdentifier(); |
| 440 | SetButton(identifier, event.jbutton.button, true); | 439 | SetButton(identifier, event.jbutton.button, true); |
| 441 | // Battery doesn't trigger an event so just update every button press | ||
| 442 | SetBattery(identifier, joystick->GetBatteryLevel()); | ||
| 443 | } | 440 | } |
| 444 | break; | 441 | break; |
| 445 | } | 442 | } |
| @@ -466,6 +463,13 @@ void SDLDriver::HandleGameControllerEvent(const SDL_Event& event) { | |||
| 466 | } | 463 | } |
| 467 | break; | 464 | break; |
| 468 | } | 465 | } |
| 466 | case SDL_JOYBATTERYUPDATED: { | ||
| 467 | if (auto joystick = GetSDLJoystickBySDLID(event.jbattery.which)) { | ||
| 468 | const PadIdentifier identifier = joystick->GetPadIdentifier(); | ||
| 469 | SetBattery(identifier, joystick->GetBatteryLevel(event.jbattery.level)); | ||
| 470 | } | ||
| 471 | break; | ||
| 472 | } | ||
| 469 | case SDL_JOYDEVICEREMOVED: | 473 | case SDL_JOYDEVICEREMOVED: |
| 470 | LOG_DEBUG(Input, "Controller removed with Instance_ID {}", event.jdevice.which); | 474 | LOG_DEBUG(Input, "Controller removed with Instance_ID {}", event.jdevice.which); |
| 471 | CloseJoystick(SDL_JoystickFromInstanceID(event.jdevice.which)); | 475 | CloseJoystick(SDL_JoystickFromInstanceID(event.jdevice.which)); |
| @@ -483,6 +487,10 @@ void SDLDriver::CloseJoysticks() { | |||
| 483 | } | 487 | } |
| 484 | 488 | ||
| 485 | SDLDriver::SDLDriver(std::string input_engine_) : InputEngine(std::move(input_engine_)) { | 489 | SDLDriver::SDLDriver(std::string input_engine_) : InputEngine(std::move(input_engine_)) { |
| 490 | // Set our application name. Currently passed to DBus by SDL and visible to the user through | ||
| 491 | // their desktop environment. | ||
| 492 | SDL_SetHint(SDL_HINT_APP_NAME, "yuzu"); | ||
| 493 | |||
| 486 | if (!Settings::values.enable_raw_input) { | 494 | if (!Settings::values.enable_raw_input) { |
| 487 | // Disable raw input. When enabled this setting causes SDL to die when a web applet opens | 495 | // Disable raw input. When enabled this setting causes SDL to die when a web applet opens |
| 488 | SDL_SetHint(SDL_HINT_JOYSTICK_RAWINPUT, "0"); | 496 | SDL_SetHint(SDL_HINT_JOYSTICK_RAWINPUT, "0"); |
| @@ -501,6 +509,9 @@ SDLDriver::SDLDriver(std::string input_engine_) : InputEngine(std::move(input_en | |||
| 501 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_JOY_CONS, "0"); | 509 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_JOY_CONS, "0"); |
| 502 | } else { | 510 | } else { |
| 503 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_JOY_CONS, "1"); | 511 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_JOY_CONS, "1"); |
| 512 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_JOYCON_HOME_LED, "0"); | ||
| 513 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_COMBINE_JOY_CONS, "0"); | ||
| 514 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_VERTICAL_JOY_CONS, "1"); | ||
| 504 | } | 515 | } |
| 505 | 516 | ||
| 506 | // Disable hidapi drivers for pro controllers when the custom joycon driver is enabled | 517 | // Disable hidapi drivers for pro controllers when the custom joycon driver is enabled |
| @@ -508,8 +519,11 @@ SDLDriver::SDLDriver(std::string input_engine_) : InputEngine(std::move(input_en | |||
| 508 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH, "0"); | 519 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH, "0"); |
| 509 | } else { | 520 | } else { |
| 510 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH, "1"); | 521 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH, "1"); |
| 522 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH_HOME_LED, "0"); | ||
| 511 | } | 523 | } |
| 512 | 524 | ||
| 525 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_SWITCH_PLAYER_LED, "1"); | ||
| 526 | |||
| 513 | // Disable hidapi driver for xbox. Already default on Windows, this causes conflict with native | 527 | // Disable hidapi driver for xbox. Already default on Windows, this causes conflict with native |
| 514 | // driver on Linux. | 528 | // driver on Linux. |
| 515 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_XBOX, "0"); | 529 | SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_XBOX, "0"); |
| @@ -789,7 +803,9 @@ ButtonMapping SDLDriver::GetButtonMappingForDevice(const Common::ParamPackage& p | |||
| 789 | // This list also excludes Screenshot since there's not really a mapping for that | 803 | // This list also excludes Screenshot since there's not really a mapping for that |
| 790 | ButtonBindings switch_to_sdl_button; | 804 | ButtonBindings switch_to_sdl_button; |
| 791 | 805 | ||
| 792 | if (SDL_GameControllerGetType(controller) == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO) { | 806 | if (SDL_GameControllerGetType(controller) == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO || |
| 807 | SDL_GameControllerGetType(controller) == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_JOYCON_LEFT || | ||
| 808 | SDL_GameControllerGetType(controller) == SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_JOYCON_RIGHT) { | ||
| 793 | switch_to_sdl_button = GetNintendoButtonBinding(joystick); | 809 | switch_to_sdl_button = GetNintendoButtonBinding(joystick); |
| 794 | } else { | 810 | } else { |
| 795 | switch_to_sdl_button = GetDefaultButtonBinding(); | 811 | switch_to_sdl_button = GetDefaultButtonBinding(); |