From: Seoyeon Kim Date: Thu, 27 Jul 2017 07:17:20 +0000 (+0900) Subject: Implement Animation SetLoopMode and GetLoopMode API X-Git-Tag: dali_1.2.52~1 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=d804ed0767c2d3f1c85fc2e94b4b6a3991ef5c88;p=platform%2Fcore%2Fuifw%2Fdali-core.git Implement Animation SetLoopMode and GetLoopMode API - Animation can play forwards and then runs backwards again using SetLoopMode(). - Enumeration 'LoopingMode' is one of RESTART and AUTO_REVERSE. Change-Id: Ideecab8060d242874cb8997918b0a6e9c7734dd9 Signed-off-by: Seoyeon Kim --- diff --git a/automated-tests/src/dali/utc-Dali-Animation.cpp b/automated-tests/src/dali/utc-Dali-Animation.cpp index d753f98..9c2f9be 100644 --- a/automated-tests/src/dali/utc-Dali-Animation.cpp +++ b/automated-tests/src/dali/utc-Dali-Animation.cpp @@ -11537,6 +11537,303 @@ int UtcDaliAnimationPlayAfterP3(void) END_TEST; } +int UtcDaliAnimationSetLoopingModeP(void) +{ + // Test Loop forever and Loop mode being set + TestApplication application; + Stage stage( Stage::GetCurrent() ); + + // Default: LoopingMode::RESTART + { + Actor actor = Actor::New(); + stage.Add( actor ); + + float durationSeconds( 1.0f ); + Animation animation = Animation::New( durationSeconds ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::RESTART ); + + Vector3 targetPosition(10.0f, 10.0f, 10.0f); + animation.AnimateTo( Property( actor, Actor::Property::POSITION ), targetPosition ); + + // Start the animation + animation.Play(); + application.SendNotification(); + application.Render(static_cast(durationSeconds*0.5f*1000.0f)/*Only half the animation*/); + + actor.Unparent(); + + application.SendNotification(); + application.Render(); + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + } + + // LoopingMode::AUTO_REVERSE + { + Actor actor = Actor::New(); + stage.Add( actor ); + + float durationSeconds( 1.0f ); + Animation animation = Animation::New( durationSeconds ); + animation.SetLooping( true ); + + bool signalReceived( false ); + AnimationFinishCheck finishCheck( signalReceived ); + animation.FinishedSignal().Connect( &application, finishCheck ); + application.SendNotification(); + + Vector3 targetPosition(100.0f, 100.0f, 100.0f); + animation.AnimateTo( Property( actor, Actor::Property::POSITION ), targetPosition ); + + DevelAnimation::SetLoopingMode( animation, DevelAnimation::LoopingMode::AUTO_REVERSE ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::AUTO_REVERSE ); + + // Start the animation + animation.Play(); + application.SendNotification(); + application.Render(0); + + for( int iterations = 0; iterations < 3; ++iterations ) + { + application.Render( static_cast< unsigned int >( durationSeconds * 500.0f )/* 50% time progress */ ); + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + + // AUTO_REVERSE mode means, for Animation duration time, the actor starts from the beginning, passes the targetPosition, + // and arrives at the beginning. + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + + application.SendNotification(); + application.Render( static_cast< unsigned int >( durationSeconds * 500.0f )/* 100% time progress */ ); + + // We did expect the animation to finish + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + DALI_TEST_EQUALS( actor.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), TEST_LOCATION ); + } + + animation.SetLooping( false ); + application.SendNotification(); + application.Render(static_cast< unsigned int >( durationSeconds * 1000.0f ) + 1u /*just beyond the animation duration*/); + + application.SendNotification(); + finishCheck.CheckSignalReceived(); + + DALI_TEST_EQUALS( actor.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), TEST_LOCATION ); + } + + // LoopingMode::AUTO_REVERSE in Reverse mode, which begin from the end + { + Actor actor = Actor::New(); + stage.Add( actor ); + + float durationSeconds( 1.0f ); + Animation animation = Animation::New( durationSeconds ); + animation.SetLooping( true ); + + bool signalReceived( false ); + AnimationFinishCheck finishCheck( signalReceived ); + animation.FinishedSignal().Connect( &application, finishCheck ); + application.SendNotification(); + + // Specify a negative multiplier to play the animation in reverse + animation.SetSpeedFactor( -1.0f ); + + Vector3 targetPosition(100.0f, 100.0f, 100.0f); + animation.AnimateTo( Property( actor, Actor::Property::POSITION ), targetPosition ); + + DevelAnimation::SetLoopingMode( animation, DevelAnimation::LoopingMode::AUTO_REVERSE ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::AUTO_REVERSE ); + + // Start the animation + animation.Play(); + application.SendNotification(); + application.Render(0); + + for( int iterations = 0; iterations < 3; ++iterations ) + { + application.Render( static_cast< unsigned int >( durationSeconds * 500.0f )/* 50% time progress */ ); + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + + // Setting a negative speed factor is to play the animation in reverse. + // So, when LoopingMode::AUTO_REVERSE and SetSpeedFactor( -1.0f ) is, for Animation duration time, + // the actor starts from the targetPosition, passes the beginning, and arrives at the targetPosition. + DALI_TEST_EQUALS( actor.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), TEST_LOCATION ); + + application.SendNotification(); + application.Render( static_cast< unsigned int >( durationSeconds * 500.0f )/* 100% time progress */ ); + + // We did expect the animation to finish + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + } + + animation.SetLooping( false ); + application.SendNotification(); + application.Render(static_cast< unsigned int >( durationSeconds * 1000.0f ) + 1u /*just beyond the animation duration*/); + + application.SendNotification(); + finishCheck.CheckSignalReceived(); + + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + } + + END_TEST; +} + +int UtcDaliAnimationSetLoopingModeP2(void) +{ + // Test Loop Count and Loop mode being set + TestApplication application; + Stage stage( Stage::GetCurrent() ); + + // LoopingMode::AUTO_REVERSE + { + Actor actor = Actor::New(); + stage.Add( actor ); + + float durationSeconds( 1.0f ); + Animation animation = Animation::New( durationSeconds ); + animation.SetLoopCount(3); + DALI_TEST_CHECK(animation.IsLooping()); + + bool signalReceived( false ); + AnimationFinishCheck finishCheck( signalReceived ); + animation.FinishedSignal().Connect( &application, finishCheck ); + application.SendNotification(); + + Vector3 targetPosition(100.0f, 100.0f, 100.0f); + animation.AnimateTo( Property( actor, Actor::Property::POSITION ), targetPosition ); + + DevelAnimation::SetLoopingMode( animation, DevelAnimation::LoopingMode::AUTO_REVERSE ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::AUTO_REVERSE ); + + // Start the animation + animation.Play(); + + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + + // Loop + float intervalSeconds = 3.0f; + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + // AUTO_REVERSE mode means, for Animation duration time, the actor starts from the beginning, passes the targetPosition, + // and arrives at the beginning. + DALI_TEST_EQUALS( actor.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), TEST_LOCATION ); + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + + application.SendNotification(); + finishCheck.CheckSignalReceived(); + DALI_TEST_EQUALS( actor.GetCurrentPosition(), Vector3( 0.0f, 0.0f, 0.0f ), TEST_LOCATION ); + + finishCheck.Reset(); + } + + // LoopingMode::AUTO_REVERSE in Reverse mode, which begin from the end + { + Actor actor = Actor::New(); + stage.Add( actor ); + + float durationSeconds( 1.0f ); + Animation animation = Animation::New( durationSeconds ); + animation.SetLoopCount(3); + DALI_TEST_CHECK(animation.IsLooping()); + + bool signalReceived( false ); + AnimationFinishCheck finishCheck( signalReceived ); + animation.FinishedSignal().Connect( &application, finishCheck ); + application.SendNotification(); + + // Specify a negative multiplier to play the animation in reverse + animation.SetSpeedFactor( -1.0f ); + + Vector3 targetPosition(100.0f, 100.0f, 100.0f); + animation.AnimateTo( Property( actor, Actor::Property::POSITION ), targetPosition ); + + DevelAnimation::SetLoopingMode( animation, DevelAnimation::LoopingMode::AUTO_REVERSE ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::AUTO_REVERSE ); + + // Start the animation + animation.Play(); + + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + + // Loop + float intervalSeconds = 3.0f; + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + // Setting a negative speed factor is to play the animation in reverse. + // So, when LoopingMode::AUTO_REVERSE and SetSpeedFactor( -1.0f ) is, for Animation duration time, + // the actor starts from the targetPosition, passes the beginning, and arrives at the targetPosition. + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + application.Render(0); + application.SendNotification(); + finishCheck.CheckSignalNotReceived(); + + application.Render(static_cast(durationSeconds*intervalSeconds*1000.0f)); + + application.SendNotification(); + finishCheck.CheckSignalReceived(); + DALI_TEST_EQUALS( actor.GetCurrentPosition(), targetPosition, TEST_LOCATION ); + + finishCheck.Reset(); + } + + END_TEST; +} + +int UtcDaliAnimationGetLoopingModeP(void) +{ + TestApplication application; + + Animation animation = Animation::New(1.0f); + + // default mode + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::RESTART ); + + DevelAnimation::SetLoopingMode( animation, DevelAnimation::LoopingMode::AUTO_REVERSE ); + DALI_TEST_CHECK( DevelAnimation::GetLoopingMode( animation ) == DevelAnimation::AUTO_REVERSE ); + + END_TEST; +} + int UtcDaliAnimationProgressSignalConnectionWithoutProgressMarkerP(void) { TestApplication application; diff --git a/dali/devel-api/animation/animation-devel.cpp b/dali/devel-api/animation/animation-devel.cpp index 5484256..79ebbb3 100644 --- a/dali/devel-api/animation/animation-devel.cpp +++ b/dali/devel-api/animation/animation-devel.cpp @@ -45,6 +45,16 @@ void PlayAfter( Animation animation, float delaySeconds ) GetImplementation( animation ).PlayAfter( delaySeconds ); } +void SetLoopingMode( Animation animation, LoopingMode loopingMode ) +{ + GetImplementation( animation ).SetLoopingMode( loopingMode ); +} + +LoopingMode GetLoopingMode( Animation animation ) +{ + return GetImplementation(animation).GetLoopingMode(); +} + } // namespace DevelAnimation } // namespace Dali diff --git a/dali/devel-api/animation/animation-devel.h b/dali/devel-api/animation/animation-devel.h index 4efa70a..209b4b0 100644 --- a/dali/devel-api/animation/animation-devel.h +++ b/dali/devel-api/animation/animation-devel.h @@ -28,6 +28,15 @@ namespace DevelAnimation { /** + * @brief Enumeration for what looping mode is in. + */ +enum LoopingMode +{ + RESTART, ///< When the animation arrives at the end in looping mode, the animation restarts from the beginning. + AUTO_REVERSE ///< When the animation arrives at the end in looping mode, the animation reverses direction and runs backwards again. +}; + +/** * @brief Set progress percentage marker to trigger ProgressHasBeenReachedSignal * * @param[in] animation the animation object to perform this operation on @@ -61,6 +70,23 @@ DALI_IMPORT_API Animation::AnimationSignalType& ProgressReachedSignal( Animation */ DALI_IMPORT_API void PlayAfter( Animation animation, float delaySeconds ); +/** + * @brief Sets the looping mode. + * + * Animation plays forwards and then restarts from the beginning or runs backwards again. + * @param[in] animation The animation object to perform this operation on + * @param[in] loopingMode The looping mode is one of RESTART and AUTO_REVERSE + */ +DALI_IMPORT_API void SetLoopingMode( Animation animation, LoopingMode loopingMode ); + +/** + * @brief Gets one of the current looping mode. + * + * @param[in] animation The animation object to perform this operation on + * @return The current looping mode + */ +DALI_IMPORT_API LoopingMode GetLoopingMode( Animation animation ); + } // namespace DevelAnimation } // namespace Dali diff --git a/dali/internal/event/animation/animation-impl.cpp b/dali/internal/event/animation/animation-impl.cpp index b7cc899..7290bb3 100644 --- a/dali/internal/event/animation/animation-impl.cpp +++ b/dali/internal/event/animation/animation-impl.cpp @@ -130,7 +130,8 @@ Animation::Animation( EventThreadServices& eventThreadServices, AnimationPlaylis mDefaultAlpha( defaultAlpha ), mState(Dali::Animation::STOPPED), mProgressReachedMarker( 0.0f ), - mDelaySeconds( 0.0f ) + mDelaySeconds( 0.0f ), + mAutoReverseEnabled( false ) { } @@ -1023,6 +1024,19 @@ Vector2 Animation::GetPlayRange() const return mPlayRange; } +void Animation::SetLoopingMode( DevelAnimation::LoopingMode loopingMode ) +{ + mAutoReverseEnabled = ( loopingMode == DevelAnimation::LoopingMode::AUTO_REVERSE ); + + // mAnimation is being used in a separate thread; queue a message to set play range + SetLoopingModeMessage( mEventThreadServices, *mAnimation, mAutoReverseEnabled ); +} + +DevelAnimation::LoopingMode Animation::GetLoopingMode() +{ + return mAutoReverseEnabled ? DevelAnimation::LoopingMode::AUTO_REVERSE : DevelAnimation::LoopingMode::RESTART; +} + bool Animation::CompareConnectorEndTimes( const Animation::ConnectorTargetValues& lhs, const Animation::ConnectorTargetValues& rhs ) { return ( ( lhs.timePeriod.delaySeconds + lhs.timePeriod.durationSeconds ) < ( rhs.timePeriod.delaySeconds + rhs.timePeriod.durationSeconds ) ); diff --git a/dali/internal/event/animation/animation-impl.h b/dali/internal/event/animation/animation-impl.h index bf1e628..760ef02 100644 --- a/dali/internal/event/animation/animation-impl.h +++ b/dali/internal/event/animation/animation-impl.h @@ -23,6 +23,7 @@ #include #include #include +#include #include #include #include @@ -364,36 +365,46 @@ public: */ void Hide(Actor& actor, float delaySeconds); - /* + /** * @copydoc Dali::Animation::SetCurrentProgress() */ void SetCurrentProgress(float progress); - /* + /** * @copydoc Dali::Animation::GetCurrentProgress() */ float GetCurrentProgress(); - /* + /** * @copydoc Dali::Animation::SetSpeedFactor() */ void SetSpeedFactor( float factor ); - /* + /** * @copydoc Dali::Animation::GetSpeedFactor() */ float GetSpeedFactor() const; - /* + /** * @copydoc Dali::Animation::SetPlayRange() */ void SetPlayRange( const Vector2& range ); - /* - * @copydoc Dali::Animation::GetPlayRange + /** + * @copydoc Dali::Animation::GetPlayRange() */ Vector2 GetPlayRange() const; + /** + * @copydoc Dali::Animation::SetLoopingMode() + */ + void SetLoopingMode( Dali::DevelAnimation::LoopingMode loopingMode ); + + /** + * @copydoc Dali::Animation::GetLoopingMode() + */ + Dali::DevelAnimation::LoopingMode GetLoopingMode(); + public: // For connecting animators to animations /** @@ -540,6 +551,7 @@ private: Dali::Animation::State mState; float mProgressReachedMarker; float mDelaySeconds; + bool mAutoReverseEnabled; ///< Flag to identify that the looping mode is auto reverse. }; } // namespace Internal diff --git a/dali/internal/update/animation/scene-graph-animation.cpp b/dali/internal/update/animation/scene-graph-animation.cpp index 9ce8ef0..709d7e7 100644 --- a/dali/internal/update/animation/scene-graph-animation.cpp +++ b/dali/internal/update/animation/scene-graph-animation.cpp @@ -77,7 +77,8 @@ Animation::Animation( float durationSeconds, float speedFactor, const Vector2& p mEndAction(endAction), mDisconnectAction(disconnectAction), mState(Stopped), - mProgressReachedSignalRequired( false ) + mProgressReachedSignalRequired( false ), + mAutoReverseEnabled( false ) { } @@ -278,6 +279,20 @@ void Animation::OnDestroy(BufferIndex bufferIndex) mState = Destroyed; } +void Animation::SetLoopingMode( bool loopingMode ) +{ + mAutoReverseEnabled = loopingMode; + + for ( AnimatorIter iter = mAnimators.Begin(), endIter = mAnimators.End(); iter != endIter; ++iter ) + { + // Send some variables together to figure out the Animation status + (*iter)->SetSpeedFactor( mSpeedFactor ); + (*iter)->SetLoopCount( mLoopCount ); + + (*iter)->SetLoopingMode( loopingMode ); + } +} + void Animation::AddAnimator( OwnerPointer& animator ) { animator->ConnectToSceneGraph(); diff --git a/dali/internal/update/animation/scene-graph-animation.h b/dali/internal/update/animation/scene-graph-animation.h index 3e27055..a30a347 100644 --- a/dali/internal/update/animation/scene-graph-animation.h +++ b/dali/internal/update/animation/scene-graph-animation.h @@ -106,7 +106,7 @@ public: return mDurationSeconds; } - /* + /** * Retrieve the current progress of the animation. * @return The current progress as a normalized value between [0,1]. */ @@ -120,7 +120,7 @@ public: return 0.0f; } - /* + /** * Sets the progress of the animation. * @param[in] The new progress as a normalized value between [0,1] */ @@ -129,6 +129,10 @@ public: mElapsedSeconds = mDurationSeconds * progress; } + /** + * Specifies a speed factor for the animation. + * @param[in] factor A value which will multiply the velocity + */ void SetSpeedFactor( float factor ) { mSpeedFactor = factor; @@ -150,7 +154,7 @@ public: return mLoopCount != 1; } - /* + /** * Get the loop count * @return the loop count */ @@ -262,6 +266,14 @@ public: } /** + * @brief Sets the looping mode. + * + * Animation plays forwards and then restarts from the beginning or runs backwards again. + * @param[in] loopingMode True when the looping mode is AUTO_REVERSE + */ + void SetLoopingMode( bool loopingMode ); + + /** * Add a newly created animator. * Animators are automatically removed, when orphaned from an animatable scene object. * @param[in] animator The animator to add. @@ -352,6 +364,7 @@ protected: State mState; bool mProgressReachedSignalRequired; // Flag to indicate the progress marker was hit + bool mAutoReverseEnabled; // Flag to identify that the looping mode is auto reverse. }; }; //namespace SceneGraph @@ -509,6 +522,17 @@ inline void PlayAfterMessage( EventThreadServices& eventThreadServices, const An new (slot) LocalType( &animation, &Animation::PlayAfter, delaySeconds ); } +inline void SetLoopingModeMessage( EventThreadServices& eventThreadServices, const Animation& animation, bool loopingMode ) +{ + typedef MessageValue1< Animation, bool > LocalType; + + // Reserve some memory inside the message queue + unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) ); + + // Construct message in the message queue memory; note that delete should not be called on the return value + new (slot) LocalType( &animation, &Animation::SetLoopingMode, loopingMode ); +} + } // namespace SceneGraph } // namespace Internal diff --git a/dali/internal/update/animation/scene-graph-animator.h b/dali/internal/update/animation/scene-graph-animator.h index d1cac15..19d4ecc 100644 --- a/dali/internal/update/animation/scene-graph-animator.h +++ b/dali/internal/update/animation/scene-graph-animator.h @@ -32,7 +32,7 @@ #include #include #include - +#include namespace Dali { @@ -70,11 +70,14 @@ public: AnimatorBase() : mDurationSeconds(1.0f), mIntervalDelaySeconds(0.0f), + mSpeedFactor(1.0f), + mLoopCount(1), mAlphaFunction(AlphaFunction::DEFAULT), mDisconnectAction(Dali::Animation::BakeFinal), mActive(false), mEnabled(true), - mConnectedToSceneGraph(false) + mConnectedToSceneGraph(false), + mAutoReverseEnabled( false ) { } @@ -111,6 +114,36 @@ public: return mDurationSeconds; } + void SetSpeedFactor( float factor ) + { + mSpeedFactor = factor; + } + + void SetLoopCount(int loopCount) + { + mLoopCount = loopCount; + } + + float SetProgress( float progress ) + { + float value = 0.0f; + + if( mAutoReverseEnabled ) + { + if( mSpeedFactor > 0.0f ) + { + value = 1.0f - 2.0f * std::abs( progress - 0.5f ); + } + // Reverse mode + else if( mSpeedFactor < 0.0f ) + { + value = 2.0f * std::abs( progress - 0.5f ); + } + } + + return value; + } + /** * Set the delay before the animator should take effect. * The default is zero i.e. no delay. @@ -148,7 +181,7 @@ public: return mAlphaFunction; } - /* + /** * Applies the alpha function to the specified progress * @param[in] Current progress * @return The progress after the alpha function has been aplied @@ -317,7 +350,7 @@ public: return mActive; } - /* + /** * Retrive wheter the animator's target object is valid and on the stage. * @return The enabled state. */ @@ -325,6 +358,16 @@ public: { return mEnabled; } + + /** + * @brief Sets the looping mode. + * @param[in] loopingMode True when the looping mode is AUTO_REVERSE + */ + void SetLoopingMode( bool loopingMode ) + { + mAutoReverseEnabled = loopingMode; + } + /** * Returns wheter the target object of the animator is still valid * or has been destroyed. @@ -358,6 +401,9 @@ protected: float mDurationSeconds; float mIntervalDelaySeconds; + float mSpeedFactor; + + int mLoopCount; AlphaFunction mAlphaFunction; @@ -365,6 +411,7 @@ protected: bool mActive:1; ///< Animator is "active" while it's running. bool mEnabled:1; ///< Animator is "enabled" while its target object is valid and on the stage. bool mConnectedToSceneGraph:1; ///< True if ConnectToSceneGraph() has been called in update-thread. + bool mAutoReverseEnabled:1; }; /** @@ -462,7 +509,13 @@ public: */ virtual void Update( BufferIndex bufferIndex, float progress, bool bake ) { - float alpha = ApplyAlphaFunction(progress); + if( mLoopCount != 1 ) // Looping mode + { + // Update the progress value + progress = SetProgress( progress ); + } + + float alpha = ApplyAlphaFunction( progress ); const PropertyType& current = mPropertyAccessor.Get( bufferIndex ); @@ -615,7 +668,13 @@ public: */ virtual void Update( BufferIndex bufferIndex, float progress, bool bake ) { - float alpha = ApplyAlphaFunction(progress); + if( mLoopCount != 1 ) // Looping mode + { + // Update the progress value + progress = SetProgress( progress ); + } + + float alpha = ApplyAlphaFunction( progress ); const T& current = mPropertyAccessor.Get( bufferIndex ); diff --git a/dali/public-api/animation/animation.h b/dali/public-api/animation/animation.h index 29160c3..c73e2b0 100644 --- a/dali/public-api/animation/animation.h +++ b/dali/public-api/animation/animation.h @@ -340,7 +340,7 @@ public: */ AlphaFunction GetDefaultAlphaFunction() const; - /* + /** * @brief Sets the progress of the animation. * * The animation will play (or continue playing) from this point. The progress