Fix bug with detachPrefab incorrectly replacing old entity aliases in patches

This commit is contained in:
srikappa
2021-06-18 11:19:59 -07:00
parent e746260f04
commit 4d90b7cfb6
3 changed files with 25 additions and 16 deletions
@@ -326,6 +326,16 @@ namespace AzToolsFramework
return *(m_nestedInstances[newInstanceAlias] = std::move(instance)); return *(m_nestedInstances[newInstanceAlias] = std::move(instance));
} }
void Instance::DetachNestedInstances(const AZStd::function<void(AZStd::unique_ptr<Instance>)>& callback)
{
for (auto&& [instanceAlias, instance] : m_nestedInstances)
{
instance->m_parent = nullptr;
callback(AZStd::move(instance));
}
m_nestedInstances.clear();
}
AZStd::unique_ptr<Instance> Instance::DetachNestedInstance(const InstanceAlias& instanceAlias) AZStd::unique_ptr<Instance> Instance::DetachNestedInstance(const InstanceAlias& instanceAlias)
{ {
AZStd::unique_ptr<Instance> removedNestedInstance; AZStd::unique_ptr<Instance> removedNestedInstance;
@@ -103,6 +103,7 @@ namespace AzToolsFramework
Instance& AddInstance(AZStd::unique_ptr<Instance> instance); Instance& AddInstance(AZStd::unique_ptr<Instance> instance);
Instance& AddInstance(AZStd::unique_ptr<Instance> instance, InstanceAlias instanceAlias); Instance& AddInstance(AZStd::unique_ptr<Instance> instance, InstanceAlias instanceAlias);
AZStd::unique_ptr<Instance> DetachNestedInstance(const InstanceAlias& instanceAlias); AZStd::unique_ptr<Instance> DetachNestedInstance(const InstanceAlias& instanceAlias);
void DetachNestedInstances(const AZStd::function<void(AZStd::unique_ptr<Instance>)>& callback);
/** /**
* Gets the aliases for the entities in the Instance DOM. * Gets the aliases for the entities in the Instance DOM.
@@ -1211,25 +1211,23 @@ namespace AzToolsFramework
const auto instanceTemplateId = instancePtr->GetTemplateId(); const auto instanceTemplateId = instancePtr->GetTemplateId();
auto parentContainerEntityId = parentInstance.GetContainerEntityId(); auto parentContainerEntityId = parentInstance.GetContainerEntityId();
instancePtr->GetNestedInstances(
[&](AZStd::unique_ptr<Instance>& nestedInstancePtr) instancePtr->DetachNestedInstances(
[&](AZStd::unique_ptr<Instance> detachedNestedInstance)
{ {
//get previous link patch PrefabDom& nestedInstanceTemplateDom =
auto linkRef = m_prefabSystemComponentInterface->FindLink(nestedInstancePtr->GetLinkId()); m_prefabSystemComponentInterface->FindTemplateDom(detachedNestedInstance->GetTemplateId());
PrefabDomValueReference linkPatches = linkRef->get().GetLinkPatches();
AZ_Assert(
linkPatches.has_value(), "Unable to get patches on link with id '%llu' during prefab creation.",
nestedInstancePtr->GetLinkId());
PrefabDom linkPatchesCopy; Instance& nestedInstanceUnderNewParent = parentInstance.AddInstance(AZStd::move(detachedNestedInstance));
linkPatchesCopy.CopyFrom(linkPatches->get(), linkPatchesCopy.GetAllocator());
RemoveLink(nestedInstancePtr, instanceTemplateId, undoBatch.GetUndoBatch());
UpdateLinkPatchesWithNewEntityAliases(linkPatchesCopy, oldEntityAliases, parentInstance);
CreateLink(*nestedInstancePtr, parentTemplateId, undoBatch.GetUndoBatch(), PrefabDom nestedInstanceDomUnderNewParent;
AZStd::move(linkPatchesCopy), true); m_instanceToTemplateInterface->GenerateDomForInstance(
nestedInstanceDomUnderNewParent, nestedInstanceUnderNewParent);
PrefabDom reparentPatch;
m_instanceToTemplateInterface->GeneratePatch(
reparentPatch, nestedInstanceTemplateDom, nestedInstanceDomUnderNewParent);
CreateLink(nestedInstanceUnderNewParent, parentTemplateId, undoBatch.GetUndoBatch(), AZStd::move(reparentPatch), true);
}); });
} }