diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 91e95bb4e3..9f391aa36b 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1990,7 +1990,7 @@ void Application::update(float deltaTime) { _myAvatar->updateLookAtTargetAvatar(); updateMyAvatarLookAtPosition(); _sixenseManager.update(deltaTime); - _prioVR.update(); + _prioVR.update(deltaTime); updateMyAvatar(deltaTime); // Sample hardware, update view frustum if needed, and send avatar data to mixer/nodes updateThreads(deltaTime); // If running non-threaded, then give the threads some time to process... _avatarManager.updateOtherAvatars(deltaTime); //loop through all the other avatars and simulate them... diff --git a/interface/src/devices/PrioVR.cpp b/interface/src/devices/PrioVR.cpp index e6e948422e..dcc3d314f3 100644 --- a/interface/src/devices/PrioVR.cpp +++ b/interface/src/devices/PrioVR.cpp @@ -37,6 +37,87 @@ static int indexOfHumanIKJoint(const char* jointName) { } } } + +static void setPalm(float deltaTime, int index) { + MyAvatar* avatar = Application::getInstance()->getAvatar(); + Hand* hand = avatar->getHand(); + PalmData* palm; + bool foundHand = false; + for (size_t j = 0; j < hand->getNumPalms(); j++) { + if (hand->getPalms()[j].getSixenseID() == index) { + palm = &(hand->getPalms()[j]); + foundHand = true; + } + } + if (!foundHand) { + PalmData newPalm(hand); + hand->getPalms().push_back(newPalm); + palm = &(hand->getPalms()[hand->getNumPalms() - 1]); + palm->setSixenseID(index); + } + + palm->setActive(true); + + // Read controller buttons and joystick into the hand + if (!Application::getInstance()->getJoystickManager()->getJoystickStates().isEmpty()) { + const JoystickState& state = Application::getInstance()->getJoystickManager()->getJoystickStates().at(0); + if (state.axes.size() >= 4 && state.buttons.size() >= 4) { + if (index == 0) { + palm->setControllerButtons(state.buttons.at(1) ? BUTTON_FWD : 0); + palm->setTrigger(state.buttons.at(0) ? 1.0f : 0.0f); + palm->setJoystick(state.axes.at(0), -state.axes.at(1)); + + } else { + palm->setControllerButtons(state.buttons.at(3) ? BUTTON_FWD : 0); + palm->setTrigger(state.buttons.at(2) ? 1.0f : 0.0f); + palm->setJoystick(state.axes.at(2), -state.axes.at(3)); + } + } + } + + glm::vec3 position; + glm::quat rotation; + + Model* skeletonModel = &Application::getInstance()->getAvatar()->getSkeletonModel(); + int jointIndex; + glm::quat inverseRotation = glm::inverse(skeletonModel->getRotation()); + if (index == 0) { + jointIndex = skeletonModel->getLeftHandJointIndex(); + skeletonModel->getJointRotation(jointIndex, rotation, true); + rotation = inverseRotation * rotation * glm::quat(glm::vec3(0.0f, -PI_OVER_TWO, 0.0f)); + + } else { + jointIndex = skeletonModel->getRightHandJointIndex(); + skeletonModel->getJointRotation(jointIndex, rotation, true); + rotation = inverseRotation * rotation * glm::quat(glm::vec3(0.0f, PI_OVER_TWO, 0.0f)); + } + skeletonModel->getJointPosition(jointIndex, position); + position = inverseRotation * (position - skeletonModel->getTranslation()); + + palm->setRawRotation(rotation); + + // Compute current velocity from position change + glm::vec3 rawVelocity; + if (deltaTime > 0.f) { + rawVelocity = (position - palm->getRawPosition()) / deltaTime; + } else { + rawVelocity = glm::vec3(0.0f); + } + palm->setRawVelocity(rawVelocity); + palm->setRawPosition(position); + + // Store the one fingertip in the palm structure so we can track velocity + const float FINGER_LENGTH = 0.3f; // meters + const glm::vec3 FINGER_VECTOR(0.0f, 0.0f, FINGER_LENGTH); + const glm::vec3 newTipPosition = position + rotation * FINGER_VECTOR; + glm::vec3 oldTipPosition = palm->getTipRawPosition(); + if (deltaTime > 0.f) { + palm->setTipVelocity((newTipPosition - oldTipPosition) / deltaTime); + } else { + palm->setTipVelocity(glm::vec3(0.f)); + } + palm->setTipPosition(newTipPosition); +} #endif PrioVR::PrioVR() { @@ -78,7 +159,7 @@ glm::quat PrioVR::getTorsoRotation() const { return _jointRotations.size() > TORSO_ROTATION_INDEX ? _jointRotations.at(TORSO_ROTATION_INDEX) : glm::quat(); } -void PrioVR::update() { +void PrioVR::update(float deltaTime) { #ifdef HAVE_PRIOVR if (!_skeletalDevice) { return; @@ -96,6 +177,10 @@ void PrioVR::update() { _lastJointRotations[i] = _jointRotations.at(i); _jointRotations[i] = safeMix(lastRotation, _jointRotations.at(i), 0.5f); } + + // convert the joysticks into palm data + setPalm(deltaTime, 0); + setPalm(deltaTime, 1); #endif } diff --git a/interface/src/devices/PrioVR.h b/interface/src/devices/PrioVR.h index 8f01574356..bb563bf807 100644 --- a/interface/src/devices/PrioVR.h +++ b/interface/src/devices/PrioVR.h @@ -43,7 +43,7 @@ public: const QVector& getHumanIKJointIndices() const { return _humanIKJointIndices; } const QVector& getJointRotations() const { return _jointRotations; } - void update(); + void update(float deltaTime); void reset(); private slots: diff --git a/interface/src/scripting/ControllerScriptingInterface.cpp b/interface/src/scripting/ControllerScriptingInterface.cpp index 286d55081d..34c1cc2f1c 100644 --- a/interface/src/scripting/ControllerScriptingInterface.cpp +++ b/interface/src/scripting/ControllerScriptingInterface.cpp @@ -74,6 +74,7 @@ bool ControllerScriptingInterface::isPrimaryButtonPressed() const { return true; } } + return false; }