History

more Models->Entities renaming

ZappoMan committed 12 years ago

Commit c4fe36b1 parent a60e66b25 files · +8 −8Browse files

Showing the changes to libraries/entities/src/EntityScriptingInterface.cpp (1 of 25 files). Show all

Unified · Split

libraries/entities/src/EntityScriptingInterface.cpp+287−0
@@ -0,0 +1,287 @@
1//
2// EntityScriptingInterface.cpp
3// libraries/models/src
4//
5// Created by Brad Hefta-Gaub on 12/6/13.
6// Copyright 2013 High Fidelity, Inc.
7//
8// Distributed under the Apache License, Version 2.0.
9// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
10//
11
12#include "EntityScriptingInterface.h"
13#include "EntityTree.h"
14
15EntityScriptingInterface::EntityScriptingInterface() :
16 _nextCreatorTokenID(0),
17 _entityTree(NULL)
18{
19}
20
21
22void EntityScriptingInterface::queueEntityMessage(PacketType packetType,
23 EntityItemID entityID, const EntityItemProperties& properties) {
24 getEntityPacketSender()->queueEntityEditMessage(packetType, entityID, properties);
25}
26
27EntityItemID EntityScriptingInterface::addEntity(const EntityItemProperties& properties) {
28
29 // The application will keep track of creatorTokenID
30 uint32_t creatorTokenID = EntityItem::getNextCreatorTokenID();
31
32 EntityItemID id(NEW_MODEL, creatorTokenID, false );
33
34 // queue the packet
35 queueEntityMessage(PacketTypeEntityAddOrEdit, id, properties);
36
37 // If we have a local model tree set, then also update it.
38 if (_entityTree) {
39 _entityTree->lockForWrite();
40 _entityTree->addEntity(id, properties);
41 _entityTree->unlock();
42 }
43
44 return id;
45}
46
47EntityItemID EntityScriptingInterface::identifyEntity(EntityItemID entityID) {
48 uint32_t actualID = entityID.id;
49
50 if (!entityID.isKnownID) {
51 actualID = EntityItem::getIDfromCreatorTokenID(entityID.creatorTokenID);
52 if (actualID == UNKNOWN_MODEL_ID) {
53 return entityID; // bailing early
54 }
55
56 // found it!
57 entityID.id = actualID;
58 entityID.isKnownID = true;
59 }
60 return entityID;
61}
62
63EntityItemProperties EntityScriptingInterface::getEntityProperties(EntityItemID entityID) {
64 EntityItemProperties results;
65 EntityItemID identity = identifyEntity(entityID);
66 if (!identity.isKnownID) {
67 results.setIsUnknownID();
68 return results;
69 }
70 if (_entityTree) {
71 _entityTree->lockForRead();
72 const EntityItem* model = _entityTree->findEntityByID(identity.id, true);
73 if (model) {
74 results.copyFromEntityItem(*model);
75 } else {
76 results.setIsUnknownID();
77 }
78 _entityTree->unlock();
79 }
80
81 return results;
82}
83
84
85
86EntityItemID EntityScriptingInterface::editEntity(EntityItemID entityID, const EntityItemProperties& properties) {
87 uint32_t actualID = entityID.id;
88
89 // if the model is unknown, attempt to look it up
90 if (!entityID.isKnownID) {
91 actualID = EntityItem::getIDfromCreatorTokenID(entityID.creatorTokenID);
92 }
93
94 // if at this point, we know the id, send the update to the model server
95 if (actualID != UNKNOWN_MODEL_ID) {
96 entityID.id = actualID;
97 entityID.isKnownID = true;
98 queueEntityMessage(PacketTypeEntityAddOrEdit, entityID, properties);
99 }
100
101 // If we have a local model tree set, then also update it. We can do this even if we don't know
102 // the actual id, because we can edit out local models just with creatorTokenID
103 if (_entityTree) {
104 _entityTree->lockForWrite();
105 _entityTree->updateEntity(entityID, properties);
106 _entityTree->unlock();
107 }
108 return entityID;
109}
110
111
112// TODO: This deleteEntity() method uses the PacketType_MODEL_ADD_OR_EDIT message to send
113// a changed model with a shouldDie() property set to true. This works and is currently the only
114// way to tell the model server to delete a model. But we should change this to use the PacketType_MODEL_ERASE
115// message which takes a list of model id's to delete.
116void EntityScriptingInterface::deleteEntity(EntityItemID entityID) {
117
118 // setup properties to kill the model
119 EntityItemProperties properties;
120 properties.setShouldDie(true);
121
122 uint32_t actualID = entityID.id;
123
124 // if the model is unknown, attempt to look it up
125 if (!entityID.isKnownID) {
126 actualID = EntityItem::getIDfromCreatorTokenID(entityID.creatorTokenID);
127 }
128
129 // if at this point, we know the id, send the update to the model server
130 if (actualID != UNKNOWN_MODEL_ID) {
131 entityID.id = actualID;
132 entityID.isKnownID = true;
133 queueEntityMessage(PacketTypeEntityAddOrEdit, entityID, properties);
134 }
135
136 // If we have a local model tree set, then also update it.
137 if (_entityTree) {
138 _entityTree->lockForWrite();
139 _entityTree->deleteEntity(entityID);
140 _entityTree->unlock();
141 }
142}
143
144EntityItemID EntityScriptingInterface::findClosestEntity(const glm::vec3& center, float radius) const {
145 EntityItemID result(UNKNOWN_MODEL_ID, UNKNOWN_MODEL_TOKEN, false);
146 if (_entityTree) {
147 _entityTree->lockForRead();
148 const EntityItem* closestEntity = _entityTree->findClosestEntity(center/(float)TREE_SCALE,
149 radius/(float)TREE_SCALE);
150 _entityTree->unlock();
151 if (closestEntity) {
152 result.id = closestEntity->getID();
153 result.isKnownID = true;
154 }
155 }
156 return result;
157}
158
159
160QVector<EntityItemID> EntityScriptingInterface::findEntities(const glm::vec3& center, float radius) const {
161 QVector<EntityItemID> result;
162 if (_entityTree) {
163 _entityTree->lockForRead();
164 QVector<const EntityItem*> models;
165 _entityTree->findEntities(center/(float)TREE_SCALE, radius/(float)TREE_SCALE, models);
166 _entityTree->unlock();
167
168 foreach (const EntityItem* model, models) {
169 EntityItemID thisEntityItemID(model->getID(), UNKNOWN_MODEL_TOKEN, true);
170 result << thisEntityItemID;
171 }
172 }
173 return result;
174}
175
176RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersection(const PickRay& ray) {
177 return findRayIntersectionWorker(ray, Octree::TryLock);
178}
179
180RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersectionBlocking(const PickRay& ray) {
181 return findRayIntersectionWorker(ray, Octree::Lock);
182}
183
184RayToEntityIntersectionResult EntityScriptingInterface::findRayIntersectionWorker(const PickRay& ray,
185 Octree::lockType lockType) {
186 RayToEntityIntersectionResult result;
187 if (_entityTree) {
188 OctreeElement* element;
189 EntityItem* intersectedEntity;
190 result.intersects = _entityTree->findRayIntersection(ray.origin, ray.direction, element, result.distance, result.face,
191 (void**)&intersectedEntity, lockType, &result.accurate);
192 if (result.intersects && intersectedEntity) {
193 result.entityID = intersectedEntity->getEntityItemID();
194 result.properties = intersectedEntity->getProperties();
195 result.intersection = ray.origin + (ray.direction * result.distance);
196 }
197 }
198 return result;
199}
200
201
202RayToEntityIntersectionResult::RayToEntityIntersectionResult() :
203 intersects(false),
204 accurate(true), // assume it's accurate
205 entityID(),
206 properties(),
207 distance(0),
208 face()
209{
210};
211
212QScriptValue RayToEntityIntersectionResultToScriptValue(QScriptEngine* engine, const RayToEntityIntersectionResult& value) {
213 QScriptValue obj = engine->newObject();
214 obj.setProperty("intersects", value.intersects);
215 obj.setProperty("accurate", value.accurate);
216 QScriptValue modelItemValue = EntityItemIDtoScriptValue(engine, value.entityID);
217 obj.setProperty("entityID", modelItemValue);
218
219 QScriptValue modelPropertiesValue = EntityItemPropertiesToScriptValue(engine, value.properties);
220 obj.setProperty("properties", modelPropertiesValue);
221
222 obj.setProperty("distance", value.distance);
223
224 QString faceName = "";
225 // handle BoxFace
226 switch (value.face) {
227 case MIN_X_FACE:
228 faceName = "MIN_X_FACE";
229 break;
230 case MAX_X_FACE:
231 faceName = "MAX_X_FACE";
232 break;
233 case MIN_Y_FACE:
234 faceName = "MIN_Y_FACE";
235 break;
236 case MAX_Y_FACE:
237 faceName = "MAX_Y_FACE";
238 break;
239 case MIN_Z_FACE:
240 faceName = "MIN_Z_FACE";
241 break;
242 case MAX_Z_FACE:
243 faceName = "MAX_Z_FACE";
244 break;
245 case UNKNOWN_FACE:
246 faceName = "UNKNOWN_FACE";
247 break;
248 }
249 obj.setProperty("face", faceName);
250
251 QScriptValue intersection = vec3toScriptValue(engine, value.intersection);
252 obj.setProperty("intersection", intersection);
253 return obj;
254}
255
256void RayToEntityIntersectionResultFromScriptValue(const QScriptValue& object, RayToEntityIntersectionResult& value) {
257 value.intersects = object.property("intersects").toVariant().toBool();
258 value.accurate = object.property("accurate").toVariant().toBool();
259 QScriptValue modelIDValue = object.property("entityID");
260 if (modelIDValue.isValid()) {
261 EntityItemIDfromScriptValue(modelIDValue, value.entityID);
262 }
263 QScriptValue modelPropertiesValue = object.property("properties");
264 if (modelPropertiesValue.isValid()) {
265 EntityItemPropertiesFromScriptValue(modelPropertiesValue, value.properties);
266 }
267 value.distance = object.property("distance").toVariant().toFloat();
268
269 QString faceName = object.property("face").toVariant().toString();
270 if (faceName == "MIN_X_FACE") {
271 value.face = MIN_X_FACE;
272 } else if (faceName == "MAX_X_FACE") {
273 value.face = MAX_X_FACE;
274 } else if (faceName == "MIN_Y_FACE") {
275 value.face = MIN_Y_FACE;
276 } else if (faceName == "MAX_Y_FACE") {
277 value.face = MAX_Y_FACE;
278 } else if (faceName == "MIN_Z_FACE") {
279 value.face = MIN_Z_FACE;
280 } else {
281 value.face = MAX_Z_FACE;
282 };
283 QScriptValue intersection = object.property("intersection");
284 if (intersection.isValid()) {
285 vec3FromScriptValue(intersection, value.intersection);
286 }
287}