diff options
| author | liamwhite <liamwhite@users.noreply.github.com> | 2022-10-25 12:13:18 -0400 | 
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-10-25 12:13:18 -0400 | 
| commit | 77803d96be3f6ec590b63966359b8f5fa56013db (patch) | |
| tree | 1c6b80a6ee305d457319ccacd71de333eaaf43f9 | |
| parent | fa913a702f94818fcddf4ffd3aaded41a41b3a3b (diff) | |
| parent | 7f66050f0c383a5c7d82c5c58098f819d4e1e0bc (diff) | |
Merge pull request #9107 from german77/gidoly_rules
input_common: cache vibration tests
| -rw-r--r-- | src/common/input.h | 5 | ||||
| -rw-r--r-- | src/core/hid/emulated_controller.cpp | 45 | ||||
| -rw-r--r-- | src/core/hid/emulated_controller.h | 5 | ||||
| -rw-r--r-- | src/core/hle/service/hid/controllers/npad.cpp | 4 | ||||
| -rw-r--r-- | src/input_common/drivers/gc_adapter.cpp | 6 | ||||
| -rw-r--r-- | src/input_common/drivers/gc_adapter.h | 4 | ||||
| -rw-r--r-- | src/input_common/drivers/sdl_driver.cpp | 64 | ||||
| -rw-r--r-- | src/input_common/drivers/sdl_driver.h | 4 | ||||
| -rw-r--r-- | src/input_common/input_engine.h | 7 | ||||
| -rw-r--r-- | src/input_common/input_poller.cpp | 6 | 
10 files changed, 93 insertions, 57 deletions
| diff --git a/src/common/input.h b/src/common/input.h index b533f3844..cb30b7254 100644 --- a/src/common/input.h +++ b/src/common/input.h @@ -100,7 +100,6 @@ enum class CameraError {  enum class VibrationAmplificationType {      Linear,      Exponential, -    Test,  };  // Analog properties for calibration @@ -325,6 +324,10 @@ public:          return VibrationError::NotSupported;      } +    virtual bool IsVibrationEnabled() { +        return false; +    } +      virtual PollingError SetPollingMode([[maybe_unused]] PollingMode polling_mode) {          return PollingError::NotSupported;      } diff --git a/src/core/hid/emulated_controller.cpp b/src/core/hid/emulated_controller.cpp index 57eff72fe..b17b00f2c 100644 --- a/src/core/hid/emulated_controller.cpp +++ b/src/core/hid/emulated_controller.cpp @@ -970,14 +970,7 @@ bool EmulatedController::SetVibration(std::size_t device_index, VibrationValue v             Common::Input::VibrationError::None;  } -bool EmulatedController::TestVibration(std::size_t device_index) { -    if (device_index >= output_devices.size()) { -        return false; -    } -    if (!output_devices[device_index]) { -        return false; -    } - +bool EmulatedController::IsVibrationEnabled(std::size_t device_index) {      const auto player_index = NpadIdTypeToIndex(npad_id_type);      const auto& player = Settings::values.players.GetValue()[player_index]; @@ -985,31 +978,15 @@ bool EmulatedController::TestVibration(std::size_t device_index) {          return false;      } -    const Common::Input::VibrationStatus test_vibration = { -        .low_amplitude = 0.001f, -        .low_frequency = DEFAULT_VIBRATION_VALUE.low_frequency, -        .high_amplitude = 0.001f, -        .high_frequency = DEFAULT_VIBRATION_VALUE.high_frequency, -        .type = Common::Input::VibrationAmplificationType::Test, -    }; - -    const Common::Input::VibrationStatus zero_vibration = { -        .low_amplitude = DEFAULT_VIBRATION_VALUE.low_amplitude, -        .low_frequency = DEFAULT_VIBRATION_VALUE.low_frequency, -        .high_amplitude = DEFAULT_VIBRATION_VALUE.high_amplitude, -        .high_frequency = DEFAULT_VIBRATION_VALUE.high_frequency, -        .type = Common::Input::VibrationAmplificationType::Test, -    }; - -    // Send a slight vibration to test for rumble support -    output_devices[device_index]->SetVibration(test_vibration); +    if (device_index >= output_devices.size()) { +        return false; +    } -    // Wait for about 15ms to ensure the controller is ready for the stop command -    std::this_thread::sleep_for(std::chrono::milliseconds(15)); +    if (!output_devices[device_index]) { +        return false; +    } -    // Stop any vibration and return the result -    return output_devices[device_index]->SetVibration(zero_vibration) == -           Common::Input::VibrationError::None; +    return output_devices[device_index]->IsVibrationEnabled();  }  bool EmulatedController::SetPollingMode(Common::Input::PollingMode polling_mode) { @@ -1234,12 +1211,6 @@ bool EmulatedController::IsConnected(bool get_temporary_value) const {      return is_connected;  } -bool EmulatedController::IsVibrationEnabled() const { -    const auto player_index = NpadIdTypeToIndex(npad_id_type); -    const auto& player = Settings::values.players.GetValue()[player_index]; -    return player.vibration_enabled; -} -  NpadIdType EmulatedController::GetNpadIdType() const {      std::scoped_lock lock{mutex};      return npad_id_type; diff --git a/src/core/hid/emulated_controller.h b/src/core/hid/emulated_controller.h index 319226bf8..d004ca56a 100644 --- a/src/core/hid/emulated_controller.h +++ b/src/core/hid/emulated_controller.h @@ -206,9 +206,6 @@ public:       */      bool IsConnected(bool get_temporary_value = false) const; -    /// Returns true if vibration is enabled -    bool IsVibrationEnabled() const; -      /// Removes all callbacks created from input devices      void UnloadInput(); @@ -339,7 +336,7 @@ public:       * Sends a small vibration to the output device       * @return true if SetVibration was successfull       */ -    bool TestVibration(std::size_t device_index); +    bool IsVibrationEnabled(std::size_t device_index);      /**       * Sets the desired data to be polled from a controller diff --git a/src/core/hle/service/hid/controllers/npad.cpp b/src/core/hle/service/hid/controllers/npad.cpp index 3b26e96de..2f871de31 100644 --- a/src/core/hle/service/hid/controllers/npad.cpp +++ b/src/core/hle/service/hid/controllers/npad.cpp @@ -868,7 +868,7 @@ bool Controller_NPad::VibrateControllerAtIndex(Core::HID::NpadIdType npad_id,          return false;      } -    if (!controller.device->IsVibrationEnabled()) { +    if (!controller.device->IsVibrationEnabled(device_index)) {          if (controller.vibration[device_index].latest_vibration_value.low_amplitude != 0.0f ||              controller.vibration[device_index].latest_vibration_value.high_amplitude != 0.0f) {              // Send an empty vibration to stop any vibrations. @@ -1001,7 +1001,7 @@ void Controller_NPad::InitializeVibrationDeviceAtIndex(Core::HID::NpadIdType npa      }      controller.vibration[device_index].device_mounted = -        controller.device->TestVibration(device_index); +        controller.device->IsVibrationEnabled(device_index);  }  void Controller_NPad::SetPermitVibrationSession(bool permit_vibration_session) { diff --git a/src/input_common/drivers/gc_adapter.cpp b/src/input_common/drivers/gc_adapter.cpp index f4dd24e7d..826fa2109 100644 --- a/src/input_common/drivers/gc_adapter.cpp +++ b/src/input_common/drivers/gc_adapter.cpp @@ -324,7 +324,7 @@ bool GCAdapter::GetGCEndpoint(libusb_device* device) {      return true;  } -Common::Input::VibrationError GCAdapter::SetRumble( +Common::Input::VibrationError GCAdapter::SetVibration(      const PadIdentifier& identifier, const Common::Input::VibrationStatus& vibration) {      const auto mean_amplitude = (vibration.low_amplitude + vibration.high_amplitude) * 0.5f;      const auto processed_amplitude = @@ -338,6 +338,10 @@ Common::Input::VibrationError GCAdapter::SetRumble(      return Common::Input::VibrationError::None;  } +bool GCAdapter::IsVibrationEnabled([[maybe_unused]] const PadIdentifier& identifier) { +    return rumble_enabled; +} +  void GCAdapter::UpdateVibrations() {      // Use 8 states to keep the switching between on/off fast enough for      // a human to feel different vibration strenght diff --git a/src/input_common/drivers/gc_adapter.h b/src/input_common/drivers/gc_adapter.h index 8682da847..7f81767f7 100644 --- a/src/input_common/drivers/gc_adapter.h +++ b/src/input_common/drivers/gc_adapter.h @@ -25,9 +25,11 @@ public:      explicit GCAdapter(std::string input_engine_);      ~GCAdapter() override; -    Common::Input::VibrationError SetRumble( +    Common::Input::VibrationError SetVibration(          const PadIdentifier& identifier, const Common::Input::VibrationStatus& vibration) override; +    bool IsVibrationEnabled(const PadIdentifier& identifier) override; +      /// Used for automapping features      std::vector<Common::ParamPackage> GetInputDevices() const override;      ButtonMapping GetButtonMappingForDevice(const Common::ParamPackage& params) override; diff --git a/src/input_common/drivers/sdl_driver.cpp b/src/input_common/drivers/sdl_driver.cpp index c175a8853..45ce588f0 100644 --- a/src/input_common/drivers/sdl_driver.cpp +++ b/src/input_common/drivers/sdl_driver.cpp @@ -114,6 +114,20 @@ public:          }          return false;      } + +    void EnableVibration(bool is_enabled) { +        has_vibration = is_enabled; +        is_vibration_tested = true; +    } + +    bool HasVibration() const { +        return has_vibration; +    } + +    bool IsVibrationTested() const { +        return is_vibration_tested; +    } +      /**       * The Pad identifier of the joystick       */ @@ -236,6 +250,8 @@ private:      u64 last_motion_update{};      bool has_gyro{false};      bool has_accel{false}; +    bool has_vibration{false}; +    bool is_vibration_tested{false};      BasicMotion motion;  }; @@ -517,7 +533,7 @@ std::vector<Common::ParamPackage> SDLDriver::GetInputDevices() const {      return devices;  } -Common::Input::VibrationError SDLDriver::SetRumble( +Common::Input::VibrationError SDLDriver::SetVibration(      const PadIdentifier& identifier, const Common::Input::VibrationStatus& vibration) {      const auto joystick =          GetSDLJoystickByGUID(identifier.guid.RawString(), static_cast<int>(identifier.port)); @@ -546,13 +562,6 @@ Common::Input::VibrationError SDLDriver::SetRumble(          .type = Common::Input::VibrationAmplificationType::Exponential,      }; -    if (vibration.type == Common::Input::VibrationAmplificationType::Test) { -        if (!joystick->RumblePlay(new_vibration)) { -            return Common::Input::VibrationError::Unknown; -        } -        return Common::Input::VibrationError::None; -    } -      vibration_queue.Push(VibrationRequest{          .identifier = identifier,          .vibration = new_vibration, @@ -561,6 +570,45 @@ Common::Input::VibrationError SDLDriver::SetRumble(      return Common::Input::VibrationError::None;  } +bool SDLDriver::IsVibrationEnabled(const PadIdentifier& identifier) { +    const auto joystick = +        GetSDLJoystickByGUID(identifier.guid.RawString(), static_cast<int>(identifier.port)); + +    constexpr Common::Input::VibrationStatus test_vibration{ +        .low_amplitude = 1, +        .low_frequency = 160.0f, +        .high_amplitude = 1, +        .high_frequency = 320.0f, +        .type = Common::Input::VibrationAmplificationType::Exponential, +    }; + +    constexpr Common::Input::VibrationStatus zero_vibration{ +        .low_amplitude = 0, +        .low_frequency = 160.0f, +        .high_amplitude = 0, +        .high_frequency = 320.0f, +        .type = Common::Input::VibrationAmplificationType::Exponential, +    }; + +    if (joystick->IsVibrationTested()) { +        return joystick->HasVibration(); +    } + +    // First vibration might fail +    joystick->RumblePlay(test_vibration); + +    // Wait for about 15ms to ensure the controller is ready for the stop command +    std::this_thread::sleep_for(std::chrono::milliseconds(15)); + +    if (!joystick->RumblePlay(zero_vibration)) { +        joystick->EnableVibration(false); +        return false; +    } + +    joystick->EnableVibration(true); +    return true; +} +  void SDLDriver::SendVibrations() {      while (!vibration_queue.Empty()) {          VibrationRequest request; diff --git a/src/input_common/drivers/sdl_driver.h b/src/input_common/drivers/sdl_driver.h index fc3a44572..d1b4471cf 100644 --- a/src/input_common/drivers/sdl_driver.h +++ b/src/input_common/drivers/sdl_driver.h @@ -61,9 +61,11 @@ public:      bool IsStickInverted(const Common::ParamPackage& params) override; -    Common::Input::VibrationError SetRumble( +    Common::Input::VibrationError SetVibration(          const PadIdentifier& identifier, const Common::Input::VibrationStatus& vibration) override; +    bool IsVibrationEnabled(const PadIdentifier& identifier) override; +  private:      struct VibrationRequest {          PadIdentifier identifier; diff --git a/src/input_common/input_engine.h b/src/input_common/input_engine.h index cfbdb26bd..d4c264a8e 100644 --- a/src/input_common/input_engine.h +++ b/src/input_common/input_engine.h @@ -108,12 +108,17 @@ public:                           [[maybe_unused]] const Common::Input::LedStatus& led_status) {}      // Sets rumble to a controller -    virtual Common::Input::VibrationError SetRumble( +    virtual Common::Input::VibrationError SetVibration(          [[maybe_unused]] const PadIdentifier& identifier,          [[maybe_unused]] const Common::Input::VibrationStatus& vibration) {          return Common::Input::VibrationError::NotSupported;      } +    // Returns true if device supports vibrations +    virtual bool IsVibrationEnabled([[maybe_unused]] const PadIdentifier& identifier) { +        return false; +    } +      // Sets polling mode to a controller      virtual Common::Input::PollingError SetPollingMode(          [[maybe_unused]] const PadIdentifier& identifier, diff --git a/src/input_common/input_poller.cpp b/src/input_common/input_poller.cpp index ccc3076ca..4ac182147 100644 --- a/src/input_common/input_poller.cpp +++ b/src/input_common/input_poller.cpp @@ -763,7 +763,11 @@ public:      Common::Input::VibrationError SetVibration(          const Common::Input::VibrationStatus& vibration_status) override { -        return input_engine->SetRumble(identifier, vibration_status); +        return input_engine->SetVibration(identifier, vibration_status); +    } + +    bool IsVibrationEnabled() override { +        return input_engine->IsVibrationEnabled(identifier);      }      Common::Input::PollingError SetPollingMode(Common::Input::PollingMode polling_mode) override { | 
