From 097c1fee7b535502e7b40360bc20d9a158782ddd Mon Sep 17 00:00:00 2001 From: bodymovin Date: Mon, 8 Apr 2024 18:19:38 +0000 Subject: [PATCH] negative speed fix negative speed states wouldn't play the animation if it didn't have transition duration or exit time. this PR fixes it by taking into account the speed multiplier when evaluating if the animation still has frames to play. Diffs= 0bc446fad negative speed fix (#6982) Co-authored-by: hernan --- .rive_head | 2 +- include/rive/animation/linear_animation_instance.hpp | 7 +++++++ src/animation/linear_animation_instance.cpp | 4 ++-- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/.rive_head b/.rive_head index 29283048..ed40a47c 100644 --- a/.rive_head +++ b/.rive_head @@ -1 +1 @@ -f832e26172cfbd11d52114ebb667e13418a5b1cd +0bc446fad2a568a7088fdaa122af0de2de1dc940 diff --git a/include/rive/animation/linear_animation_instance.hpp b/include/rive/animation/linear_animation_instance.hpp index a7cb9f6f..4919bd7f 100644 --- a/include/rive/animation/linear_animation_instance.hpp +++ b/include/rive/animation/linear_animation_instance.hpp @@ -69,6 +69,13 @@ class LinearAnimationInstance : public Scene (directedSpeed() < 0 && m_time > m_animation->startSeconds()); } + bool keepGoing(float speedMultiplier) const + { + return this->loopValue() != static_cast(rive::Loop::oneShot) || + (directedSpeed() * speedMultiplier > 0 && m_time < m_animation->endSeconds()) || + (directedSpeed() * speedMultiplier < 0 && m_time > m_animation->startSeconds()); + } + float totalTime() const { return m_totalTime; } float lastTotalTime() const { return m_lastTotalTime; } float spilledTime() const { return m_spilledTime; } diff --git a/src/animation/linear_animation_instance.cpp b/src/animation/linear_animation_instance.cpp index 7e132d46..ff7fe55a 100644 --- a/src/animation/linear_animation_instance.cpp +++ b/src/animation/linear_animation_instance.cpp @@ -58,7 +58,7 @@ bool LinearAnimationInstance::advance(float elapsedSeconds, KeyedCallbackReporte // NOTE: // do not track spilled time, if our one shot loop is already completed. // stop gap before we move spilled tracking into state machine logic. - bool killSpilledTime = !this->keepGoing(); + bool killSpilledTime = !this->keepGoing(elapsedSeconds); float lastTime = m_time; m_time += deltaSeconds; @@ -165,7 +165,7 @@ bool LinearAnimationInstance::advance(float elapsedSeconds, KeyedCallbackReporte } m_didLoop = didLoop; - return this->keepGoing(); + return this->keepGoing(elapsedSeconds); } void LinearAnimationInstance::time(float value)