From e2c4b4d3064707ac5310e755566f8c51e23ce252 Mon Sep 17 00:00:00 2001 From: SamGondelman Date: Fri, 3 Jun 2016 10:17:08 -0700 Subject: [PATCH] added haptic support to sdl and touch (needs testing) --- plugins/hifiSdl2/src/Joystick.cpp | 11 ++++++- plugins/hifiSdl2/src/Joystick.h | 3 ++ plugins/hifiSdl2/src/SDL2Manager.cpp | 2 +- .../oculus/src/OculusControllerManager.cpp | 31 +++++++++++++++++++ plugins/oculus/src/OculusControllerManager.h | 11 +++++++ 5 files changed, 56 insertions(+), 2 deletions(-) diff --git a/plugins/hifiSdl2/src/Joystick.cpp b/plugins/hifiSdl2/src/Joystick.cpp index a109656489..136c021913 100644 --- a/plugins/hifiSdl2/src/Joystick.cpp +++ b/plugins/hifiSdl2/src/Joystick.cpp @@ -21,9 +21,10 @@ Joystick::Joystick(SDL_JoystickID instanceId, SDL_GameController* sdlGameControl InputDevice("GamePad"), _sdlGameController(sdlGameController), _sdlJoystick(SDL_GameControllerGetJoystick(_sdlGameController)), + _sdlHaptic(SDL_HapticOpenFromJoystick(_sdlJoystick)), _instanceId(instanceId) { - + SDL_HapticRumbleInit(_sdlHaptic); } Joystick::~Joystick() { @@ -31,6 +32,7 @@ Joystick::~Joystick() { } void Joystick::closeJoystick() { + SDL_HapticClose(_sdlHaptic); SDL_GameControllerClose(_sdlGameController); } @@ -62,6 +64,13 @@ void Joystick::handleButtonEvent(const SDL_ControllerButtonEvent& event) { } } +bool Joystick::triggerHapticPulse(float strength, float duration, bool leftHand) { + if (SDL_HapticRumblePlay(_sdlHaptic, strength, duration) != 0) { + return false; + } + return true; +} + controller::Input::NamedVector Joystick::getAvailableInputs() const { using namespace controller; static const Input::NamedVector availableInputs{ diff --git a/plugins/hifiSdl2/src/Joystick.h b/plugins/hifiSdl2/src/Joystick.h index e2eaeaef8b..4f785f85ce 100644 --- a/plugins/hifiSdl2/src/Joystick.h +++ b/plugins/hifiSdl2/src/Joystick.h @@ -36,6 +36,8 @@ public: virtual QString getDefaultMappingConfig() const override; virtual void update(float deltaTime, const controller::InputCalibrationData& inputCalibrationData) override; virtual void focusOutEvent() override; + + bool triggerHapticPulse(float strength, float duration, bool leftHand) override; Joystick() : InputDevice("GamePad") {} ~Joystick(); @@ -52,6 +54,7 @@ public: private: SDL_GameController* _sdlGameController; SDL_Joystick* _sdlJoystick; + SDL_Haptic* _sdlHaptic; SDL_JoystickID _instanceId; }; diff --git a/plugins/hifiSdl2/src/SDL2Manager.cpp b/plugins/hifiSdl2/src/SDL2Manager.cpp index 0bdb68f830..09e783864c 100644 --- a/plugins/hifiSdl2/src/SDL2Manager.cpp +++ b/plugins/hifiSdl2/src/SDL2Manager.cpp @@ -49,7 +49,7 @@ SDL_JoystickID SDL2Manager::getInstanceId(SDL_GameController* controller) { } void SDL2Manager::init() { - bool initSuccess = (SDL_Init(SDL_INIT_GAMECONTROLLER) == 0); + bool initSuccess = (SDL_Init(SDL_INIT_GAMECONTROLLER | SDL_INIT_HAPTIC) == 0); if (initSuccess) { int joystickCount = SDL_NumJoysticks(); diff --git a/plugins/oculus/src/OculusControllerManager.cpp b/plugins/oculus/src/OculusControllerManager.cpp index 09ab6ec159..3151db1d90 100644 --- a/plugins/oculus/src/OculusControllerManager.cpp +++ b/plugins/oculus/src/OculusControllerManager.cpp @@ -55,6 +55,11 @@ bool OculusControllerManager::activate() { userInputMapper->registerDevice(_touch); } + _leftHapticTimer.setSingleShot(true); + _rightHapticTimer.setSingleShot(true); + connect(&_leftHapticTimer, SIGNAL(timeout()), this, SLOT(stopHapticPulse(true))); + connect(&_rightHapticTimer, SIGNAL(timeout()), this, SLOT(stopHapticPulse(false))); + return true; } @@ -105,6 +110,12 @@ void OculusControllerManager::pluginFocusOutEvent() { } } +void OculusControllerManager::stopHapticPulse(bool leftHand) { + if (_touch) { + _touch->stopHapticPulse(leftHand); + } +} + using namespace controller; static const std::vector> BUTTON_MAP { { @@ -228,6 +239,26 @@ void OculusControllerManager::TouchDevice::handlePose(float deltaTime, pose.velocity = toGlm(handPose.LinearVelocity); } +bool OculusControllerManager::TouchDevice::triggerHapticPulse(float strength, float duration, bool leftHand) { + auto handType = (leftHand ? ovrControllerType_LTouch : ovrControllerType_RTouch); + if (ovr_SetControllerVibration(_parent._session, handType, 1.0f, strength) != ovrSuccess) { + return false; + } + + if (leftHand) { + _parent._leftHapticTimer.start(duration); + } else { + _parent._rightHapticTimer.start(duration); + } + + return true; +} + +void OculusControllerManager::TouchDevice::stopHapticPulse(bool leftHand) { + auto handType = (leftHand ? ovrControllerType_LTouch : ovrControllerType_RTouch); + ovr_SetControllerVibration(_parent._session, handType, 0.0f, 0.0f); +} + controller::Input::NamedVector OculusControllerManager::TouchDevice::getAvailableInputs() const { using namespace controller; QVector availableInputs{ diff --git a/plugins/oculus/src/OculusControllerManager.h b/plugins/oculus/src/OculusControllerManager.h index 980e1286f8..20e5726dff 100644 --- a/plugins/oculus/src/OculusControllerManager.h +++ b/plugins/oculus/src/OculusControllerManager.h @@ -10,6 +10,7 @@ #define hifi__OculusControllerManager #include +#include #include #include @@ -32,6 +33,9 @@ public: void pluginFocusOutEvent() override; void pluginUpdate(float deltaTime, const controller::InputCalibrationData& inputCalibrationData) override; +private slots: + void stopHapticPulse(bool leftHand); + private: class OculusInputDevice : public controller::InputDevice { public: @@ -64,6 +68,11 @@ private: void update(float deltaTime, const controller::InputCalibrationData& inputCalibrationData) override; void focusOutEvent() override; + bool triggerHapticPulse(float strength, float duration, bool leftHand) override; + + private: + void stopHapticPulse(bool leftHand); + private: void handlePose(float deltaTime, const controller::InputCalibrationData& inputCalibrationData, ovrHandType hand, const ovrPoseStatef& handPose); int _trackedControllers { 0 }; @@ -73,6 +82,8 @@ private: ovrSession _session { nullptr }; ovrInputState _inputState {}; RemoteDevice::Pointer _remote; + QTimer _leftHapticTimer; + QTimer _rightHapticTimer; TouchDevice::Pointer _touch; static const QString NAME; };