From 7c8b44247b8dc36ffbe723082803b9697160d880 Mon Sep 17 00:00:00 2001 From: Martin Felis Date: Sun, 2 Apr 2023 21:24:12 +0200 Subject: [PATCH] Fixed SpeedScale node not properly propagating time. --- src/AnimGraph/AnimGraphData.h | 32 ++++++++++++++++++++++++++++++++ src/AnimGraph/AnimGraphEditor.cc | 7 +++++-- src/AnimGraph/AnimGraphNodes.cc | 2 +- src/AnimGraph/AnimGraphNodes.h | 8 ++++---- src/main.cc | 11 ++++++++--- 5 files changed, 50 insertions(+), 10 deletions(-) diff --git a/src/AnimGraph/AnimGraphData.h b/src/AnimGraph/AnimGraphData.h index fe1ab50..4a14722 100644 --- a/src/AnimGraph/AnimGraphData.h +++ b/src/AnimGraph/AnimGraphData.h @@ -188,6 +188,31 @@ struct Socket { m_value_string = value; } } + + template + T GetValue() const { + if constexpr (std::is_same::value) { + return m_value.flag; + } + + if constexpr (std::is_same::value) { + return m_value.float_value; + } + + if constexpr (std::is_same::value) { + return m_value.vec3; + } + + if constexpr (std::is_same::value) { + return m_value.quat; + } + + if constexpr (std::is_same::value) { + return m_value_string; + } + + return T(); + } }; template @@ -356,6 +381,13 @@ struct NodeDescriptorBase { return *static_cast(socket->m_reference.ptr); } + template + T GetPropertyValue(const char* name) { + Socket* socket = FindSocket(name, m_properties); + assert(GetSocketType() == socket->m_type); + return socket->GetValue(); + } + virtual void UpdateFlags(){}; protected: diff --git a/src/AnimGraph/AnimGraphEditor.cc b/src/AnimGraph/AnimGraphEditor.cc index 81b0f0f..df79453 100644 --- a/src/AnimGraph/AnimGraphEditor.cc +++ b/src/AnimGraph/AnimGraphEditor.cc @@ -172,9 +172,12 @@ void AnimGraphEditorRenderSidebar( -100.f, 100.f); } else if (property.m_type == SocketType::SocketTypeBool) { - ImGui::Checkbox( + bool flag_value = property.GetValue(); + if (ImGui::Checkbox( property.m_name.c_str(), - reinterpret_cast(property.m_reference.ptr)); + &flag_value)) { + property.SetValue(flag_value); + } } else if (property.m_type == SocketType::SocketTypeString) { char string_buf[1024]; memset(string_buf, '\0', sizeof(string_buf)); diff --git a/src/AnimGraph/AnimGraphNodes.cc b/src/AnimGraph/AnimGraphNodes.cc index a020692..317dee5 100644 --- a/src/AnimGraph/AnimGraphNodes.cc +++ b/src/AnimGraph/AnimGraphNodes.cc @@ -82,7 +82,7 @@ void AnimSamplerNode::Evaluate(AnimGraphContext& context) { ozz::animation::SamplingJob sampling_job; sampling_job.animation = m_animation; sampling_job.context = &m_sampling_context; - sampling_job.ratio = m_time_now; + sampling_job.ratio = fmodf(m_time_now, m_animation->duration()); sampling_job.output = make_span(o_output->m_local_matrices); if (!sampling_job.Run()) { diff --git a/src/AnimGraph/AnimGraphNodes.h b/src/AnimGraph/AnimGraphNodes.h index 88d90c1..91767cc 100644 --- a/src/AnimGraph/AnimGraphNodes.h +++ b/src/AnimGraph/AnimGraphNodes.h @@ -138,7 +138,7 @@ struct NodeDescriptor : public NodeDescriptorBase { Socket* weight_input_socket = FindSocket("Weight", m_inputs); assert(weight_input_socket != nullptr); - if (GetProperty("Sync") == true) { + if (GetPropertyValue("Sync") == true) { weight_input_socket->m_flags = SocketFlags::SocketFlagAffectsTime; } else { weight_input_socket->m_flags = SocketFlags::SocketFlagNone; @@ -156,8 +156,8 @@ struct SpeedScaleNode : public AnimNode { float* i_speed_scale = nullptr; void UpdateTime(float time_last, float time_now) override { - m_time_last = time_last; - m_time_now = time_last + (time_now - time_last) * (*i_speed_scale); + m_time_last = m_time_now; + m_time_now = m_time_last + (time_now - time_last) * (*i_speed_scale); m_state = AnimNodeEvalState::TimeUpdated; } @@ -196,7 +196,7 @@ struct AnimSamplerNode : public AnimNode { virtual bool Init(AnimGraphContext& context) override; void UpdateTime(float time_last, float time_now) override { m_time_last = time_last; - m_time_now = fmodf(time_last + (time_now - time_last), m_animation->duration()); + m_time_now = time_now; m_state = AnimNodeEvalState::TimeUpdated; } virtual void Evaluate(AnimGraphContext& context) override; diff --git a/src/main.cc b/src/main.cc index fb745f9..d06f4f2 100644 --- a/src/main.cc +++ b/src/main.cc @@ -76,6 +76,7 @@ static struct { } loaded; struct { double frame; + double anim_update_time; float absolute; uint64_t laptime; float factor; @@ -511,7 +512,10 @@ int main() { stm_round_to_common_refresh_rate(stm_laptime(&state.time.laptime))); if (!state.time.paused) { + state.time.anim_update_time = state.time.frame; state.time.absolute += state.time.frame * state.time.factor; + } else { + state.time.anim_update_time = 0.; } if (state.ozz.animation != nullptr) { @@ -725,7 +729,8 @@ int main() { ImGui::SameLine(); if (ImGui::Button("Step")) { - state.time.absolute += state.time.frame; + state.time.anim_update_time = 1. / 30.f; + state.time.absolute += state.time.anim_update_time; } if (state.ozz.animation != nullptr) { @@ -758,9 +763,9 @@ int main() { skinned_mesh.CalcModelMatrices(); } - if (state.time.use_graph && anim_graph.m_nodes.size() > 0) { + if (state.time.use_graph && anim_graph.m_nodes.size() > 0 && state.time.anim_update_time > 0.) { anim_graph.markActiveNodes(); - anim_graph.updateTime(state.time.frame); + anim_graph.updateTime(state.time.anim_update_time); anim_graph.evaluate(anim_graph_context); skinned_mesh.m_local_matrices = anim_graph_output.m_local_matrices;