From 143a315f1d1ee4a8bc5ded4add1c89744d8745e7 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Tue, 20 Mar 2018 15:29:50 -0700 Subject: [PATCH] Fade edited objects are now selected with ray picking --- .../scripting/SelectionScriptingInterface.cpp | 22 ++++- .../scripting/SelectionScriptingInterface.h | 27 ++++- libraries/render-utils/src/FadeEffectJobs.cpp | 99 ++++++++----------- libraries/render-utils/src/FadeEffectJobs.h | 1 - .../utilities/render/debugTransition.js | 50 +++++++++- 5 files changed, 137 insertions(+), 62 deletions(-) diff --git a/interface/src/scripting/SelectionScriptingInterface.cpp b/interface/src/scripting/SelectionScriptingInterface.cpp index 233e61c8ae..f8a62e848c 100644 --- a/interface/src/scripting/SelectionScriptingInterface.cpp +++ b/interface/src/scripting/SelectionScriptingInterface.cpp @@ -110,7 +110,6 @@ bool SelectionScriptingInterface::enableListHighlight(const QString& listName, c } if (!(*highlightStyle).isBoundToList()) { - setupHandler(listName); (*highlightStyle).setBoundToList(true); } @@ -172,6 +171,18 @@ render::HighlightStyle SelectionScriptingInterface::getHighlightStyle(const QStr } } +bool SelectionScriptingInterface::enableListToScene(const QString& listName) { + setupHandler(listName); + + return true; +} + +bool SelectionScriptingInterface::disableListToScene(const QString& listName) { + removeHandler(listName); + + return true; +} + template bool SelectionScriptingInterface::addToGameplayObjects(const QString& listName, T idToAdd) { { QWriteLocker lock(&_selectionListsLock); @@ -303,6 +314,15 @@ void SelectionScriptingInterface::setupHandler(const QString& selectionName) { (*handler)->initialize(selectionName); } +void SelectionScriptingInterface::removeHandler(const QString& selectionName) { + QWriteLocker lock(&_selectionHandlersLock); + auto handler = _handlerMap.find(selectionName); + if (handler != _handlerMap.end()) { + delete handler.value(); + _handlerMap.erase(handler); + } +} + void SelectionScriptingInterface::onSelectedItemsListChanged(const QString& listName) { { QWriteLocker lock(&_selectionHandlersLock); diff --git a/interface/src/scripting/SelectionScriptingInterface.h b/interface/src/scripting/SelectionScriptingInterface.h index 8295375870..3046ac371e 100644 --- a/interface/src/scripting/SelectionScriptingInterface.h +++ b/interface/src/scripting/SelectionScriptingInterface.h @@ -160,13 +160,14 @@ public: * If the Selection doesn't exist, it will be created. * All objects in the list will be displayed with the highlight effect as specified from the highlightStyle. * The function can be called several times with different values in the style to modify it. - * + * * @function Selection.enableListHighlight * @param listName {string} name of the selection * @param highlightStyle {jsObject} highlight style fields (see Selection.getListHighlightStyle for a detailed description of the highlightStyle). * @returns {bool} true if the selection was successfully enabled for highlight. */ Q_INVOKABLE bool enableListHighlight(const QString& listName, const QVariantMap& highlightStyle); + /**jsdoc * Disable highlighting for the named selection. * If the Selection doesn't exist or wasn't enabled for highliting then nothing happens simply returning false. @@ -175,7 +176,27 @@ public: * @param listName {string} name of the selection * @returns {bool} true if the selection was successfully disabled for highlight, false otherwise. */ - Q_INVOKABLE bool disableListHighlight(const QString& listName); + Q_INVOKABLE bool disableListHighlight(const QString& listName); + /**jsdoc + * Enable scene selection for the named selection. + * If the Selection doesn't exist, it will be created. + * All objects in the list will be sent to a scene selection. + * + * @function Selection.enableListToScene + * @param listName {string} name of the selection + * @returns {bool} true if the selection was successfully enabled on the scene. + */ + Q_INVOKABLE bool enableListToScene(const QString& listName); + /**jsdoc + * Disable scene selection for the named selection. + * If the Selection doesn't exist or wasn't enabled on the scene then nothing happens simply returning false. + * + * @function Selection.disableListToScene + * @param listName {string} name of the selection + * @returns {bool} true if the selection was successfully disabled on the scene, false otherwise. + */ + Q_INVOKABLE bool disableListToScene(const QString& listName); + /**jsdoc * Query the highlight style values for the named selection. * If the Selection doesn't exist or hasn't been highlight enabled yet, it will return an empty object. @@ -223,7 +244,7 @@ private: template bool removeFromGameplayObjects(const QString& listName, T idToRemove); void setupHandler(const QString& selectionName); - + void removeHandler(const QString& selectionName); }; diff --git a/libraries/render-utils/src/FadeEffectJobs.cpp b/libraries/render-utils/src/FadeEffectJobs.cpp index da3f8dddc0..e6de306c6d 100644 --- a/libraries/render-utils/src/FadeEffectJobs.cpp +++ b/libraries/render-utils/src/FadeEffectJobs.cpp @@ -39,43 +39,52 @@ void FadeEditJob::run(const render::RenderContextPointer& renderContext, const F auto scene = renderContext->_scene; if (_isEditEnabled) { - float minIsectDistance = std::numeric_limits::max(); - auto& itemBounds = inputs.get0(); - auto editedItem = findNearestItem(renderContext, itemBounds, minIsectDistance); - render::Transaction transaction; - bool hasTransaction{ false }; + static const std::string selectionName("TransitionEdit"); + auto scene = renderContext->_scene; + if (!scene->isSelectionEmpty(selectionName)) { + auto selection = scene->getSelection(selectionName); + auto editedItem = selection.getItems().front(); + render::Transaction transaction; + bool hasTransaction{ false }; - if (editedItem != _editedItem && render::Item::isValidID(_editedItem)) { - // Remove transition from previously edited item as we've changed edited item - hasTransaction = true; + if (editedItem != _editedItem && render::Item::isValidID(_editedItem)) { + // Remove transition from previously edited item as we've changed edited item + hasTransaction = true; + transaction.removeTransitionFromItem(_editedItem); + } + _editedItem = editedItem; + + if (render::Item::isValidID(_editedItem)) { + static const render::Transition::Type categoryToTransition[FADE_CATEGORY_COUNT] = { + render::Transition::ELEMENT_ENTER_DOMAIN, + render::Transition::BUBBLE_ISECT_OWNER, + render::Transition::BUBBLE_ISECT_TRESPASSER, + render::Transition::USER_ENTER_DOMAIN, + render::Transition::AVATAR_CHANGE + }; + + auto transitionType = categoryToTransition[inputs.get1()]; + + transaction.queryTransitionOnItem(_editedItem, [transitionType, scene](render::ItemID id, const render::Transition* transition) { + if (transition == nullptr || transition->isFinished || transition->eventType != transitionType) { + // Relaunch transition + render::Transaction transaction; + transaction.addTransitionToItem(id, transitionType); + scene->enqueueTransaction(transaction); + } + }); + hasTransaction = true; + } + + if (hasTransaction) { + scene->enqueueTransaction(transaction); + } + } else if (render::Item::isValidID(_editedItem)) { + // Remove transition from previously edited item as we've disabled fade edition + render::Transaction transaction; transaction.removeTransitionFromItem(_editedItem); - } - _editedItem = editedItem; - - if (render::Item::isValidID(_editedItem)) { - static const render::Transition::Type categoryToTransition[FADE_CATEGORY_COUNT] = { - render::Transition::ELEMENT_ENTER_DOMAIN, - render::Transition::BUBBLE_ISECT_OWNER, - render::Transition::BUBBLE_ISECT_TRESPASSER, - render::Transition::USER_ENTER_DOMAIN, - render::Transition::AVATAR_CHANGE - }; - - auto transitionType = categoryToTransition[inputs.get1()]; - - transaction.queryTransitionOnItem(_editedItem, [transitionType, scene](render::ItemID id, const render::Transition* transition) { - if (transition == nullptr || transition->isFinished || transition->eventType!=transitionType) { - // Relaunch transition - render::Transaction transaction; - transaction.addTransitionToItem(id, transitionType); - scene->enqueueTransaction(transaction); - } - }); - hasTransaction = true; - } - - if (hasTransaction) { scene->enqueueTransaction(transaction); + _editedItem = render::Item::INVALID_ITEM_ID; } } else if (render::Item::isValidID(_editedItem)) { @@ -87,28 +96,6 @@ void FadeEditJob::run(const render::RenderContextPointer& renderContext, const F } } -render::ItemID FadeEditJob::findNearestItem(const render::RenderContextPointer& renderContext, const render::ItemBounds& inputs, float& minIsectDistance) const { - const glm::vec3 rayOrigin = renderContext->args->getViewFrustum().getPosition(); - const glm::vec3 rayDirection = renderContext->args->getViewFrustum().getDirection(); - BoxFace face; - glm::vec3 normal; - float isectDistance; - render::ItemID nearestItem = render::Item::INVALID_ITEM_ID; - const float minDistance = 1.f; - const float maxDistance = 50.f; - - for (const auto& itemBound : inputs) { - if (!itemBound.bound.contains(rayOrigin) && itemBound.bound.findRayIntersection(rayOrigin, rayDirection, isectDistance, face, normal)) { - auto& item = renderContext->_scene->getItem(itemBound.id); - if (item.getKey().isWorldSpace() && isectDistance>minDistance && isectDistance < minIsectDistance && isectDistance