Merge branch devel/master (1.0.49) into tizen
[platform/core/uifw/dali-core.git] / dali / internal / update / nodes / node.h
1 #ifndef __DALI_INTERNAL_SCENE_GRAPH_NODE_H__
2 #define __DALI_INTERNAL_SCENE_GRAPH_NODE_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/actors/actor-enumerations.h>
23 #include <dali/public-api/actors/draw-mode.h>
24 #include <dali/devel-api/common/set-wrapper.h>
25 #include <dali/public-api/math/quaternion.h>
26 #include <dali/public-api/math/math-utils.h>
27 #include <dali/public-api/math/vector3.h>
28 #include <dali/internal/common/message.h>
29 #include <dali/internal/event/common/event-thread-services.h>
30 #include <dali/internal/update/common/animatable-property.h>
31 #include <dali/internal/update/common/property-owner.h>
32 #include <dali/internal/update/common/property-vector3.h>
33 #include <dali/internal/update/common/scene-graph-buffers.h>
34 #include <dali/internal/update/common/inherited-property.h>
35 #include <dali/integration-api/debug.h>
36 #include <dali/internal/update/nodes/node-declarations.h>
37 #include <dali/internal/update/node-attachments/node-attachment-declarations.h>
38 #include <dali/internal/render/data-providers/node-data-provider.h>
39
40 namespace Dali
41 {
42
43 namespace Internal
44 {
45
46 // value types used by messages
47 template <> struct ParameterType< ColorMode > : public BasicType< ColorMode > {};
48 template <> struct ParameterType< PositionInheritanceMode > : public BasicType< PositionInheritanceMode > {};
49
50 namespace SceneGraph
51 {
52
53 class DiscardQueue;
54 class Layer;
55 class NodeAttachment;
56 class RenderTask;
57 class UpdateManager;
58
59 /**
60  * Flag whether property has changed, during the Update phase.
61  */
62 enum NodePropertyFlags
63 {
64   NothingFlag          = 0x000,
65   TransformFlag        = 0x001,
66   VisibleFlag          = 0x002,
67   ColorFlag            = 0x004,
68   SizeFlag             = 0x008,
69   OverlayFlag          = 0x010,
70   SortModifierFlag     = 0x020,
71   ChildDeletedFlag     = 0x040
72 };
73
74 static const int AllFlags = ( ChildDeletedFlag << 1 ) - 1; // all the flags
75
76 /**
77  * Size is not inherited.
78  * VisibleFlag is inherited so that attachments can be synchronized with nodes after they become visible
79  */
80 static const int InheritedDirtyFlags = TransformFlag | VisibleFlag | ColorFlag | OverlayFlag;
81
82 // Flags which require the scene renderable lists to be updated
83 static const int RenderableUpdateFlags = TransformFlag | SortModifierFlag | ChildDeletedFlag;
84
85 /**
86  * Node is the base class for all nodes in the Scene Graph.
87  *
88  * Each node provides a transformation which applies to the node and
89  * its children.  Node data is double-buffered. This allows an update
90  * thread to modify node data, without interferring with another
91  * thread reading the values from the previous update traversal.
92  */
93 class Node : public PropertyOwner, public NodeDataProvider
94 {
95 public:
96
97   // Defaults
98   static const PositionInheritanceMode DEFAULT_POSITION_INHERITANCE_MODE;
99   static const ColorMode DEFAULT_COLOR_MODE;
100
101   // Creation methods
102
103   /**
104    * Construct a new Node.
105    */
106   static Node* New();
107
108   /**
109    * Virtual destructor
110    */
111   virtual ~Node();
112
113   /**
114    * When a Node is marked "active" it has been disconnected, but its properties have been modified.
115    * @note An inactive Node will be skipped during the UpdateManager ResetProperties stage.
116    * @param[in] isActive True if the Node is active.
117    */
118   void SetActive( bool isActive )
119   {
120     mIsActive = isActive;
121   }
122
123   /**
124    * Query whether the Node is active.
125    * @return True if the Node is active.
126    */
127   bool IsActive() const
128   {
129     return mIsActive;
130   }
131
132   /**
133    * Called during UpdateManager::DestroyNode shortly before Node is destroyed.
134    */
135   void OnDestroy();
136
137   // Layer interface
138
139   /**
140    * Query whether the node is a layer.
141    * @return True if the node is a layer.
142    */
143   bool IsLayer()
144   {
145     return (GetLayer() != NULL);
146   }
147
148   /**
149    * Convert a node to a layer.
150    * @return A pointer to the layer, or NULL.
151    */
152   virtual Layer* GetLayer()
153   {
154     return NULL;
155   }
156
157   // Attachments
158
159   /**
160    * Attach an object to this Node; This should only be done by UpdateManager::AttachToNode.
161    * @pre The Node does not already have an attachment.
162    * @param[in] attachment The object to attach.
163    */
164   void Attach( NodeAttachment& attachment );
165
166   /**
167    * Query the node if it has an attachment.
168    * @return True if it has an attachment.
169    */
170   bool HasAttachment() const
171   {
172     return mAttachment;
173   }
174
175   /**
176    * Retreive the object attached to this node.
177    * @return The attachment.
178    */
179   NodeAttachment& GetAttachment() const
180   {
181     return *mAttachment;
182   }
183
184   // Containment methods
185
186   /**
187    * Query whether a node is the root node. Root nodes cannot have a parent node.
188    * A node becomes a root node, when it is installed by UpdateManager.
189    * @return True if the node is a root node.
190    */
191   bool IsRoot() const
192   {
193     return mIsRoot;
194   }
195
196   /**
197    * Set whether a node is the root node. Root nodes cannot have a parent node.
198    * This method should only be called by UpdateManager.
199    * @pre When isRoot is true, the node must not have a parent.
200    * @param[in] isRoot Whether the node is now a root node.
201    */
202   void SetRoot(bool isRoot);
203
204   /**
205    * Retrieve the parent of a Node.
206    * @return The parent node, or NULL if the Node has not been added to the scene-graph.
207    */
208   Node* GetParent()
209   {
210     return mParent;
211   }
212
213   /**
214    * Retrieve the parent of a Node.
215    * @return The parent node, or NULL if the Node has not been added to the scene-graph.
216    */
217   const Node* GetParent() const
218   {
219     return mParent;
220   }
221
222   /**
223    * Connect a node to the scene-graph.
224    * @pre A node cannot be added to itself.
225    * @pre The parent node is connected to the scene-graph.
226    * @pre The childNode does not already have a parent.
227    * @pre The childNode is not a root node.
228    * @param[in] childNode The child to add.
229    * @param[in] index to insert at, if not supplied or -1 it will be appended
230    *
231    */
232   void ConnectChild( Node* childNode, int index = -1);
233
234   /**
235    * Disconnect a child (& its children) from the scene-graph.
236    * @pre childNode is a child of this Node.
237    * @param[in] updateBufferIndex The current update buffer index.
238    * @param[in] childNode The node to disconnect.
239    * @param[in] connectedNodes Disconnected Node attachments should be removed from here.
240    * @param[in] disconnectedNodes Disconnected Node attachments should be added here.
241    */
242   void DisconnectChild( BufferIndex updateBufferIndex, Node& childNode, std::set<Node*>& connectedNodes,  std::set<Node*>& disconnectedNodes );
243
244   /**
245    * Retrieve the children a Node.
246    * @return The container of children.
247    */
248   const NodeContainer& GetChildren() const
249   {
250     return mChildren;
251   }
252
253   /**
254    * Retrieve the children a Node.
255    * @return The container of children.
256    */
257   NodeContainer& GetChildren()
258   {
259     return mChildren;
260   }
261
262   // Update methods
263
264   /**
265    * Flag that one of the node values has changed in the current frame.
266    * @param[in] flag The flag to set.
267    */
268   void SetDirtyFlag(NodePropertyFlags flag)
269   {
270     mDirtyFlags |= flag;
271   }
272
273   /**
274    * Flag that all of the node values are dirty.
275    */
276   void SetAllDirtyFlags()
277   {
278     mDirtyFlags = AllFlags;
279   }
280
281   /**
282    * Query whether a node is dirty.
283    * @return The dirty flags
284    */
285   int GetDirtyFlags() const;
286
287   /**
288    * Query whether a node is clean.
289    * @return True if the node is clean.
290    */
291   bool IsClean() const
292   {
293     return ( NothingFlag == GetDirtyFlags() );
294   }
295
296   /**
297    * Retrieve the parent-origin of the node.
298    * @return The parent-origin.
299    */
300   const Vector3& GetParentOrigin() const
301   {
302     return mParentOrigin.mValue;
303   }
304
305   /**
306    * Sets both the local & base parent-origins of the node.
307    * @param[in] origin The new local & base parent-origins.
308    */
309   void SetParentOrigin(const Vector3& origin)
310   {
311     mParentOrigin.mValue = origin;
312     mParentOrigin.OnSet();
313   }
314
315   /**
316    * Retrieve the anchor-point of the node.
317    * @return The anchor-point.
318    */
319   const Vector3& GetAnchorPoint() const
320   {
321     return mAnchorPoint.mValue;
322   }
323
324   /**
325    * Sets both the local & base anchor-points of the node.
326    * @param[in] anchor The new local & base anchor-points.
327    */
328   void SetAnchorPoint(const Vector3& anchor)
329   {
330     mAnchorPoint.mValue = anchor;
331     mAnchorPoint.OnSet();
332   }
333
334   /**
335    * Retrieve the local position of the node, relative to its parent.
336    * @param[in] bufferIndex The buffer to read from.
337    * @return The local position.
338    */
339   const Vector3& GetPosition(BufferIndex bufferIndex) const
340   {
341     return mPosition[bufferIndex];
342   }
343
344   /**
345    * Sets both the local & base positions of the node.
346    * @param[in] updateBufferIndex The current update buffer index.
347    * @param[in] position The new local & base position.
348    */
349   void BakePosition(BufferIndex updateBufferIndex, const Vector3& position)
350   {
351     mPosition.Bake( updateBufferIndex, position );
352   }
353
354   /**
355    * Sets the world of the node derived from the position of all its parents.
356    * @param[in] updateBufferIndex The current update buffer index.
357    * @param[in] position The world position.
358    */
359   void SetWorldPosition( BufferIndex updateBufferIndex, const Vector3& position )
360   {
361     mWorldPosition.Set( updateBufferIndex, position );
362   }
363
364   /**
365    * Sets the position of the node derived from the position of all its parents.
366    * This method should only be called when the parent's world position is up-to-date.
367    * With a non-central anchor-point, the local orientation and scale affects the world position.
368    * Therefore the world orientation & scale must be updated before the world position.
369    * @pre The node has a parent.
370    * @param[in] updateBufferIndex The current update buffer index.
371    */
372   void InheritWorldPosition(BufferIndex updateBufferIndex)
373   {
374     DALI_ASSERT_DEBUG(mParent != NULL);
375
376     switch( mPositionInheritanceMode )
377     {
378       case INHERIT_PARENT_POSITION  : ///@see Dali::PositionInheritanceMode for how these modes are expected to work
379       {
380         Vector3 finalPosition(-0.5f, -0.5f, -0.5f);
381
382         finalPosition += mParentOrigin.mValue;
383         finalPosition *= mParent->GetSize(updateBufferIndex);
384         finalPosition += mPosition[updateBufferIndex];
385         finalPosition *= mParent->GetWorldScale(updateBufferIndex);
386         const Quaternion& parentWorldOrientation = mParent->GetWorldOrientation(updateBufferIndex);
387         if(!parentWorldOrientation.IsIdentity())
388         {
389           finalPosition *= parentWorldOrientation;
390         }
391
392         // check if a node needs to be offsetted locally (only applies when AnchorPoint is not central)
393         // dont use operator== as that does a slower comparison (and involves function calls)
394         Vector3 localOffset(0.5f, 0.5f, 0.5f);    // AnchorPoint::CENTER
395         localOffset -= mAnchorPoint.mValue;
396
397         if( ( fabsf( localOffset.x ) >= Math::MACHINE_EPSILON_0 ) ||
398             ( fabsf( localOffset.y ) >= Math::MACHINE_EPSILON_0 ) ||
399             ( fabsf( localOffset.z ) >= Math::MACHINE_EPSILON_0 ) )
400         {
401           localOffset *= mSize[updateBufferIndex];
402
403           Vector3 scale = mWorldScale[updateBufferIndex];
404
405           // Pick up sign of local scale
406           if (mScale[updateBufferIndex].x < 0.0f)
407           {
408             scale.x = -scale.x;
409           }
410           if (mScale[updateBufferIndex].y < 0.0f)
411           {
412             scale.y = -scale.y;
413           }
414           if (mScale[updateBufferIndex].z < 0.0f)
415           {
416             scale.z = -scale.z;
417           }
418
419           // If the anchor-point is not central, then position is affected by the local orientation & scale
420           localOffset *= scale;
421           const Quaternion& localWorldOrientation = mWorldOrientation[updateBufferIndex];
422           if(!localWorldOrientation.IsIdentity())
423           {
424             localOffset *= localWorldOrientation;
425           }
426           finalPosition += localOffset;
427         }
428
429         finalPosition += mParent->GetWorldPosition(updateBufferIndex);
430         mWorldPosition.Set( updateBufferIndex, finalPosition );
431         break;
432       }
433       case USE_PARENT_POSITION_PLUS_LOCAL_POSITION :
434       {
435         // copy parents position plus local transform
436         mWorldPosition.Set( updateBufferIndex, mParent->GetWorldPosition(updateBufferIndex) + mPosition[updateBufferIndex] );
437         break;
438       }
439       case USE_PARENT_POSITION :
440       {
441         // copy parents position
442         mWorldPosition.Set( updateBufferIndex, mParent->GetWorldPosition(updateBufferIndex) );
443         break;
444       }
445       case DONT_INHERIT_POSITION :
446       {
447         // use local position as world position
448         mWorldPosition.Set( updateBufferIndex, mPosition[updateBufferIndex] );
449         break;
450       }
451     }
452   }
453
454   /**
455    * Copies the previous inherited position, if this changed in the previous frame.
456    * This method should be called instead of InheritWorldPosition i.e. if the inherited position
457    * does not need to be recalculated in the current frame.
458    * @param[in] updateBufferIndex The current update buffer index.
459    */
460   void CopyPreviousWorldPosition( BufferIndex updateBufferIndex )
461   {
462     mWorldPosition.CopyPrevious( updateBufferIndex );
463   }
464
465   /**
466    * Retrieve the position of the node derived from the position of all its parents.
467    * @return The world position.
468    */
469   const Vector3& GetWorldPosition( BufferIndex bufferIndex ) const
470   {
471     return mWorldPosition[bufferIndex];
472   }
473
474   /**
475    * Set the position inheritance mode.
476    * @see Dali::Actor::PositionInheritanceMode
477    * @param[in] mode The new position inheritance mode.
478    */
479   void SetPositionInheritanceMode( PositionInheritanceMode mode )
480   {
481     mPositionInheritanceMode = mode;
482
483     SetDirtyFlag(TransformFlag);
484   }
485
486   /**
487    * @return The position inheritance mode.
488    */
489   PositionInheritanceMode GetPositionInheritanceMode() const
490   {
491     return mPositionInheritanceMode;
492   }
493
494   /**
495    * Retrieve the local orientation of the node, relative to its parent.
496    * @param[in] bufferIndex The buffer to read from.
497    * @return The local orientation.
498    */
499   const Quaternion& GetOrientation(BufferIndex bufferIndex) const
500   {
501     return mOrientation[bufferIndex];
502   }
503
504   /**
505    * Sets both the local & base orientations of the node.
506    * @param[in] updateBufferIndex The current update buffer index.
507    * @param[in] orientation The new local & base orientation.
508    */
509   void BakeOrientation(BufferIndex updateBufferIndex, const Quaternion& orientation)
510   {
511     mOrientation.Bake( updateBufferIndex, orientation );
512   }
513
514   /**
515    * Sets the orientation of the node derived from the rotation of all its parents.
516    * @param[in] updateBufferIndex The current update buffer index.
517    * @param[in] orientation The world orientation.
518    */
519   void SetWorldOrientation( BufferIndex updateBufferIndex, const Quaternion& orientation )
520   {
521     mWorldOrientation.Set( updateBufferIndex, orientation );
522   }
523
524   /**
525    * Sets the orientation of the node derived from the rotation of all its parents.
526    * This method should only be called when the parents world orientation is up-to-date.
527    * @pre The node has a parent.
528    * @param[in] updateBufferIndex The current update buffer index.
529    */
530   void InheritWorldOrientation( BufferIndex updateBufferIndex )
531   {
532     DALI_ASSERT_DEBUG(mParent != NULL);
533
534     const Quaternion& localOrientation = mOrientation[updateBufferIndex];
535
536     if(localOrientation.IsIdentity())
537     {
538       mWorldOrientation.Set( updateBufferIndex, mParent->GetWorldOrientation(updateBufferIndex) );
539     }
540     else
541     {
542       Quaternion finalOrientation( mParent->GetWorldOrientation(updateBufferIndex) );
543       finalOrientation *= localOrientation;
544       mWorldOrientation.Set( updateBufferIndex, finalOrientation );
545     }
546   }
547
548   /**
549    * Copies the previous inherited orientation, if this changed in the previous frame.
550    * This method should be called instead of InheritWorldOrientation i.e. if the inherited orientation
551    * does not need to be recalculated in the current frame.
552    * @param[in] updateBufferIndex The current update buffer index.
553    */
554   void CopyPreviousWorldOrientation( BufferIndex updateBufferIndex )
555   {
556     mWorldOrientation.CopyPrevious( updateBufferIndex );
557   }
558
559   /**
560    * Retrieve the orientation of the node derived from the rotation of all its parents.
561    * @param[in] bufferIndex The buffer to read from.
562    * @return The world rotation.
563    */
564   const Quaternion& GetWorldOrientation( BufferIndex bufferIndex ) const
565   {
566     return mWorldOrientation[bufferIndex];
567   }
568
569   /**
570    * Set whether the Node inherits orientation.
571    * @param[in] inherit True if the parent orientation is inherited.
572    */
573   void SetInheritOrientation(bool inherit)
574   {
575     if (inherit != mInheritOrientation)
576     {
577       mInheritOrientation = inherit;
578
579       SetDirtyFlag(TransformFlag);
580     }
581   }
582
583   /**
584    * Query whether the node inherits orientation from its parent.
585    * @return True if the parent orientation is inherited.
586    */
587   bool IsOrientationInherited() const
588   {
589     return mInheritOrientation;
590   }
591
592   /**
593    * Retrieve the local scale of the node, relative to its parent.
594    * @param[in] bufferIndex The buffer to read from.
595    * @return The local scale.
596    */
597   const Vector3& GetScale(BufferIndex bufferIndex) const
598   {
599     return mScale[bufferIndex];
600   }
601
602   /**
603    * Sets the scale of the node derived from the scale of all its parents and a pre-scale
604    * @param[in] updateBufferIndex The current update buffer index.
605    * @param[in] scale The world scale.
606    */
607   void SetWorldScale(BufferIndex updateBufferIndex, const Vector3& scale)
608   {
609     mWorldScale.Set( updateBufferIndex, scale );
610   }
611
612   /**
613    * Sets the scale of the node derived from the scale of all its parents and a pre-scale.
614    * This method should only be called when the parents world scale is up-to-date.
615    * @pre The node has a parent.
616    * @param[in] updateBufferIndex The current update buffer index.
617    */
618   void InheritWorldScale(BufferIndex updateBufferIndex)
619   {
620     DALI_ASSERT_DEBUG(mParent != NULL);
621
622     mWorldScale.Set( updateBufferIndex, mParent->GetWorldScale(updateBufferIndex) * mScale[updateBufferIndex] );
623   }
624
625   /**
626    * Copies the previous inherited scale, if this changed in the previous frame.
627    * This method should be called instead of InheritWorldScale i.e. if the inherited scale
628    * does not need to be recalculated in the current frame.
629    * @param[in] updateBufferIndex The current update buffer index.
630    */
631   void CopyPreviousWorldScale( BufferIndex updateBufferIndex )
632   {
633     mWorldScale.CopyPrevious( updateBufferIndex );
634   }
635
636   /**
637    * Retrieve the scale of the node derived from the scale of all its parents.
638    * @param[in] bufferIndex The buffer to read from.
639    * @return The world scale.
640    */
641   const Vector3& GetWorldScale( BufferIndex bufferIndex ) const
642   {
643     return mWorldScale[bufferIndex];
644   }
645
646   /**
647    * Set whether the Node inherits scale.
648    * @param inherit True if the Node inherits scale.
649    */
650   void SetInheritScale( bool inherit )
651   {
652     if( inherit != mInheritScale )
653     {
654       mInheritScale = inherit;
655
656       SetDirtyFlag( TransformFlag );
657     }
658   }
659
660   /**
661    * Query whether the Node inherits scale.
662    * @return if scale is inherited
663    */
664   bool IsScaleInherited() const
665   {
666     return mInheritScale;
667   }
668
669   /**
670    * Copies the previously used size, if this changed in the previous frame.
671    * @param[in] updateBufferIndex The current update buffer index.
672    */
673   void CopyPreviousSize( BufferIndex updateBufferIndex )
674   {
675     SetSize( updateBufferIndex, GetSize( 1u - updateBufferIndex ) );
676   }
677
678   /**
679    * Retrieve the visibility of the node.
680    * @param[in] bufferIndex The buffer to read from.
681    * @return True if the node is visible.
682    */
683   bool IsVisible(BufferIndex bufferIndex) const
684   {
685     return mVisible[bufferIndex];
686   }
687
688   /**
689    * Retrieves whether a node is fully visible.
690    * A node is fully visible if is visible and all its ancestors are visible.
691    * @param[in] updateBufferIndex The current update buffer index.
692    * @return True if the node is fully visible.
693    */
694   bool IsFullyVisible( BufferIndex updateBufferIndex ) const;
695
696   /**
697    * Retrieve the opacity of the node.
698    * @param[in] bufferIndex The buffer to read from.
699    * @return The opacity.
700    */
701   float GetOpacity(BufferIndex bufferIndex) const
702   {
703     return mColor[bufferIndex].a;
704   }
705
706   /**
707    * Retrieve the color of the node.
708    * @param[in] bufferIndex The buffer to read from.
709    * @return The color.
710    */
711   const Vector4& GetColor(BufferIndex bufferIndex) const
712   {
713     return mColor[bufferIndex];
714   }
715
716   /**
717    * Sets the color of the node derived from the color of all its parents.
718    * @param[in] color The world color.
719    * @param[in] updateBufferIndex The current update buffer index.
720    */
721   void SetWorldColor(const Vector4& color, BufferIndex updateBufferIndex)
722   {
723     mWorldColor.Set( updateBufferIndex, color );
724   }
725
726   /**
727    * Sets the color of the node derived from the color of all its parents.
728    * This method should only be called when the parents world color is up-to-date.
729    * @pre The node has a parent.
730    * @param[in] updateBufferIndex The current update buffer index.
731    */
732   void InheritWorldColor( BufferIndex updateBufferIndex )
733   {
734     DALI_ASSERT_DEBUG(mParent != NULL);
735
736     // default first
737     if( mColorMode == USE_OWN_MULTIPLY_PARENT_ALPHA )
738     {
739       const Vector4& ownColor = mColor[updateBufferIndex];
740       mWorldColor.Set( updateBufferIndex, ownColor.r, ownColor.g, ownColor.b, ownColor.a * mParent->GetWorldColor(updateBufferIndex).a );
741     }
742     else if( mColorMode == USE_OWN_MULTIPLY_PARENT_COLOR )
743     {
744       mWorldColor.Set( updateBufferIndex, mParent->GetWorldColor(updateBufferIndex) * mColor[updateBufferIndex] );
745     }
746     else if( mColorMode == USE_PARENT_COLOR )
747     {
748       mWorldColor.Set( updateBufferIndex, mParent->GetWorldColor(updateBufferIndex) );
749     }
750     else // USE_OWN_COLOR
751     {
752       mWorldColor.Set( updateBufferIndex, mColor[updateBufferIndex] );
753     }
754   }
755
756   /**
757    * Copies the previous inherited scale, if this changed in the previous frame.
758    * This method should be called instead of InheritWorldScale i.e. if the inherited scale
759    * does not need to be recalculated in the current frame.
760    * @param[in] updateBufferIndex The current update buffer index.
761    */
762   void CopyPreviousWorldColor( BufferIndex updateBufferIndex )
763   {
764     mWorldColor.CopyPrevious( updateBufferIndex );
765   }
766
767   /**
768    * Retrieve the color of the node, possibly derived from the color
769    * of all its parents, depending on the value of mColorMode.
770    * @param[in] bufferIndex The buffer to read from.
771    * @return The world color.
772    */
773   const Vector4& GetWorldColor(BufferIndex bufferIndex) const
774   {
775     return mWorldColor[bufferIndex];
776   }
777
778   /**
779    * Set the color mode. This specifies whether the Node uses its own color,
780    * or inherits its parent color.
781    * @param[in] colorMode The new color mode.
782    */
783   void SetColorMode(ColorMode colorMode)
784   {
785     mColorMode = colorMode;
786
787     SetDirtyFlag(ColorFlag);
788   }
789
790   /**
791    * Retrieve the color mode.
792    * @return The color mode.
793    */
794   ColorMode GetColorMode() const
795   {
796     return mColorMode;
797   }
798
799   /**
800    * Sets the size of the node.
801    * @param[in] bufferIndex The buffer to write to.
802    * @param[in] size The size to write.
803    */
804   void SetSize( BufferIndex bufferIndex, const Vector3& size )
805   {
806     mSize[bufferIndex] = size;
807   }
808
809   /**
810    * Retrieve the size of the node.
811    * @param[in] bufferIndex The buffer to read from.
812    * @return The size.
813    */
814   const Vector3& GetSize(BufferIndex bufferIndex) const
815   {
816     return mSize[bufferIndex];
817   }
818
819   /**
820    * Set the world-matrix of a node, with scale + rotation + translation.
821    * Scale and rotation are centered at the origin.
822    * Translation is applied independently of the scale or rotatation axis.
823    * @param[in] updateBufferIndex The current update buffer index.
824    * @param[in] scale The scale.
825    * @param[in] rotation The rotation.
826    * @param[in] translation The translation.
827    */
828   void SetWorldMatrix( BufferIndex updateBufferIndex, const Vector3& scale, const Quaternion& rotation, const Vector3& translation )
829   {
830     mWorldMatrix.Get( updateBufferIndex ).SetTransformComponents( scale, rotation, translation );
831     mWorldMatrix.SetDirty( updateBufferIndex );
832   }
833
834   /**
835    * Retrieve the cached world-matrix of a node.
836    * @param[in] bufferIndex The buffer to read from.
837    * @return The world-matrix.
838    */
839   const Matrix& GetWorldMatrix( BufferIndex bufferIndex ) const
840   {
841     return mWorldMatrix[ bufferIndex ];
842   }
843
844   /**
845    * Copy previous frames world matrix
846    * @param[in] updateBufferIndex The current update buffer index.
847    */
848   void CopyPreviousWorldMatrix( BufferIndex updateBufferIndex )
849   {
850     mWorldMatrix.CopyPrevious( updateBufferIndex );
851   }
852
853   /**
854    * Mark the node as exclusive to a single RenderTask.
855    * @param[in] renderTask The render-task, or NULL if the Node is not exclusive to a single RenderTask.
856    */
857   void SetExclusiveRenderTask( RenderTask* renderTask )
858   {
859     mExclusiveRenderTask = renderTask;
860   }
861
862   /**
863    * Query whether the node is exclusive to a single RenderTask.
864    * @return The render-task, or NULL if the Node is not exclusive to a single RenderTask.
865    */
866   RenderTask* GetExclusiveRenderTask() const
867   {
868     return mExclusiveRenderTask;
869   }
870
871   /**
872    * Set how the Node and its children should be drawn; see Dali::Actor::SetDrawMode() for more details.
873    * @param[in] drawMode The new draw-mode to use.
874    */
875   void SetDrawMode( const DrawMode::Type& drawMode )
876   {
877     mDrawMode = drawMode;
878   }
879
880   /**
881    * Returns whether node is an overlay or not.
882    * @return True if node is an overlay, false otherwise.
883    */
884   DrawMode::Type GetDrawMode() const
885   {
886     return mDrawMode;
887   }
888
889   /**
890    * Equality operator, checks for identity, not values.
891    *
892    */
893   bool operator==( const Node* rhs ) const
894   {
895     if ( this == rhs )
896     {
897       return true;
898     }
899     return false;
900   }
901
902   /**
903    * Set the inhibit local transform flag.@n
904    * Setting this flag will stop the node's local transform (position, scale and orientation)
905    * being applied on top of its parents transformation.
906    * @param[in] flag When true, local transformation is inhibited when calculating the world matrix.
907    */
908   void SetInhibitLocalTransform( bool flag )
909   {
910     SetDirtyFlag( TransformFlag );
911     mInhibitLocalTransform = flag;
912   }
913
914   /**
915    * Get the inhibit local transform flag.@n
916    * See @ref SetInhibitLocalTransform
917    * @result A flag, when true, local transformation is inhibited when calculating the world matrix.
918    */
919   bool GetInhibitLocalTransform() const
920   {
921     return mInhibitLocalTransform;
922   }
923
924   unsigned short GetDepth() const
925   {
926     return mDepth;
927   }
928
929 protected:
930
931   /**
932    * Set the parent of a Node.
933    * @param[in] parentNode the new parent.
934    */
935   void SetParent(Node& parentNode);
936
937   /**
938    * Protected constructor; See also Node::New()
939    */
940   Node();
941
942 private: // from NodeDataProvider
943
944   /**
945    * @copydoc NodeDataProvider::GetModelMatrix
946    */
947   virtual const Matrix& GetModelMatrix( unsigned int bufferId )
948   {
949     return GetWorldMatrix( bufferId );
950   }
951
952   /**
953    * @copydoc NodeDataProvider::GetRenderColor
954    */
955   virtual const Vector4& GetRenderColor( unsigned int bufferId )
956   {
957     return GetWorldColor( bufferId );
958   }
959
960   virtual const Vector3& GetRenderSize( unsigned int bufferId )
961   {
962     return GetSize( bufferId );
963   }
964
965
966 private:
967
968   // Undefined
969   Node(const Node&);
970
971   // Undefined
972   Node& operator=(const Node& rhs);
973
974   /**
975    * @copydoc Dali::Internal::SceneGraph::PropertyOwner::ResetDefaultProperties()
976    */
977   virtual void ResetDefaultProperties( BufferIndex updateBufferIndex );
978
979   /**
980    * Recursive helper to disconnect a Node and its children.
981    * Disconnected Nodes have no parent or children.
982    * @param[in] updateBufferIndex The current update buffer index.
983    * @param[in] connectedNodes Disconnected Node attachments should be removed from here.
984    * @param[in] disconnectedNodes Disconnected Node attachments should be added here.
985    */
986   void RecursiveDisconnectFromSceneGraph( BufferIndex updateBufferIndex, std::set<Node*>& connectedNodes, std::set<Node*>& disconnectedNodes );
987
988 public: // Default properties
989
990   PropertyVector3                mParentOrigin;  ///< Local transform; the position is relative to this. Sets the TransformFlag dirty when changed
991   PropertyVector3                mAnchorPoint;   ///< Local transform; local center of rotation. Sets the TransformFlag dirty when changed
992
993   AnimatableProperty<Vector3>    mSize;          ///< Size is provided for layouting
994   AnimatableProperty<Vector3>    mPosition;      ///< Local transform; distance between parent-origin & anchor-point
995   AnimatableProperty<Quaternion> mOrientation;   ///< Local transform; rotation relative to parent node
996   AnimatableProperty<Vector3>    mScale;         ///< Local transform; scale relative to parent node
997   AnimatableProperty<bool>       mVisible;       ///< Visibility can be inherited from the Node hierachy
998   AnimatableProperty<Vector4>    mColor;         ///< Color can be inherited from the Node hierarchy
999
1000   // Inherited properties; read-only from public API
1001
1002   InheritedVector3    mWorldPosition;     ///< Full inherited position
1003   InheritedQuaternion mWorldOrientation;  ///< Full inherited orientation
1004   InheritedVector3    mWorldScale;        ///< Full inherited scale
1005   InheritedMatrix     mWorldMatrix;       ///< Full inherited world matrix
1006   InheritedColor      mWorldColor;        ///< Full inherited color
1007
1008 protected:
1009
1010   Node*               mParent;                       ///< Pointer to parent node (a child is owned by its parent)
1011   RenderTask*         mExclusiveRenderTask;          ///< Nodes can be marked as exclusive to a single RenderTask
1012
1013   NodeAttachmentOwner mAttachment;                   ///< Optional owned attachment
1014   NodeContainer       mChildren;                     ///< Container of children; not owned
1015
1016
1017   // flags, compressed to bitfield
1018   unsigned short mDepth: 12;                        ///< Depth in the hierarchy
1019   int  mDirtyFlags:8;                               ///< A composite set of flags for each of the Node properties
1020
1021   bool mIsRoot:1;                                    ///< True if the node cannot have a parent
1022   bool mInheritOrientation:1;                        ///< Whether the parent's orientation should be inherited.
1023   bool mInheritScale:1;                              ///< Whether the parent's scale should be inherited.
1024   bool mInhibitLocalTransform:1;                     ///< whether local transform should be applied.
1025   bool mIsActive:1;                                  ///< When a Node is marked "active" it has been disconnected, and its properties have not been modified
1026
1027   DrawMode::Type          mDrawMode:2;               ///< How the Node and its children should be drawn
1028   PositionInheritanceMode mPositionInheritanceMode:2;///< Determines how position is inherited, 2 bits is enough
1029   ColorMode               mColorMode:2;              ///< Determines whether mWorldColor is inherited, 2 bits is enough
1030
1031   // Changes scope, should be at end of class
1032   DALI_LOG_OBJECT_STRING_DECLARATION;
1033 };
1034
1035 // Messages for Node
1036
1037 inline void SetInheritOrientationMessage( EventThreadServices& eventThreadServices, const Node& node, bool inherit )
1038 {
1039   typedef MessageValue1< Node, bool > LocalType;
1040
1041   // Reserve some memory inside the message queue
1042   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1043
1044   // Construct message in the message queue memory; note that delete should not be called on the return value
1045   new (slot) LocalType( &node, &Node::SetInheritOrientation, inherit );
1046 }
1047
1048
1049
1050 inline void SetParentOriginMessage( EventThreadServices& eventThreadServices, const Node& node, const Vector3& origin )
1051 {
1052   typedef MessageValue1< Node, Vector3 > LocalType;
1053
1054   // Reserve some memory inside the message queue
1055   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1056
1057   // Construct message in the message queue memory; note that delete should not be called on the return value
1058   new (slot) LocalType( &node, &Node::SetParentOrigin, origin );
1059 }
1060
1061 inline void SetAnchorPointMessage( EventThreadServices& eventThreadServices, const Node& node, const Vector3& anchor )
1062 {
1063   typedef MessageValue1< Node, Vector3 > LocalType;
1064
1065   // Reserve some memory inside the message queue
1066   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1067
1068   // Construct message in the message queue memory; note that delete should not be called on the return value
1069   new (slot) LocalType( &node, &Node::SetAnchorPoint, anchor );
1070 }
1071
1072 inline void SetPositionInheritanceModeMessage( EventThreadServices& eventThreadServices, const Node& node, PositionInheritanceMode mode )
1073 {
1074   typedef MessageValue1< Node, PositionInheritanceMode > LocalType;
1075
1076   // Reserve some memory inside the message queue
1077   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1078
1079   // Construct message in the message queue memory; note that delete should not be called on the return value
1080   new (slot) LocalType( &node, &Node::SetPositionInheritanceMode, mode );
1081 }
1082
1083 inline void SetInheritScaleMessage( EventThreadServices& eventThreadServices, const Node& node, bool inherit )
1084 {
1085   typedef MessageValue1< Node, bool > LocalType;
1086
1087   // Reserve some memory inside the message queue
1088   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1089
1090   // Construct message in the message queue memory; note that delete should not be called on the return value
1091   new (slot) LocalType( &node, &Node::SetInheritScale, inherit );
1092 }
1093
1094 inline void SetColorModeMessage( EventThreadServices& eventThreadServices, const Node& node, ColorMode colorMode )
1095 {
1096   typedef MessageValue1< Node, ColorMode > LocalType;
1097
1098   // Reserve some memory inside the message queue
1099   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1100
1101   // Construct message in the message queue memory; note that delete should not be called on the return value
1102   new (slot) LocalType( &node, &Node::SetColorMode, colorMode );
1103 }
1104
1105 inline void SetDrawModeMessage( EventThreadServices& eventThreadServices, const Node& node, DrawMode::Type drawMode )
1106 {
1107   typedef MessageValue1< Node, DrawMode::Type > LocalType;
1108
1109   // Reserve some memory inside the message queue
1110   unsigned int* slot = eventThreadServices.ReserveMessageSlot( sizeof( LocalType ) );
1111
1112   // Construct message in the message queue memory; note that delete should not be called on the return value
1113   new (slot) LocalType( &node, &Node::SetDrawMode, drawMode );
1114 }
1115
1116 } // namespace SceneGraph
1117
1118 } // namespace Internal
1119
1120 } // namespace Dali
1121
1122 #endif // __DALI_INTERNAL_SCENE_GRAPH_NODE_H_