void EntityImporterBase::createEntity(const RootEntity & obj, OpVector & res) { ++mStats.entitiesProcessedCount; ++mStats.entitiesCreateCount; EventProgress.emit(); m_state = ENTITY_CREATING; assert(mTreeStack.size() > 1); std::deque<StackEntry>::reverse_iterator I = mTreeStack.rbegin(); ++I; assert(I != mTreeStack.rend()); const std::string & loc = I->restored_id; RootEntity create_arg = obj.copy(); create_arg->removeAttrFlag(Atlas::Objects::Entity::CONTAINS_FLAG); create_arg->removeAttrFlag(Atlas::Objects::Entity::VELOCITY_FLAG); create_arg->removeAttrFlag(Atlas::Objects::ID_FLAG); create_arg->setLoc(loc); //Remove any attribute which references another entity from the Create op. //This is because the attribute will at this time with certainty refer to the wrong or a non-existing entity. //The attribute will later on be set through a Set op in sendResolvedEntityReferences(). auto referenceMapEntryI = mEntitiesWithReferenceAttributes.find(obj->getId()); if (referenceMapEntryI != mEntitiesWithReferenceAttributes.end()) { for (const auto& attributeName : referenceMapEntryI->second) { create_arg->removeAttr(attributeName); } } Create create; create->setArgs1(create_arg); create->setFrom(mAvatarId); create->setSerialno(newSerialNumber()); mCreateEntityMapping.insert(std::make_pair(create->getSerialno(), obj->getId())); res.push_back(create); }
void EntityImporterBase::createEntity(const RootEntity & obj, OpVector & res) { ++mStats.entitiesProcessedCount; ++mStats.entitiesCreateCount; EventProgress.emit(); m_state = ENTITY_CREATING; assert(mTreeStack.size() > 1); auto I = mTreeStack.rbegin(); ++I; assert(I != mTreeStack.rend()); const std::string & loc = I->restored_id; RootEntity create_arg = obj.copy(); create_arg->removeAttrFlag(Atlas::Objects::Entity::CONTAINS_FLAG); create_arg->removeAttrFlag(Atlas::Objects::Entity::VELOCITY_FLAG); create_arg->removeAttrFlag(Atlas::Objects::ID_FLAG); create_arg->setLoc(loc); //Remove any attribute which references another entity from the Create op. //This is because the attribute will at this time with certainty refer to the wrong or a non-existing entity. //The attribute will later on be set through a Set op in sendResolvedEntityReferences(). auto referenceMapEntryI = mEntitiesWithReferenceAttributes.find(obj->getId()); if (referenceMapEntryI != mEntitiesWithReferenceAttributes.end()) { std::set<std::string> resolvedAttributes; for (const auto& referenceEntry : referenceMapEntryI->second) { size_t resolvedEntitiesCount = 0; //Check if all the referenced entities perhaps already have been created. for (const auto& entityId : referenceEntry.referencedEntities) { auto resolvedI = mEntityIdMap.find(entityId); if (resolvedI != mEntityIdMap.end()) { resolvedEntitiesCount++; } } //If all entities were resolved, we should resolve the property now. if (resolvedEntitiesCount == referenceEntry.referencedEntities.size()) { Element element = create_arg->getAttr(referenceEntry.propertyName); resolveEntityReferences(element); create_arg->setAttr(referenceEntry.propertyName, element); resolvedAttributes.insert(referenceEntry.propertyName); } else { create_arg->removeAttr(referenceEntry.propertyName); } } //Remove those attributes that were resolved if (resolvedAttributes.size() == referenceMapEntryI->second.size()) { //All attributes were resolved, remove the entry completely. mEntitiesWithReferenceAttributes.erase(referenceMapEntryI); } else { //Only remove those entries that were destroyed. std::vector<ReferencedEntry> copy; for (auto& referenceEntry : referenceMapEntryI->second) { if (resolvedAttributes.find(referenceEntry.propertyName) == resolvedAttributes.end()) { copy.push_back(std::move(referenceEntry)); } } referenceMapEntryI->second = std::move(copy); } } Create create; create->setArgs1(create_arg); create->setFrom(mAvatarId); create->setSerialno(newSerialNumber()); mCreateEntityMapping.insert(std::make_pair(create->getSerialno(), obj->getId())); res.push_back(create); }