diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index 3c62a4b7a9..99e418bf4f 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -30,6 +30,8 @@ Line3DOverlay::Line3DOverlay(const Line3DOverlay* line3DOverlay) : setLocalTransform(line3DOverlay->getLocalTransform()); _direction = line3DOverlay->getDirection(); _length = line3DOverlay->getLength(); + _endParentID = line3DOverlay->getEndParentID(); + _endParentJointIndex = line3DOverlay->getEndJointIndex(); } Line3DOverlay::~Line3DOverlay() { @@ -45,9 +47,18 @@ glm::vec3 Line3DOverlay::getStart() const { glm::vec3 Line3DOverlay::getEnd() const { bool success; + glm::vec3 localEnd; + glm::vec3 worldEnd; - glm::vec3 localEnd = getLocalEnd(); - glm::vec3 worldEnd = localToWorld(localEnd, getParentID(), getParentJointIndex(), success); + if (_endParentID != QUuid()) { + glm::vec3 localOffset = _direction * _length; + bool success; + worldEnd = localToWorld(localOffset, _endParentID, _endParentJointIndex, success); + return worldEnd; + } + + localEnd = getLocalEnd(); + worldEnd = localToWorld(localEnd, getParentID(), getParentJointIndex(), success); if (!success) { qDebug() << "Line3DOverlay::getEnd failed"; } @@ -60,15 +71,33 @@ void Line3DOverlay::setStart(const glm::vec3& start) { void Line3DOverlay::setEnd(const glm::vec3& end) { bool success; + glm::vec3 localStart; + glm::vec3 localEnd; + glm::vec3 offset; - glm::vec3 localStart = getLocalStart(); - glm::vec3 localEnd = worldToLocal(end, getParentID(), getParentJointIndex(), success); + if (_endParentID != QUuid()) { + offset = worldToLocal(end, _endParentID, _endParentJointIndex, success); + } else { + localStart = getLocalStart(); + localEnd = worldToLocal(end, getParentID(), getParentJointIndex(), success); + offset = localEnd - localStart; + } if (!success) { qDebug() << "Line3DOverlay::setEnd failed"; return; } + _direction = glm::normalize(offset); + _length = glm::length(offset); +} - glm::vec3 offset = localEnd - localStart; +void Line3DOverlay::setLocalEnd(const glm::vec3& localEnd) { + glm::vec3 offset; + if (_endParentID != QUuid()) { + offset = localEnd; + } else { + glm::vec3 localStart = getLocalStart(); + offset = localEnd - localStart; + } _direction = glm::normalize(offset); _length = glm::length(offset); } @@ -136,16 +165,6 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { } properties.remove("start"); // so that Base3DOverlay doesn't respond to it - auto localStart = properties["localStart"]; - if (localStart.isValid()) { - setLocalPosition(vec3FromVariant(localStart)); - // in case "end" isn't updated... - glm::vec3 offset = getLocalEnd() - getLocalStart(); - _direction = glm::normalize(offset); - _length = glm::length(offset); - } - properties.remove("localStart"); // so that Base3DOverlay doesn't respond to it - auto end = properties["end"]; // if "end" property was not there, check to see if they included aliases: endPoint if (!end.isValid()) { @@ -157,14 +176,6 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { } properties.remove("end"); // so that Base3DOverlay doesn't respond to it - auto localEnd = properties["localEnd"]; - if (localEnd.isValid()) { - glm::vec3 offset = vec3FromVariant(localEnd) - getLocalStart(); - _direction = glm::normalize(offset); - _length = glm::length(offset); - } - properties.remove("localEnd"); // so that Base3DOverlay doesn't respond to it - auto length = properties["length"]; if (length.isValid()) { _length = length.toFloat(); @@ -172,6 +183,27 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { Base3DOverlay::setProperties(properties); + auto endParentIDProp = properties["endParentID"]; + if (endParentIDProp.isValid()) { + _endParentID = QUuid(endParentIDProp.toString()); + } + auto endParentJointIndexProp = properties["endParentJointIndex"]; + if (endParentJointIndexProp.isValid()) { + _endParentJointIndex = endParentJointIndexProp.toInt(); + } + + auto localStart = properties["localStart"]; + if (localStart.isValid()) { + glm::vec3 tmpLocalEnd = getLocalEnd(); + setLocalStart(vec3FromVariant(localStart)); + setLocalEnd(tmpLocalEnd); + } + + auto localEnd = properties["localEnd"]; + if (localEnd.isValid()) { + setLocalEnd(vec3FromVariant(localEnd)); + } + // these are saved until after Base3DOverlay::setProperties so parenting infomation can be set, first if (newStartSet) { setStart(newStart); diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index b67e5a0254..aceecff6b2 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -15,7 +15,7 @@ class Line3DOverlay : public Base3DOverlay { Q_OBJECT - + public: static QString const TYPE; virtual QString getType() const override { return TYPE; } @@ -37,6 +37,9 @@ public: void setStart(const glm::vec3& start); void setEnd(const glm::vec3& end); + void setLocalStart(const glm::vec3& localStart) { setLocalPosition(localStart); } + void setLocalEnd(const glm::vec3& localEnd); + void setGlow(const float& glow) { _glow = glow; } void setGlowWidth(const float& glowWidth) { _glowWidth = glowWidth; } @@ -51,10 +54,19 @@ public: float getLength() const { return _length; } glm::vec3 getLocalStart() const { return getLocalPosition(); } glm::vec3 getLocalEnd() const { return getLocalStart() + _direction * _length; } + QUuid getEndParentID() const { return _endParentID; } + quint16 getEndJointIndex() const { return _endParentJointIndex; } private: + QUuid _endParentID; + quint16 _endParentJointIndex { INVALID_JOINT_INDEX }; + + // _direction and _length are in the parent's frame. If _endParentID is set, they are + // relative to that. Otherwise, they are relative to the local-start-position (which is the + // same as localPosition) glm::vec3 _direction; // in parent frame float _length { 1.0 }; // in parent frame + float _glow { 0.0 }; float _glowWidth { 0.0 }; int _geometryCacheID; diff --git a/scripts/system/controllers/handControllerGrab.js b/scripts/system/controllers/handControllerGrab.js index c98793fc51..ad5ab5e883 100644 --- a/scripts/system/controllers/handControllerGrab.js +++ b/scripts/system/controllers/handControllerGrab.js @@ -999,7 +999,7 @@ function MyController(hand) { } }; - this.overlayLineOn = function(closePoint, farPoint, color) { + this.overlayLineOn = function(closePoint, farPoint, color, farParentID) { if (this.overlayLine === null) { var lineProperties; if (this.hand === RIGHT_HAND) { @@ -1014,7 +1014,8 @@ function MyController(hand) { visible: true, alpha: 1, parentID: AVATAR_SELF_ID, - parentJointIndex: this.controllerJointIndex + parentJointIndex: this.controllerJointIndex, + endParentID: farParentID }; } else { lineProperties = { @@ -1033,12 +1034,16 @@ function MyController(hand) { } else { if (this.hand === RIGHT_HAND) { - Overlays.editOverlay(this.overlayLine, { - // start: closePoint, - // end: farPoint, - length: Vec3.distance(farPoint, closePoint), - color: color, - }); + if (farParentID && farParentID != NULL_UUID) { + Overlays.editOverlay(this.overlayLine, { + color: color, + }); + } else { + Overlays.editOverlay(this.overlayLine, { + length: Vec3.distance(farPoint, closePoint), + color: color, + }); + } } else { Overlays.editOverlay(this.overlayLine, { start: closePoint, @@ -2191,7 +2196,10 @@ function MyController(hand) { var rayPickInfo = this.calcRayPickInfo(this.hand); - this.overlayLineOn(rayPickInfo.searchRay.origin, Vec3.subtract(grabbedProperties.position, this.offsetPosition), COLORS_GRAB_DISTANCE_HOLD); + this.overlayLineOn(rayPickInfo.searchRay.origin, + Vec3.subtract(grabbedProperties.position, this.offsetPosition), + COLORS_GRAB_DISTANCE_HOLD, + this.grabbedEntity); var distanceToObject = Vec3.length(Vec3.subtract(MyAvatar.position, this.currentObjectPosition)); var success = Entities.updateAction(this.grabbedEntity, this.actionID, {