diff --git a/libraries/input-plugins/src/input-plugins/ViveControllerManager.cpp b/libraries/input-plugins/src/input-plugins/ViveControllerManager.cpp index 430fe9167d..0316961f7c 100644 --- a/libraries/input-plugins/src/input-plugins/ViveControllerManager.cpp +++ b/libraries/input-plugins/src/input-plugins/ViveControllerManager.cpp @@ -13,19 +13,29 @@ #include -//#include #include +#include "NumericalConstants.h" #include "UserActivityLogger.h" #include Q_DECLARE_LOGGING_CATEGORY(inputplugins) Q_LOGGING_CATEGORY(inputplugins, "hifi.inputplugins") - extern vr::IVRSystem *_hmd; extern vr::TrackedDevicePose_t _trackedDevicePose[vr::k_unMaxTrackedDeviceCount]; extern mat4 _trackedDevicePoseMat4[vr::k_unMaxTrackedDeviceCount]; +const unsigned int LEFT_MASK = 0U; +const unsigned int RIGHT_MASK = 1U; + +const uint64_t VR_BUTTON_A = 1U << 1; +const uint64_t VR_GRIP_BUTTON = 1U << 2; +const uint64_t VR_TRACKPAD_BUTTON = 1ULL << 32; + +const unsigned int BUTTON_A = 1U << 1; +const unsigned int GRIP_BUTTON = 1U << 2; +const unsigned int TRACKPAD_BUTTON = 1U << 3; + ViveControllerManager& ViveControllerManager::getInstance() { static ViveControllerManager sharedInstance; return sharedInstance; @@ -57,61 +67,64 @@ void ViveControllerManager::update() { if (!_hmd) { return; } + _buttonPressedMap.clear(); if (_isInitialized && _isEnabled) { PerformanceTimer perfTimer("Vive Controllers"); - int trackedControllerCount = 0; + int numTrackedControllers = 0; - for (vr::TrackedDeviceIndex_t unTrackedDevice = vr::k_unTrackedDeviceIndex_Hmd + 1; - unTrackedDevice < vr::k_unMaxTrackedDeviceCount && trackedControllerCount < 2; ++unTrackedDevice) { + for (vr::TrackedDeviceIndex_t device = vr::k_unTrackedDeviceIndex_Hmd + 1; + device < vr::k_unMaxTrackedDeviceCount && numTrackedControllers < 2; ++device) { - if (!_hmd->IsTrackedDeviceConnected(unTrackedDevice)) { + if (!_hmd->IsTrackedDeviceConnected(device)) { continue; } - if(_hmd->GetTrackedDeviceClass(unTrackedDevice) != vr::TrackedDeviceClass_Controller) { + if(_hmd->GetTrackedDeviceClass(device) != vr::TrackedDeviceClass_Controller) { + continue; + } + + if (!_trackedDevicePose[device].bPoseIsValid) { continue; } - trackedControllerCount++; + numTrackedControllers++; - if(!_trackedDevicePose[unTrackedDevice].bPoseIsValid) { - continue; - } - - const mat4& mat = _trackedDevicePoseMat4[unTrackedDevice]; + const mat4& mat = _trackedDevicePoseMat4[device]; - handlePoseEvent(mat, trackedControllerCount - 1); + handlePoseEvent(mat, numTrackedControllers - 1); // handle inputs - //vr::VRControllerState_t* controllerState; - //if(_hmd->GetControllerState(unTrackedDevice, controllerState)) { - // - //} - + vr::VRControllerState_t controllerState = vr::VRControllerState_t(); + if (_hmd->GetControllerState(device, &controllerState)) { + handleButtonEvent(controllerState.ulButtonPressed, numTrackedControllers - 1); + for (int i = 0; i < 5; i++) { + handleAxisEvent(Axis(i), controllerState.rAxis[i].x, controllerState.rAxis[i].y, numTrackedControllers - 1); + } + } } auto userInputMapper = DependencyManager::get(); - if (trackedControllerCount == 0) { + if (numTrackedControllers == 0) { if (_deviceID != 0) { userInputMapper->removeDevice(_deviceID); _deviceID = 0; _poseStateMap[makeInput(LEFT_HAND).getChannel()] = UserInputMapper::PoseValue(); _poseStateMap[makeInput(RIGHT_HAND).getChannel()] = UserInputMapper::PoseValue(); } - _trackedControllers = trackedControllerCount; + _trackedControllers = numTrackedControllers; return; } - if (_trackedControllers == 0 && trackedControllerCount > 0) { + if (_trackedControllers == 0 && numTrackedControllers > 0) { registerToUserInputMapper(*userInputMapper); assignDefaultInputMapping(*userInputMapper); UserActivityLogger::getInstance().connectedDevice("spatial_controller", "steamVR"); } - _trackedControllers = trackedControllerCount; + _trackedControllers = numTrackedControllers; } } @@ -120,18 +133,27 @@ void ViveControllerManager::focusOutEvent() { _buttonPressedMap.clear(); }; -void ViveControllerManager::handleAxisEvent(float stickX, float stickY, float trigger, int index) { -// _axisStateMap[makeInput(AXIS_Y_POS, index).getChannel()] = (stickY > 0.0f) ? stickY : 0.0f; -// _axisStateMap[makeInput(AXIS_Y_NEG, index).getChannel()] = (stickY < 0.0f) ? -stickY : 0.0f; -// _axisStateMap[makeInput(AXIS_X_POS, index).getChannel()] = (stickX > 0.0f) ? stickX : 0.0f; -// _axisStateMap[makeInput(AXIS_X_NEG, index).getChannel()] = (stickX < 0.0f) ? -stickX : 0.0f; -// _axisStateMap[makeInput(BACK_TRIGGER, index).getChannel()] = trigger; +void ViveControllerManager::handleAxisEvent(Axis axis, float x, float y, int index) { + if (axis == TRACKPAD_AXIS) { + _axisStateMap[makeInput(AXIS_Y_POS, index).getChannel()] = (y > 0.0f) ? y : 0.0f; + _axisStateMap[makeInput(AXIS_Y_NEG, index).getChannel()] = (y < 0.0f) ? -y : 0.0f; + _axisStateMap[makeInput(AXIS_X_POS, index).getChannel()] = (x > 0.0f) ? x : 0.0f; + _axisStateMap[makeInput(AXIS_X_NEG, index).getChannel()] = (x < 0.0f) ? -x : 0.0f; + } else if (axis == TRIGGER_AXIS) { + _axisStateMap[makeInput(BACK_TRIGGER, index).getChannel()] = x; + } } -void ViveControllerManager::handleButtonEvent(unsigned int buttons, int index) { -// if (buttons & BUTTON_0) { -// _buttonPressedMap.insert(makeInput(BUTTON_0, index).getChannel()); -// } +void ViveControllerManager::handleButtonEvent(uint64_t buttons, int index) { + if (buttons & VR_BUTTON_A) { + _buttonPressedMap.insert(makeInput(BUTTON_A, index).getChannel()); + } + if (buttons & VR_GRIP_BUTTON) { + _buttonPressedMap.insert(makeInput(GRIP_BUTTON, index).getChannel()); + } + if (buttons & VR_TRACKPAD_BUTTON) { + _buttonPressedMap.insert(makeInput(TRACKPAD_BUTTON, index).getChannel()); + } } void ViveControllerManager::handlePoseEvent(const mat4& mat, int index) { @@ -140,8 +162,15 @@ void ViveControllerManager::handlePoseEvent(const mat4& mat, int index) { glm::vec3 position = glm::vec3(mat[3][0], mat[3][1], mat[3][2]) - headPos; glm::quat rotation = glm::quat_cast(mat); - //rotation = glm::angleAxis(PI, glm::vec3(0.0f, 1.0f, 0.0f)) * rotation; - _poseStateMap[makeInput(JointChannel(index)).getChannel()] = UserInputMapper::PoseValue(position, rotation); + + // Flip the rotation appropriately for each hand + if (index == LEFT_HAND) { + rotation = rotation * glm::angleAxis(PI, glm::vec3(1.0f, 0.0f, 0.0f)) * glm::angleAxis(PI_OVER_TWO, glm::vec3(0.0f, 0.0f, 1.0f)); + } else if (index == RIGHT_HAND) { + rotation = rotation * glm::angleAxis(PI, glm::vec3(1.0f, 0.0f, 0.0f)) * glm::angleAxis(PI + PI_OVER_TWO, glm::vec3(0.0f, 0.0f, 1.0f)); + } + + _poseStateMap[makeInput(JointChannel(index)).getChannel()] = UserInputMapper::PoseValue(position, - rotation); } void ViveControllerManager::registerToUserInputMapper(UserInputMapper& mapper) { @@ -154,35 +183,25 @@ void ViveControllerManager::registerToUserInputMapper(UserInputMapper& mapper) { proxy->getPose = [this](const UserInputMapper::Input& input, int timestamp) -> UserInputMapper::PoseValue { return this->getPose(input.getChannel()); }; proxy->getAvailabeInputs = [this] () -> QVector { QVector availableInputs; -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_0, 0), "Left Start")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_1, 0), "Left Button 1")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_2, 0), "Left Button 2")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_3, 0), "Left Button 3")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_4, 0), "Left Button 4")); -// -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_FWD, 0), "L1")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BACK_TRIGGER, 0), "L2")); -// -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_POS, 0), "Left Stick Up")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_NEG, 0), "Left Stick Down")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_POS, 0), "Left Stick Right")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_NEG, 0), "Left Stick Left")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_TRIGGER, 0), "Left Trigger Press")); -// -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_0, 1), "Right Start")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_1, 1), "Right Button 1")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_2, 1), "Right Button 2")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_3, 1), "Right Button 3")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_4, 1), "Right Button 4")); -// -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_FWD, 1), "R1")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BACK_TRIGGER, 1), "R2")); -// -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_POS, 1), "Right Stick Up")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_NEG, 1), "Right Stick Down")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_POS, 1), "Right Stick Right")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_NEG, 1), "Right Stick Left")); -// availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_TRIGGER, 1), "Right Trigger Press")); + availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_A, 0), "Left Button A")); + availableInputs.append(UserInputMapper::InputPair(makeInput(GRIP_BUTTON, 0), "Left Grip Button")); + availableInputs.append(UserInputMapper::InputPair(makeInput(TRACKPAD_BUTTON, 0), "Left Trackpad Button")); + + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_POS, 0), "Left Trackpad Up")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_NEG, 0), "Left Trackpad Down")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_POS, 0), "Left Trackpad Right")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_NEG, 0), "Left Trackpad Left")); + availableInputs.append(UserInputMapper::InputPair(makeInput(BACK_TRIGGER, 0), "Left Back Trigger")); + + availableInputs.append(UserInputMapper::InputPair(makeInput(BUTTON_A, 1), "Right Button A")); + availableInputs.append(UserInputMapper::InputPair(makeInput(GRIP_BUTTON, 1), "Right Grip Button")); + availableInputs.append(UserInputMapper::InputPair(makeInput(TRACKPAD_BUTTON, 1), "Right Trackpad Button")); + + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_POS, 1), "Right Trackpad Up")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_Y_NEG, 1), "Right Trackpad Down")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_POS, 1), "Right Trackpad Right")); + availableInputs.append(UserInputMapper::InputPair(makeInput(AXIS_X_NEG, 1), "Right Trackpad Left")); + availableInputs.append(UserInputMapper::InputPair(makeInput(BACK_TRIGGER, 1), "Right Back Trigger")); return availableInputs; }; @@ -196,36 +215,28 @@ void ViveControllerManager::registerToUserInputMapper(UserInputMapper& mapper) { void ViveControllerManager::assignDefaultInputMapping(UserInputMapper& mapper) { const float JOYSTICK_MOVE_SPEED = 1.0f; - const float JOYSTICK_YAW_SPEED = 0.5f; - const float JOYSTICK_PITCH_SPEED = 0.25f; - const float BUTTON_MOVE_SPEED = 1.0f; const float BOOM_SPEED = 0.1f; -// // Left Joystick: Movement, strafing -// mapper.addInputChannel(UserInputMapper::LONGITUDINAL_FORWARD, makeInput(AXIS_Y_POS, 0), JOYSTICK_MOVE_SPEED); -// mapper.addInputChannel(UserInputMapper::LONGITUDINAL_BACKWARD, makeInput(AXIS_Y_NEG, 0), JOYSTICK_MOVE_SPEED); -// mapper.addInputChannel(UserInputMapper::LATERAL_RIGHT, makeInput(AXIS_X_POS, 0), JOYSTICK_MOVE_SPEED); -// mapper.addInputChannel(UserInputMapper::LATERAL_LEFT, makeInput(AXIS_X_NEG, 0), JOYSTICK_MOVE_SPEED); -// -// // Right Joystick: Camera orientation -// mapper.addInputChannel(UserInputMapper::YAW_RIGHT, makeInput(AXIS_X_POS, 1), JOYSTICK_YAW_SPEED); -// mapper.addInputChannel(UserInputMapper::YAW_LEFT, makeInput(AXIS_X_NEG, 1), JOYSTICK_YAW_SPEED); -// mapper.addInputChannel(UserInputMapper::PITCH_UP, makeInput(AXIS_Y_POS, 1), JOYSTICK_PITCH_SPEED); -// mapper.addInputChannel(UserInputMapper::PITCH_DOWN, makeInput(AXIS_Y_NEG, 1), JOYSTICK_PITCH_SPEED); -// -// // Buttons -// mapper.addInputChannel(UserInputMapper::BOOM_IN, makeInput(BUTTON_3, 0), BOOM_SPEED); -// mapper.addInputChannel(UserInputMapper::BOOM_OUT, makeInput(BUTTON_1, 0), BOOM_SPEED); -// -// mapper.addInputChannel(UserInputMapper::VERTICAL_UP, makeInput(BUTTON_3, 1), BUTTON_MOVE_SPEED); -// mapper.addInputChannel(UserInputMapper::VERTICAL_DOWN, makeInput(BUTTON_1, 1), BUTTON_MOVE_SPEED); -// -// mapper.addInputChannel(UserInputMapper::SHIFT, makeInput(BUTTON_2, 0)); -// mapper.addInputChannel(UserInputMapper::SHIFT, makeInput(BUTTON_2, 1)); -// -// mapper.addInputChannel(UserInputMapper::ACTION1, makeInput(BUTTON_4, 0)); -// mapper.addInputChannel(UserInputMapper::ACTION2, makeInput(BUTTON_4, 1)); + // Left Trackpad: Movement, strafing + mapper.addInputChannel(UserInputMapper::LONGITUDINAL_FORWARD, makeInput(AXIS_Y_POS, 0), JOYSTICK_MOVE_SPEED); + mapper.addInputChannel(UserInputMapper::LONGITUDINAL_BACKWARD, makeInput(AXIS_Y_NEG, 0), JOYSTICK_MOVE_SPEED); + mapper.addInputChannel(UserInputMapper::LATERAL_RIGHT, makeInput(AXIS_X_POS, 0), JOYSTICK_MOVE_SPEED); + mapper.addInputChannel(UserInputMapper::LATERAL_LEFT, makeInput(AXIS_X_NEG, 0), JOYSTICK_MOVE_SPEED); + + // Right Trackpad: Vertical movement, zooming + mapper.addInputChannel(UserInputMapper::VERTICAL_UP, makeInput(AXIS_Y_POS, 1), JOYSTICK_MOVE_SPEED); + mapper.addInputChannel(UserInputMapper::VERTICAL_DOWN, makeInput(AXIS_Y_NEG, 1), JOYSTICK_MOVE_SPEED); + mapper.addInputChannel(UserInputMapper::BOOM_IN, makeInput(AXIS_X_POS, 1), BOOM_SPEED); + mapper.addInputChannel(UserInputMapper::BOOM_OUT, makeInput(AXIS_X_NEG, 1), BOOM_SPEED); + // Buttons + mapper.addInputChannel(UserInputMapper::SHIFT, makeInput(GRIP_BUTTON, 0)); + mapper.addInputChannel(UserInputMapper::SHIFT, makeInput(GRIP_BUTTON, 1)); + + mapper.addInputChannel(UserInputMapper::ACTION1, makeInput(BUTTON_A, 0)); + mapper.addInputChannel(UserInputMapper::ACTION2, makeInput(BUTTON_A, 1)); + + // Hands mapper.addInputChannel(UserInputMapper::LEFT_HAND, makeInput(LEFT_HAND)); mapper.addInputChannel(UserInputMapper::RIGHT_HAND, makeInput(RIGHT_HAND)); } @@ -260,13 +271,11 @@ UserInputMapper::PoseValue ViveControllerManager::getPose(int channel) const { } UserInputMapper::Input ViveControllerManager::makeInput(unsigned int button, int index) { - return UserInputMapper::Input(); -// return UserInputMapper::Input(_deviceID, button | (index == 0 ? LEFT_MASK : RIGHT_MASK), UserInputMapper::ChannelType::BUTTON); + return UserInputMapper::Input(_deviceID, button | (index == 0 ? LEFT_MASK : RIGHT_MASK), UserInputMapper::ChannelType::BUTTON); } UserInputMapper::Input ViveControllerManager::makeInput(ViveControllerManager::JoystickAxisChannel axis, int index) { - return UserInputMapper::Input(); -// return UserInputMapper::Input(_deviceID, axis | (index == 0 ? LEFT_MASK : RIGHT_MASK), UserInputMapper::ChannelType::AXIS); + return UserInputMapper::Input(_deviceID, axis | (index == 0 ? LEFT_MASK : RIGHT_MASK), UserInputMapper::ChannelType::AXIS); } UserInputMapper::Input ViveControllerManager::makeInput(JointChannel joint) { diff --git a/libraries/input-plugins/src/input-plugins/ViveControllerManager.h b/libraries/input-plugins/src/input-plugins/ViveControllerManager.h index f780bd0671..b738df05f8 100644 --- a/libraries/input-plugins/src/input-plugins/ViveControllerManager.h +++ b/libraries/input-plugins/src/input-plugins/ViveControllerManager.h @@ -24,11 +24,19 @@ class ViveControllerManager : public QObject { public: enum JoystickAxisChannel { - AXIS_Y_POS = 1U << 0, - AXIS_Y_NEG = 1U << 3, - AXIS_X_POS = 1U << 4, - AXIS_X_NEG = 1U << 5, - BACK_TRIGGER = 1U << 6, + AXIS_Y_POS = 1U << 1, + AXIS_Y_NEG = 1U << 2, + AXIS_X_POS = 1U << 3, + AXIS_X_NEG = 1U << 4, + BACK_TRIGGER = 1U << 5, + }; + + enum Axis { + TRACKPAD_AXIS = 0, + TRIGGER_AXIS, + AXIS_2, + AXIS_3, + AXIS_4, }; enum JointChannel { @@ -63,8 +71,8 @@ private: ViveControllerManager(); ~ViveControllerManager(); - void handleButtonEvent(unsigned int buttons, int index); - void handleAxisEvent(float x, float y, float trigger, int index); + void handleButtonEvent(uint64_t buttons, int index); + void handleAxisEvent(Axis axis, float x, float y, int index); void handlePoseEvent(const mat4& mat, int index); bool _isInitialized;