From bc5ef8eb113f32295a7a12e1d8fc1b5096e49658 Mon Sep 17 00:00:00 2001 From: Zander Otavka Date: Fri, 24 Jul 2015 17:50:17 -0700 Subject: [PATCH] Clean up C++ relating to panels. --- .../src/ui/overlays/BillboardOverlay.cpp | 28 ++----- interface/src/ui/overlays/FloatingUIPanel.cpp | 53 +++++++------ interface/src/ui/overlays/FloatingUIPanel.h | 22 ++++-- interface/src/ui/overlays/Overlays.cpp | 75 ++++++++++--------- interface/src/ui/overlays/Overlays.h | 10 ++- interface/src/ui/overlays/PanelAttachable.cpp | 46 ++++++++++++ interface/src/ui/overlays/PanelAttachable.h | 7 +- 7 files changed, 151 insertions(+), 90 deletions(-) diff --git a/interface/src/ui/overlays/BillboardOverlay.cpp b/interface/src/ui/overlays/BillboardOverlay.cpp index 3e8333b859..8ffa909e12 100644 --- a/interface/src/ui/overlays/BillboardOverlay.cpp +++ b/interface/src/ui/overlays/BillboardOverlay.cpp @@ -13,17 +13,15 @@ #include +#include #include #include #include +#include #include "Application.h" #include "GeometryUtil.h" -#include "DeferredLightingEffect.h" - -#include - QString const BillboardOverlay::TYPE = "billboard"; @@ -107,7 +105,7 @@ void BillboardOverlay::render(RenderArgs* args) { batch->setModelTransform(transform); batch->setResourceTexture(0, _texture->getGPUTexture()); - DependencyManager::get()->bindSimpleProgram(*batch, true, true, false); + DependencyManager::get()->bindSimpleProgram(*batch, true, true, false, true); DependencyManager::get()->renderQuad( *batch, topLeft, bottomRight, texCoordTopLeft, texCoordBottomRight, glm::vec4(color.red / MAX_COLOR, color.green / MAX_COLOR, color.blue / MAX_COLOR, alpha) @@ -118,6 +116,7 @@ void BillboardOverlay::render(RenderArgs* args) { void BillboardOverlay::setProperties(const QScriptValue &properties) { Planar3DOverlay::setProperties(properties); + PanelAttachable::setProperties(properties); QScriptValue urlValue = properties.property("url"); if (urlValue.isValid()) { @@ -162,21 +161,6 @@ void BillboardOverlay::setProperties(const QScriptValue &properties) { if (isFacingAvatarValue.isValid()) { _isFacingAvatar = isFacingAvatarValue.toVariant().toBool(); } - - QScriptValue offsetPosition = properties.property("offsetPosition"); - if (offsetPosition.isValid()) { - QScriptValue x = offsetPosition.property("x"); - QScriptValue y = offsetPosition.property("y"); - QScriptValue z = offsetPosition.property("z"); - - if (x.isValid() && y.isValid() && z.isValid()) { - glm::vec3 newPosition; - newPosition.x = x.toVariant().toFloat(); - newPosition.y = y.toVariant().toFloat(); - newPosition.z = z.toVariant().toFloat(); - setOffsetPosition(newPosition); - } - } } QScriptValue BillboardOverlay::getProperty(const QString& property) { @@ -193,6 +177,10 @@ QScriptValue BillboardOverlay::getProperty(const QString& property) { return vec3toScriptValue(_scriptEngine, getOffsetPosition()); } + QScriptValue value = PanelAttachable::getProperty(_scriptEngine, property); + if (value.isValid()) { + return value; + } return Planar3DOverlay::getProperty(property); } diff --git a/interface/src/ui/overlays/FloatingUIPanel.cpp b/interface/src/ui/overlays/FloatingUIPanel.cpp index a862e4fcd4..eedb4bffd1 100644 --- a/interface/src/ui/overlays/FloatingUIPanel.cpp +++ b/interface/src/ui/overlays/FloatingUIPanel.cpp @@ -20,7 +20,6 @@ #include "Application.h" #include "Base3DOverlay.h" - std::function const FloatingUIPanel::AVATAR_POSITION = []() -> glm::vec3 { return DependencyManager::get()->getMyAvatar()->getPosition(); }; @@ -30,12 +29,6 @@ std::function const FloatingUIPanel::AVATAR_ORIENTATION = []() -> g glm::angleAxis(glm::pi(), IDENTITY_UP); }; -FloatingUIPanel::FloatingUIPanel() : - _anchorPosition(AVATAR_POSITION), - _offsetRotation(AVATAR_ORIENTATION) -{ -} - glm::vec3 FloatingUIPanel::getPosition() const { return getOffsetRotation() * getOffsetPosition() + getAnchorPosition(); } @@ -44,18 +37,30 @@ glm::quat FloatingUIPanel::getRotation() const { return getOffsetRotation() * getFacingRotation(); } -void FloatingUIPanel::setAnchorPosition(glm::vec3 position) { +void FloatingUIPanel::setAnchorPosition(const glm::vec3& position) { setAnchorPosition([position]() -> glm::vec3 { return position; }); } -void FloatingUIPanel::setOffsetRotation(glm::quat rotation) { +void FloatingUIPanel::setOffsetRotation(const glm::quat& rotation) { setOffsetRotation([rotation]() -> glm::quat { return rotation; }); } +void FloatingUIPanel::addChild(unsigned int childId) { + if (!_children.contains(childId)) { + _children.append(childId); + } +} + +void FloatingUIPanel::removeChild(unsigned int childId) { + if (_children.contains(childId)) { + _children.removeOne(childId); + } +} + QScriptValue FloatingUIPanel::getProperty(const QString &property) { if (property == "anchorPosition") { return vec3toScriptValue(_scriptEngine, getAnchorPosition()); @@ -76,15 +81,15 @@ QScriptValue FloatingUIPanel::getProperty(const QString &property) { void FloatingUIPanel::setProperties(const QScriptValue &properties) { QScriptValue anchor = properties.property("anchorPosition"); if (anchor.isValid()) { - QScriptValue type = anchor.property("type"); + QScriptValue bindType = anchor.property("bind"); QScriptValue value = anchor.property("value"); - if (type.isValid()) { - QString typeString = type.toVariant().toString(); - if (typeString == "myAvatar") { + if (bindType.isValid()) { + QString bindTypeString = bindType.toVariant().toString(); + if (bindTypeString == "myAvatar") { setAnchorPosition(AVATAR_POSITION); } else if (value.isValid()) { - if (typeString == "overlay") { + if (bindTypeString == "overlay") { Overlay::Pointer overlay = Application::getInstance()->getOverlays() .getOverlay(value.toVariant().toUInt()); if (overlay->is3D()) { @@ -93,13 +98,13 @@ void FloatingUIPanel::setProperties(const QScriptValue &properties) { return overlay3D->getPosition(); }); } - } else if (typeString == "panel") { + } else if (bindTypeString == "panel") { FloatingUIPanel::Pointer panel = Application::getInstance()->getOverlays() .getPanel(value.toVariant().toUInt()); setAnchorPosition([panel]() -> glm::vec3 { return panel->getPosition(); }); - } else if (typeString == "vec3") { + } else if (bindTypeString == "vec3") { QScriptValue x = value.property("x"); QScriptValue y = value.property("y"); QScriptValue z = value.property("z"); @@ -117,15 +122,15 @@ void FloatingUIPanel::setProperties(const QScriptValue &properties) { QScriptValue offsetRotation = properties.property("offsetRotation"); if (offsetRotation.isValid()) { - QScriptValue type = offsetRotation.property("type"); + QScriptValue bindType = offsetRotation.property("bind"); QScriptValue value = offsetRotation.property("value"); - if (type.isValid()) { - QString typeString = type.toVariant().toString(); - if (typeString == "myAvatar") { + if (bindType.isValid()) { + QString bindTypeString = bindType.toVariant().toString(); + if (bindTypeString == "myAvatar") { setOffsetRotation(AVATAR_ORIENTATION); } else if (value.isValid()) { - if (typeString == "overlay") { + if (bindTypeString == "overlay") { Overlay::Pointer overlay = Application::getInstance()->getOverlays() .getOverlay(value.toVariant().toUInt()); if (overlay->is3D()) { @@ -134,13 +139,13 @@ void FloatingUIPanel::setProperties(const QScriptValue &properties) { return overlay3D->getRotation(); }); } - } else if (typeString == "panel") { + } else if (bindTypeString == "panel") { FloatingUIPanel::Pointer panel = Application::getInstance()->getOverlays() .getPanel(value.toVariant().toUInt()); setOffsetRotation([panel]() -> glm::quat { return panel->getRotation(); }); - } else if (typeString == "quat") { + } else if (bindTypeString == "quat") { QScriptValue x = value.property("x"); QScriptValue y = value.property("y"); QScriptValue z = value.property("z"); @@ -174,7 +179,7 @@ void FloatingUIPanel::setProperties(const QScriptValue &properties) { } QScriptValue facingRotation = properties.property("facingRotation"); - if (offsetRotation.isValid()) { + if (facingRotation.isValid()) { QScriptValue x = facingRotation.property("x"); QScriptValue y = facingRotation.property("y"); QScriptValue z = facingRotation.property("z"); diff --git a/interface/src/ui/overlays/FloatingUIPanel.h b/interface/src/ui/overlays/FloatingUIPanel.h index abc1328928..f65fa93c26 100644 --- a/interface/src/ui/overlays/FloatingUIPanel.h +++ b/interface/src/ui/overlays/FloatingUIPanel.h @@ -12,6 +12,8 @@ #ifndef hifi_FloatingUIPanel_h #define hifi_FloatingUIPanel_h +#include + #include #include #include @@ -21,8 +23,6 @@ class FloatingUIPanel : public QObject { public: typedef std::shared_ptr Pointer; - QList children; - void init(QScriptEngine* scriptEngine) { _scriptEngine = scriptEngine; } glm::vec3 getAnchorPosition() const { return _anchorPosition(); } @@ -33,11 +33,16 @@ public: glm::quat getRotation() const; void setAnchorPosition(const std::function& func) { _anchorPosition = func; } - void setAnchorPosition(glm::vec3 position); + void setAnchorPosition(const glm::vec3& position); void setOffsetRotation(const std::function& func) { _offsetRotation = func; } - void setOffsetRotation(glm::quat rotation); - void setOffsetPosition(glm::vec3 position) { _offsetPosition = position; } - void setFacingRotation(glm::quat rotation) { _facingRotation = rotation; } + void setOffsetRotation(const glm::quat& rotation); + void setOffsetPosition(const glm::vec3& position) { _offsetPosition = position; } + void setFacingRotation(const glm::quat& rotation) { _facingRotation = rotation; } + + const QList& getChildren() { return _children; } + void addChild(unsigned int childId); + void removeChild(unsigned int childId); + unsigned int popLastChild() { return _children.takeLast(); } QScriptValue getProperty(const QString& property); void setProperties(const QScriptValue& properties); @@ -46,11 +51,12 @@ private: static std::function const AVATAR_POSITION; static std::function const AVATAR_ORIENTATION; - std::function _anchorPosition; - std::function _offsetRotation; + std::function _anchorPosition{AVATAR_POSITION}; + std::function _offsetRotation{AVATAR_ORIENTATION}; glm::vec3 _offsetPosition{0, 0, 0}; glm::quat _facingRotation{1, 0, 0, 0}; QScriptEngine* _scriptEngine; + QList _children; }; #endif // hifi_FloatingUIPanel_h diff --git a/interface/src/ui/overlays/Overlays.cpp b/interface/src/ui/overlays/Overlays.cpp index fb9f64c84e..bce219b4b4 100644 --- a/interface/src/ui/overlays/Overlays.cpp +++ b/interface/src/ui/overlays/Overlays.cpp @@ -135,23 +135,6 @@ Overlay::Pointer Overlays::getOverlay(unsigned int id) const { return nullptr; } -void Overlays::setAttachedPanel(Overlay::Pointer overlay, unsigned int overlayId, const QScriptValue& property) { - auto attachable = std::dynamic_pointer_cast(overlay); - if (attachable) { - if (property.isValid()) { - unsigned int attachedPanelId = property.toVariant().toUInt(); - if (_panels.contains(attachedPanelId)) { - auto panel = _panels[attachedPanelId]; - panel->children.append(overlayId); - attachable->setAttachedPanel(panel); - } else { - attachable->getAttachedPanel()->children.removeAll(overlayId); - attachable->setAttachedPanel(nullptr); - } - } - } -} - unsigned int Overlays::addOverlay(const QString& type, const QScriptValue& properties) { Overlay::Pointer thisOverlay = nullptr; @@ -183,9 +166,7 @@ unsigned int Overlays::addOverlay(const QString& type, const QScriptValue& prope if (thisOverlay) { thisOverlay->setProperties(properties); - unsigned int overlayId = addOverlay(thisOverlay); - setAttachedPanel(thisOverlay, overlayId, properties.property("attachedPanel")); - return overlayId; + return addOverlay(thisOverlay); } return 0; } @@ -252,8 +233,6 @@ bool Overlays::editOverlay(unsigned int id, const QScriptValue& properties) { thisOverlay->setProperties(properties); } - setAttachedPanel(thisOverlay, id, properties.property("attachedPanel")); - return true; } return false; @@ -273,8 +252,16 @@ void Overlays::deleteOverlay(unsigned int id) { } } + auto attachable = std::dynamic_pointer_cast(overlayToDelete); + if (attachable && attachable->getAttachedPanel()) { + attachable->getAttachedPanel()->removeChild(id); + attachable->setAttachedPanel(nullptr); + } + QWriteLocker lock(&_deleteLock); _overlaysToDelete.push_back(overlayToDelete); + + emit overlayDeleted(id); } QString Overlays::getOverlayType(unsigned int overlayId) const { @@ -285,6 +272,33 @@ QString Overlays::getOverlayType(unsigned int overlayId) const { return ""; } +unsigned int Overlays::getAttachedPanel(unsigned int childId) const { + Overlay::Pointer overlay = getOverlay(childId); + auto attachable = std::dynamic_pointer_cast(overlay); + if (attachable) { + return _panels.key(attachable->getAttachedPanel()); + } + return 0; +} + +void Overlays::setAttachedPanel(unsigned int childId, unsigned int panelId) { + Overlay::Pointer overlay = getOverlay(childId); + auto attachable = std::dynamic_pointer_cast(overlay); + if (attachable) { + if (_panels.contains(panelId)) { + auto panel = _panels[panelId]; + panel->addChild(childId); + attachable->setAttachedPanel(panel); + } else { + auto panel = attachable->getAttachedPanel(); + if (panel) { + panel->removeChild(childId); + attachable->setAttachedPanel(nullptr); + } + } + } +} + unsigned int Overlays::getOverlayAtPoint(const glm::vec2& point) { glm::vec2 pointCopy = point; if (qApp->isHMDMode()) { @@ -328,16 +342,7 @@ OverlayPropertyResult Overlays::getProperty(unsigned int id, const QString& prop Overlay::Pointer thisOverlay = getOverlay(id); QReadLocker lock(&_lock); if (thisOverlay) { - if (property == "attachedPanel") { - auto panelAttachable = std::dynamic_pointer_cast(thisOverlay); - if (panelAttachable) { - result.value = _panels.key(panelAttachable->getAttachedPanel()); - } else { - result.value = 0; - } - } else { - result.value = thisOverlay->getProperty(property); - } + result.value = thisOverlay->getProperty(property); } return result; } @@ -553,7 +558,9 @@ void Overlays::deletePanel(unsigned int panelId) { } } - while (!panelToDelete->children.isEmpty()) { - deleteOverlay(panelToDelete->children.takeLast()); + while (!panelToDelete->getChildren().isEmpty()) { + deleteOverlay(panelToDelete->popLastChild()); } + + emit panelDeleted(panelId); } diff --git a/interface/src/ui/overlays/Overlays.h b/interface/src/ui/overlays/Overlays.h index ee4fa5b7d4..ce2c3efeae 100644 --- a/interface/src/ui/overlays/Overlays.h +++ b/interface/src/ui/overlays/Overlays.h @@ -87,9 +87,12 @@ public slots: /// deletes a particle void deleteOverlay(unsigned int id); - /// + /// get the string type of the overlay used in addOverlay QString getOverlayType(unsigned int overlayId) const; + unsigned int getAttachedPanel(unsigned int childId) const; + void setAttachedPanel(unsigned int childId, unsigned int panelId); + /// returns the top most 2D overlay at the screen point, or 0 if not overlay at that point unsigned int getOverlayAtPoint(const glm::vec2& point); @@ -122,9 +125,12 @@ public slots: /// deletes a panel and all child overlays void deletePanel(unsigned int panelId); +signals: + void overlayDeleted(unsigned int id); + void panelDeleted(unsigned int id); + private: void cleanupOverlaysToDelete(); - void setAttachedPanel(Overlay::Pointer overlay, unsigned int overlayId, const QScriptValue& property); QMap _overlaysHUD; QMap _overlaysWorld; diff --git a/interface/src/ui/overlays/PanelAttachable.cpp b/interface/src/ui/overlays/PanelAttachable.cpp index bedf7d9fd5..e114fa143e 100644 --- a/interface/src/ui/overlays/PanelAttachable.cpp +++ b/interface/src/ui/overlays/PanelAttachable.cpp @@ -11,6 +11,8 @@ #include "PanelAttachable.h" +#include + PanelAttachable::PanelAttachable() : _attachedPanel(nullptr), _facingRotation(1, 0, 0, 0) @@ -33,3 +35,47 @@ void PanelAttachable::setTransforms(Transform* transform) { transform->postRotate(getFacingRotation() * getAttachedPanel()->getFacingRotation()); } } + +QScriptValue PanelAttachable::getProperty(QScriptEngine* scriptEngine, const QString &property) { + if (property == "offsetPosition") { + return vec3toScriptValue(scriptEngine, getOffsetPosition()); + } + if (property == "facingRotation") { + return quatToScriptValue(scriptEngine, getFacingRotation()); + } + return QScriptValue(); +} + +void PanelAttachable::setProperties(const QScriptValue &properties) { + QScriptValue offsetPosition = properties.property("offsetPosition"); + if (offsetPosition.isValid()) { + QScriptValue x = offsetPosition.property("x"); + QScriptValue y = offsetPosition.property("y"); + QScriptValue z = offsetPosition.property("z"); + + if (x.isValid() && y.isValid() && z.isValid()) { + glm::vec3 newPosition; + newPosition.x = x.toVariant().toFloat(); + newPosition.y = y.toVariant().toFloat(); + newPosition.z = z.toVariant().toFloat(); + setOffsetPosition(newPosition); + } + } + + QScriptValue facingRotation = properties.property("facingRotation"); + if (facingRotation.isValid()) { + QScriptValue x = facingRotation.property("x"); + QScriptValue y = facingRotation.property("y"); + QScriptValue z = facingRotation.property("z"); + QScriptValue w = facingRotation.property("w"); + + if (x.isValid() && y.isValid() && z.isValid() && w.isValid()) { + glm::quat newRotation; + newRotation.x = x.toVariant().toFloat(); + newRotation.y = y.toVariant().toFloat(); + newRotation.z = z.toVariant().toFloat(); + newRotation.w = w.toVariant().toFloat(); + setFacingRotation(newRotation); + } + } +} diff --git a/interface/src/ui/overlays/PanelAttachable.h b/interface/src/ui/overlays/PanelAttachable.h index 097fc9a517..e1fc490d00 100644 --- a/interface/src/ui/overlays/PanelAttachable.h +++ b/interface/src/ui/overlays/PanelAttachable.h @@ -27,8 +27,11 @@ public: glm::quat getFacingRotation() const { return _facingRotation; } void setAttachedPanel(FloatingUIPanel::Pointer panel) { _attachedPanel = panel; } - void setOffsetPosition(glm::vec3 position) { _offsetPosition = position; } - void setFacingRotation(glm::quat rotation) { _facingRotation = rotation; } + void setOffsetPosition(const glm::vec3& position) { _offsetPosition = position; } + void setFacingRotation(const glm::quat& rotation) { _facingRotation = rotation; } + + QScriptValue getProperty(QScriptEngine* scriptEngine, const QString& property); + void setProperties(const QScriptValue& properties); protected: void setTransforms(Transform* transform);