Compare commits

...

1 Commits

Author SHA1 Message Date
german77
cff2d507ac input_common/sdl: Implement HD rumble 2021-07-27 13:12:55 -05:00
3 changed files with 28 additions and 9 deletions

View File

@@ -64,6 +64,7 @@ if (YUZU_USE_EXTERNAL_SDL2)
endforeach() endforeach()
option(HIDAPI "" ON) option(HIDAPI "" ON)
set(WAYLAND_LIBDECOR OFF CACHE BOOL "" FORCE)
endif() endif()
set(SDL_STATIC ON) set(SDL_STATIC ON)
set(SDL_SHARED OFF) set(SDL_SHARED OFF)

2
externals/SDL vendored

View File

@@ -77,6 +77,14 @@ public:
} }
} }
bool HasHDRumble() const {
if (sdl_controller) {
return (SDL_GameControllerGetType(sdl_controller.get()) ==
SDL_CONTROLLER_TYPE_NINTENDO_SWITCH_PRO);
}
return false;
}
void SetButton(int button, bool value) { void SetButton(int button, bool value) {
std::lock_guard lock{mutex}; std::lock_guard lock{mutex};
state.buttons.insert_or_assign(button, value); state.buttons.insert_or_assign(button, value);
@@ -160,9 +168,15 @@ public:
return static_cast<float>(state.axes.at(axis)) / (32767.0f * range); return static_cast<float>(state.axes.at(axis)) / (32767.0f * range);
} }
bool RumblePlay(u16 amp_low, u16 amp_high) { bool RumblePlay(u16 amp_low, u16 amp_high, u16 freq_low, u16 freq_high) {
constexpr u32 rumble_max_duration_ms = 1000; constexpr u32 rumble_max_duration_ms = 1000;
if (HasHDRumble()) {
const u64 effect =
(u64{amp_low} << 48) | (u64{amp_low} << 32) | (u64{amp_low} << 16) | freq_high;
return SDL_GameControllerSendEffect(sdl_controller.get(), &effect, sizeof(effect)) == 0;
}
if (sdl_controller) { if (sdl_controller) {
return SDL_GameControllerRumble(sdl_controller.get(), amp_low, amp_high, return SDL_GameControllerRumble(sdl_controller.get(), amp_low, amp_high,
rumble_max_duration_ms) != -1; rumble_max_duration_ms) != -1;
@@ -563,20 +577,24 @@ public:
: joystick(std::move(joystick_)) {} : joystick(std::move(joystick_)) {}
u8 GetStatus() const override { u8 GetStatus() const override {
joystick->RumblePlay(1, 1); joystick->RumblePlay(1, 1, 160, 320);
return joystick->RumblePlay(0, 0); return joystick->RumblePlay(0, 0, 160, 320);
} }
bool SetRumblePlay(f32 amp_low, [[maybe_unused]] f32 freq_low, f32 amp_high, bool SetRumblePlay(f32 amp_low, f32 freq_low, f32 amp_high, f32 freq_high) const override {
[[maybe_unused]] f32 freq_high) const override { const bool has_hd_rumble = joystick->HasHDRumble();
const auto process_amplitude = [](f32 amplitude) { const auto process_amplitude = [has_hd_rumble](f32 amplitude) {
if (has_hd_rumble) {
return static_cast<u16>(amplitude * 0xFFFF);
}
// Adjust amplitude for non HD controllers
return static_cast<u16>((amplitude + std::pow(amplitude, 0.3f)) * 0.5f * 0xFFFF); return static_cast<u16>((amplitude + std::pow(amplitude, 0.3f)) * 0.5f * 0xFFFF);
}; };
const auto processed_amp_low = process_amplitude(amp_low); const auto processed_amp_low = process_amplitude(amp_low);
const auto processed_amp_high = process_amplitude(amp_high); const auto processed_amp_high = process_amplitude(amp_high);
return joystick->RumblePlay(processed_amp_low, processed_amp_high); return joystick->RumblePlay(processed_amp_low, processed_amp_high,
static_cast<u16>(freq_low), static_cast<u16>(freq_high));
} }
private: private: