AlphaFunction refactoring
[platform/core/uifw/dali-core.git] / dali / internal / update / animation / scene-graph-constraint.h
1 #ifndef __DALI_INTERNAL_SCENE_GRAPH_CONSTRAINT_H__
2 #define __DALI_INTERNAL_SCENE_GRAPH_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 // INTERNAL INCLUDES
22 #include <dali/public-api/animation/alpha-function.h>
23 #include <dali/public-api/common/dali-common.h>
24 #include <dali/public-api/signals/callback.h>
25 #include <dali/internal/event/animation/property-constraint-ptr.h>
26 #include <dali/internal/update/common/animatable-property.h>
27 #include <dali/internal/update/common/property-owner.h>
28 #include <dali/internal/update/animation/scene-graph-constraint-base.h>
29 #include <dali/internal/render/common/performance-monitor.h>
30
31 namespace Dali
32 {
33
34 namespace Internal
35 {
36
37 namespace SceneGraph
38 {
39
40 /**
41  * Used to constrain a property of a scene-object.
42  * The constraint function takes another scene-object property as an input.
43  */
44 template < class PropertyType, typename PropertyAccessorType >
45 class Constraint : public ConstraintBase
46 {
47 public:
48
49   typedef typename PropertyConstraintPtr< PropertyType >::Type ConstraintFunctionPtr;
50
51   /**
52    * Create a new scene-graph constraint.
53    * @param[in] targetProperty The target property.
54    * @param[in] ownerSet A set of property owners; func is connected to the properties provided by these objects.
55    * @param[in] func The function to calculate the final constrained value.
56    * @return A smart-pointer to a newly allocated constraint.
57    */
58   static ConstraintBase* New( const PropertyBase& targetProperty,
59                               PropertyOwnerContainer& ownerContainer,
60                               ConstraintFunctionPtr func )
61   {
62     // Scene-graph thread can edit these objects
63     PropertyBase& property = const_cast< PropertyBase& >( targetProperty );
64
65     return new Constraint< PropertyType, PropertyAccessorType >( property,
66                                                                  ownerContainer,
67                                                                  func );
68   }
69
70   /**
71    * Virtual destructor.
72    */
73   virtual ~Constraint()
74   {
75   }
76
77   /**
78    * Query whether the constraint needs to be applied. If a constraint depends on a set of properties,
79    * then it should be applied when any of those properties have changed.
80    */
81   bool ApplyNeeded()
82   {
83     if ( mFirstApply )
84     {
85       mFirstApply = false;
86       return true;
87     }
88
89     if ( ! mTargetProperty.IsClean() ||
90            mFunc->InputsChanged() )
91     {
92       return true;
93     }
94
95     // We don't need to reapply constraint if none of the properties changed
96     return false;
97   }
98
99   /**
100    * @copydoc Dali::Internal::SceneGraph::ConstraintBase::Apply()
101    */
102   virtual void Apply( BufferIndex updateBufferIndex )
103   {
104     if ( mDisconnected )
105     {
106       return; // Early-out when property owners have been disconnected
107     }
108
109     if ( mFunc->InputsInitialized() &&
110          ApplyNeeded() )
111     {
112       PropertyType current = mTargetProperty.Get( updateBufferIndex );
113       mFunc->Apply( updateBufferIndex, current );
114
115       // Optionally bake the final value
116       if ( Dali::Constraint::Bake == mRemoveAction )
117       {
118         mTargetProperty.Bake( updateBufferIndex, current );
119       }
120       else
121       {
122         mTargetProperty.Set( updateBufferIndex, current );
123       }
124
125       INCREASE_COUNTER(PerformanceMonitor::CONSTRAINTS_APPLIED);
126     }
127     else
128     {
129       INCREASE_COUNTER(PerformanceMonitor::CONSTRAINTS_SKIPPED);
130     }
131   }
132
133 private:
134
135   /**
136    * @copydoc Dali::Internal::SceneGraph::Constraint::New()
137    */
138   Constraint( PropertyBase& targetProperty,
139               PropertyOwnerContainer& ownerContainer,
140               ConstraintFunctionPtr func )
141   : ConstraintBase( ownerContainer ),
142     mTargetProperty( &targetProperty ),
143     mFunc( func )
144   {
145   }
146
147   // Undefined
148   Constraint( const Constraint& constraint );
149
150   // Undefined
151   Constraint& operator=( const Constraint& rhs );
152
153   /**
154    * @copydoc Dali::Internal::SceneGraph::ConstraintBase::OnDisconnect()
155    */
156   virtual void OnDisconnect()
157   {
158     // Discard target object/property pointers
159     mTargetProperty.Reset();
160     mFunc = NULL;
161   }
162
163 protected:
164
165   PropertyAccessorType mTargetProperty; ///< Raw-pointer to the target property. Not owned.
166
167   ConstraintFunctionPtr mFunc;
168 };
169
170 } // namespace SceneGraph
171
172 } // namespace Internal
173
174 } // namespace Dali
175
176 #endif // __DALI_INTERNAL_SCENE_GRAPH_CONSTRAINT_H__