diff --git a/libraries/entities/src/EntityTree.cpp b/libraries/entities/src/EntityTree.cpp index 5d23cf704b..fb7fbe6499 100644 --- a/libraries/entities/src/EntityTree.cpp +++ b/libraries/entities/src/EntityTree.cpp @@ -2553,9 +2553,8 @@ bool EntityTree::writeToMap(QVariantMap& entityDescription, OctreeElementPointer } entityDescription["DataVersion"] = _persistDataVersion; entityDescription["Id"] = _persistID; - // V8TODO: Creating new script engine each time is very inefficient - ScriptEnginePointer engine = newScriptEngine(); - RecurseOctreeToMapOperator theOperator(entityDescription, element, engine.get(), skipDefaultValues, + const std::lock_guard scriptLock(scriptEngineMutex); + RecurseOctreeToMapOperator theOperator(entityDescription, element, scriptEngine.get(), skipDefaultValues, skipThoseWithBadParents, _myAvatar); withReadLock([&] { recurseTreeWithOperator(&theOperator); @@ -2704,8 +2703,6 @@ bool EntityTree::readFromMap(QVariantMap& map, const bool isImport) { // to a ScriptValue, and then to EntityItemProperties. These properties are used // to add the new entity to the EntityTree. QVariantList entitiesQList = map["Entities"].toList(); - // V8TODO: Creating new script engine each time is very inefficient - ScriptEnginePointer scriptEngine = newScriptEngine(); if (entitiesQList.length() == 0) { qCDebug(entities) << "EntityTree::readFromMap: entitiesQList.length() == 0, Empty map or invalidly formed file"; @@ -2730,9 +2727,12 @@ bool EntityTree::readFromMap(QVariantMap& map, const bool isImport) { " mapped it to parentJointIndex " << entityMap["parentJointIndex"].toInt(); } - ScriptValue entityScriptValue = variantMapToScriptValue(entityMap, *scriptEngine); EntityItemProperties properties; - EntityItemPropertiesFromScriptValueIgnoreReadOnly(entityScriptValue, properties); + { + const std::lock_guard scriptLock(scriptEngineMutex); + ScriptValue entityScriptValue = variantMapToScriptValue(entityMap, *scriptEngine); + EntityItemPropertiesFromScriptValueIgnoreReadOnly(entityScriptValue, properties); + } EntityItemID entityItemID; if (entityMap.contains("id")) { @@ -2881,9 +2881,8 @@ bool EntityTree::readFromMap(QVariantMap& map, const bool isImport) { } bool EntityTree::writeToJSON(QString& jsonString, const OctreeElementPointer& element) { - // V8TODO: Creating new script engine each time is very inefficient - ScriptEnginePointer engine = newScriptEngine(); - RecurseOctreeToJSONOperator theOperator(element, engine.get(), jsonString); + const std::lock_guard scriptLock(scriptEngineMutex); + RecurseOctreeToJSONOperator theOperator(element, scriptEngine.get(), jsonString); withReadLock([&] { recurseTreeWithOperator(&theOperator); }); diff --git a/libraries/entities/src/EntityTree.h b/libraries/entities/src/EntityTree.h index 78fab3af6f..d5c3a74eb7 100644 --- a/libraries/entities/src/EntityTree.h +++ b/libraries/entities/src/EntityTree.h @@ -385,6 +385,10 @@ private: // Return an AACube containing object and all its entity descendants AACube updateEntityQueryAACubeWorker(SpatiallyNestablePointer object, EntityEditPacketSender* packetSender, MovingEntitiesOperator& moveOperator, bool force, bool tellServer); + + // Script engine for writing entity tree data to and from JSON + std::mutex scriptEngineMutex; + ScriptEnginePointer scriptEngine{ newScriptEngine() }; }; void convertGrabUserDataToProperties(EntityItemProperties& properties);