Merge "remove the exports for enumerated property types" into tizen
[platform/core/uifw/dali-core.git] / dali / internal / event / animation / active-constraint-impl.h
1 #ifndef __DALI_INTERNAL_ACTIVE_CONSTRAINT_H__
2 #define __DALI_INTERNAL_ACTIVE_CONSTRAINT_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/public-api/common/set-wrapper.h>
26 #include <dali/internal/common/event-to-update.h>
27 #include <dali/internal/common/message.h>
28 #include <dali/internal/event/common/proxy-object.h>
29 #include <dali/internal/event/common/thread-local-storage.h>
30 #include <dali/internal/event/common/stage-impl.h>
31 #include <dali/internal/event/animation/active-constraint-base.h>
32 #include <dali/internal/event/animation/constraint-source-impl.h>
33 #include <dali/internal/event/animation/property-constraint-ptr.h>
34 #include <dali/internal/update/common/animatable-property.h>
35 #include <dali/internal/update/common/property-owner.h>
36 #include <dali/internal/update/common/property-owner-messages.h>
37 #include <dali/internal/update/animation/scene-graph-constraint.h>
38 #include <dali/internal/update/animation/property-accessor.h>
39 #include <dali/internal/update/animation/property-component-accessor.h>
40
41 namespace Dali
42 {
43
44 namespace Internal
45 {
46
47 /**
48  * Connects a constraint which takes another property as an input.
49  */
50 template < typename PropertyType >
51 class ActiveConstraint : public ActiveConstraintBase
52 {
53 public:
54
55   typedef SceneGraph::Constraint< PropertyType, PropertyAccessor<PropertyType> > SceneGraphConstraint;
56   typedef const SceneGraph::AnimatableProperty<PropertyType>* ScenePropertyPtr;
57   typedef typename PropertyConstraintPtr<PropertyType>::Type ConstraintFunctionPtr;
58   typedef boost::function< PropertyType (const PropertyType&, const PropertyType&, float) > InterpolatorFunction;
59
60   /**
61    * Construct a new active-constraint.
62    * @param[in] targetIndex The index of the property to constrain.
63    * @param[in] sources The sources of the input properties passed to func.
64    * @param[in] func The constraint function.
65    * @param[in] interpolator The interpolator function.
66    * @return A newly allocated active-constraint.
67    */
68   static ActiveConstraintBase* New( Property::Index targetIndex,
69                                     SourceContainer& sources,
70                                     ConstraintFunctionPtr func,
71                                     InterpolatorFunction interpolator )
72   {
73     ThreadLocalStorage& tls = ThreadLocalStorage::Get();
74
75     return new ActiveConstraint< PropertyType >( tls.GetEventToUpdate(), targetIndex, sources, sources.size(), func, interpolator );
76   }
77
78   /**
79    * Virtual destructor.
80    */
81   virtual ~ActiveConstraint()
82   {
83     // This is not responsible for removing constraints.
84   }
85
86   /**
87    * @copydoc ActiveConstraintBase::Clone()
88    */
89   virtual ActiveConstraintBase* Clone()
90   {
91     ActiveConstraintBase* clone( NULL );
92
93     ConstraintFunctionPtr funcPtr( mUserFunction->Clone() );
94
95     clone = new ActiveConstraint< PropertyType >( mEventToUpdate,
96                                                   mTargetIndex,
97                                                   mSources,
98                                                   mSourceCount,
99                                                   funcPtr,
100                                                   mInterpolatorFunction );
101
102     clone->SetAlphaFunction(mAlphaFunction);
103     clone->SetRemoveAction(mRemoveAction);
104     clone->SetTag( mTag );
105
106     return clone;
107   }
108
109 private:
110
111   /**
112    * Private constructor; see also ActiveConstraint::New().
113    */
114   ActiveConstraint( EventToUpdate& eventToUpdate,
115                     Property::Index targetIndex,
116                     SourceContainer& sources,
117                     unsigned int sourceCount,
118                     ConstraintFunctionPtr& func,
119                     InterpolatorFunction& interpolator )
120   : ActiveConstraintBase( eventToUpdate, targetIndex, sources, sourceCount ),
121     mTargetIndex( targetIndex ),
122     mUserFunction( func ),
123     mInterpolatorFunction( interpolator )
124   {
125   }
126
127   // Undefined
128   ActiveConstraint( const ActiveConstraint& );
129
130   // Undefined
131   ActiveConstraint& operator=( const ActiveConstraint& rhs );
132
133   /**
134    * Create and connect a constraint for a scene-object.
135    */
136   void ConnectConstraint()
137   {
138     // Should not come here any proxies have been destroyed
139     DALI_ASSERT_DEBUG( NULL != mTargetProxy );
140     DALI_ASSERT_DEBUG( mSources.size() == mSourceCount );
141
142     // Guard against double connections
143     DALI_ASSERT_DEBUG( NULL == mSceneGraphConstraint );
144
145     // Short-circuit until the target scene-object exists
146     SceneGraph::PropertyOwner* targetObject = const_cast< SceneGraph::PropertyOwner* >( mTargetProxy->GetSceneObject() );
147     if ( NULL == targetObject )
148     {
149       return;
150     }
151
152     // Build a set of property-owners, providing the scene-graph properties
153     SceneGraph::PropertyOwnerSet propertyOwners;
154     propertyOwners.insert( targetObject );
155
156     // Build the constraint function; this requires a scene-graph property from each source
157     ConstraintFunctionPtr func( ConnectConstraintFunction( propertyOwners ) );
158
159     if ( func )
160     {
161       // Create the SceneGraphConstraint, and connect to the scene-graph
162
163       const SceneGraph::PropertyBase* targetProperty = mTargetProxy->GetSceneObjectAnimatableProperty( mTargetIndex );
164
165       // The targetProperty should exist, when targetObject exists
166       DALI_ASSERT_ALWAYS( NULL != targetProperty && "Constraint target property does not exist" );
167
168       // Connect the constraint
169       SceneGraph::ConstraintBase* sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty,
170                                                                                      propertyOwners,
171                                                                                      func,
172                                                                                      mInterpolatorFunction,
173                                                                                      mCustomWeight );
174       DALI_ASSERT_DEBUG( NULL != sceneGraphConstraint );
175       sceneGraphConstraint->SetInitialWeight( mOffstageWeight );
176       sceneGraphConstraint->SetRemoveAction( mRemoveAction );
177
178       // object is being used in a separate thread; queue a message to apply the constraint
179       ApplyConstraintMessage( Stage::GetCurrent()->GetUpdateInterface(), *targetObject, *sceneGraphConstraint );
180
181       // Keep a raw-pointer to the scene-graph constraint
182       mSceneGraphConstraint = sceneGraphConstraint;
183
184       // Notify ProxyObject base-class that the scene-graph constraint has been added
185       OnSceneObjectAdd();
186     }
187   }
188
189   /**
190    * Helper for ConnectConstraint. Creates a connected constraint-function.
191    * Also populates the property-owner set, for each input connected to the constraint-function.
192    * @param[out] propertyOwners The set of property-owners providing the scene-graph properties.
193    * @return A connected constraint-function, or NULL if the scene-graph properties are not available.
194    */
195   PropertyConstraintBase<PropertyType>* ConnectConstraintFunction( SceneGraph::PropertyOwnerSet& propertyOwners )
196   {
197     PropertyConstraintBase<PropertyType>* func = mUserFunction->Clone();
198     bool usingComponentFunc( false );
199
200     for ( SourceIter iter = mSources.begin(); mSources.end() != iter; ++iter )
201     {
202       Source& source = *iter;
203
204       PropertyInputImpl* inputProperty( NULL );
205       int componentIndex( Property::INVALID_COMPONENT_INDEX );
206
207       if ( OBJECT_PROPERTY == source.sourceType )
208       {
209         DALI_ASSERT_ALWAYS( source.object->IsPropertyAConstraintInput( source.propertyIndex ) );
210
211         SceneGraph::PropertyOwner* owner = const_cast< SceneGraph::PropertyOwner* >( source.object->GetSceneObject() );
212
213         // The property owner will not exist, if the target proxy-object is off-stage
214         if( NULL != owner )
215         {
216           propertyOwners.insert( owner );
217           inputProperty = const_cast< PropertyInputImpl* >( source.object->GetSceneObjectInputProperty( source.propertyIndex ) );
218           componentIndex = source.object->GetPropertyComponentIndex( source.propertyIndex );
219
220           // The scene-object property should exist, when the property owner exists
221           DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
222         }
223       }
224       else if ( LOCAL_PROPERTY == source.sourceType )
225       {
226         DALI_ASSERT_ALWAYS( mTargetProxy->IsPropertyAConstraintInput( source.propertyIndex ) );
227
228         inputProperty = const_cast< PropertyInputImpl* >( mTargetProxy->GetSceneObjectInputProperty( source.propertyIndex ) );
229         componentIndex = mTargetProxy->GetPropertyComponentIndex( source.propertyIndex );
230
231         // The target scene-object should provide this property
232         DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
233       }
234       else
235       {
236         DALI_ASSERT_ALWAYS( PARENT_PROPERTY == source.sourceType && "Constraint source property type is invalid" );
237
238         ProxyObject* proxyParent = dynamic_cast< Actor& >( *mTargetProxy ).GetParent();
239
240         // This will not exist, if the target proxy-object is off-stage
241         if ( NULL != proxyParent )
242         {
243           DALI_ASSERT_ALWAYS( proxyParent->IsPropertyAConstraintInput( source.propertyIndex ) );
244
245           SceneGraph::PropertyOwner* owner = const_cast< SceneGraph::PropertyOwner* >( proxyParent->GetSceneObject() );
246
247           // The property owner will not exist, if the parent proxy-object is off-stage
248           if ( NULL != owner )
249           {
250             propertyOwners.insert( owner );
251             inputProperty = const_cast< PropertyInputImpl* >( proxyParent->GetSceneObjectInputProperty( source.propertyIndex ) );
252             componentIndex = proxyParent->GetPropertyComponentIndex( source.propertyIndex );
253
254             // The scene-object property should exist, when the property owner exists
255             DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
256           }
257         }
258       }
259
260       if ( NULL == inputProperty )
261       {
262         delete func;
263         func = NULL;
264
265         // Exit if a scene-graph object is not available from one of the sources
266         break;
267       }
268       else if ( Property::INVALID_COMPONENT_INDEX != componentIndex )
269       {
270         // Special case where component indices are required
271         if ( !usingComponentFunc )
272         {
273           PropertyConstraintBase<PropertyType>* componentFunc = func->CloneComponentFunc();
274           usingComponentFunc = true;
275
276           // Switch to function supporting component indices
277           delete func;
278           func = componentFunc;
279         }
280       }
281
282       func->SetInput( ( iter - mSources.begin() ), componentIndex, *inputProperty );
283     }
284
285     return func;
286   }
287
288 protected:
289
290   Property::Index mTargetIndex;
291
292   ConstraintFunctionPtr mUserFunction;
293   InterpolatorFunction mInterpolatorFunction;
294 };
295
296 /**
297  * Variant which allows float components to be animated individually.
298  */
299 template <>
300 class ActiveConstraint<float> : public ActiveConstraintBase
301 {
302 public:
303
304   typedef typename PropertyConstraintPtr<float>::Type ConstraintFunctionPtr;
305   typedef boost::function< float (const float&, const float&, float) > InterpolatorFunction;
306
307   /**
308    * Construct a new active-constraint.
309    * @param[in] targetIndex The index of the property to constrain.
310    * @param[in] sources The sources of the input properties passed to func.
311    * @param[in] func The constraint function.
312    * @param[in] interpolator The interpolator function.
313    * @return A newly allocated active-constraint.
314    */
315   static ActiveConstraintBase* New( Property::Index targetIndex,
316                                     SourceContainer& sources,
317                                     ConstraintFunctionPtr func,
318                                     InterpolatorFunction interpolator )
319   {
320     ThreadLocalStorage& tls = ThreadLocalStorage::Get();
321
322     return new ActiveConstraint< float >( tls.GetEventToUpdate(), targetIndex, sources, sources.size(), func, interpolator );
323   }
324
325   /**
326    * Virtual destructor.
327    */
328   virtual ~ActiveConstraint()
329   {
330     // This is not responsible for removing constraints.
331   }
332
333   /**
334    * @copydoc ActiveConstraintBase::Clone()
335    */
336   virtual ActiveConstraintBase* Clone()
337   {
338     ActiveConstraintBase* clone( NULL );
339
340     ConstraintFunctionPtr funcPtr( mUserFunction->Clone() );
341
342     clone = new ActiveConstraint< float >( mEventToUpdate,
343                                            mTargetIndex,
344                                            mSources,
345                                            mSourceCount,
346                                            funcPtr,
347                                            mInterpolatorFunction );
348
349     clone->SetAlphaFunction(mAlphaFunction);
350     clone->SetRemoveAction(mRemoveAction);
351     clone->SetTag( mTag );
352
353     return clone;
354   }
355
356 private:
357
358   /**
359    * Private constructor; see also ActiveConstraint::New().
360    */
361   ActiveConstraint( EventToUpdate& eventToUpdate,
362                     Property::Index targetIndex,
363                     SourceContainer& sources,
364                     unsigned int sourceCount,
365                     ConstraintFunctionPtr& func,
366                     InterpolatorFunction& interpolator )
367   : ActiveConstraintBase( eventToUpdate, targetIndex, sources, sourceCount ),
368     mTargetIndex( targetIndex ),
369     mUserFunction( func ),
370     mInterpolatorFunction( interpolator )
371   {
372   }
373
374   // Undefined
375   ActiveConstraint( const ActiveConstraint& );
376
377   // Undefined
378   ActiveConstraint& operator=( const ActiveConstraint& rhs );
379
380   /**
381    * Create and connect a constraint for a scene-object.
382    */
383   void ConnectConstraint()
384   {
385     // Should not come here any proxies have been destroyed
386     DALI_ASSERT_DEBUG( NULL != mTargetProxy );
387     DALI_ASSERT_DEBUG( mSources.size() == mSourceCount );
388
389     // Guard against double connections
390     DALI_ASSERT_DEBUG( NULL == mSceneGraphConstraint );
391
392     // Short-circuit until the target scene-object exists
393     SceneGraph::PropertyOwner* targetObject = const_cast< SceneGraph::PropertyOwner* >( mTargetProxy->GetSceneObject() );
394     if ( NULL == targetObject )
395     {
396       return;
397     }
398
399     // Build a set of property-owners, providing the scene-graph properties
400     SceneGraph::PropertyOwnerSet propertyOwners;
401     propertyOwners.insert( targetObject );
402
403     // Build the constraint function; this requires a scene-graph property from each source
404     ConstraintFunctionPtr func( ConnectConstraintFunction( propertyOwners ) );
405
406     if ( func )
407     {
408       // Create the SceneGraphConstraint, and connect to the scene-graph
409
410       const SceneGraph::PropertyBase* targetProperty = mTargetProxy->GetSceneObjectAnimatableProperty( mTargetIndex );
411
412       // The targetProperty should exist, when targetObject exists
413       DALI_ASSERT_ALWAYS( NULL != targetProperty && "Constraint target property does not exist" );
414
415       const int componentIndex = mTargetProxy->GetPropertyComponentIndex( mTargetIndex );
416
417       SceneGraph::ConstraintBase* sceneGraphConstraint( NULL );
418
419       if ( Property::INVALID_COMPONENT_INDEX == componentIndex )
420       {
421         // Not a Vector3 or Vector4 component, expecting float type
422         DALI_ASSERT_DEBUG( PropertyTypes::Get< float >() == targetProperty->GetType() );
423
424         typedef SceneGraph::Constraint< float, PropertyAccessor<float> > SceneGraphConstraint;
425
426         sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty,
427                                                            propertyOwners,
428                                                            func,
429                                                            mInterpolatorFunction,
430                                                            mCustomWeight );
431       }
432       else
433       {
434         // Expecting Vector3 or Vector4 type
435
436         if ( PropertyTypes::Get< Vector3 >() == targetProperty->GetType() )
437         {
438           // Constrain float component of Vector3 property
439
440           if ( 0 == componentIndex )
441           {
442             typedef SceneGraph::Constraint< float, PropertyComponentAccessorX<Vector3> > SceneGraphConstraint;
443             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
444           }
445           else if ( 1 == componentIndex )
446           {
447             typedef SceneGraph::Constraint< float, PropertyComponentAccessorY<Vector3> > SceneGraphConstraint;
448             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
449           }
450           else if ( 2 == componentIndex )
451           {
452             typedef SceneGraph::Constraint< float, PropertyComponentAccessorZ<Vector3> > SceneGraphConstraint;
453             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
454           }
455         }
456         else if ( PropertyTypes::Get< Vector4 >() == targetProperty->GetType() )
457         {
458           // Constrain float component of Vector4 property
459
460           if ( 0 == componentIndex )
461           {
462             typedef SceneGraph::Constraint< float, PropertyComponentAccessorX<Vector4> > SceneGraphConstraint;
463             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
464           }
465           else if ( 1 == componentIndex )
466           {
467             typedef SceneGraph::Constraint< float, PropertyComponentAccessorY<Vector4> > SceneGraphConstraint;
468             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
469           }
470           else if ( 2 == componentIndex )
471           {
472             typedef SceneGraph::Constraint< float, PropertyComponentAccessorZ<Vector4> > SceneGraphConstraint;
473             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
474           }
475           else if ( 3 == componentIndex )
476           {
477             typedef SceneGraph::Constraint< float, PropertyComponentAccessorW<Vector4> > SceneGraphConstraint;
478             sceneGraphConstraint = SceneGraphConstraint::New( *targetProperty, propertyOwners, func, mInterpolatorFunction, mCustomWeight );
479           }
480         }
481       }
482
483       DALI_ASSERT_DEBUG( NULL != sceneGraphConstraint );
484       sceneGraphConstraint->SetInitialWeight( mOffstageWeight );
485       sceneGraphConstraint->SetRemoveAction( mRemoveAction );
486
487         // object is being used in a separate thread; queue a message to apply the constraint
488       ApplyConstraintMessage( Stage::GetCurrent()->GetUpdateInterface(), *targetObject, *sceneGraphConstraint );
489
490       // Keep a raw-pointer to the scene-graph constraint
491       mSceneGraphConstraint = sceneGraphConstraint;
492
493       // Notify ProxyObject base-class that the scene-graph constraint has been added
494       OnSceneObjectAdd();
495     }
496   }
497
498   /**
499    * Helper for ConnectConstraint. Creates a connected constraint-function.
500    * Also populates the property-owner set, for each input connected to the constraint-function.
501    * @param[out] propertyOwners The set of property-owners providing the scene-graph properties.
502    * @return A connected constraint-function, or NULL if the scene-graph properties are not available.
503    */
504   PropertyConstraintBase<float>* ConnectConstraintFunction( SceneGraph::PropertyOwnerSet& propertyOwners )
505   {
506     PropertyConstraintBase<float>* func = mUserFunction->Clone();
507     bool usingComponentFunc( false );
508
509     for ( SourceIter iter = mSources.begin(); mSources.end() != iter; ++iter )
510     {
511       Source& source = *iter;
512
513       PropertyInputImpl* inputProperty( NULL );
514       int componentIndex( Property::INVALID_COMPONENT_INDEX );
515
516       if ( OBJECT_PROPERTY == source.sourceType )
517       {
518         DALI_ASSERT_ALWAYS( source.object->IsPropertyAConstraintInput( source.propertyIndex ) );
519
520         SceneGraph::PropertyOwner* owner = const_cast< SceneGraph::PropertyOwner* >( source.object->GetSceneObject() );
521
522         // The property owner will not exist, if the target proxy-object is off-stage
523         if( NULL != owner )
524         {
525           propertyOwners.insert( owner );
526           inputProperty = const_cast< PropertyInputImpl* >( source.object->GetSceneObjectInputProperty( source.propertyIndex ) );
527           componentIndex = source.object->GetPropertyComponentIndex( source.propertyIndex );
528
529           // The scene-object property should exist, when the property owner exists
530           DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
531         }
532       }
533       else if ( LOCAL_PROPERTY == source.sourceType )
534       {
535         DALI_ASSERT_ALWAYS( mTargetProxy->IsPropertyAConstraintInput( source.propertyIndex ) );
536
537         inputProperty = const_cast< PropertyInputImpl* >( mTargetProxy->GetSceneObjectInputProperty( source.propertyIndex ) );
538         componentIndex = mTargetProxy->GetPropertyComponentIndex( source.propertyIndex );
539
540         // The target scene-object should provide this property
541         DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
542       }
543       else
544       {
545         DALI_ASSERT_ALWAYS( PARENT_PROPERTY == source.sourceType && "Constraint source property type is invalid" );
546
547         ProxyObject* proxyParent = dynamic_cast< Actor& >( *mTargetProxy ).GetParent();
548
549         // This will not exist, if the target proxy-object is off-stage
550         if ( NULL != proxyParent )
551         {
552           DALI_ASSERT_ALWAYS( proxyParent->IsPropertyAConstraintInput( source.propertyIndex ) );
553
554           SceneGraph::PropertyOwner* owner = const_cast< SceneGraph::PropertyOwner* >( proxyParent->GetSceneObject() );
555
556           // The property owner will not exist, if the parent proxy-object is off-stage
557           if ( NULL != owner )
558           {
559             propertyOwners.insert( owner );
560             inputProperty = const_cast< PropertyInputImpl* >( proxyParent->GetSceneObjectInputProperty( source.propertyIndex ) );
561             componentIndex = proxyParent->GetPropertyComponentIndex( source.propertyIndex );
562
563             // The scene-object property should exist, when the property owner exists
564             DALI_ASSERT_ALWAYS( NULL != inputProperty && "Constraint source property does not exist" );
565           }
566         }
567       }
568
569       if ( NULL == inputProperty )
570       {
571         delete func;
572         func = NULL;
573
574         // Exit if a scene-graph object is not available from one of the sources
575         break;
576       }
577       else if ( Property::INVALID_COMPONENT_INDEX != componentIndex )
578       {
579         // Special case where component indices are required
580         if ( !usingComponentFunc )
581         {
582           PropertyConstraintBase<float>* componentFunc = func->CloneComponentFunc();
583           usingComponentFunc = true;
584
585           // Switch to function supporting component indices
586           delete func;
587           func = componentFunc;
588         }
589       }
590
591       func->SetInput( ( iter - mSources.begin() ), componentIndex, *inputProperty );
592     }
593
594     return func;
595   }
596
597 protected:
598
599   Property::Index mTargetIndex;
600
601   ConstraintFunctionPtr mUserFunction;
602   InterpolatorFunction mInterpolatorFunction;
603 };
604
605 } // namespace Internal
606
607 } // namespace Dali
608
609 #endif // __DALI_INTERNAL_ACTIVE_CONSTRAINT_H__