Revert "Split Local and owned Avatar Entity scripts into their own ScriptEngine"

This commit is contained in:
kasenvr 2020-11-16 22:35:46 -05:00 committed by GitHub
parent c3439a8ae7
commit 21f8eac936
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 109 additions and 183 deletions

View file

@ -470,9 +470,7 @@ void EntityScriptServer::resetEntitiesScriptEngine() {
scriptEngines->runScriptInitializers(newEngine); scriptEngines->runScriptInitializers(newEngine);
newEngine->runInThread(); newEngine->runInThread();
auto newEngineSP = qSharedPointerCast<EntitiesScriptEngineProvider>(newEngine); auto newEngineSP = qSharedPointerCast<EntitiesScriptEngineProvider>(newEngine);
// On the entity script server, these are the same DependencyManager::get<EntityScriptingInterface>()->setEntitiesScriptEngine(newEngineSP);
DependencyManager::get<EntityScriptingInterface>()->setPersistentEntitiesScriptEngine(newEngineSP);
DependencyManager::get<EntityScriptingInterface>()->setNonPersistentEntitiesScriptEngine(newEngineSP);
if (_entitiesScriptEngine) { if (_entitiesScriptEngine) {
disconnect(_entitiesScriptEngine.data(), &ScriptEngine::entityScriptDetailsUpdated, disconnect(_entitiesScriptEngine.data(), &ScriptEngine::entityScriptDetailsUpdated,

View file

@ -158,98 +158,79 @@ render::ItemID EntityTreeRenderer::renderableIdForEntityId(const EntityItemID& i
int EntityTreeRenderer::_entitiesScriptEngineCount = 0; int EntityTreeRenderer::_entitiesScriptEngineCount = 0;
void EntityTreeRenderer::setupEntityScriptEngineSignals(const ScriptEnginePointer& scriptEngine) { void EntityTreeRenderer::resetEntitiesScriptEngine() {
_entitiesScriptEngine = scriptEngineFactory(ScriptEngine::ENTITY_CLIENT_SCRIPT, NO_SCRIPT,
QString("about:Entities %1").arg(++_entitiesScriptEngineCount));
DependencyManager::get<ScriptEngines>()->runScriptInitializers(_entitiesScriptEngine);
_entitiesScriptEngine->runInThread();
auto entitiesScriptEngineProvider = qSharedPointerCast<EntitiesScriptEngineProvider>(_entitiesScriptEngine);
auto entityScriptingInterface = DependencyManager::get<EntityScriptingInterface>(); auto entityScriptingInterface = DependencyManager::get<EntityScriptingInterface>();
entityScriptingInterface->setEntitiesScriptEngine(entitiesScriptEngineProvider);
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mousePressOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) { connect(_entitiesScriptEngine.data(), &ScriptEngine::entityScriptPreloadFinished, [&](const EntityItemID& entityID) {
scriptEngine->callEntityScriptMethod(entityID, "mousePressOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseDoublePressOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "mouseDoublePressOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseMoveOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "mouseMoveOnEntity", event);
// FIXME: this is a duplicate of mouseMoveOnEntity, but it seems like some scripts might use this naming
scriptEngine->callEntityScriptMethod(entityID, "mouseMoveEvent", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseReleaseOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "mouseReleaseOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::clickDownOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "clickDownOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::holdingClickOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "holdingClickOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::clickReleaseOnEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "clickReleaseOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverEnterEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "hoverEnterEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverOverEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "hoverOverEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverLeaveEntity, scriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
scriptEngine->callEntityScriptMethod(entityID, "hoverLeaveEntity", event);
});
connect(scriptEngine.data(), &ScriptEngine::entityScriptPreloadFinished, [&](const EntityItemID& entityID) {
EntityItemPointer entity = getTree()->findEntityByID(entityID); EntityItemPointer entity = getTree()->findEntityByID(entityID);
if (entity) { if (entity) {
entity->setScriptHasFinishedPreload(true); entity->setScriptHasFinishedPreload(true);
} }
}); });
}
void EntityTreeRenderer::resetPersistentEntitiesScriptEngine() { // Connect mouse events to entity script callbacks
if (_persistentEntitiesScriptEngine) { if (!_mouseAndPreloadSignalHandlersConnected) {
_persistentEntitiesScriptEngine->unloadAllEntityScripts(true);
_persistentEntitiesScriptEngine->stop(); connect(entityScriptingInterface.data(), &EntityScriptingInterface::mousePressOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_persistentEntitiesScriptEngine->waitTillDoneRunning(); _entitiesScriptEngine->callEntityScriptMethod(entityID, "mousePressOnEntity", event);
_persistentEntitiesScriptEngine->disconnectNonEssentialSignals(); });
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseDoublePressOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "mouseDoublePressOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseMoveOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "mouseMoveOnEntity", event);
// FIXME: this is a duplicate of mouseMoveOnEntity, but it seems like some scripts might use this naming
_entitiesScriptEngine->callEntityScriptMethod(entityID, "mouseMoveEvent", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::mouseReleaseOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "mouseReleaseOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::clickDownOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "clickDownOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::holdingClickOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "holdingClickOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::clickReleaseOnEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "clickReleaseOnEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverEnterEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "hoverEnterEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverOverEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "hoverOverEntity", event);
});
connect(entityScriptingInterface.data(), &EntityScriptingInterface::hoverLeaveEntity, _entitiesScriptEngine.data(), [&](const EntityItemID& entityID, const PointerEvent& event) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "hoverLeaveEntity", event);
});
_mouseAndPreloadSignalHandlersConnected = true;
} }
_persistentEntitiesScriptEngine = scriptEngineFactory(ScriptEngine::ENTITY_CLIENT_SCRIPT, NO_SCRIPT,
QString("about:Entities %1").arg(++_entitiesScriptEngineCount));
DependencyManager::get<ScriptEngines>()->runScriptInitializers(_persistentEntitiesScriptEngine);
_persistentEntitiesScriptEngine->runInThread();
auto entitiesScriptEngineProvider = qSharedPointerCast<EntitiesScriptEngineProvider>(_persistentEntitiesScriptEngine);
auto entityScriptingInterface = DependencyManager::get<EntityScriptingInterface>();
entityScriptingInterface->setPersistentEntitiesScriptEngine(entitiesScriptEngineProvider);
setupEntityScriptEngineSignals(_persistentEntitiesScriptEngine);
}
void EntityTreeRenderer::resetNonPersistentEntitiesScriptEngine() {
if (_nonPersistentEntitiesScriptEngine) {
_nonPersistentEntitiesScriptEngine->unloadAllEntityScripts(false);
_nonPersistentEntitiesScriptEngine->stop();
_nonPersistentEntitiesScriptEngine->waitTillDoneRunning();
_nonPersistentEntitiesScriptEngine->disconnectNonEssentialSignals();
}
_nonPersistentEntitiesScriptEngine = scriptEngineFactory(ScriptEngine::ENTITY_CLIENT_SCRIPT, NO_SCRIPT,
QString("about:Entities %1").arg(++_entitiesScriptEngineCount));
DependencyManager::get<ScriptEngines>()->runScriptInitializers(_nonPersistentEntitiesScriptEngine);
_nonPersistentEntitiesScriptEngine->runInThread();
auto entitiesScriptEngineProvider = qSharedPointerCast<EntitiesScriptEngineProvider>(_nonPersistentEntitiesScriptEngine);
DependencyManager::get<EntityScriptingInterface>()->setNonPersistentEntitiesScriptEngine(entitiesScriptEngineProvider);
setupEntityScriptEngineSignals(_nonPersistentEntitiesScriptEngine);
} }
void EntityTreeRenderer::stopDomainAndNonOwnedEntities() { void EntityTreeRenderer::stopDomainAndNonOwnedEntities() {
leaveDomainAndNonOwnedEntities(); leaveDomainAndNonOwnedEntities();
// unload and stop the engine // unload and stop the engine
if (_nonPersistentEntitiesScriptEngine) { if (_entitiesScriptEngine) {
QList<EntityItemID> entitiesWithEntityScripts = _nonPersistentEntitiesScriptEngine->getListOfEntityScriptIDs(); QList<EntityItemID> entitiesWithEntityScripts = _entitiesScriptEngine->getListOfEntityScriptIDs();
foreach (const EntityItemID& entityID, entitiesWithEntityScripts) { foreach (const EntityItemID& entityID, entitiesWithEntityScripts) {
EntityItemPointer entityItem = getTree()->findEntityByEntityItemID(entityID); EntityItemPointer entityItem = getTree()->findEntityByEntityItemID(entityID);
if (entityItem && !entityItem->getScript().isEmpty()) { if (entityItem && !entityItem->getScript().isEmpty()) {
if (!(entityItem->isLocalEntity() || entityItem->isMyAvatarEntity())) { if (!(entityItem->isLocalEntity() || entityItem->isMyAvatarEntity())) {
_nonPersistentEntitiesScriptEngine->unloadEntityScript(entityID, true); if (_currentEntitiesInside.contains(entityID)) {
_entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
}
_entitiesScriptEngine->unloadEntityScript(entityID, true);
} }
} }
} }
@ -259,10 +240,6 @@ void EntityTreeRenderer::stopDomainAndNonOwnedEntities() {
void EntityTreeRenderer::clearDomainAndNonOwnedEntities() { void EntityTreeRenderer::clearDomainAndNonOwnedEntities() {
stopDomainAndNonOwnedEntities(); stopDomainAndNonOwnedEntities();
if (!_shuttingDown && _wantScripts) {
resetNonPersistentEntitiesScriptEngine();
}
std::unordered_map<EntityItemID, EntityRendererPointer> savedEntities; std::unordered_map<EntityItemID, EntityRendererPointer> savedEntities;
std::unordered_set<EntityRendererPointer> savedRenderables; std::unordered_set<EntityRendererPointer> savedRenderables;
// remove all entities from the scene // remove all entities from the scene
@ -292,22 +269,16 @@ void EntityTreeRenderer::clearDomainAndNonOwnedEntities() {
void EntityTreeRenderer::clear() { void EntityTreeRenderer::clear() {
leaveAllEntities(); leaveAllEntities();
// unload and stop the engine
if (_entitiesScriptEngine) {
// do this here (instead of in deleter) to avoid marshalling unload signals back to this thread
_entitiesScriptEngine->unloadAllEntityScripts(true);
_entitiesScriptEngine->stop();
}
// reset the engine // reset the engine
auto scene = _viewState->getMain3DScene(); auto scene = _viewState->getMain3DScene();
if (_shuttingDown) { if (_shuttingDown) {
// unload and stop the engines
if (_nonPersistentEntitiesScriptEngine) {
// do this here (instead of in deleter) to avoid marshalling unload signals back to this thread
_nonPersistentEntitiesScriptEngine->unloadAllEntityScripts(true);
_nonPersistentEntitiesScriptEngine->stop();
}
if (_persistentEntitiesScriptEngine) {
// do this here (instead of in deleter) to avoid marshalling unload signals back to this thread
_persistentEntitiesScriptEngine->unloadAllEntityScripts(true);
_persistentEntitiesScriptEngine->stop();
}
if (scene) { if (scene) {
render::Transaction transaction; render::Transaction transaction;
for (const auto& entry : _entitiesInScene) { for (const auto& entry : _entitiesInScene) {
@ -318,8 +289,7 @@ void EntityTreeRenderer::clear() {
} }
} else { } else {
if (_wantScripts) { if (_wantScripts) {
resetPersistentEntitiesScriptEngine(); resetEntitiesScriptEngine();
resetNonPersistentEntitiesScriptEngine();
} }
if (scene) { if (scene) {
for (const auto& entry : _entitiesInScene) { for (const auto& entry : _entitiesInScene) {
@ -343,17 +313,13 @@ void EntityTreeRenderer::clear() {
} }
void EntityTreeRenderer::reloadEntityScripts() { void EntityTreeRenderer::reloadEntityScripts() {
_persistentEntitiesScriptEngine->unloadAllEntityScripts(); _entitiesScriptEngine->unloadAllEntityScripts();
_persistentEntitiesScriptEngine->resetModuleCache(); _entitiesScriptEngine->resetModuleCache();
_nonPersistentEntitiesScriptEngine->unloadAllEntityScripts();
_nonPersistentEntitiesScriptEngine->resetModuleCache();
for (const auto& entry : _entitiesInScene) { for (const auto& entry : _entitiesInScene) {
const auto& renderer = entry.second; const auto& renderer = entry.second;
const auto& entity = renderer->getEntity(); const auto& entity = renderer->getEntity();
if (entity && !entity->getScript().isEmpty()) { if (!entity->getScript().isEmpty()) {
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; _entitiesScriptEngine->loadEntityScript(entity->getEntityItemID(), resolveScriptURL(entity->getScript()), true);
scriptEngine->loadEntityScript(entity->getEntityItemID(), resolveScriptURL(entity->getScript()), true);
} }
} }
} }
@ -363,8 +329,7 @@ void EntityTreeRenderer::init() {
EntityTreePointer entityTree = std::static_pointer_cast<EntityTree>(_tree); EntityTreePointer entityTree = std::static_pointer_cast<EntityTree>(_tree);
if (_wantScripts) { if (_wantScripts) {
resetPersistentEntitiesScriptEngine(); resetEntitiesScriptEngine();
resetNonPersistentEntitiesScriptEngine();
} }
forceRecheckEntities(); // setup our state to force checking our inside/outsideness of entities forceRecheckEntities(); // setup our state to force checking our inside/outsideness of entities
@ -376,11 +341,8 @@ void EntityTreeRenderer::init() {
} }
void EntityTreeRenderer::shutdown() { void EntityTreeRenderer::shutdown() {
if (_persistentEntitiesScriptEngine) { if (_entitiesScriptEngine) {
_persistentEntitiesScriptEngine->disconnectNonEssentialSignals(); // disconnect all slots/signals from the script engine, except essential _entitiesScriptEngine->disconnectNonEssentialSignals(); // disconnect all slots/signals from the script engine, except essential
}
if (_nonPersistentEntitiesScriptEngine) {
_nonPersistentEntitiesScriptEngine->disconnectNonEssentialSignals(); // disconnect all slots/signals from the script engine, except essential
} }
_shuttingDown = true; _shuttingDown = true;
@ -696,16 +658,12 @@ void EntityTreeRenderer::checkEnterLeaveEntities() {
// EntityItemIDs from here. The callEntityScriptMethod() method is robust against attempting to call scripts // EntityItemIDs from here. The callEntityScriptMethod() method is robust against attempting to call scripts
// for entity IDs that no longer exist. // for entity IDs that no longer exist.
if (_persistentEntitiesScriptEngine && _nonPersistentEntitiesScriptEngine) { if (_entitiesScriptEngine) {
// for all of our previous containing entities, if they are no longer containing then send them a leave event // for all of our previous containing entities, if they are no longer containing then send them a leave event
foreach(const EntityItemID& entityID, _currentEntitiesInside) { foreach(const EntityItemID& entityID, _currentEntitiesInside) {
if (!entitiesContainingAvatar.contains(entityID)) { if (!entitiesContainingAvatar.contains(entityID)) {
emit leaveEntity(entityID); emit leaveEntity(entityID);
auto entity = getTree()->findEntityByEntityItemID(entityID); _entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
if (entity) {
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine;
scriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
}
} }
} }
@ -713,11 +671,7 @@ void EntityTreeRenderer::checkEnterLeaveEntities() {
foreach(const EntityItemID& entityID, entitiesContainingAvatar) { foreach(const EntityItemID& entityID, entitiesContainingAvatar) {
if (!_currentEntitiesInside.contains(entityID)) { if (!_currentEntitiesInside.contains(entityID)) {
emit enterEntity(entityID); emit enterEntity(entityID);
auto entity = getTree()->findEntityByEntityItemID(entityID); _entitiesScriptEngine->callEntityScriptMethod(entityID, "enterEntity");
if (entity) {
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine;
scriptEngine->callEntityScriptMethod(entityID, "enterEntity");
}
} }
} }
_currentEntitiesInside = entitiesContainingAvatar; _currentEntitiesInside = entitiesContainingAvatar;
@ -733,8 +687,8 @@ void EntityTreeRenderer::leaveDomainAndNonOwnedEntities() {
EntityItemPointer entityItem = getTree()->findEntityByEntityItemID(entityID); EntityItemPointer entityItem = getTree()->findEntityByEntityItemID(entityID);
if (entityItem && !(entityItem->isLocalEntity() || entityItem->isMyAvatarEntity())) { if (entityItem && !(entityItem->isLocalEntity() || entityItem->isMyAvatarEntity())) {
emit leaveEntity(entityID); emit leaveEntity(entityID);
if (_nonPersistentEntitiesScriptEngine) { if (_entitiesScriptEngine) {
_nonPersistentEntitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity"); _entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
} }
} else { } else {
currentEntitiesInsideToSave.insert(entityID); currentEntitiesInsideToSave.insert(entityID);
@ -752,12 +706,8 @@ void EntityTreeRenderer::leaveAllEntities() {
// for all of our previous containing entities, if they are no longer containing then send them a leave event // for all of our previous containing entities, if they are no longer containing then send them a leave event
foreach(const EntityItemID& entityID, _currentEntitiesInside) { foreach(const EntityItemID& entityID, _currentEntitiesInside) {
emit leaveEntity(entityID); emit leaveEntity(entityID);
EntityItemPointer entityItem = getTree()->findEntityByEntityItemID(entityID); if (_entitiesScriptEngine) {
if (entityItem) { _entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
auto& scriptEngine = (entityItem->isLocalEntity() || entityItem->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine;
if (scriptEngine) {
scriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
}
} }
} }
_currentEntitiesInside.clear(); _currentEntitiesInside.clear();
@ -1053,12 +1003,11 @@ void EntityTreeRenderer::deletingEntity(const EntityItemID& entityID) {
return; return;
} }
auto& scriptEngine = (itr->second->getEntity()->isLocalEntity() || itr->second->getEntity()->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; if (_tree && !_shuttingDown && _entitiesScriptEngine && !itr->second->getEntity()->getScript().isEmpty()) {
if (_tree && !_shuttingDown && scriptEngine && !itr->second->getEntity()->getScript().isEmpty()) {
if (_currentEntitiesInside.contains(entityID)) { if (_currentEntitiesInside.contains(entityID)) {
scriptEngine->callEntityScriptMethod(entityID, "leaveEntity"); _entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
} }
scriptEngine->unloadEntityScript(entityID, true); _entitiesScriptEngine->unloadEntityScript(entityID, true);
} }
auto scene = _viewState->getMain3DScene(); auto scene = _viewState->getMain3DScene();
@ -1103,21 +1052,20 @@ void EntityTreeRenderer::checkAndCallPreload(const EntityItemID& entityID, bool
if (!entity) { if (!entity) {
return; return;
} }
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; bool shouldLoad = entity->shouldPreloadScript() && _entitiesScriptEngine;
bool shouldLoad = entity->shouldPreloadScript() && scriptEngine;
QString scriptUrl = entity->getScript(); QString scriptUrl = entity->getScript();
if ((shouldLoad && unloadFirst) || scriptUrl.isEmpty()) { if ((shouldLoad && unloadFirst) || scriptUrl.isEmpty()) {
if (scriptEngine) { if (_entitiesScriptEngine) {
if (_currentEntitiesInside.contains(entityID)) { if (_currentEntitiesInside.contains(entityID)) {
scriptEngine->callEntityScriptMethod(entityID, "leaveEntity"); _entitiesScriptEngine->callEntityScriptMethod(entityID, "leaveEntity");
} }
scriptEngine->unloadEntityScript(entityID); _entitiesScriptEngine->unloadEntityScript(entityID);
} }
entity->scriptHasUnloaded(); entity->scriptHasUnloaded();
} }
if (shouldLoad) { if (shouldLoad) {
entity->setScriptHasFinishedPreload(false); entity->setScriptHasFinishedPreload(false);
scriptEngine->loadEntityScript(entityID, resolveScriptURL(scriptUrl), reload); _entitiesScriptEngine->loadEntityScript(entityID, resolveScriptURL(scriptUrl), reload);
entity->scriptHasPreloaded(); entity->scriptHasPreloaded();
} }
} }
@ -1224,9 +1172,8 @@ void EntityTreeRenderer::entityCollisionWithEntity(const EntityItemID& idA, cons
if ((myNodeID == entityASimulatorID && entityAIsDynamic) || (myNodeID == entityBSimulatorID && (!entityAIsDynamic || entityASimulatorID.isNull()))) { if ((myNodeID == entityASimulatorID && entityAIsDynamic) || (myNodeID == entityBSimulatorID && (!entityAIsDynamic || entityASimulatorID.isNull()))) {
playEntityCollisionSound(entityA, collision); playEntityCollisionSound(entityA, collision);
emit collisionWithEntity(idA, idB, collision); emit collisionWithEntity(idA, idB, collision);
auto& scriptEngine = (entityA->isLocalEntity() || entityA->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; if (_entitiesScriptEngine) {
if (scriptEngine) { _entitiesScriptEngine->callEntityScriptMethod(idA, "collisionWithEntity", idB, collision);
scriptEngine->callEntityScriptMethod(idA, "collisionWithEntity", idB, collision);
} }
} }
@ -1236,9 +1183,8 @@ void EntityTreeRenderer::entityCollisionWithEntity(const EntityItemID& idA, cons
Collision invertedCollision(collision); Collision invertedCollision(collision);
invertedCollision.invert(); invertedCollision.invert();
emit collisionWithEntity(idB, idA, invertedCollision); emit collisionWithEntity(idB, idA, invertedCollision);
auto& scriptEngine = (entityB->isLocalEntity() || entityB->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; if (_entitiesScriptEngine) {
if (scriptEngine) { _entitiesScriptEngine->callEntityScriptMethod(idB, "collisionWithEntity", idA, invertedCollision);
scriptEngine->callEntityScriptMethod(idB, "collisionWithEntity", idA, invertedCollision);
} }
} }
} }

View file

@ -173,9 +173,7 @@ private:
EntityRendererPointer renderableForEntity(const EntityItemPointer& entity) const { return renderableForEntityId(entity->getID()); } EntityRendererPointer renderableForEntity(const EntityItemPointer& entity) const { return renderableForEntityId(entity->getID()); }
render::ItemID renderableIdForEntity(const EntityItemPointer& entity) const { return renderableIdForEntityId(entity->getID()); } render::ItemID renderableIdForEntity(const EntityItemPointer& entity) const { return renderableIdForEntityId(entity->getID()); }
void resetPersistentEntitiesScriptEngine(); void resetEntitiesScriptEngine();
void resetNonPersistentEntitiesScriptEngine();
void setupEntityScriptEngineSignals(const ScriptEnginePointer& scriptEngine);
void findBestZoneAndMaybeContainingEntities(QSet<EntityItemID>& entitiesContainingAvatar); void findBestZoneAndMaybeContainingEntities(QSet<EntityItemID>& entitiesContainingAvatar);
@ -198,8 +196,7 @@ private:
QSet<EntityItemID> _currentEntitiesInside; QSet<EntityItemID> _currentEntitiesInside;
bool _wantScripts; bool _wantScripts;
ScriptEnginePointer _nonPersistentEntitiesScriptEngine; // used for domain + non-owned avatar entities, cleared on domain switch ScriptEnginePointer _entitiesScriptEngine;
ScriptEnginePointer _persistentEntitiesScriptEngine; // used for local + owned avatar entities, persists on domain switch, cleared on reload content
void playEntityCollisionSound(const EntityItemPointer& entity, const Collision& collision); void playEntityCollisionSound(const EntityItemPointer& entity, const Collision& collision);
@ -217,6 +214,8 @@ private:
std::function<RayToEntityIntersectionResult(unsigned int)> _getPrevRayPickResultOperator; std::function<RayToEntityIntersectionResult(unsigned int)> _getPrevRayPickResultOperator;
std::function<void(unsigned int, bool)> _setPrecisionPickingOperator; std::function<void(unsigned int, bool)> _setPrecisionPickingOperator;
bool _mouseAndPreloadSignalHandlersConnected { false };
class LayeredZone { class LayeredZone {
public: public:
LayeredZone(std::shared_ptr<ZoneEntityItem> zone) : zone(zone), id(zone->getID()), volume(zone->getVolumeEstimate()) {} LayeredZone(std::shared_ptr<ZoneEntityItem> zone) : zone(zone), id(zone->getID()), volume(zone->getVolumeEstimate()) {}

View file

@ -1046,26 +1046,18 @@ QSizeF EntityScriptingInterface::textSize(const QUuid& id, const QString& text)
return EntityTree::textSize(id, text); return EntityTree::textSize(id, text);
} }
void EntityScriptingInterface::setPersistentEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine) { void EntityScriptingInterface::setEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine) {
std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock); std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock);
_persistentEntitiesScriptEngine = engine; _entitiesScriptEngine = engine;
}
void EntityScriptingInterface::setNonPersistentEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine) {
std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock);
_nonPersistentEntitiesScriptEngine = engine;
} }
void EntityScriptingInterface::callEntityMethod(const QUuid& id, const QString& method, const QStringList& params) { void EntityScriptingInterface::callEntityMethod(const QUuid& id, const QString& method, const QStringList& params) {
PROFILE_RANGE(script_entities, __FUNCTION__); PROFILE_RANGE(script_entities, __FUNCTION__);
auto entity = getEntityTree()->findEntityByEntityItemID(id);
if (entity) {
std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock); std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock);
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; if (_entitiesScriptEngine) {
if (scriptEngine) { EntityItemID entityID{ id };
scriptEngine->callEntityScriptMethod(id, method, params); _entitiesScriptEngine->callEntityScriptMethod(entityID, method, params);
}
} }
} }
@ -1107,13 +1099,9 @@ void EntityScriptingInterface::handleEntityScriptCallMethodPacket(QSharedPointer
params << paramString; params << paramString;
} }
auto entity = getEntityTree()->findEntityByEntityItemID(entityID);
if (entity) {
std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock); std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock);
auto& scriptEngine = (entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine; if (_entitiesScriptEngine) {
if (scriptEngine) { _entitiesScriptEngine->callEntityScriptMethod(entityID, method, params, senderNode->getUUID());
scriptEngine->callEntityScriptMethod(entityID, method, params, senderNode->getUUID());
}
} }
} }
} }
@ -1344,7 +1332,7 @@ bool EntityPropertyMetadataRequest::script(EntityItemID entityID, QScriptValue h
if (entitiesScriptEngine) { if (entitiesScriptEngine) {
request->setFuture(entitiesScriptEngine->getLocalEntityScriptDetails(entityID)); request->setFuture(entitiesScriptEngine->getLocalEntityScriptDetails(entityID));
} }
}, entityID); });
if (!request->isStarted()) { if (!request->isStarted()) {
request->deleteLater(); request->deleteLater();
callScopedHandlerObject(handler, _engine->makeError("Entities Scripting Provider unavailable", "InternalError"), QScriptValue()); callScopedHandlerObject(handler, _engine->makeError("Entities Scripting Provider unavailable", "InternalError"), QScriptValue());

View file

@ -181,8 +181,7 @@ public:
void setEntityTree(EntityTreePointer modelTree); void setEntityTree(EntityTreePointer modelTree);
EntityTreePointer getEntityTree() { return _entityTree; } EntityTreePointer getEntityTree() { return _entityTree; }
void setPersistentEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine); void setEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine);
void setNonPersistentEntitiesScriptEngine(QSharedPointer<EntitiesScriptEngineProvider> engine);
void resetActivityTracking(); void resetActivityTracking();
ActivityTracking getActivityTracking() const { return _activityTracking; } ActivityTracking getActivityTracking() const { return _activityTracking; }
@ -2511,12 +2510,9 @@ signals:
void webEventReceived(const EntityItemID& entityItemID, const QVariant& message); void webEventReceived(const EntityItemID& entityItemID, const QVariant& message);
protected: protected:
void withEntitiesScriptEngine(std::function<void(QSharedPointer<EntitiesScriptEngineProvider>)> function, const EntityItemID& id) { void withEntitiesScriptEngine(std::function<void(QSharedPointer<EntitiesScriptEngineProvider>)> function) {
auto entity = getEntityTree()->findEntityByEntityItemID(id);
if (entity) {
std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock); std::lock_guard<std::recursive_mutex> lock(_entitiesScriptEngineLock);
function((entity->isLocalEntity() || entity->isMyAvatarEntity()) ? _persistentEntitiesScriptEngine : _nonPersistentEntitiesScriptEngine); function(_entitiesScriptEngine);
}
}; };
private slots: private slots:
@ -2546,8 +2542,7 @@ private:
EntityTreePointer _entityTree; EntityTreePointer _entityTree;
std::recursive_mutex _entitiesScriptEngineLock; std::recursive_mutex _entitiesScriptEngineLock;
QSharedPointer<EntitiesScriptEngineProvider> _persistentEntitiesScriptEngine; QSharedPointer<EntitiesScriptEngineProvider> _entitiesScriptEngine;
QSharedPointer<EntitiesScriptEngineProvider> _nonPersistentEntitiesScriptEngine;
bool _bidOnSimulationOwnership { false }; bool _bidOnSimulationOwnership { false };