14 #ifndef hifi_EntityTreeRenderer_h
15 #define hifi_EntityTreeRenderer_h
19 #include <QtCore/QSet>
20 #include <QtCore/QStack>
21 #include <QtGui/QMouseEvent>
22 #include <QtCore/QSharedPointer>
24 #include <AudioInjectorManager.h>
25 #include <EntityScriptingInterface.h>
26 #include <EntityTree.h>
27 #include <PointerEvent.h>
28 #include <ScriptCache.h>
29 #include <TextureCache.h>
30 #include <OctreeProcessor.h>
31 #include <render/Forward.h>
32 #include <workload/Space.h>
33 #include <FadeProperties.h>
43 using ScriptEnginePointer = std::shared_ptr<ScriptEngine>;
44 using ScriptManagerPointer = std::shared_ptr<ScriptManager>;
46 namespace render {
namespace entities {
48 using EntityRendererPointer = std::shared_ptr<EntityRenderer>;
49 using EntityRendererWeakPointer = std::weak_ptr<EntityRenderer>;
53 using EntityRenderer = render::entities::EntityRenderer;
54 using EntityRendererPointer = render::entities::EntityRendererPointer;
55 using EntityRendererWeakPointer = render::entities::EntityRendererWeakPointer;
57 using ModelPointer = std::shared_ptr<Model>;
58 using ModelWeakPointer = std::weak_ptr<Model>;
60 using CalculateEntityLoadingPriority = std::function<float(
const EntityItem& item)>;
63 class EntityTreeRenderer :
public OctreeProcessor,
public Dependency {
68 virtual ~EntityTreeRenderer();
70 QSharedPointer<EntityTreeRenderer> getSharedFromThis() {
71 return qSharedPointerCast<EntityTreeRenderer>(sharedFromThis());
74 virtual char getMyNodeType()
const override {
return NodeType::EntityServer; }
75 virtual PacketType getMyQueryMessageType()
const override {
return PacketType::EntityQuery; }
76 virtual PacketType getExpectedPacketType()
const override {
return PacketType::EntityData; }
79 static CalculateEntityLoadingPriority getEntityLoadingPriorityOperator() {
return _calculateEntityLoadingPriorityFunc; }
80 static float getEntityLoadingPriority(
const EntityItem& item) {
return _calculateEntityLoadingPriorityFunc(item); }
81 static void setEntityLoadingPriorityFunction(CalculateEntityLoadingPriority fn) { _calculateEntityLoadingPriorityFunc = fn; }
83 void setMouseRayPickID(
unsigned int rayPickID) { _mouseRayPickID = rayPickID; }
84 unsigned int getMouseRayPickID() {
return _mouseRayPickID; }
85 void setMouseRayPickResultOperator(std::function<RayToEntityIntersectionResult(
unsigned int)> getPrevRayPickResultOperator) { _getPrevRayPickResultOperator = getPrevRayPickResultOperator; }
86 void setSetPrecisionPickingOperator(std::function<
void(
unsigned int,
bool)> setPrecisionPickingOperator) { _setPrecisionPickingOperator = setPrecisionPickingOperator; }
90 void update(
bool simulate);
92 EntityTreePointer getTree() {
return std::static_pointer_cast<EntityTree>(_tree); }
94 void processEraseMessage(ReceivedMessage& message,
const SharedNodePointer& sourceNode);
96 virtual void init()
override;
99 virtual void clearDomainAndNonOwnedEntities()
override;
100 virtual void clear()
override;
103 void reloadEntityScripts();
105 void fadeOutRenderable(
const EntityRendererPointer& renderable);
106 FadeProperties getLayeredZoneFadeProperties(
const TransitionType type)
const {
return _layeredZones.getFadeProperties(type); }
109 QUuid mousePressEvent(QMouseEvent* event);
110 void mouseReleaseEvent(QMouseEvent* event);
111 void mouseDoublePressEvent(QMouseEvent* event);
112 void mouseMoveEvent(QMouseEvent* event);
116 void connectSignalsToSlots(EntityScriptingInterface* entityScriptingInterface);
119 QList<EntityItemID>& getEntitiesLastInScene() {
return _entityIDsLastInScene; }
121 std::pair<bool, bool> getZoneInteractionProperties();
125 bool wantsHandControllerPointerEvents(
const EntityItemID&
id)
const;
126 void setProxyWindow(
const EntityItemID&
id, QWindow* proxyWindow);
127 void setCollisionSound(
const EntityItemID&
id,
const SharedSoundPointer& sound);
133 workload::SpacePointer getWorkloadSpace()
const {
return _space; }
137 static void setAddMaterialToEntityOperator(std::function<
bool(
const QUuid&, graphics::MaterialLayer,
const std::string&)> addMaterialToEntityOperator) { _addMaterialToEntityOperator = addMaterialToEntityOperator; }
138 static void setRemoveMaterialFromEntityOperator(std::function<
bool(
const QUuid&, graphics::MaterialPointer,
const std::string&)> removeMaterialFromEntityOperator) { _removeMaterialFromEntityOperator = removeMaterialFromEntityOperator; }
139 static bool addMaterialToEntity(
const QUuid& entityID, graphics::MaterialLayer material,
const std::string& parentMaterialName);
140 static bool removeMaterialFromEntity(
const QUuid& entityID, graphics::MaterialPointer material,
const std::string& parentMaterialName);
142 static void setAddMaterialToAvatarOperator(std::function<
bool(
const QUuid&, graphics::MaterialLayer,
const std::string&)> addMaterialToAvatarOperator) { _addMaterialToAvatarOperator = addMaterialToAvatarOperator; }
143 static void setRemoveMaterialFromAvatarOperator(std::function<
bool(
const QUuid&, graphics::MaterialPointer,
const std::string&)> removeMaterialFromAvatarOperator) { _removeMaterialFromAvatarOperator = removeMaterialFromAvatarOperator; }
144 static bool addMaterialToAvatar(
const QUuid& avatarID, graphics::MaterialLayer material,
const std::string& parentMaterialName);
145 static bool removeMaterialFromAvatar(
const QUuid& avatarID, graphics::MaterialPointer material,
const std::string& parentMaterialName);
147 size_t getPrevNumEntityUpdates()
const {
return _prevNumEntityUpdates; }
148 size_t getPrevTotalNeededEntityUpdates()
const {
return _prevTotalNeededEntityUpdates; }
150 bool layeredZonesHaveFade(
const TransitionType type)
const {
return _layeredZones.hasFade(type); }
154 bool unloadFirst =
false,
155 const QString& oldOverrideURL =
"",
156 const QString& newOverrideURL =
"");
157 void unloadEntityScript(
const EntityItemID& entityID,
const QString& scriptURL);
158 void updateScriptUserData(
const EntityItemID& entityID,
const QString& scriptURL,
const QString& userData);
168 void entityScriptChanging(
const EntityItemID& entityID,
const bool reload);
170 void updateEntityRenderStatus(
bool shouldRenderEntities);
174 void setDisplayModelBounds(
bool value) { _displayModelBounds = value; }
175 void setPrecisionPicking(
bool value) { _setPrecisionPickingOperator(_mouseRayPickID, value); }
176 EntityRendererPointer renderableForEntityId(
const EntityItemID&
id)
const;
177 render::ItemID renderableIdForEntityId(
const EntityItemID&
id)
const;
179 void handleSpaceUpdate(std::pair<int32_t, glm::vec4> proxyUpdate);
182 virtual OctreePointer createTree()
override {
183 EntityTreePointer newTree = std::make_shared<EntityTree>(
true);
184 newTree->createRootElement();
189 void addPendingEntities(
const render::ScenePointer& scene, render::Transaction& transaction);
190 void updateChangedEntities(
const render::ScenePointer& scene, render::Transaction& transaction);
191 EntityRendererPointer renderableForEntity(
const EntityItemPointer& entity)
const {
return renderableForEntityId(entity->getID()); }
192 render::ItemID renderableIdForEntity(
const EntityItemPointer& entity)
const {
return renderableIdForEntityId(entity->getID()); }
194 void resetPersistentEntitiesScriptEngine();
195 void resetNonPersistentEntitiesScriptEngine();
196 void setupEntityScriptEngineSignals(
const ScriptManagerPointer& scriptManager);
198 void findBestZoneAndMaybeContainingEntities(QSet<EntityItemID>& entitiesContainingAvatar);
200 bool applyLayeredZones();
201 void stopDomainAndNonOwnedEntities();
206 ScriptValueList createEntityArgs(
const EntityItemID& entityID);
207 void checkEnterLeaveEntities();
208 void leaveDomainAndNonOwnedEntities();
209 void leaveAllEntities();
210 void forceRecheckEntities();
212 glm::vec3 _avatarPosition { 0.0f };
213 bool _forceRecheckEntities {
true };
214 QSet<EntityItemID> _currentEntitiesInside;
217 ScriptManagerPointer _nonPersistentEntitiesScriptManager;
218 ScriptManagerPointer _persistentEntitiesScriptManager;
220 void playEntityCollisionSound(
const EntityItemPointer& entity,
const Collision& collision);
222 bool _lastPointerEventValid;
226 bool _displayModelBounds;
228 bool _shuttingDown {
false };
230 QMultiMap<QUrl, EntityItemID> _waitingOnPreload;
232 unsigned int _mouseRayPickID;
233 std::function<RayToEntityIntersectionResult(
unsigned int)> _getPrevRayPickResultOperator;
234 std::function<void(
unsigned int,
bool)> _setPrecisionPickingOperator;
238 LayeredZone(std::shared_ptr<ZoneEntityItem> zone) : zone(zone), id(zone->getID()), volume(zone->getVolumeEstimate()) {}
241 bool operator<(
const LayeredZone& r)
const {
return volume < r.volume || (volume == r.volume &&
id < r.id); }
242 bool operator==(
const LayeredZone& r)
const {
return zone.lock() && zone.lock() == r.zone.lock(); }
243 bool operator!=(
const LayeredZone& r)
const {
return !(*
this == r); }
244 bool operator<=(
const LayeredZone& r)
const {
return (*
this < r) || (*
this == r); }
246 std::weak_ptr<ZoneEntityItem> zone;
251 class LayeredZones :
public std::vector<LayeredZone> {
253 bool clearDomainAndNonOwnedZones();
255 void sort() { std::sort(begin(), end(), std::less<LayeredZone>()); }
256 bool equals(
const LayeredZones& other)
const;
257 bool update(std::shared_ptr<ZoneEntityItem> zone,
const glm::vec3& position, EntityTreeRenderer* entityTreeRenderer);
259 void appendRenderIDs(render::ItemIDs& list, EntityTreeRenderer* entityTreeRenderer)
const;
260 std::pair<bool, bool> getZoneInteractionProperties()
const;
261 FadeProperties getFadeProperties(
const TransitionType type)
const;
262 bool hasFade(
const TransitionType type)
const;
265 LayeredZones _layeredZones;
266 uint64_t _lastZoneCheck { 0 };
267 const uint64_t ZONE_CHECK_INTERVAL = USECS_PER_MSEC * 100;
268 const float ZONE_CHECK_DISTANCE = 0.001f;
270 float _avgRenderableUpdateCost { 0.0f };
272 ReadWriteLockable _changedEntitiesGuard;
273 std::unordered_set<EntityItemID> _changedEntities;
274 size_t _prevNumEntityUpdates { 0 };
275 size_t _prevTotalNeededEntityUpdates { 0 };
277 std::unordered_set<EntityRendererPointer> _renderablesToUpdate;
278 std::unordered_map<EntityItemID, EntityRendererPointer> _entitiesInScene;
279 std::unordered_map<EntityItemID, EntityItemWeakPointer> _entitiesToAdd;
282 QList<EntityItemID> _entityIDsLastInScene;
284 static int _entitiesScriptEngineCount;
285 static CalculateEntityLoadingPriority _calculateEntityLoadingPriorityFunc;
287 mutable std::mutex _spaceLock;
288 workload::SpacePointer _space{
new workload::Space() };
289 workload::Transaction::Updates _spaceUpdates;
291 static std::function<bool(
const QUuid&, graphics::MaterialLayer,
const std::string&)> _addMaterialToEntityOperator;
292 static std::function<bool(
const QUuid&, graphics::MaterialPointer,
const std::string&)> _removeMaterialFromEntityOperator;
293 static std::function<bool(
const QUuid&, graphics::MaterialLayer,
const std::string&)> _addMaterialToAvatarOperator;
294 static std::function<bool(
const QUuid&, graphics::MaterialPointer,
const std::string&)> _removeMaterialFromAvatarOperator;
Interface provided by Application to other objects that need access to scripting services of the appl...
Definition: AbstractScriptingServicesInterface.h:26
Interface provided by Application to other objects that need access to the current view state details...
Definition: AbstractViewStateInterface.h:31
Utility for processing, packing, queueing and sending of outbound edit voxel messages.
Definition: EntityEditPacketSender.h:25
Abstract ID for editing model items. Used in EntityItem JS API.
Definition: EntityItemID.h:28
A generic 3D model displaying geometry loaded from a URL.
Definition: Model.h:85
Represents a 2D or 3D pointer to the scripting engine. Exposed as PointerEvent
Definition: PointerEvent.h:32
Provides an engine-independent interface for a scripting engine.
Definition: ScriptEngine.h:93
Manages a single scripting engine.
Definition: ScriptManager.h:281