[dali_1.0.11] Merge branch 'tizen'
[platform/core/uifw/dali-core.git] / dali / internal / update / animation / scene-graph-animator.h
1 #ifndef __DALI_INTERNAL_SCENE_GRAPH_ANIMATOR_H__
2 #define __DALI_INTERNAL_SCENE_GRAPH_ANIMATOR_H__
3
4 /*
5  * Copyright (c) 2014 Samsung Electronics Co., Ltd.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  */
20
21 // EXTERNAL INCLUDES
22 #include <boost/function.hpp>
23
24 // INTERNAL INCLUDES
25 #include <dali/internal/common/owner-container.h>
26 #include <dali/internal/event/animation/key-frames-impl.h>
27 #include <dali/internal/update/nodes/node.h>
28 #include <dali/internal/update/common/property-base.h>
29 #include <dali/internal/common/observer-pointer.h>
30 #include <dali/public-api/animation/alpha-functions.h>
31 #include <dali/public-api/animation/animation.h>
32 #include <dali/public-api/animation/time-period.h>
33 #include <dali/public-api/common/dali-common.h>
34 #include <dali/public-api/math/quaternion.h>
35 #include <dali/public-api/math/radian.h>
36
37 namespace Dali
38 {
39
40 namespace Internal
41 {
42
43 namespace SceneGraph
44 {
45
46 class AnimatorBase;
47
48 typedef OwnerContainer< AnimatorBase* > AnimatorContainer;
49
50 typedef AnimatorContainer::Iterator AnimatorIter;
51 typedef AnimatorContainer::ConstIterator AnimatorConstIter;
52
53 /**
54  * An abstract base class for Animators, which can be added to scene graph animations.
55  * Each animator changes a single property of an object in the scene graph.
56  */
57 class AnimatorBase
58 {
59 public:
60
61   typedef float (*AlphaFunc)(float progress); ///< Definition of an alpha function
62
63   /**
64    * Constructor.
65    */
66   AnimatorBase()
67   : mDurationSeconds(1.0f),
68     mInitialDelaySeconds(0.0f),
69     mAlphaFunc(AlphaFunctions::Linear),
70     mDisconnectAction(Dali::Animation::BakeFinal)
71   {
72   }
73
74   /**
75    * Virtual destructor.
76    */
77   virtual ~AnimatorBase()
78   {
79   }
80
81   /**
82    * Set the duration of the animator.
83    * @pre durationSeconds must be zero or greater; zero is useful when animating boolean values.
84    * @param [in] seconds Duration in seconds.
85    */
86   void SetDuration(float seconds)
87   {
88     DALI_ASSERT_DEBUG(seconds >= 0.0f);
89
90     mDurationSeconds = seconds;
91   }
92
93   /**
94    * Retrieve the duration of the animator.
95    * @return The duration in seconds.
96    */
97   float GetDuration()
98   {
99     return mDurationSeconds;
100   }
101
102   /**
103    * Set the delay before the animator should take effect.
104    * The default is zero i.e. no delay.
105    * @param [in] seconds The delay in seconds.
106    */
107   void SetInitialDelay(float seconds)
108   {
109     mInitialDelaySeconds = seconds;
110   }
111
112   /**
113    * Retrieve the initial delay of the animator.
114    * @return The delay in seconds.
115    */
116   float GetInitialDelay()
117   {
118     return mInitialDelaySeconds;
119   }
120
121   /**
122    * Set the alpha function for an animator.
123    * @param [in] alphaFunc The alpha function to apply to the animation progress.
124    */
125   void SetAlphaFunc(AlphaFunc alphaFunc)
126   {
127     mAlphaFunc = alphaFunc;
128   }
129
130   /**
131    * Retrieve the alpha function of an animator.
132    * @return The function.
133    */
134   AlphaFunc GetAlphaFunc() const
135   {
136     return mAlphaFunc;
137   }
138
139   /**
140    * Whether to bake the animation if attached property owner is disconnected.
141    * @param [in] action The disconnect action.
142    */
143   void SetDisconnectAction( Dali::Animation::EndAction action )
144   {
145     mDisconnectAction = action;
146   }
147
148   /**
149    * This must be called when the animator is attached to the scene-graph.
150    * @pre The animatable scene object must also be attached to the scene-graph.
151    * @param[in] propertyOwner The scene-object that owns the animatable property.
152    */
153   virtual void Attach( PropertyOwner* propertyOwner ) = 0;
154
155   /**
156    * Update the scene object attached to the animator.
157    * @param[in] bufferIndex The buffer to animate.
158    * @param[in] progress A value from 0 to 1, where 0 is the start of the animation, and 1 is the end point.
159    * @param[in] bake Bake.
160    * @return True if the update was applied, false if the animator has been orphaned.
161    */
162   virtual bool Update(BufferIndex bufferIndex, float progress, bool bake) = 0;
163
164   /**
165    * Query whether the animator is still attached to a scene object.
166    * The attachment will be automatically severed, when the object is destroyed.
167    * @return True if the animator is attached.
168    */
169   virtual bool IsAttached() const = 0;
170
171 protected:
172
173   float mDurationSeconds;
174   float mInitialDelaySeconds;
175
176   AlphaFunc mAlphaFunc;
177
178   Dali::Animation::EndAction mDisconnectAction;
179 };
180
181 /**
182  * An animator for a specific property type PropertyType.
183  */
184 template < typename PropertyType, typename PropertyAccessorType >
185 class Animator : public AnimatorBase, public PropertyOwner::Observer
186 {
187 public:
188
189   typedef boost::function< PropertyType (float, const PropertyType&) > AnimatorFunction;
190
191   /**
192    * Construct a new property animator.
193    * @param[in] property The animatable property; only valid while the Animator is attached.
194    * @param[in] animatorFunction The function used to animate the property.
195    * @param[in] alphaFunction The alpha function to apply.
196    * @param[in] timePeriod The time period of this animation.
197    * @return A newly allocated animator.
198    */
199   static AnimatorBase* New( const PropertyBase& property,
200                             AnimatorFunction animatorFunction,
201                             AlphaFunction alphaFunction,
202                             const TimePeriod& timePeriod )
203   {
204     typedef Animator< PropertyType, PropertyAccessorType > AnimatorType;
205
206     // The property was const in the actor-thread, but animators are used in the scene-graph thread.
207     AnimatorType* animator = new AnimatorType( const_cast<PropertyBase*>( &property ),
208                                                animatorFunction );
209
210     animator->SetAlphaFunc( alphaFunction );
211     animator->SetInitialDelay( timePeriod.delaySeconds );
212     animator->SetDuration( timePeriod.durationSeconds );
213
214     return animator;
215   }
216
217   /**
218    * Virtual destructor.
219    */
220   virtual ~Animator()
221   {
222     if (mPropertyOwner)
223     {
224       mPropertyOwner->RemoveObserver(*this);
225     }
226   }
227
228   /**
229    * From AnimatorBase.
230    * @param[in] propertyOwner The scene-object that owns the animatable property.
231    */
232   virtual void Attach( PropertyOwner* propertyOwner )
233   {
234     mPropertyOwner = propertyOwner;
235
236     if (mPropertyOwner)
237     {
238       mPropertyOwner->AddObserver(*this);
239     }
240   }
241
242   /**
243    * From AnimatorBase.
244    */
245   virtual bool Update( BufferIndex bufferIndex, float progress, bool bake )
246   {
247     // If the object dies, the animator has no effect
248     if ( mPropertyOwner )
249     {
250       float alpha = mAlphaFunc( progress );
251
252       const PropertyType& current = mPropertyAccessor.Get( bufferIndex );
253
254       const PropertyType result = mAnimatorFunction( alpha, current );
255
256       if ( bake )
257       {
258         mPropertyAccessor.Bake( bufferIndex, result );
259       }
260       else
261       {
262         mPropertyAccessor.Set( bufferIndex, result );
263       }
264
265       mCurrentProgress = progress;
266     }
267
268     return IsAttached(); // return false if orphaned
269   }
270
271   /**
272    * From AnimatorBase.
273    */
274   virtual bool IsAttached() const
275   {
276     return NULL != mPropertyOwner;
277   }
278
279   /**
280    * Called when mPropertyOwner is disconnected from the scene graph.
281    */
282   virtual void PropertyOwnerDisconnected( BufferIndex bufferIndex, PropertyOwner& owner )
283   {
284     // Bake the value if required
285     if ( mDisconnectAction != Dali::Animation::Discard )
286     {
287       // Bake to target-value if BakeFinal, otherwise bake current value
288       Update( bufferIndex, ( mDisconnectAction == Dali::Animation::Bake ? mCurrentProgress : 1.0f ), true );
289     }
290
291     mPropertyOwner = NULL;
292     mPropertyAccessor.Reset();
293   }
294
295   /**
296    * Called shortly before mPropertyOwner is destroyed, along with its property.
297    */
298   virtual void PropertyOwnerDestroyed( PropertyOwner& owner )
299   {
300     mPropertyOwner = NULL;
301     mPropertyAccessor.Reset();
302   }
303
304 private:
305
306   /**
307    * Private constructor; see also Animator::New().
308    */
309   Animator( PropertyBase* property,
310             AnimatorFunction animatorFunction )
311   : mPropertyOwner( NULL ),
312     mPropertyAccessor( property ),
313     mAnimatorFunction( animatorFunction ),
314     mCurrentProgress( 0.0f )
315   {
316   }
317
318   // Undefined
319   Animator( const Animator& );
320
321   // Undefined
322   Animator& operator=( const Animator& );
323
324 protected:
325
326   PropertyOwner* mPropertyOwner;
327   PropertyAccessorType mPropertyAccessor;
328
329   AnimatorFunction mAnimatorFunction;
330   float mCurrentProgress;
331 };
332
333 } // namespace SceneGraph
334
335
336 // Common Update functions
337
338 struct AnimateByFloat
339 {
340   AnimateByFloat(const float& relativeValue)
341   : mRelative(relativeValue)
342   {
343   }
344
345   float operator()(float alpha, const float& property)
346   {
347     return float(property + mRelative * alpha);
348   }
349
350   float mRelative;
351 };
352
353 struct AnimateToFloat
354 {
355   AnimateToFloat(const float& targetValue)
356   : mTarget(targetValue)
357   {
358   }
359
360   float operator()(float alpha, const float& property)
361   {
362     return float(property + ((mTarget - property) * alpha));
363   }
364
365   float mTarget;
366 };
367
368 struct AnimateByInteger
369 {
370   AnimateByInteger(const int& relativeValue)
371   : mRelative(relativeValue)
372   {
373   }
374
375   float operator()(float alpha, const int& property)
376   {
377     return int(property + mRelative * alpha + 0.5f );
378   }
379
380   int mRelative;
381 };
382
383 struct AnimateToInteger
384 {
385   AnimateToInteger(const int& targetValue)
386   : mTarget(targetValue)
387   {
388   }
389
390   float operator()(float alpha, const int& property)
391   {
392     return int(property + ((mTarget - property) * alpha) + 0.5f);
393   }
394
395   int mTarget;
396 };
397
398 struct AnimateByVector2
399 {
400   AnimateByVector2(const Vector2& relativeValue)
401   : mRelative(relativeValue)
402   {
403   }
404
405   Vector2 operator()(float alpha, const Vector2& property)
406   {
407     return Vector2(property + mRelative * alpha);
408   }
409
410   Vector2 mRelative;
411 };
412
413 struct AnimateToVector2
414 {
415   AnimateToVector2(const Vector2& targetValue)
416   : mTarget(targetValue)
417   {
418   }
419
420   Vector2 operator()(float alpha, const Vector2& property)
421   {
422     return Vector2(property + ((mTarget - property) * alpha));
423   }
424
425   Vector2 mTarget;
426 };
427
428 struct AnimateByVector3
429 {
430   AnimateByVector3(const Vector3& relativeValue)
431   : mRelative(relativeValue)
432   {
433   }
434
435   Vector3 operator()(float alpha, const Vector3& property)
436   {
437     return Vector3(property + mRelative * alpha);
438   }
439
440   Vector3 mRelative;
441 };
442
443 struct AnimateToVector3
444 {
445   AnimateToVector3(const Vector3& targetValue)
446   : mTarget(targetValue)
447   {
448   }
449
450   Vector3 operator()(float alpha, const Vector3& property)
451   {
452     return Vector3(property + ((mTarget - property) * alpha));
453   }
454
455   Vector3 mTarget;
456 };
457
458 struct AnimateByVector4
459 {
460   AnimateByVector4(const Vector4& relativeValue)
461   : mRelative(relativeValue)
462   {
463   }
464
465   Vector4 operator()(float alpha, const Vector4& property)
466   {
467     return Vector4(property + mRelative * alpha);
468   }
469
470   Vector4 mRelative;
471 };
472
473 struct AnimateToVector4
474 {
475   AnimateToVector4(const Vector4& targetValue)
476   : mTarget(targetValue)
477   {
478   }
479
480   Vector4 operator()(float alpha, const Vector4& property)
481   {
482     return Vector4(property + ((mTarget - property) * alpha));
483   }
484
485   Vector4 mTarget;
486 };
487
488 struct AnimateByOpacity
489 {
490   AnimateByOpacity(const float& relativeValue)
491   : mRelative(relativeValue)
492   {
493   }
494
495   Vector4 operator()(float alpha, const Vector4& property)
496   {
497     Vector4 result(property);
498     result.a += mRelative * alpha;
499
500     return result;
501   }
502
503   float mRelative;
504 };
505
506 struct AnimateToOpacity
507 {
508   AnimateToOpacity(const float& targetValue)
509   : mTarget(targetValue)
510   {
511   }
512
513   Vector4 operator()(float alpha, const Vector4& property)
514   {
515     Vector4 result(property);
516     result.a = property.a + ((mTarget - property.a) * alpha);
517
518     return result;
519   }
520
521   float mTarget;
522 };
523
524 struct AnimateByBoolean
525 {
526   AnimateByBoolean(bool relativeValue)
527   : mRelative(relativeValue)
528   {
529   }
530
531   bool operator()(float alpha, const bool& property)
532   {
533     // Alpha is not useful here, just keeping to the same template as other update functors
534     return bool(alpha >= 1.0f ? (property || mRelative) : property);
535   }
536
537   bool mRelative;
538 };
539
540 struct AnimateToBoolean
541 {
542   AnimateToBoolean(bool targetValue)
543   : mTarget(targetValue)
544   {
545   }
546
547   bool operator()(float alpha, const bool& property)
548   {
549     // Alpha is not useful here, just keeping to the same template as other update functors
550     return bool(alpha >= 1.0f ? mTarget : property);
551   }
552
553   bool mTarget;
554 };
555
556 struct RotateByAngleAxis
557 {
558   RotateByAngleAxis(const Radian& angleRadians, const Vector3& axis)
559   : mAngleRadians(angleRadians),
560     mAxis(axis.x, axis.y, axis.z, 0.0f)
561   {
562   }
563
564   Quaternion operator()(float alpha, const Quaternion& rotation)
565   {
566     if (alpha > 0.0f)
567     {
568       return rotation * Quaternion(mAngleRadians * alpha, mAxis);
569     }
570
571     return rotation;
572   }
573
574   float mAngleRadians;
575   Vector4 mAxis;
576 };
577
578 struct RotateToQuaternion
579 {
580   RotateToQuaternion(const Quaternion& targetValue)
581   : mTarget(targetValue)
582   {
583   }
584
585   Quaternion operator()(float alpha, const Quaternion& rotation)
586   {
587     return Quaternion::Slerp(rotation, mTarget, alpha);
588   }
589
590   Quaternion mTarget;
591 };
592
593
594 struct KeyFrameBooleanFunctor
595 {
596   KeyFrameBooleanFunctor(KeyFrameBooleanPtr keyFrames)
597   : mKeyFrames(keyFrames)
598   {
599   }
600
601   bool operator()(float progress, const bool& property)
602   {
603     if(mKeyFrames->IsActive(progress))
604     {
605       return mKeyFrames->GetValue(progress);
606     }
607     return property;
608   }
609
610   KeyFrameBooleanPtr mKeyFrames;
611 };
612
613 struct KeyFrameNumberFunctor
614 {
615   KeyFrameNumberFunctor(KeyFrameNumberPtr keyFrames)
616   : mKeyFrames(keyFrames)
617   {
618   }
619
620   float operator()(float progress, const float& property)
621   {
622     if(mKeyFrames->IsActive(progress))
623     {
624       return mKeyFrames->GetValue(progress);
625     }
626     return property;
627   }
628
629   KeyFrameNumberPtr mKeyFrames;
630 };
631
632 struct KeyFrameIntegerFunctor
633 {
634   KeyFrameIntegerFunctor(KeyFrameIntegerPtr keyFrames)
635   : mKeyFrames(keyFrames)
636   {
637   }
638
639   float operator()(float progress, const int& property)
640   {
641     if(mKeyFrames->IsActive(progress))
642     {
643       return mKeyFrames->GetValue(progress);
644     }
645     return property;
646   }
647
648   KeyFrameIntegerPtr mKeyFrames;
649 };
650
651 struct KeyFrameVector2Functor
652 {
653   KeyFrameVector2Functor(KeyFrameVector2Ptr keyFrames)
654   : mKeyFrames(keyFrames)
655   {
656   }
657
658   Vector2 operator()(float progress, const Vector2& property)
659   {
660     if(mKeyFrames->IsActive(progress))
661     {
662       return mKeyFrames->GetValue(progress);
663     }
664     return property;
665   }
666
667   KeyFrameVector2Ptr mKeyFrames;
668 };
669
670
671 struct KeyFrameVector3Functor
672 {
673   KeyFrameVector3Functor(KeyFrameVector3Ptr keyFrames)
674   : mKeyFrames(keyFrames)
675   {
676   }
677
678   Vector3 operator()(float progress, const Vector3& property)
679   {
680     if(mKeyFrames->IsActive(progress))
681     {
682       return mKeyFrames->GetValue(progress);
683     }
684     return property;
685   }
686
687   KeyFrameVector3Ptr mKeyFrames;
688 };
689
690 struct KeyFrameVector4Functor
691 {
692   KeyFrameVector4Functor(KeyFrameVector4Ptr keyFrames)
693   : mKeyFrames(keyFrames)
694   {
695   }
696
697   Vector4 operator()(float progress, const Vector4& property)
698   {
699     if(mKeyFrames->IsActive(progress))
700     {
701       return mKeyFrames->GetValue(progress);
702     }
703     return property;
704   }
705
706   KeyFrameVector4Ptr mKeyFrames;
707 };
708
709 struct KeyFrameQuaternionFunctor
710 {
711   KeyFrameQuaternionFunctor(KeyFrameQuaternionPtr keyFrames)
712   : mKeyFrames(keyFrames)
713   {
714   }
715
716   Quaternion operator()(float progress, const Quaternion& property)
717   {
718     if(mKeyFrames->IsActive(progress))
719     {
720       return mKeyFrames->GetValue(progress);
721     }
722     return property;
723   }
724
725   KeyFrameQuaternionPtr mKeyFrames;
726 };
727
728
729
730
731 } // namespace Internal
732
733 } // namespace Dali
734
735 #endif // __DALI_INTERNAL_SCENE_GRAPH_ANIMATOR_H__