[LYN-4727] Scene Settings: Updating a default motion in the Scene Settings freezes the tool #1590
This commit is contained in:
@@ -84,12 +84,11 @@ namespace EMotionFX
|
||||
}
|
||||
|
||||
// Apply motion meta data.
|
||||
EMotionFX::Pipeline::Rule::MotionMetaData motionMetaData;
|
||||
if (EMotionFX::Pipeline::Rule::LoadFromGroup<EMotionFX::Pipeline::Rule::MotionMetaDataRule, EMotionFX::Pipeline::Rule::MotionMetaData>(motionGroup, motionMetaData))
|
||||
AZStd::shared_ptr<EMotionFX::Pipeline::Rule::MotionMetaData> motionMetaData;
|
||||
if (EMotionFX::Pipeline::Rule::LoadFromGroup<EMotionFX::Pipeline::Rule::MotionMetaDataRule>(motionGroup, motionMetaData))
|
||||
{
|
||||
motion->SetEventTable(AZStd::unique_ptr<MotionEventTable>(motionMetaData.m_motionEventTable));
|
||||
motion->GetEventTable()->InitAfterLoading(motion);
|
||||
motion->SetMotionExtractionFlags(motionMetaData.m_motionExtractionFlags);
|
||||
motion->SetEventTable(motionMetaData->GetClonedEventTable(motion));
|
||||
motion->SetMotionExtractionFlags(motionMetaData->GetMotionExtractionFlags());
|
||||
}
|
||||
|
||||
ExporterLib::SaveMotion(filename, motion, MCore::Endian::ENDIAN_LITTLE);
|
||||
|
||||
@@ -16,9 +16,11 @@
|
||||
#include <SceneAPIExt/Rules/MetaDataRule.h>
|
||||
#include <SceneAPIExt/Rules/MotionRangeRule.h>
|
||||
#include <SceneAPIExt/Rules/MotionCompressionSettingsRule.h>
|
||||
#include <SceneAPIExt/Rules/MotionMetaDataRule.h>
|
||||
#include <SceneAPIExt/Rules/MotionSamplingRule.h>
|
||||
#include <SceneAPIExt/Groups/MotionGroup.h>
|
||||
|
||||
#include <EMotionFX/CommandSystem/Source/MetaData.h>
|
||||
#include <EMotionFX/Source/MotionData/NonUniformMotionData.h>
|
||||
|
||||
namespace EMotionFX
|
||||
@@ -89,7 +91,7 @@ namespace EMotionFX
|
||||
|
||||
serializeContext->Class<IMotionGroup, AZ::SceneAPI::DataTypes::IGroup>()->Version(1);
|
||||
|
||||
serializeContext->Class<MotionGroup, IMotionGroup>()->Version(5, VersionConverter)
|
||||
serializeContext->Class<MotionGroup, IMotionGroup>()->Version(6, VersionConverter)
|
||||
->Field("name", &MotionGroup::m_name)
|
||||
->Field("selectedRootBone", &MotionGroup::m_selectedRootBone)
|
||||
->Field("id", &MotionGroup::m_id)
|
||||
@@ -225,6 +227,60 @@ namespace EMotionFX
|
||||
}
|
||||
}
|
||||
|
||||
// Motion meta data introduced (no more string- or object-based commands stored in the former meta data rule)
|
||||
if (version < 6)
|
||||
{
|
||||
AZ::SerializeContext::DataElementNode* ruleContainerNode = classElement.FindSubElement(AZ_CRC("rules", 0x899a993c));
|
||||
if (!ruleContainerNode)
|
||||
{
|
||||
AZ_TracePrintf(AZ::SceneAPI::Utilities::ErrorWindow, "Can't find rule container.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
AZ::SerializeContext::DataElementNode* rulesNode = ruleContainerNode->FindSubElement(AZ_CRC("rules", 0x899a993c));
|
||||
if (!rulesNode)
|
||||
{
|
||||
AZ_TracePrintf(AZ::SceneAPI::Utilities::ErrorWindow, "Can't find rules within rule container.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
const int numRules = rulesNode->GetNumSubElements();
|
||||
for (int i = 0; i < numRules; ++i)
|
||||
{
|
||||
AZ::SerializeContext::DataElementNode& sharedPointerNode = rulesNode->GetSubElement(i);
|
||||
if (sharedPointerNode.GetNumSubElements() == 1)
|
||||
{
|
||||
AZ::SerializeContext::DataElementNode& currentRuleNode = sharedPointerNode.GetSubElement(0);
|
||||
if (currentRuleNode.GetId() == azrtti_typeid<Rule::MetaDataRule>())
|
||||
{
|
||||
// Read the old, command-based meta data rule and retrieve the command objects.
|
||||
Rule::MetaDataRule oldMetaDataRule;
|
||||
currentRuleNode.GetData<Rule::MetaDataRule>(oldMetaDataRule);
|
||||
const AZStd::vector<MCore::Command*>& commands = oldMetaDataRule.GetMetaData<const AZStd::vector<MCore::Command*>&>();
|
||||
|
||||
// Apply the commands onto a temporary motion.
|
||||
auto motion = new EMotionFX::Motion("");
|
||||
motion->SetMotionData(aznew EMotionFX::NonUniformMotionData());
|
||||
CommandSystem::MetaData::ApplyMetaDataOnMotion(motion, commands);
|
||||
|
||||
// Construct the new motion meta data rule.
|
||||
auto metaData = AZStd::make_shared<EMotionFX::Pipeline::Rule::MotionMetaData>(motion->GetMotionExtractionFlags(), motion->GetEventTable());
|
||||
auto metaDataRule = AZStd::make_shared<EMotionFX::Pipeline::Rule::MotionMetaDataRule>(metaData);
|
||||
|
||||
// Add the new motion meta data rule.
|
||||
AZ::SceneAPI::Containers::RuleContainer ruleContainer;
|
||||
ruleContainerNode->GetDataHierarchy<AZ::SceneAPI::Containers::RuleContainer>(context, ruleContainer);
|
||||
ruleContainer.RemoveRule(i);
|
||||
ruleContainer.AddRule(metaDataRule);
|
||||
ruleContainerNode->SetData(context, ruleContainer);
|
||||
|
||||
motion->Destroy();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@ namespace EMotionFX
|
||||
return false;
|
||||
}
|
||||
|
||||
outData = rule->GetData();
|
||||
outData = AZStd::move(rule->GetData());
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -28,15 +28,46 @@ namespace EMotionFX::Pipeline::Rule
|
||||
;
|
||||
}
|
||||
|
||||
MotionMetaDataRule::MotionMetaDataRule()
|
||||
: ExternalToolRule<MotionMetaData>()
|
||||
MotionMetaData::MotionMetaData(EMotionFX::EMotionExtractionFlags extractionFlags, EMotionFX::MotionEventTable* eventTable)
|
||||
: m_motionExtractionFlags(extractionFlags)
|
||||
{
|
||||
m_motionEventTable = CloneMotionEventTable(eventTable);
|
||||
}
|
||||
|
||||
MotionMetaData::MotionMetaData()
|
||||
: m_motionExtractionFlags(static_cast<EMotionFX::EMotionExtractionFlags>(0))
|
||||
{
|
||||
}
|
||||
|
||||
MotionMetaDataRule::MotionMetaDataRule(const MotionMetaData& data)
|
||||
: MotionMetaDataRule()
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> MotionMetaData::GetClonedEventTable(EMotionFX::Motion* targetMotion) const
|
||||
{
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> clonedEventTable = CloneMotionEventTable(m_motionEventTable.get());
|
||||
clonedEventTable->InitAfterLoading(targetMotion);
|
||||
return clonedEventTable;
|
||||
}
|
||||
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> MotionMetaData::CloneMotionEventTable(EMotionFX::MotionEventTable* sourceEventTable)
|
||||
{
|
||||
AZ::SerializeContext* serializeContext = nullptr;
|
||||
AZ::ComponentApplicationBus::BroadcastResult(serializeContext, &AZ::ComponentApplicationBus::Events::GetSerializeContext);
|
||||
if (!serializeContext)
|
||||
{
|
||||
AZ_Error("EMotionFX", false, "Cannot clone motion event table for motion meta data. Can't get serialize context from component application.");
|
||||
return {};
|
||||
}
|
||||
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> clonedEventTable(serializeContext->CloneObject<EMotionFX::MotionEventTable>(sourceEventTable));
|
||||
return clonedEventTable;
|
||||
}
|
||||
|
||||
MotionMetaDataRule::MotionMetaDataRule()
|
||||
: ExternalToolRule<AZStd::shared_ptr<MotionMetaData>>()
|
||||
{
|
||||
}
|
||||
|
||||
MotionMetaDataRule::MotionMetaDataRule(const AZStd::shared_ptr<MotionMetaData>& data)
|
||||
: m_data(data)
|
||||
{
|
||||
m_data = data;
|
||||
}
|
||||
|
||||
void MotionMetaDataRule::Reflect(AZ::ReflectContext* context)
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#pragma once
|
||||
|
||||
#include <AzCore/Memory/SystemAllocator.h>
|
||||
#include <AzCore/std/smart_ptr/unique_ptr.h>
|
||||
#include <EMotionFX/Source/MotionEventTable.h>
|
||||
#include <SceneAPI/SceneCore/DataTypes/Rules/IRule.h>
|
||||
#include <SceneAPI/SceneData/SceneDataConfiguration.h>
|
||||
@@ -20,32 +21,39 @@ namespace EMotionFX::Pipeline::Rule
|
||||
AZ_RTTI(EMotionFX::Pipeline::Rule::MotionMetaData, "{A381A915-3CB3-4F60-82B3-70865CFA1F4F}");
|
||||
AZ_CLASS_ALLOCATOR(MotionMetaData, AZ::SystemAllocator, 0)
|
||||
|
||||
MotionMetaData() = default;
|
||||
MotionMetaData();
|
||||
MotionMetaData(EMotionFX::EMotionExtractionFlags extractionFlags, EMotionFX::MotionEventTable* eventTable);
|
||||
virtual ~MotionMetaData() = default;
|
||||
|
||||
EMotionFX::EMotionExtractionFlags GetMotionExtractionFlags() const { return m_motionExtractionFlags; }
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> GetClonedEventTable(EMotionFX::Motion* targetMotion) const;
|
||||
|
||||
static void Reflect(AZ::ReflectContext* context);
|
||||
|
||||
EMotionFX::MotionEventTable* m_motionEventTable = nullptr;
|
||||
private:
|
||||
static AZStd::unique_ptr<EMotionFX::MotionEventTable> CloneMotionEventTable(EMotionFX::MotionEventTable* sourceEventTable);
|
||||
|
||||
EMotionFX::EMotionExtractionFlags m_motionExtractionFlags;
|
||||
AZStd::unique_ptr<EMotionFX::MotionEventTable> m_motionEventTable;
|
||||
};
|
||||
|
||||
class MotionMetaDataRule
|
||||
: public ExternalToolRule<MotionMetaData>
|
||||
: public ExternalToolRule<AZStd::shared_ptr<MotionMetaData>>
|
||||
{
|
||||
public:
|
||||
AZ_RTTI(EMotionFX::Pipeline::Rule::MotionMetaDataRule, "{E68D0C3D-CBFF-4536-95C1-676474B351A5}", AZ::SceneAPI::DataTypes::IRule);
|
||||
AZ_CLASS_ALLOCATOR(MotionMetaDataRule, AZ::SystemAllocator, 0)
|
||||
|
||||
MotionMetaDataRule();
|
||||
MotionMetaDataRule(const MotionMetaData& data);
|
||||
MotionMetaDataRule(const AZStd::shared_ptr<MotionMetaData>& data);
|
||||
~MotionMetaDataRule() final = default;
|
||||
|
||||
const MotionMetaData& GetData() const override { return m_data; }
|
||||
void SetData(const MotionMetaData& data) override { m_data = data; }
|
||||
const AZStd::shared_ptr<MotionMetaData>& GetData() const override { return m_data; }
|
||||
void SetData(const AZStd::shared_ptr<MotionMetaData>& data) override { m_data = data; }
|
||||
|
||||
static void Reflect(AZ::ReflectContext* context);
|
||||
|
||||
private:
|
||||
MotionMetaData m_data;
|
||||
AZStd::shared_ptr<MotionMetaData> m_data;
|
||||
};
|
||||
} // EMotionFX::Pipeline::Rule
|
||||
|
||||
@@ -315,10 +315,8 @@ namespace EMStudio
|
||||
EMotionFX::Pipeline::Rule::RemoveRuleFromGroup<EMotionFX::Pipeline::Rule::MetaDataRule, const AZStd::vector<MCore::Command*>>(*scene, group);
|
||||
|
||||
// Add motion meta data.
|
||||
EMotionFX::Pipeline::Rule::MotionMetaData motionMetaData;
|
||||
motionMetaData.m_motionEventTable = motion->GetEventTable();
|
||||
motionMetaData.m_motionExtractionFlags = motion->GetMotionExtractionFlags();
|
||||
EMotionFX::Pipeline::Rule::SaveToGroup<EMotionFX::Pipeline::Rule::MotionMetaDataRule, EMotionFX::Pipeline::Rule::MotionMetaData>(*scene, group, motionMetaData);
|
||||
auto motionMetaData = AZStd::make_shared<EMotionFX::Pipeline::Rule::MotionMetaData>(motion->GetMotionExtractionFlags(), motion->GetEventTable());
|
||||
EMotionFX::Pipeline::Rule::SaveToGroup<EMotionFX::Pipeline::Rule::MotionMetaDataRule, AZStd::shared_ptr<EMotionFX::Pipeline::Rule::MotionMetaData>>(*scene, group, motionMetaData);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user