From 8bcb984180701874f18e9bd41b0cc0ae0aa76f0f Mon Sep 17 00:00:00 2001 From: ExMatics HydrogenC <33123710+HydrogenC@users.noreply.github.com> Date: Sun, 19 Nov 2023 17:02:07 +0800 Subject: [PATCH 1/2] Implement SetNodeTransform --- Source/Engine/Level/Actors/AnimatedModel.cpp | 21 ++++++++++++++++++++ Source/Engine/Level/Actors/AnimatedModel.h | 16 +++++++++++++++ 2 files changed, 37 insertions(+) diff --git a/Source/Engine/Level/Actors/AnimatedModel.cpp b/Source/Engine/Level/Actors/AnimatedModel.cpp index 88f7e6876..6c67620ae 100644 --- a/Source/Engine/Level/Actors/AnimatedModel.cpp +++ b/Source/Engine/Level/Actors/AnimatedModel.cpp @@ -172,6 +172,27 @@ void AnimatedModel::GetNodeTransformation(const StringView& nodeName, Matrix& no GetNodeTransformation(SkinnedModel ? SkinnedModel->FindNode(nodeName) : -1, nodeTransformation, worldSpace); } +void AnimatedModel::SetNodeTransformation(int32 nodeIndex, const Matrix& nodeTransformation, bool worldSpace) +{ + if (GraphInstance.NodesPose.IsEmpty()) + const_cast(this)->PreInitSkinningData(); // Ensure to have valid nodes pose to return + CHECK(nodeIndex >= 0 && nodeIndex < GraphInstance.NodesPose.Count()); + GraphInstance.NodesPose[nodeIndex] = nodeTransformation; + if (worldSpace) + { + Matrix world; + _transform.GetWorld(world); + Matrix invWorld; + Matrix::Invert(world, invWorld); + GraphInstance.NodesPose[nodeIndex] = GraphInstance.NodesPose[nodeIndex] * invWorld; + } + OnAnimationUpdated(); +} +void AnimatedModel::SetNodeTransformation(const StringView& nodeName, const Matrix& nodeTransformation, bool worldSpace) +{ + SetNodeTransformation(SkinnedModel ? SkinnedModel->FindNode(nodeName) : -1, nodeTransformation, worldSpace); +} + int32 AnimatedModel::FindClosestNode(const Vector3& location, bool worldSpace) const { if (GraphInstance.NodesPose.IsEmpty()) diff --git a/Source/Engine/Level/Actors/AnimatedModel.h b/Source/Engine/Level/Actors/AnimatedModel.h index 0c5c4d73b..3a4575bce 100644 --- a/Source/Engine/Level/Actors/AnimatedModel.h +++ b/Source/Engine/Level/Actors/AnimatedModel.h @@ -229,6 +229,22 @@ public: /// True if convert matrices into world-space, otherwise returned values will be in local-space of the actor. API_FUNCTION() void GetNodeTransformation(const StringView& nodeName, API_PARAM(Out) Matrix& nodeTransformation, bool worldSpace = false) const; + /// + /// Gets the node final transformation. + /// + /// The index of the skinned model skeleton node. + /// The final node transformation matrix. + /// True if convert matrices from world-space, otherwise values will be in local-space of the actor. + API_FUNCTION() void SetNodeTransformation(int32 nodeIndex, const Matrix& nodeTransformation, bool worldSpace = false); + + /// + /// Gets the node final transformation. + /// + /// The name of the skinned model skeleton node. + /// The final node transformation matrix. + /// True if convert matrices from world-space, otherwise values will be in local-space of the actor. + API_FUNCTION() void SetNodeTransformation(const StringView& nodeName, const Matrix& nodeTransformation, bool worldSpace = false); + /// /// Finds the closest node to a given location. /// From ddcb792767fe198a2ffa194e926ff721a0626ba7 Mon Sep 17 00:00:00 2001 From: ExMatics HydrogenC <33123710+HydrogenC@users.noreply.github.com> Date: Sun, 19 Nov 2023 17:07:42 +0800 Subject: [PATCH 2/2] Improve documentation --- Source/Engine/Level/Actors/AnimatedModel.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Source/Engine/Level/Actors/AnimatedModel.h b/Source/Engine/Level/Actors/AnimatedModel.h index 3a4575bce..029e17b62 100644 --- a/Source/Engine/Level/Actors/AnimatedModel.h +++ b/Source/Engine/Level/Actors/AnimatedModel.h @@ -230,7 +230,7 @@ public: API_FUNCTION() void GetNodeTransformation(const StringView& nodeName, API_PARAM(Out) Matrix& nodeTransformation, bool worldSpace = false) const; /// - /// Gets the node final transformation. + /// Sets the node final transformation. If multiple nodes are to be set within a frame, do not use set worldSpace to true, and do the conversion yourself to avoid recalculation of inv matrices. /// /// The index of the skinned model skeleton node. /// The final node transformation matrix. @@ -238,7 +238,7 @@ public: API_FUNCTION() void SetNodeTransformation(int32 nodeIndex, const Matrix& nodeTransformation, bool worldSpace = false); /// - /// Gets the node final transformation. + /// Sets the node final transformation. If multiple nodes are to be set within a frame, do not use set worldSpace to true, and do the conversion yourself to avoid recalculation of inv matrices. /// /// The name of the skinned model skeleton node. /// The final node transformation matrix.