From f93b1d3325bd12a1f0f1c8e7a08161f6936dc908 Mon Sep 17 00:00:00 2001 From: ericrius1 Date: Mon, 12 Oct 2015 17:05:34 -0700 Subject: [PATCH] Correctly whitelisting entities for ray picking --- examples/controllers/handControllerGrab.js | 3 ++- .../whiteboard/whiteboardEntityScript.js | 7 ++---- .../painting/whiteboard/whiteboardSpawner.js | 4 +-- .../entities/src/EntityScriptingInterface.cpp | 25 ++++++++++++------- .../entities/src/EntityScriptingInterface.h | 4 +-- libraries/entities/src/EntityTreeElement.cpp | 14 ++++++++++- libraries/shared/src/RegisteredMetaTypes.cpp | 17 +++++++++++++ libraries/shared/src/RegisteredMetaTypes.h | 2 ++ 8 files changed, 56 insertions(+), 20 deletions(-) diff --git a/examples/controllers/handControllerGrab.js b/examples/controllers/handControllerGrab.js index 26cb522f9a..562e5396b1 100644 --- a/examples/controllers/handControllerGrab.js +++ b/examples/controllers/handControllerGrab.js @@ -253,6 +253,7 @@ function MyController(hand, triggerAction) { return; } + // the trigger is being pressed, do a ray test var handPosition = this.getHandPosition(); var pickRay = { @@ -568,7 +569,7 @@ function MyController(hand, triggerAction) { this.setState(STATE_RELEASE); return; } - + print("AHHHHHH") Entities.callEntityMethod(this.grabbedEntity, "continueNearGrabbingNonColliding"); }; diff --git a/examples/painting/whiteboard/whiteboardEntityScript.js b/examples/painting/whiteboard/whiteboardEntityScript.js index 139c92c710..6d651c974e 100644 --- a/examples/painting/whiteboard/whiteboardEntityScript.js +++ b/examples/painting/whiteboard/whiteboardEntityScript.js @@ -22,6 +22,7 @@ var TIP_CONTROLLER_OFFSET = 1; Whiteboard = function() { _this = this; + print("WAAAAAH"); }; Whiteboard.prototype = { @@ -52,12 +53,8 @@ origin: handPosition, direction: Quat.getUp(this.getHandRotation()) }; + this.intersection = Entities.findRayIntersection(pickRay, true, [this.entityID]); - if (this.intersection.intersects) { - if(JSON.stringify(this.intersection.entityID) === JSON.stringify(this.entityID)) { - print('YAAAAA') - } - } }, releaseGrab: function() { diff --git a/examples/painting/whiteboard/whiteboardSpawner.js b/examples/painting/whiteboard/whiteboardSpawner.js index 31a72212c3..506323dd59 100644 --- a/examples/painting/whiteboard/whiteboardSpawner.js +++ b/examples/painting/whiteboard/whiteboardSpawner.js @@ -15,7 +15,7 @@ Script.include("../../libraries/utils.js"); -var scriptURL = Script.resolvePath("whiteBoardEntityScript.js"); +var scriptURL = Script.resolvePath("whiteBoardEntityScript.js?v1" +Math.random()); var rotation = Quat.safeEulerAngles(Camera.getOrientation()); rotation = Quat.fromPitchYawRollDegrees(0, rotation.y, 0); @@ -26,7 +26,7 @@ var whiteboard = Entities.addEntity({ position: center, rotation: rotation, script: scriptURL, - dimensions: {x: 2, y: 1.5, z: 0.01}, + dimensions: {x: 2, y: 1.5, z: 0.1}, color: {red: 255, green: 255, blue: 255} }); diff --git a/libraries/entities/src/EntityScriptingInterface.cpp b/libraries/entities/src/EntityScriptingInterface.cpp index d260e73948..692ca7a638 100644 --- a/libraries/entities/src/EntityScriptingInterface.cpp +++ b/libraries/entities/src/EntityScriptingInterface.cpp @@ -279,12 +279,14 @@ QVector EntityScriptingInterface::findEntitiesInBox(const glm::vec3& corn return result; } -RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersection(const PickRay& ray, bool precisionPicking, const QVector& entityIdsToInclude) { - return findRayIntersectionWorker(ray, Octree::TryLock, precisionPicking, entityIdsToInclude); +RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersection(const PickRay& ray, bool precisionPicking, const QScriptValue& entityIdsToInclude) { + QVector entities = qVectorQUuidFromScriptValue(entityIdsToInclude); + return findRayIntersectionWorker(ray, Octree::TryLock, precisionPicking, entities); } -RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersectionBlocking(const PickRay& ray, bool precisionPicking, const QVector& entityIdsToInclude) { - return findRayIntersectionWorker(ray, Octree::Lock, precisionPicking, entityIdsToInclude); +RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersectionBlocking(const PickRay& ray, bool precisionPicking, const QScriptValue& entityIdsToInclude) { + const QVector& entities = qVectorQUuidFromScriptValue(entityIdsToInclude); + return findRayIntersectionWorker(ray, Octree::Lock, precisionPicking, entities); } RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersectionWorker(const PickRay& ray, @@ -414,15 +416,20 @@ void RayToEntityIntersectionResultFromScriptValue(const QScriptValue& object, Ra QString faceName = object.property("face").toVariant().toString(); if (faceName == "MIN_X_FACE") { value.face = MIN_X_FACE; - } else if (faceName == "MAX_X_FACE") { + } + else if (faceName == "MAX_X_FACE") { value.face = MAX_X_FACE; - } else if (faceName == "MIN_Y_FACE") { + } + else if (faceName == "MIN_Y_FACE") { value.face = MIN_Y_FACE; - } else if (faceName == "MAX_Y_FACE") { + } + else if (faceName == "MAX_Y_FACE") { value.face = MAX_Y_FACE; - } else if (faceName == "MIN_Z_FACE") { + } + else if (faceName == "MIN_Z_FACE") { value.face = MIN_Z_FACE; - } else { + } + else { value.face = MAX_Z_FACE; }; QScriptValue intersection = object.property("intersection"); diff --git a/libraries/entities/src/EntityScriptingInterface.h b/libraries/entities/src/EntityScriptingInterface.h index 56610f2924..48f13e81bd 100644 --- a/libraries/entities/src/EntityScriptingInterface.h +++ b/libraries/entities/src/EntityScriptingInterface.h @@ -111,11 +111,11 @@ public slots: /// If the scripting context has visible entities, this will determine a ray intersection, the results /// may be inaccurate if the engine is unable to access the visible entities, in which case result.accurate /// will be false. - Q_INVOKABLE RayToEntityIntersectionResult findRayIntersection(const PickRay& ray, bool precisionPicking = false, const QVector& entityIdsToInclude = QVector()); + Q_INVOKABLE RayToEntityIntersectionResult findRayIntersection(const PickRay& ray, bool precisionPicking = false, const QScriptValue& entityIdsToInclude = QScriptValue()); /// If the scripting context has visible entities, this will determine a ray intersection, and will block in /// order to return an accurate result - Q_INVOKABLE RayToEntityIntersectionResult findRayIntersectionBlocking(const PickRay& ray, bool precisionPicking = false, const QVector& entityIdsToInclude = QVector()); + Q_INVOKABLE RayToEntityIntersectionResult findRayIntersectionBlocking(const PickRay& ray, bool precisionPicking = false, const QScriptValue& entityIdsToInclude = QScriptValue()); Q_INVOKABLE void setLightsArePickable(bool value); Q_INVOKABLE bool getLightsArePickable() const; diff --git a/libraries/entities/src/EntityTreeElement.cpp b/libraries/entities/src/EntityTreeElement.cpp index d1f7adef94..89e8e2d6d8 100644 --- a/libraries/entities/src/EntityTreeElement.cpp +++ b/libraries/entities/src/EntityTreeElement.cpp @@ -501,8 +501,20 @@ bool EntityTreeElement::findDetailedRayIntersection(const glm::vec3& origin, con int entityNumber = 0; bool somethingIntersected = false; forEachEntity([&](EntityItemPointer entity) { + if (entityIdsToInclude.size() > 0) { + bool entityInWhiteList = false; + //We only want to search whitelist if there is one, otherwise everything except blacklisted items are valid + for (int i = 0; i < entityIdsToInclude.size(); i++) { + if (entityIdsToInclude.at(i) == entity->getID()) { + entityInWhiteList = true; + } + } + if (!entityInWhiteList) { + // qDebug() << "entity not found in whitelist!"; + return; + } + } - qDebug() << "entity Ids to ignore:************* " << entityIdsToInclude; AABox entityBox = entity->getAABox(); float localDistance; BoxFace localFace; diff --git a/libraries/shared/src/RegisteredMetaTypes.cpp b/libraries/shared/src/RegisteredMetaTypes.cpp index b2389f4db6..27921336cf 100644 --- a/libraries/shared/src/RegisteredMetaTypes.cpp +++ b/libraries/shared/src/RegisteredMetaTypes.cpp @@ -104,6 +104,23 @@ QVector qVectorFloatFromScriptValue(const QScriptValue& array) { return newVector; } +QVector qVectorQUuidFromScriptValue(const QScriptValue& array) { + if (!array.isArray()) { + return QVector(); + } + QVector newVector; + int length = array.property("length").toInteger(); + newVector.reserve(length); + for (int i = 0; i < length; i++) { + QString uuidAsString = array.property(i).toString(); + QUuid fromString(uuidAsString); + newVector << fromString; + } + + return newVector; +} + + QScriptValue qVectorFloatToScriptValue(QScriptEngine* engine, const QVector& vector) { QScriptValue array = engine->newArray(); for (int i = 0; i < vector.size(); i++) { diff --git a/libraries/shared/src/RegisteredMetaTypes.h b/libraries/shared/src/RegisteredMetaTypes.h index c419741c3b..cd1e3b0d3e 100644 --- a/libraries/shared/src/RegisteredMetaTypes.h +++ b/libraries/shared/src/RegisteredMetaTypes.h @@ -65,6 +65,8 @@ QScriptValue qVectorFloatToScriptValue(QScriptEngine* engine, const QVector& vector); QVector qVectorFloatFromScriptValue(const QScriptValue& array); +QVector qVectorQUuidFromScriptValue(const QScriptValue& array); + class PickRay { public: PickRay() : origin(0.0f), direction(0.0f) { }