From a282d83546a691fe5a06fb8e8b0fe8868ad9261e Mon Sep 17 00:00:00 2001 From: Brad Hefta-Gaub Date: Mon, 24 Oct 2016 07:46:04 -0700 Subject: [PATCH] more work on extra lasers --- .../src/scripting/HMDScriptingInterface.cpp | 20 +++++-- .../src/scripting/HMDScriptingInterface.h | 2 +- .../display-plugins/hmd/HmdDisplayPlugin.cpp | 56 ++++++++++++++++--- .../display-plugins/hmd/HmdDisplayPlugin.h | 10 +++- libraries/plugins/src/plugins/DisplayPlugin.h | 3 + .../system/controllers/handControllerGrab.js | 3 + .../controllers/handControllerPointer.js | 25 +++++++++ scripts/system/libraries/controllers.js | 3 +- 8 files changed, 107 insertions(+), 15 deletions(-) diff --git a/interface/src/scripting/HMDScriptingInterface.cpp b/interface/src/scripting/HMDScriptingInterface.cpp index abeae690f0..476317b5a6 100644 --- a/interface/src/scripting/HMDScriptingInterface.cpp +++ b/interface/src/scripting/HMDScriptingInterface.cpp @@ -130,16 +130,26 @@ bool HMDScriptingInterface::setHandLasers(int hands, bool enabled, const glm::ve color, direction); } -bool HMDScriptingInterface::setExtraLaser(const vec3& worldStart, bool enabled, const vec4& color, const vec3& direction) const { +bool HMDScriptingInterface::setExtraLaser(const glm::vec3& worldStart, bool enabled, const glm::vec4& color, const glm::vec3& direction) const { auto offscreenUi = DependencyManager::get(); offscreenUi->executeOnUiThread([offscreenUi, enabled] { offscreenUi->getDesktop()->setProperty("hmdHandMouseActive", enabled); }); - mat4 extraLaserPose; - return qApp->getActiveDisplayPlugin()->setExtraLaser(extraLaserPose, - enabled ? DisplayPlugin::HandLaserMode::Overlay : DisplayPlugin::HandLaserMode::None, - color, direction); + + auto myAvatar = DependencyManager::get()->getMyAvatar(); + auto sensorToWorld = myAvatar->getSensorToWorldMatrix(); + auto worldToSensor = glm::inverse(sensorToWorld); + auto sensorStart = ::transformPoint(worldToSensor, worldStart); + auto sensorDirection = ::transformVectorFast(worldToSensor, direction); // wrong + + qDebug() << __FUNCTION__ << "worldStart:" << worldStart << "sensorStart:" << sensorStart; + qDebug() << __FUNCTION__ << "direction:" << direction << "sensorDirection:" << sensorDirection; + qDebug() << __FUNCTION__ << "enabled:" << enabled; + + + return qApp->getActiveDisplayPlugin()->setExtraLaser(enabled ? DisplayPlugin::HandLaserMode::Overlay : DisplayPlugin::HandLaserMode::None, + color, sensorStart, sensorDirection); } void HMDScriptingInterface::disableExtraLaser() const { diff --git a/interface/src/scripting/HMDScriptingInterface.h b/interface/src/scripting/HMDScriptingInterface.h index 101c7f6445..53c8161a46 100644 --- a/interface/src/scripting/HMDScriptingInterface.h +++ b/interface/src/scripting/HMDScriptingInterface.h @@ -44,7 +44,7 @@ public: Q_INVOKABLE bool setHandLasers(int hands, bool enabled, const glm::vec4& color, const glm::vec3& direction) const; Q_INVOKABLE void disableHandLasers(int hands) const; - Q_INVOKABLE bool setExtraLaser(const vec3& worldStart, bool enabled, const vec4& color, const vec3& direction) const; + Q_INVOKABLE bool setExtraLaser(const glm::vec3& worldStart, bool enabled, const glm::vec4& color, const glm::vec3& direction) const; Q_INVOKABLE void disableExtraLaser() const; diff --git a/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.cpp b/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.cpp index 5cdaae395a..16b7da863a 100644 --- a/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.cpp +++ b/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.cpp @@ -116,6 +116,7 @@ void HmdDisplayPlugin::customizeContext() { for (size_t i = 0; i < _geometryIds.size(); ++i) { _geometryIds[i] = geometryCache->allocateID(); } + _extraLaserID = geometryCache->allocateID(); } void HmdDisplayPlugin::uncustomizeContext() { @@ -135,6 +136,7 @@ void HmdDisplayPlugin::uncustomizeContext() { for (size_t i = 0; i < _geometryIds.size(); ++i) { geometryCache->releaseID(_geometryIds[i]); } + geometryCache->releaseID(_extraLaserID); Parent::uncustomizeContext(); } @@ -366,6 +368,8 @@ void HmdDisplayPlugin::updateFrameData() { _presentUiModelTransform = _uiModelTransform; _presentExtraLaser = _extraLaser; + _presentExtraLaserStart = _extraLaserStart; + _presentExtraLaserPose = _extraLaserPose; }); @@ -389,10 +393,6 @@ void HmdDisplayPlugin::updateFrameData() { mat4 model = _presentHandPoses[i]; vec3 castStart = vec3(model[3]); vec3 castDirection = glm::quat_cast(model) * laserDirection; - if (glm::abs(glm::length2(castDirection) - 1.0f) > EPSILON) { - castDirection = glm::normalize(castDirection); - castDirection = glm::inverse(_presentUiModelTransform.getRotation()) * castDirection; - } // this offset needs to match GRAB_POINT_SPHERE_OFFSET in scripts/system/libraries/controllers.js:19 static const vec3 GRAB_POINT_SPHERE_OFFSET(0.04f, 0.13f, 0.039f); // x = upward, y = forward, z = lateral @@ -444,6 +444,8 @@ void HmdDisplayPlugin::updateFrameData() { const auto& handLaser = _presentExtraLaser; const vec3& laserDirection = handLaser.direction; + + /* mat4 model = _presentExtraLaserPose; vec3 castStart = vec3(model[3]); vec3 castDirection = glm::quat_cast(model) * laserDirection; @@ -455,6 +457,10 @@ void HmdDisplayPlugin::updateFrameData() { // FIXME - no offset vec3 grabPointOffset {0}; castStart += glm::quat_cast(model) * grabPointOffset; + */ + + vec3 castStart = _presentExtraLaserStart; + vec3 castDirection = laserDirection; // FIXME fetch the actual UI radius from... somewhere? float uiRadius = 1.0f; @@ -464,9 +470,13 @@ void HmdDisplayPlugin::updateFrameData() { if (glm::intersectRaySphere(castStart, castDirection, _presentUiModelTransform.getTranslation(), uiRadius * uiRadius, distance)) { + _presentExtraLaserPoints.first = castStart; _presentExtraLaserPoints.second = _presentExtraLaserPoints.first + (castDirection * distance); + qDebug() << __FUNCTION__ << "_presentExtraLaserPoints.first:" << _presentExtraLaserPoints.first; + qDebug() << __FUNCTION__ << "_presentExtraLaserPoints.second:" << _presentExtraLaserPoints.second; + vec3 intersectionPosition = castStart + (castDirection * distance) - _presentUiModelTransform.getTranslation(); intersectionPosition = glm::inverse(_presentUiModelTransform.getRotation()) * intersectionPosition; @@ -484,6 +494,8 @@ void HmdDisplayPlugin::updateFrameData() { yawPitch /= CompositorHelper::VIRTUAL_UI_TARGET_FOV; yawPitch += 0.5f; extraGlowPoint = yawPitch; + } else { + qDebug() << "no extraGlowPoint..."; } } } @@ -496,6 +508,8 @@ void HmdDisplayPlugin::updateFrameData() { // Setup the uniforms { + qDebug() << __FUNCTION__ << "extraGlowPoint:" << extraGlowPoint; + auto& uniforms = _overlayRenderer.uniforms; uniforms.alpha = _compositeOverlayAlpha; uniforms.glowPoints = vec4(handGlowPoints[0], handGlowPoints[1]); @@ -692,6 +706,23 @@ bool HmdDisplayPlugin::setExtraLaser(mat4 extraLaserPose, HandLaserMode mode, co return true; } +bool HmdDisplayPlugin::setExtraLaser(HandLaserMode mode, const vec4& color, const glm::vec3& sensorSpaceStart, const vec3& sensorSpaceDirection) { + HandLaserInfo info; + info.mode = mode; + info.color = color; + info.direction = sensorSpaceDirection; + withNonPresentThreadLock([&] { + _extraLaser = info; + _extraLaserStart = sensorSpaceStart; + }); + + qDebug() << __FUNCTION__ << "info.mode:" << (int)info.mode; + // FIXME defer to a child class plugin to determine if hand lasers are actually + // available based on the presence or absence of hand controllers + return true; +} + + void HmdDisplayPlugin::compositeExtra() { // If neither hand laser is activated, exit if (!_presentHandLasers[0].valid() && !_presentHandLasers[1].valid()) { @@ -713,14 +744,25 @@ void HmdDisplayPlugin::compositeExtra() { return; } const auto& laser = _presentHandLasers[index]; - - const float glowIntensity = 1.0f; - const float glowWidth = 0.05f; if (laser.valid()) { const auto& points = _presentHandLaserPoints[index]; geometryCache->renderGlowLine(batch, points.first, points.second, laser.color, _geometryIds[index]); } }); + + if (_presentExtraLaser.valid()) { + const auto& points = _presentExtraLaserPoints; + qDebug() << __FUNCTION__ << "_presentExtraLaserPoints... points.first:" << points.first; + + geometryCache->renderGlowLine(batch, points.first, points.second, _presentExtraLaser.color, _extraLaserID); + } else { + qDebug() << __FUNCTION__ << "INVALID LASER --- mode != HandLaserMode::None - " << (_presentExtraLaser.mode != HandLaserMode::None) + << "mode:" << (int)_presentExtraLaser.mode + << "color.a > 0.0f - " << (_presentExtraLaser.color.a > 0.0f) << "direction:" << _presentExtraLaser.direction; + + } + + }); } diff --git a/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.h b/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.h index 47ce080fed..7e3cfbaacb 100644 --- a/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.h +++ b/libraries/display-plugins/src/display-plugins/hmd/HmdDisplayPlugin.h @@ -38,7 +38,9 @@ public: virtual glm::mat4 getHeadPose() const override; bool setHandLaser(uint32_t hands, HandLaserMode mode, const vec4& color, const vec3& direction) override; + bool setExtraLaser(mat4 extraLaserPose, HandLaserMode mode, const vec4& color, const vec3& direction) override; + bool setExtraLaser(HandLaserMode mode, const vec4& color, const glm::vec3& sensorSpaceStart, const vec3& sensorSpaceDirection) override; bool wantVsync() const override { return false; @@ -79,14 +81,20 @@ protected: Transform _presentUiModelTransform; std::array _presentHandLasers; std::array _geometryIds; + int _extraLaserID; std::array _presentHandPoses; std::array, 2> _presentHandLaserPoints; HandLaserInfo _extraLaser; HandLaserInfo _presentExtraLaser; + vec3 _extraLaserStart; + vec3 _presentExtraLaserStart; + std::pair _presentExtraLaserPoints; + + // FIXME - kill these mat4 _extraLaserPose; mat4 _presentExtraLaserPose; - std::pair _presentExtraLaserPoints; + std::array _eyeOffsets; std::array _eyeProjections; diff --git a/libraries/plugins/src/plugins/DisplayPlugin.h b/libraries/plugins/src/plugins/DisplayPlugin.h index e97d4bff9a..92abc1c4d3 100644 --- a/libraries/plugins/src/plugins/DisplayPlugin.h +++ b/libraries/plugins/src/plugins/DisplayPlugin.h @@ -118,6 +118,9 @@ public: virtual bool setExtraLaser(mat4 extraLaserPose, HandLaserMode mode, const vec4& color, const vec3& direction) { return false; } + virtual bool setExtraLaser(HandLaserMode mode, const vec4& color, const glm::vec3& sensorSpaceStart, const vec3& sensorSpaceDirection) { + return false; + } virtual bool suppressKeyboard() { return false; } virtual void unsuppressKeyboard() {}; diff --git a/scripts/system/controllers/handControllerGrab.js b/scripts/system/controllers/handControllerGrab.js index db70c01d12..e913ce9df0 100644 --- a/scripts/system/controllers/handControllerGrab.js +++ b/scripts/system/controllers/handControllerGrab.js @@ -891,6 +891,9 @@ function MyController(hand) { }; this.overlayLineOn = function(closePoint, farPoint, color) { + print("overlayLineOn()... closePoint:", closePoint.x +","+closePoint.y+","+closePoint.z, + "farPoint:", farPoint.x +","+farPoint.y+","+farPoint.z); + if (this.overlayLine === null) { var lineProperties = { glow: 1.0, diff --git a/scripts/system/controllers/handControllerPointer.js b/scripts/system/controllers/handControllerPointer.js index 80f8976810..7f90f8c666 100644 --- a/scripts/system/controllers/handControllerPointer.js +++ b/scripts/system/controllers/handControllerPointer.js @@ -447,12 +447,24 @@ function clearSystemLaser() { return; } HMD.disableHandLasers(BOTH_HUD_LASERS); + HMD.disableExtraLaser(); systemLaserOn = false; weMovedReticle = true; Reticle.position = { x: -1, y: -1 }; } function setColoredLaser() { // answer trigger state if lasers supported, else falsey. var color = (activeTrigger.state === 'full') ? LASER_TRIGGER_COLOR_XYZW : LASER_SEARCH_COLOR_XYZW; + + if (!HMD.isHandControllerAvailable()){ + var position = MyAvatar.getHeadPosition(); + //var direction = Quat.multiply(MyAvatar.headOrientation, Quat.angleAxis(-90, { x: 1, y: 0, z: 0 })); + var direction = { x: 1, y: -1, z: 0 }; + + Vec3.print("Calling HMD.setExtraLaser() position:", position); + Vec3.print("Calling HMD.setExtraLaser() direction:", direction); + return HMD.setExtraLaser(position,true, color, direction); + } + return HMD.setHandLasers(activeHudLaser, true, color, SYSTEM_LASER_DIRECTION) && activeTrigger.state; } @@ -491,11 +503,24 @@ function update() { if (!hudPoint2d) { return off(); } + + if (true) { + var color = (activeTrigger.state === 'full') ? LASER_TRIGGER_COLOR_XYZW : LASER_SEARCH_COLOR_XYZW; + + var position = MyAvatar.getHeadPosition(); + //var direction = Quat.multiply(MyAvatar.headOrientation, Quat.angleAxis(-90, { x: 1, y: 0, z: 0 })); + var direction = { x: 1, y: -1, z: 0 }; + Vec3.print("update().... Calling HMD.setExtraLaser() position:", position); + Vec3.print("update().... Calling HMD.setExtraLaser() direction:", direction); + HMD.setExtraLaser(position,true, color, direction); + } + // If there's a HUD element at the (newly moved) reticle, just make it visible and bail. if (isPointingAtOverlay(hudPoint2d)) { if (HMD.active) { Reticle.depth = hudReticleDistance(); } + if (activeTrigger.state && (!systemLaserOn || (systemLaserOn !== activeTrigger.state))) { // last=>wrong color // If the active plugin doesn't implement hand lasers, show the mouse reticle instead. systemLaserOn = setColoredLaser(); diff --git a/scripts/system/libraries/controllers.js b/scripts/system/libraries/controllers.js index 11a0d29276..4b7b0a83d6 100644 --- a/scripts/system/libraries/controllers.js +++ b/scripts/system/libraries/controllers.js @@ -42,7 +42,8 @@ getControllerWorldLocation = function (handController, doOffset) { if (doOffset) { position = Vec3.sum(position, Vec3.multiplyQbyV(orientation, getGrabPointSphereOffset(handController))); } - } else if (!HMD.isHandControllerAvailable()){ + } else if (!HMD.isHandControllerAvailable()) { + //print("getControllerWorldLocation(), no hand controllers -- use head"); position = MyAvatar.getHeadPosition(); orientation = Quat.multiply(MyAvatar.headOrientation, Quat.angleAxis(-90, { x: 1, y: 0, z: 0 })); valid = true;