Geometry Batching
[platform/core/uifw/dali-core.git] / dali / internal / update / manager / update-manager.cpp
1 /*
2  * Copyright (c) 2016 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // CLASS HEADER
19 #include <dali/internal/update/manager/update-manager.h>
20
21 // INTERNAL INCLUDES
22 #include <dali/public-api/common/stage.h>
23 #include <dali/devel-api/common/set-wrapper.h>
24 #include <dali/devel-api/common/owner-container.h>
25 #include <dali/devel-api/threading/mutex.h>
26
27 #include <dali/integration-api/core.h>
28 #include <dali/integration-api/render-controller.h>
29 #include <dali/internal/common/shader-data.h>
30 #include <dali/integration-api/debug.h>
31
32 #include <dali/internal/common/core-impl.h>
33 #include <dali/internal/common/message.h>
34
35 #include <dali/internal/event/common/notification-manager.h>
36 #include <dali/internal/event/common/property-notification-impl.h>
37 #include <dali/internal/event/common/property-notifier.h>
38 #include <dali/internal/event/effects/shader-factory.h>
39
40 #include <dali/internal/update/animation/scene-graph-animator.h>
41 #include <dali/internal/update/animation/scene-graph-animation.h>
42 #include <dali/internal/update/common/discard-queue.h>
43 #include <dali/internal/update/common/scene-graph-buffers.h>
44 #include <dali/internal/update/common/texture-cache-dispatcher.h>
45 #include <dali/internal/update/controllers/render-message-dispatcher.h>
46 #include <dali/internal/update/controllers/scene-controller-impl.h>
47 #include <dali/internal/update/gestures/scene-graph-pan-gesture.h>
48 #include <dali/internal/update/manager/object-owner-container.h>
49 #include <dali/internal/update/manager/process-render-tasks.h>
50 #include <dali/internal/update/manager/sorted-layers.h>
51 #include <dali/internal/update/manager/update-algorithms.h>
52 #include <dali/internal/update/manager/update-manager-debug.h>
53 #include <dali/internal/update/manager/transform-manager.h>
54 #include <dali/internal/update/nodes/node.h>
55 #include <dali/internal/update/nodes/scene-graph-layer.h>
56 #include <dali/internal/update/queue/update-message-queue.h>
57 #include <dali/internal/update/render-tasks/scene-graph-render-task.h>
58 #include <dali/internal/update/render-tasks/scene-graph-render-task-list.h>
59 #include <dali/internal/update/rendering/scene-graph-texture-set.h>
60 #include <dali/internal/update/resources/resource-manager.h>
61 #include <dali/internal/update/manager/geometry-batcher.h>
62 #include <dali/internal/update/render-tasks/scene-graph-camera.h>
63
64 #include <dali/internal/render/common/render-instruction-container.h>
65 #include <dali/internal/render/common/render-manager.h>
66 #include <dali/internal/render/queue/render-queue.h>
67 #include <dali/internal/render/gl-resources/texture-cache.h>
68 #include <dali/internal/render/shaders/scene-graph-shader.h>
69
70 // Un-comment to enable node tree debug logging
71 //#define NODE_TREE_LOGGING 1
72
73 #if ( defined( DEBUG_ENABLED ) && defined( NODE_TREE_LOGGING ) )
74 #define SNAPSHOT_NODE_LOGGING \
75 const int FRAME_COUNT_TRIGGER = 16;\
76 if( mImpl->frameCounter >= FRAME_COUNT_TRIGGER )\
77   {\
78     if ( NULL != mImpl->root )\
79     {\
80       mImpl->frameCounter = 0;\
81       PrintNodeTree( *mImpl->root, mSceneGraphBuffers.GetUpdateBufferIndex(), "" );\
82     }\
83   }\
84 mImpl->frameCounter++;
85 #else
86 #define SNAPSHOT_NODE_LOGGING
87 #endif
88
89 #if defined(DEBUG_ENABLED)
90 extern Debug::Filter* gRenderTaskLogFilter;
91 #endif
92
93
94 using namespace Dali::Integration;
95 using Dali::Internal::Update::MessageQueue;
96
97 namespace Dali
98 {
99
100 namespace Internal
101 {
102
103 namespace SceneGraph
104 {
105
106 typedef OwnerContainer< Shader* >              ShaderContainer;
107 typedef ShaderContainer::Iterator              ShaderIter;
108 typedef ShaderContainer::ConstIterator         ShaderConstIter;
109
110 typedef std::vector<Internal::ShaderDataPtr>   ShaderDataBinaryQueue;
111
112 typedef OwnerContainer<PanGesture*>            GestureContainer;
113 typedef GestureContainer::Iterator             GestureIter;
114 typedef GestureContainer::ConstIterator        GestureConstIter;
115
116 typedef OwnerContainer< TextureSet* >          TextureSetContainer;
117 typedef TextureSetContainer::Iterator          TextureSetIter;
118 typedef TextureSetContainer::ConstIterator     TextureSetConstIter;
119
120 /**
121  * Structure to contain UpdateManager internal data
122  */
123 struct UpdateManager::Impl
124 {
125   Impl( NotificationManager& notificationManager,
126         CompleteNotificationInterface& animationFinishedNotifier,
127         PropertyNotifier& propertyNotifier,
128         ResourceManager& resourceManager,
129         DiscardQueue& discardQueue,
130         RenderController& renderController,
131         RenderManager& renderManager,
132         RenderQueue& renderQueue,
133         SceneGraphBuffers& sceneGraphBuffers,
134         GeometryBatcher& geometryBatcher )
135   : renderMessageDispatcher( renderManager, renderQueue, sceneGraphBuffers ),
136     notificationManager( notificationManager ),
137     transformManager(),
138     animationFinishedNotifier( animationFinishedNotifier ),
139     propertyNotifier( propertyNotifier ),
140     shaderSaver( NULL ),
141     resourceManager( resourceManager ),
142     discardQueue( discardQueue ),
143     renderController( renderController ),
144     sceneController( NULL ),
145     renderManager( renderManager ),
146     renderQueue( renderQueue ),
147     renderInstructions( renderManager.GetRenderInstructionContainer() ),
148     geometryBatcher( geometryBatcher ),
149     backgroundColor( Dali::Stage::DEFAULT_BACKGROUND_COLOR ),
150     taskList( renderMessageDispatcher, resourceManager ),
151     systemLevelTaskList( renderMessageDispatcher, resourceManager ),
152     root( NULL ),
153     systemLevelRoot( NULL ),
154     renderers( sceneGraphBuffers, discardQueue ),
155     textureSets(),
156     messageQueue( renderController, sceneGraphBuffers ),
157     keepRenderingSeconds( 0.0f ),
158     animationFinishedDuringUpdate( false ),
159     nodeDirtyFlags( TransformFlag ), // set to TransformFlag to ensure full update the first time through Update()
160     previousUpdateScene( false ),
161     frameCounter( 0 ),
162     renderSortingHelper(),
163     renderTaskWaiting( false )
164   {
165     sceneController = new SceneControllerImpl( renderMessageDispatcher, renderQueue, discardQueue );
166
167     renderers.SetSceneController( *sceneController );
168
169     discardQueue.SetGeometryBatcher( &geometryBatcher );
170
171     // create first 'dummy' node
172     nodes.PushBack(0u);
173   }
174
175   ~Impl()
176   {
177     // Disconnect render tasks from nodes, before destroying the nodes
178     RenderTaskList::RenderTaskContainer& tasks = taskList.GetTasks();
179     for (RenderTaskList::RenderTaskContainer::Iterator iter = tasks.Begin(); iter != tasks.End(); ++iter)
180     {
181       (*iter)->SetSourceNode( NULL );
182     }
183     // ..repeat for system level RenderTasks
184     RenderTaskList::RenderTaskContainer& systemLevelTasks = systemLevelTaskList.GetTasks();
185     for (RenderTaskList::RenderTaskContainer::Iterator iter = systemLevelTasks.Begin(); iter != systemLevelTasks.End(); ++iter)
186     {
187       (*iter)->SetSourceNode( NULL );
188     }
189
190     // UpdateManager owns the Nodes
191     Vector<Node*>::Iterator iter = nodes.Begin()+1;
192     Vector<Node*>::Iterator endIter = nodes.End();
193     for(;iter!=endIter;++iter)
194     {
195       (*iter)->OnDestroy();
196       delete(*iter);
197     }
198
199     // If there is root, reset it, otherwise do nothing as rendering was never started
200     if( root )
201     {
202       root->OnDestroy();
203
204       delete root;
205       root = NULL;
206     }
207
208     if( systemLevelRoot )
209     {
210       systemLevelRoot->OnDestroy();
211
212       delete systemLevelRoot;
213       systemLevelRoot = NULL;
214     }
215
216     delete sceneController;
217   }
218
219   SceneGraphBuffers                   sceneGraphBuffers;             ///< Used to keep track of which buffers are being written or read
220   RenderMessageDispatcher             renderMessageDispatcher;       ///< Used for passing messages to the render-thread
221   NotificationManager&                notificationManager;           ///< Queues notification messages for the event-thread.
222   TransformManager                    transformManager;              ///< Used to update the transformation matrices of the nodes
223   CompleteNotificationInterface&      animationFinishedNotifier;     ///< Provides notification to applications when animations are finished.
224   PropertyNotifier&                   propertyNotifier;              ///< Provides notification to applications when properties are modified.
225   ShaderSaver*                        shaderSaver;                   ///< Saves shader binaries.
226   ResourceManager&                    resourceManager;               ///< resource manager
227   DiscardQueue&                       discardQueue;                  ///< Nodes are added here when disconnected from the scene-graph.
228   RenderController&                   renderController;              ///< render controller
229   SceneControllerImpl*                sceneController;               ///< scene controller
230   RenderManager&                      renderManager;                 ///< This is responsible for rendering the results of each "update"
231   RenderQueue&                        renderQueue;                   ///< Used to queue messages for the next render
232   RenderInstructionContainer&         renderInstructions;            ///< Used to prepare the render instructions
233   GeometryBatcher&                    geometryBatcher;               ///< An instance of the GeometryBatcher
234
235   Vector4                             backgroundColor;               ///< The glClear color used at the beginning of each frame.
236
237   RenderTaskList                      taskList;                      ///< The list of scene graph render-tasks
238   RenderTaskList                      systemLevelTaskList;           ///< Separate render-tasks for system-level content
239
240   Layer*                              root;                          ///< The root node (root is a layer)
241   Layer*                              systemLevelRoot;               ///< A separate root-node for system-level content
242
243   Vector<Node*>                       nodes;                         ///< A container of all instantiated nodes
244
245   SortedLayerPointers                 sortedLayers;                  ///< A container of Layer pointers sorted by depth
246   SortedLayerPointers                 systemLevelSortedLayers;       ///< A separate container of system-level Layers
247
248   OwnerContainer< Camera* >           cameras;                       ///< A container of cameras
249   OwnerContainer< PropertyOwner* >    customObjects;                 ///< A container of owned objects (with custom properties)
250
251   AnimationContainer                  animations;                    ///< A container of owned animations
252   PropertyNotificationContainer       propertyNotifications;         ///< A container of owner property notifications.
253
254   ObjectOwnerContainer<Renderer>      renderers;
255   TextureSetContainer                 textureSets;                     ///< A container of texture sets
256
257   ShaderContainer                     shaders;                       ///< A container of owned shaders
258
259   MessageQueue                        messageQueue;                  ///< The messages queued from the event-thread
260   ShaderDataBinaryQueue               renderCompiledShaders;         ///< Shaders compiled on Render thread are inserted here for update thread to pass on to event thread.
261   ShaderDataBinaryQueue               updateCompiledShaders;         ///< Shaders to be sent from Update to Event
262   Mutex                               compiledShaderMutex;           ///< lock to ensure no corruption on the renderCompiledShaders
263
264   float                               keepRenderingSeconds;          ///< Set via Dali::Stage::KeepRendering
265   bool                                animationFinishedDuringUpdate; ///< Flag whether any animations finished during the Update()
266
267   int                                 nodeDirtyFlags;                ///< cumulative node dirty flags from previous frame
268   bool                                previousUpdateScene;           ///< True if the scene was updated in the previous frame (otherwise it was optimized out)
269
270   int                                 frameCounter;                  ///< Frame counter used in debugging to choose which frame to debug and which to ignore.
271   RendererSortingHelper               renderSortingHelper;           ///< helper used to sort transparent renderers
272
273   GestureContainer                    gestures;                      ///< A container of owned gesture detectors
274   bool                                renderTaskWaiting;             ///< A REFRESH_ONCE render task is waiting to be rendered
275 };
276
277 UpdateManager::UpdateManager( NotificationManager& notificationManager,
278                               CompleteNotificationInterface& animationFinishedNotifier,
279                               PropertyNotifier& propertyNotifier,
280                               ResourceManager& resourceManager,
281                               DiscardQueue& discardQueue,
282                               RenderController& controller,
283                               RenderManager& renderManager,
284                               RenderQueue& renderQueue,
285                               TextureCacheDispatcher& textureCacheDispatcher,
286                               GeometryBatcher& geometryBatcher )
287   : mImpl(NULL)
288 {
289   mImpl = new Impl( notificationManager,
290                     animationFinishedNotifier,
291                     propertyNotifier,
292                     resourceManager,
293                     discardQueue,
294                     controller,
295                     renderManager,
296                     renderQueue,
297                     mSceneGraphBuffers,
298                     geometryBatcher );
299
300   textureCacheDispatcher.SetBufferIndices( &mSceneGraphBuffers );
301   mImpl->geometryBatcher.SetUpdateManager( this );
302 }
303
304 UpdateManager::~UpdateManager()
305 {
306   delete mImpl;
307 }
308
309 void UpdateManager::InstallRoot( SceneGraph::Layer* layer, bool systemLevel )
310 {
311   DALI_ASSERT_DEBUG( layer->IsLayer() );
312   DALI_ASSERT_DEBUG( layer->GetParent() == NULL);
313
314   if ( !systemLevel )
315   {
316     DALI_ASSERT_DEBUG( mImpl->root == NULL && "Root Node already installed" );
317     mImpl->root = layer;
318     mImpl->root->CreateTransform( &mImpl->transformManager );
319   }
320   else
321   {
322     DALI_ASSERT_DEBUG( mImpl->systemLevelRoot == NULL && "System-level Root Node already installed" );
323     mImpl->systemLevelRoot = layer;
324     mImpl->systemLevelRoot->CreateTransform( &mImpl->transformManager );
325   }
326
327   layer->SetRoot(true);
328 }
329
330 void UpdateManager::AddNode( Node* node )
331 {
332   DALI_ASSERT_ALWAYS( NULL != node );
333   DALI_ASSERT_ALWAYS( NULL == node->GetParent() ); // Should not have a parent yet
334
335   // Nodes must be sorted by pointer
336   Vector<Node*>::Iterator begin = mImpl->nodes.Begin();
337   for(Vector<Node*>::Iterator iter = mImpl->nodes.End()-1; iter >= begin; --iter)
338   {
339     if(node > (*iter))
340     {
341       mImpl->nodes.Insert((iter+1), node);
342       node->CreateTransform( &mImpl->transformManager );
343       node->mGeometryBatcher = &mImpl->geometryBatcher;
344       break;
345     }
346   }
347 }
348
349 void UpdateManager::ConnectNode( Node* parent, Node* node )
350 {
351   DALI_ASSERT_ALWAYS( NULL != parent );
352   DALI_ASSERT_ALWAYS( NULL != node );
353   DALI_ASSERT_ALWAYS( NULL == node->GetParent() ); // Should not have a parent yet
354
355   parent->ConnectChild( node );
356 }
357
358 void UpdateManager::DisconnectNode( Node* node )
359 {
360   Node* parent = node->GetParent();
361   DALI_ASSERT_ALWAYS( NULL != parent );
362   parent->SetDirtyFlag( ChildDeletedFlag ); // make parent dirty so that render items dont get reused
363
364   parent->DisconnectChild( mSceneGraphBuffers.GetUpdateBufferIndex(), *node );
365 }
366
367 void UpdateManager::DestroyNode( Node* node )
368 {
369   DALI_ASSERT_ALWAYS( NULL != node );
370   DALI_ASSERT_ALWAYS( NULL == node->GetParent() ); // Should have been disconnected
371
372   Vector<Node*>::Iterator iter = mImpl->nodes.Begin()+1;
373   Vector<Node*>::Iterator endIter = mImpl->nodes.End();
374   for(;iter!=endIter;++iter)
375   {
376     if((*iter) == node)
377     {
378       mImpl->nodes.Erase(iter);
379       break;
380     }
381   }
382
383   mImpl->discardQueue.Add( mSceneGraphBuffers.GetUpdateBufferIndex(), node );
384
385   // Notify the Node about impending destruction
386   node->OnDestroy();
387 }
388
389 void UpdateManager::AddCamera( Camera* camera )
390 {
391   DALI_ASSERT_DEBUG( camera != NULL );
392
393   mImpl->cameras.PushBack( camera ); // takes ownership
394 }
395
396 void UpdateManager::RemoveCamera( const Camera* camera )
397 {
398   // Find the camera
399   OwnerContainer<Camera*>::Iterator iter = mImpl->cameras.Begin();
400   OwnerContainer<Camera*>::ConstIterator end = mImpl->cameras.End();
401   for ( ; iter != end; ++iter )
402   {
403     Camera* value = *iter;
404     if ( camera == value )
405     {
406       // Transfer ownership to the discard queue
407       mImpl->discardQueue.Add( mSceneGraphBuffers.GetUpdateBufferIndex(), mImpl->cameras.Release( iter ) );
408
409       return;
410     }
411   }
412
413 }
414
415 void UpdateManager::AddObject( PropertyOwner* object )
416 {
417   DALI_ASSERT_DEBUG( NULL != object );
418
419   mImpl->customObjects.PushBack( object );
420 }
421
422 void UpdateManager::RemoveObject( PropertyOwner* object )
423 {
424   DALI_ASSERT_DEBUG( NULL != object );
425
426   OwnerContainer< PropertyOwner* >& customObjects = mImpl->customObjects;
427
428   // Find the object and destroy it
429   for ( OwnerContainer< PropertyOwner* >::Iterator iter = customObjects.Begin(); iter != customObjects.End(); ++iter )
430   {
431     PropertyOwner* current = *iter;
432     if ( current == object )
433     {
434       customObjects.Erase( iter );
435       return;
436     }
437   }
438
439   // Should not reach here
440   DALI_ASSERT_DEBUG(false);
441 }
442
443 void UpdateManager::AddAnimation( Animation* animation )
444 {
445   mImpl->animations.PushBack( animation );
446 }
447
448 void UpdateManager::StopAnimation( Animation* animation )
449 {
450   DALI_ASSERT_DEBUG( animation && "NULL animation called to stop" );
451
452   bool animationFinished = animation->Stop( mSceneGraphBuffers.GetUpdateBufferIndex() );
453
454   mImpl->animationFinishedDuringUpdate = mImpl->animationFinishedDuringUpdate || animationFinished;
455 }
456
457 void UpdateManager::RemoveAnimation( Animation* animation )
458 {
459   DALI_ASSERT_DEBUG( animation && "NULL animation called to remove" );
460
461   animation->OnDestroy( mSceneGraphBuffers.GetUpdateBufferIndex() );
462
463   DALI_ASSERT_DEBUG( animation->GetState() == Animation::Destroyed );
464 }
465
466 bool UpdateManager::IsAnimationRunning() const
467 {
468   bool isRunning(false);
469   AnimationContainer& animations = mImpl->animations;
470
471   // Find any animation that isn't stopped or paused
472
473   const AnimationIter endIter = animations.End();
474   for ( AnimationIter iter = animations.Begin(); !isRunning && iter != endIter; ++iter )
475   {
476     const Animation::State state = (*iter)->GetState();
477
478     if (state != Animation::Stopped &&
479         state != Animation::Paused)
480     {
481       isRunning = true;
482     }
483   }
484
485   return isRunning;
486 }
487
488 void UpdateManager::AddPropertyNotification( PropertyNotification* propertyNotification )
489 {
490   mImpl->propertyNotifications.PushBack( propertyNotification );
491 }
492
493 void UpdateManager::RemovePropertyNotification( PropertyNotification* propertyNotification )
494 {
495   PropertyNotificationContainer &propertyNotifications = mImpl->propertyNotifications;
496   PropertyNotificationIter iter = propertyNotifications.Begin();
497
498   while ( iter != propertyNotifications.End() )
499   {
500     if( *iter == propertyNotification )
501     {
502       propertyNotifications.Erase(iter);
503       break;
504     }
505     ++iter;
506   }
507 }
508
509 void UpdateManager::PropertyNotificationSetNotify( PropertyNotification* propertyNotification, PropertyNotification::NotifyMode notifyMode )
510 {
511   DALI_ASSERT_DEBUG( propertyNotification && "propertyNotification scene graph object missing" );
512   propertyNotification->SetNotifyMode( notifyMode );
513 }
514
515 ObjectOwnerContainer<Renderer>& UpdateManager::GetRendererOwner()
516 {
517   return mImpl->renderers;
518 }
519
520 void UpdateManager::AddShader( Shader* shader )
521 {
522   DALI_ASSERT_DEBUG( NULL != shader );
523
524   if( mImpl->shaders.Count() == 0 )
525   {
526     // the first added shader becomes our default shader
527     // Construct message in the render queue memory; note that delete should not be called on the return value
528     typedef MessageValue1< RenderManager, Shader* > DerivedType;
529
530     // Reserve some memory inside the render queue
531     unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
532
533     // Construct message in the render queue memory; note that delete should not be called on the return value
534     new (slot) DerivedType( &mImpl->renderManager, &RenderManager::SetDefaultShader, shader );
535   }
536
537   mImpl->shaders.PushBack( shader );
538 }
539
540 void UpdateManager::RemoveShader( Shader* shader )
541 {
542   DALI_ASSERT_DEBUG(shader != NULL);
543
544   ShaderContainer& shaders = mImpl->shaders;
545
546   // Find the shader and destroy it
547   for ( ShaderIter iter = shaders.Begin(); iter != shaders.End(); ++iter )
548   {
549     Shader& current = **iter;
550     if ( &current == shader )
551     {
552       // Transfer ownership to the discard queue
553       // This keeps the shader alive, until the render-thread has finished with it
554       mImpl->discardQueue.Add( mSceneGraphBuffers.GetUpdateBufferIndex(), shaders.Release( iter ) );
555
556       return;
557     }
558   }
559   // Should not reach here
560   DALI_ASSERT_DEBUG(false);
561 }
562
563 void UpdateManager::SetShaderProgram( Shader* shader,
564                                       Internal::ShaderDataPtr shaderData, bool modifiesGeometry )
565 {
566   if( shaderData )
567   {
568
569     typedef MessageValue3< Shader, Internal::ShaderDataPtr, ProgramCache*, bool> DerivedType;
570
571     // Reserve some memory inside the render queue
572     unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
573
574     // Construct message in the render queue memory; note that delete should not be called on the return value
575     new (slot) DerivedType( shader, &Shader::SetProgram, shaderData, mImpl->renderManager.GetProgramCache(), modifiesGeometry );
576   }
577 }
578
579 void UpdateManager::SaveBinary( Internal::ShaderDataPtr shaderData )
580 {
581   DALI_ASSERT_DEBUG( shaderData && "No NULL shader data pointers please." );
582   DALI_ASSERT_DEBUG( shaderData->GetBufferSize() > 0 && "Shader binary empty so nothing to save." );
583   {
584     // lock as update might be sending previously compiled shaders to event thread
585     Mutex::ScopedLock lock( mImpl->compiledShaderMutex );
586     mImpl->renderCompiledShaders.push_back( shaderData );
587   }
588 }
589
590 RenderTaskList* UpdateManager::GetRenderTaskList( bool systemLevel )
591 {
592   if ( !systemLevel )
593   {
594     // copy the list, this is only likely to happen once in application life cycle
595     return &(mImpl->taskList);
596   }
597   else
598   {
599     // copy the list, this is only likely to happen once in application life cycle
600     return &(mImpl->systemLevelTaskList);
601   }
602 }
603
604 void UpdateManager::AddGesture( PanGesture* gesture )
605 {
606   DALI_ASSERT_DEBUG( NULL != gesture );
607
608   mImpl->gestures.PushBack( gesture );
609 }
610
611 void UpdateManager::RemoveGesture( PanGesture* gesture )
612 {
613   DALI_ASSERT_DEBUG( gesture != NULL );
614
615   GestureContainer& gestures = mImpl->gestures;
616
617   // Find the gesture and destroy it
618   for ( GestureIter iter = gestures.Begin(), endIter = gestures.End(); iter != endIter; ++iter )
619   {
620     PanGesture& current = **iter;
621     if ( &current == gesture )
622     {
623       mImpl->gestures.Erase( iter );
624       return;
625     }
626   }
627   // Should not reach here
628   DALI_ASSERT_DEBUG(false);
629 }
630
631 void UpdateManager::AddTextureSet( TextureSet* textureSet )
632 {
633   DALI_ASSERT_DEBUG( NULL != textureSet );
634   mImpl->textureSets.PushBack( textureSet );
635 }
636
637 void UpdateManager::RemoveTextureSet( TextureSet* textureSet )
638 {
639   DALI_ASSERT_DEBUG(textureSet != NULL);
640   size_t textureSetCount( mImpl->textureSets.Size() );
641   for( size_t i(0); i<textureSetCount; ++i )
642   {
643     if( textureSet == mImpl->textureSets[i] )
644     {
645       mImpl->textureSets.Remove( mImpl->textureSets.Begin() + i );
646       return;
647     }
648   }
649 }
650
651 unsigned int* UpdateManager::ReserveMessageSlot( std::size_t size, bool updateScene )
652 {
653   return mImpl->messageQueue.ReserveMessageSlot( size, updateScene );
654 }
655
656 void UpdateManager::EventProcessingStarted()
657 {
658   mImpl->messageQueue.EventProcessingStarted();
659 }
660
661 bool UpdateManager::FlushQueue()
662 {
663   return mImpl->messageQueue.FlushQueue();
664 }
665
666 void UpdateManager::ResetProperties( BufferIndex bufferIndex )
667 {
668   // Clear the "animations finished" flag; This should be set if any (previously playing) animation is stopped
669   mImpl->animationFinishedDuringUpdate = false;
670
671   // Animated properties have to be reset to their original value each frame
672
673   // Reset root properties
674   if ( mImpl->root )
675   {
676     mImpl->root->ResetToBaseValues( bufferIndex );
677   }
678   if ( mImpl->systemLevelRoot )
679   {
680     mImpl->systemLevelRoot->ResetToBaseValues( bufferIndex );
681   }
682
683   // Reset all the nodes
684   Vector<Node*>::Iterator iter = mImpl->nodes.Begin()+1;
685   Vector<Node*>::Iterator endIter = mImpl->nodes.End();
686   for(;iter != endIter; ++iter)
687   {
688     (*iter)->ResetToBaseValues( bufferIndex );
689   }
690
691   // Reset system-level render-task list properties to base values
692   const RenderTaskList::RenderTaskContainer& systemLevelTasks = mImpl->systemLevelTaskList.GetTasks();
693
694   for (RenderTaskList::RenderTaskContainer::ConstIterator iter = systemLevelTasks.Begin(); iter != systemLevelTasks.End(); ++iter)
695   {
696     (*iter)->ResetToBaseValues( bufferIndex );
697   }
698
699   // Reset render-task list properties to base values.
700   const RenderTaskList::RenderTaskContainer& tasks = mImpl->taskList.GetTasks();
701
702   for (RenderTaskList::RenderTaskContainer::ConstIterator iter = tasks.Begin(); iter != tasks.End(); ++iter)
703   {
704     (*iter)->ResetToBaseValues( bufferIndex );
705   }
706
707   // Reset custom object properties to base values
708   for (OwnerContainer<PropertyOwner*>::Iterator iter = mImpl->customObjects.Begin(); iter != mImpl->customObjects.End(); ++iter)
709   {
710     (*iter)->ResetToBaseValues( bufferIndex );
711   }
712
713   mImpl->renderers.ResetToBaseValues( bufferIndex );
714
715   // Reset animatable shader properties to base values
716   for (ShaderIter iter = mImpl->shaders.Begin(); iter != mImpl->shaders.End(); ++iter)
717   {
718     (*iter)->ResetToBaseValues( bufferIndex );
719   }
720 }
721
722 bool UpdateManager::ProcessGestures( BufferIndex bufferIndex, unsigned int lastVSyncTimeMilliseconds, unsigned int nextVSyncTimeMilliseconds )
723 {
724   bool gestureUpdated( false );
725
726   // constrain gestures... (in construction order)
727   GestureContainer& gestures = mImpl->gestures;
728
729   for ( GestureIter iter = gestures.Begin(), endIter = gestures.End(); iter != endIter; ++iter )
730   {
731     PanGesture& gesture = **iter;
732     gesture.ResetToBaseValues( bufferIndex ); // Needs to be done every time as gesture data is written directly to an update-buffer rather than via a message
733     gestureUpdated |= gesture.UpdateProperties( lastVSyncTimeMilliseconds, nextVSyncTimeMilliseconds );
734   }
735
736   return gestureUpdated;
737 }
738
739 void UpdateManager::Animate( BufferIndex bufferIndex, float elapsedSeconds )
740 {
741   AnimationContainer &animations = mImpl->animations;
742   AnimationIter iter = animations.Begin();
743   bool animationLooped = false;
744   while ( iter != animations.End() )
745   {
746     Animation* animation = *iter;
747     bool finished = false;
748     bool looped = false;
749     animation->Update( bufferIndex, elapsedSeconds, looped, finished );
750
751     mImpl->animationFinishedDuringUpdate = mImpl->animationFinishedDuringUpdate || finished;
752     animationLooped = animationLooped || looped;
753
754     // Remove animations that had been destroyed but were still waiting for an update
755     if (animation->GetState() == Animation::Destroyed)
756     {
757       iter = animations.Erase(iter);
758     }
759     else
760     {
761       ++iter;
762     }
763   }
764
765   // queue the notification on finished or looped (to update loop count)
766   if ( mImpl->animationFinishedDuringUpdate || animationLooped )
767   {
768     // The application should be notified by NotificationManager, in another thread
769     mImpl->notificationManager.QueueCompleteNotification( &mImpl->animationFinishedNotifier );
770   }
771 }
772
773 void UpdateManager::ConstrainCustomObjects( BufferIndex bufferIndex )
774 {
775   //Constrain custom objects (in construction order)
776   OwnerContainer< PropertyOwner* >& customObjects = mImpl->customObjects;
777   const OwnerContainer< PropertyOwner* >::Iterator endIter = customObjects.End();
778   for ( OwnerContainer< PropertyOwner* >::Iterator iter = customObjects.Begin(); endIter != iter; ++iter )
779   {
780     PropertyOwner& object = **iter;
781     ConstrainPropertyOwner( object, bufferIndex );
782   }
783 }
784
785 void UpdateManager::ConstrainRenderTasks( BufferIndex bufferIndex )
786 {
787   // Constrain system-level render-tasks
788   const RenderTaskList::RenderTaskContainer& systemLevelTasks = mImpl->systemLevelTaskList.GetTasks();
789   for ( RenderTaskList::RenderTaskContainer::ConstIterator iter = systemLevelTasks.Begin(); iter != systemLevelTasks.End(); ++iter )
790   {
791     RenderTask& task = **iter;
792     ConstrainPropertyOwner( task, bufferIndex );
793   }
794
795   // Constrain render-tasks
796   const RenderTaskList::RenderTaskContainer& tasks = mImpl->taskList.GetTasks();
797   for ( RenderTaskList::RenderTaskContainer::ConstIterator iter = tasks.Begin(); iter != tasks.End(); ++iter )
798   {
799     RenderTask& task = **iter;
800     ConstrainPropertyOwner( task, bufferIndex );
801   }
802 }
803
804 void UpdateManager::ConstrainShaders( BufferIndex bufferIndex )
805 {
806   // constrain shaders... (in construction order)
807   ShaderContainer& shaders = mImpl->shaders;
808   for ( ShaderIter iter = shaders.Begin(); iter != shaders.End(); ++iter )
809   {
810     Shader& shader = **iter;
811     ConstrainPropertyOwner( shader, bufferIndex );
812   }
813 }
814
815 void UpdateManager::ProcessPropertyNotifications( BufferIndex bufferIndex )
816 {
817   PropertyNotificationContainer &notifications = mImpl->propertyNotifications;
818   PropertyNotificationIter iter = notifications.Begin();
819
820   while ( iter != notifications.End() )
821   {
822     PropertyNotification* notification = *iter;
823     bool valid = notification->Check( bufferIndex );
824     if(valid)
825     {
826       mImpl->notificationManager.QueueMessage( PropertyChangedMessage( mImpl->propertyNotifier, notification, notification->GetValidity() ) );
827     }
828     ++iter;
829   }
830 }
831
832 void UpdateManager::PrepareTextureSets( BufferIndex bufferIndex )
833 {
834   size_t textureSetCount( mImpl->textureSets.Size() );
835   for( size_t i(0); i<textureSetCount; ++i )
836   {
837     //Prepare texture set
838     mImpl->textureSets[i]->Prepare( mImpl->resourceManager );
839   }
840 }
841
842 void UpdateManager::ForwardCompiledShadersToEventThread()
843 {
844   DALI_ASSERT_DEBUG( (mImpl->shaderSaver != 0) && "shaderSaver should be wired-up during startup." );
845   if( mImpl->shaderSaver )
846   {
847     // lock and swap the queues
848     {
849       // render might be attempting to send us more binaries at the same time
850       Mutex::ScopedLock lock( mImpl->compiledShaderMutex );
851       mImpl->renderCompiledShaders.swap( mImpl->updateCompiledShaders );
852     }
853
854     if( mImpl->updateCompiledShaders.size() > 0 )
855     {
856       ShaderSaver& factory = *mImpl->shaderSaver;
857       ShaderDataBinaryQueue::iterator i   = mImpl->updateCompiledShaders.begin();
858       ShaderDataBinaryQueue::iterator end = mImpl->updateCompiledShaders.end();
859       for( ; i != end; ++i )
860       {
861         mImpl->notificationManager.QueueMessage( ShaderCompiledMessage( factory, *i ) );
862       }
863       // we don't need them in update anymore
864       mImpl->updateCompiledShaders.clear();
865     }
866   }
867 }
868
869 void UpdateManager::UpdateRenderers( BufferIndex bufferIndex )
870 {
871   const OwnerContainer<Renderer*>& rendererContainer( mImpl->renderers.GetObjectContainer() );
872   unsigned int rendererCount( rendererContainer.Size() );
873   for( unsigned int i(0); i<rendererCount; ++i )
874   {
875     //Apply constraints
876     ConstrainPropertyOwner( *rendererContainer[i], bufferIndex );
877
878     rendererContainer[i]->PrepareRender( bufferIndex );
879   }
880 }
881
882 void UpdateManager::UpdateNodes( BufferIndex bufferIndex )
883 {
884   mImpl->nodeDirtyFlags = NothingFlag;
885
886   if ( !mImpl->root )
887   {
888     return;
889   }
890
891   // Prepare resources, update shaders, for each node
892   // And add the renderers to the sorted layers. Start from root, which is also a layer
893   mImpl->nodeDirtyFlags = UpdateNodeTree( *( mImpl->root ),
894                                           bufferIndex,
895                                           mImpl->resourceManager,
896                                           mImpl->renderQueue );
897
898   if ( mImpl->systemLevelRoot )
899   {
900     mImpl->nodeDirtyFlags |= UpdateNodeTree( *( mImpl->systemLevelRoot ),
901                                              bufferIndex,
902                                              mImpl->resourceManager,
903                                              mImpl->renderQueue );
904   }
905 }
906
907 unsigned int UpdateManager::Update( float elapsedSeconds,
908                                     unsigned int lastVSyncTimeMilliseconds,
909                                     unsigned int nextVSyncTimeMilliseconds )
910 {
911   const BufferIndex bufferIndex = mSceneGraphBuffers.GetUpdateBufferIndex();
912
913   //Clear nodes/resources which were previously discarded
914   mImpl->discardQueue.Clear( bufferIndex );
915
916   //Grab any loaded resources
917   bool resourceChanged = mImpl->resourceManager.UpdateCache( bufferIndex );
918
919   //Process Touches & Gestures
920   const bool gestureUpdated = ProcessGestures( bufferIndex, lastVSyncTimeMilliseconds, nextVSyncTimeMilliseconds );
921
922   const bool updateScene =                                  // The scene-graph requires an update if..
923       (mImpl->nodeDirtyFlags & RenderableUpdateFlags) ||    // ..nodes were dirty in previous frame OR
924       IsAnimationRunning()                            ||    // ..at least one animation is running OR
925       mImpl->messageQueue.IsSceneUpdateRequired()     ||    // ..a message that modifies the scene graph node tree is queued OR
926       resourceChanged                                 ||    // ..one or more resources were updated/changed OR
927       gestureUpdated;                                       // ..a gesture property was updated
928
929
930   // Although the scene-graph may not require an update, we still need to synchronize double-buffered
931   // values if the scene was updated in the previous frame.
932   if( updateScene || mImpl->previousUpdateScene )
933   {
934     //Reset properties from the previous update
935     ResetProperties( bufferIndex );
936     mImpl->transformManager.ResetToBaseValue();
937   }
938
939   //Process the queued scene messages
940   mImpl->messageQueue.ProcessMessages( bufferIndex );
941
942   //Post Process Ids of resources updated by renderer
943   mImpl->resourceManager.PostProcessResources( bufferIndex );
944
945   //Forward compiled shader programs to event thread for saving
946   ForwardCompiledShadersToEventThread();
947
948   // Although the scene-graph may not require an update, we still need to synchronize double-buffered
949   // renderer lists if the scene was updated in the previous frame.
950   // We should not start skipping update steps or reusing lists until there has been two frames where nothing changes
951   if( updateScene || mImpl->previousUpdateScene )
952   {
953     //Animate
954     Animate( bufferIndex, elapsedSeconds );
955
956     //Constraint custom objects
957     ConstrainCustomObjects( bufferIndex );
958
959     //Prepare texture sets and apply constraints to them
960     PrepareTextureSets( bufferIndex );
961
962     //Clear the lists of renderers from the previous update
963     for( size_t i(0); i<mImpl->sortedLayers.size(); ++i )
964     {
965       mImpl->sortedLayers[i]->ClearRenderables();
966     }
967
968     for( size_t i(0); i<mImpl->systemLevelSortedLayers.size(); ++i )
969     {
970       mImpl->systemLevelSortedLayers[i]->ClearRenderables();
971     }
972
973     //Update node hierarchy, apply constraints and perform sorting / culling.
974     //This will populate each Layer with a list of renderers which are ready.
975     UpdateNodes( bufferIndex );
976
977     //Apply constraints to RenderTasks, shaders
978     ConstrainRenderTasks( bufferIndex );
979     ConstrainShaders( bufferIndex );
980
981     //Update renderers and apply constraints
982     UpdateRenderers( bufferIndex );
983
984     //Update the trnasformations of all the nodes
985     mImpl->transformManager.Update();
986
987     //Process Property Notifications
988     ProcessPropertyNotifications( bufferIndex );
989
990     //Update geometry batcher
991     mImpl->geometryBatcher.Update( bufferIndex );
992
993     //Process the RenderTasks; this creates the instructions for rendering the next frame.
994     //reset the update buffer index and make sure there is enough room in the instruction container
995     mImpl->renderInstructions.ResetAndReserve( bufferIndex,
996                                                mImpl->taskList.GetTasks().Count() + mImpl->systemLevelTaskList.GetTasks().Count() );
997
998     if ( NULL != mImpl->root )
999     {
1000       ProcessRenderTasks(  bufferIndex,
1001                            mImpl->taskList,
1002                            *mImpl->root,
1003                            mImpl->sortedLayers,
1004                            mImpl->renderSortingHelper,
1005                            mImpl->geometryBatcher,
1006                            mImpl->renderInstructions );
1007
1008       // Process the system-level RenderTasks last
1009       if ( NULL != mImpl->systemLevelRoot )
1010       {
1011         ProcessRenderTasks(  bufferIndex,
1012                              mImpl->systemLevelTaskList,
1013                              *mImpl->systemLevelRoot,
1014                              mImpl->systemLevelSortedLayers,
1015                              mImpl->renderSortingHelper,
1016                              mImpl->geometryBatcher,
1017                              mImpl->renderInstructions );
1018       }
1019     }
1020   }
1021
1022   // check the countdown and notify (note, at the moment this is only done for normal tasks, not for systemlevel tasks)
1023   bool doRenderOnceNotify = false;
1024   mImpl->renderTaskWaiting = false;
1025   const RenderTaskList::RenderTaskContainer& tasks = mImpl->taskList.GetTasks();
1026   for ( RenderTaskList::RenderTaskContainer::ConstIterator iter = tasks.Begin(), endIter = tasks.End();
1027         endIter != iter; ++iter )
1028   {
1029     RenderTask& renderTask(*(*iter));
1030
1031     renderTask.UpdateState();
1032
1033     if( renderTask.IsWaitingToRender() &&
1034         renderTask.ReadyToRender( bufferIndex ) /*avoid updating forever when source actor is off-stage*/ )
1035     {
1036       mImpl->renderTaskWaiting = true; // keep update/render threads alive
1037     }
1038
1039     if( renderTask.HasRendered() )
1040     {
1041       doRenderOnceNotify = true;
1042     }
1043   }
1044
1045   if( doRenderOnceNotify )
1046   {
1047     DALI_LOG_INFO(gRenderTaskLogFilter, Debug::General, "Notify a render task has finished\n");
1048     mImpl->notificationManager.QueueCompleteNotification( mImpl->taskList.GetCompleteNotificationInterface() );
1049   }
1050
1051   // Macro is undefined in release build.
1052   SNAPSHOT_NODE_LOGGING;
1053
1054   // A ResetProperties() may be required in the next frame
1055   mImpl->previousUpdateScene = updateScene;
1056
1057   // Check whether further updates are required
1058   unsigned int keepUpdating = KeepUpdatingCheck( elapsedSeconds );
1059
1060   // tell the update manager that we're done so the queue can be given to event thread
1061   mImpl->notificationManager.UpdateCompleted();
1062
1063   // The update has finished; swap the double-buffering indices
1064   mSceneGraphBuffers.Swap();
1065
1066   return keepUpdating;
1067 }
1068
1069 unsigned int UpdateManager::KeepUpdatingCheck( float elapsedSeconds ) const
1070 {
1071   // Update the duration set via Stage::KeepRendering()
1072   if ( mImpl->keepRenderingSeconds > 0.0f )
1073   {
1074     mImpl->keepRenderingSeconds -= elapsedSeconds;
1075   }
1076
1077   unsigned int keepUpdatingRequest = KeepUpdating::NOT_REQUESTED;
1078
1079   // If Stage::KeepRendering() has been called, then continue until the duration has elapsed.
1080   // Keep updating until no messages are received and no animations are running.
1081   // If an animation has just finished, update at least once more for Discard end-actions.
1082   // No need to check for renderQueue as there is always a render after update and if that
1083   // render needs another update it will tell the adaptor to call update again
1084
1085   if ( mImpl->keepRenderingSeconds > 0.0f )
1086   {
1087     keepUpdatingRequest |= KeepUpdating::STAGE_KEEP_RENDERING;
1088   }
1089
1090   if ( IsAnimationRunning() ||
1091        mImpl->animationFinishedDuringUpdate )
1092   {
1093     keepUpdatingRequest |= KeepUpdating::ANIMATIONS_RUNNING;
1094   }
1095
1096   if ( mImpl->renderTaskWaiting )
1097   {
1098     keepUpdatingRequest |= KeepUpdating::RENDER_TASK_SYNC;
1099   }
1100
1101   return keepUpdatingRequest;
1102 }
1103
1104 void UpdateManager::SetBackgroundColor( const Vector4& color )
1105 {
1106   typedef MessageValue1< RenderManager, Vector4 > DerivedType;
1107
1108   // Reserve some memory inside the render queue
1109   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1110
1111   // Construct message in the render queue memory; note that delete should not be called on the return value
1112   new (slot) DerivedType( &mImpl->renderManager, &RenderManager::SetBackgroundColor, color );
1113 }
1114
1115 void UpdateManager::SetDefaultSurfaceRect( const Rect<int>& rect )
1116 {
1117   typedef MessageValue1< RenderManager, Rect<int> > DerivedType;
1118
1119   // Reserve some memory inside the render queue
1120   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1121
1122   // Construct message in the render queue memory; note that delete should not be called on the return value
1123   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::SetDefaultSurfaceRect, rect );
1124 }
1125
1126 void UpdateManager::KeepRendering( float durationSeconds )
1127 {
1128   mImpl->keepRenderingSeconds = std::max( mImpl->keepRenderingSeconds, durationSeconds );
1129 }
1130
1131 void UpdateManager::SetLayerDepths( const SortedLayerPointers& layers, bool systemLevel )
1132 {
1133   if ( !systemLevel )
1134   {
1135     // just copy the vector of pointers
1136     mImpl->sortedLayers = layers;
1137   }
1138   else
1139   {
1140     mImpl->systemLevelSortedLayers = layers;
1141   }
1142 }
1143
1144 void UpdateManager::SetShaderSaver( ShaderSaver& upstream )
1145 {
1146   mImpl->shaderSaver = &upstream;
1147 }
1148
1149 void UpdateManager::AddSampler( Render::Sampler* sampler )
1150 {
1151   typedef MessageValue1< RenderManager, Render::Sampler* > DerivedType;
1152
1153   // Reserve some memory inside the render queue
1154   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1155
1156   // Construct message in the render queue memory; note that delete should not be called on the return value
1157   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddSampler, sampler );
1158 }
1159
1160 void UpdateManager::RemoveSampler( Render::Sampler* sampler )
1161 {
1162   typedef MessageValue1< RenderManager, Render::Sampler* > DerivedType;
1163
1164   // Reserve some memory inside the render queue
1165   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1166
1167   // Construct message in the render queue memory; note that delete should not be called on the return value
1168   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemoveSampler, sampler );
1169 }
1170
1171 void UpdateManager::SetFilterMode( Render::Sampler* sampler, unsigned int minFilterMode, unsigned int magFilterMode )
1172 {
1173   typedef MessageValue3< RenderManager, Render::Sampler*, unsigned int, unsigned int > DerivedType;
1174
1175   // Reserve some memory inside the render queue
1176   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1177
1178   // Construct message in the render queue memory; note that delete should not be called on the return value
1179   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::SetFilterMode, sampler, minFilterMode, magFilterMode );
1180 }
1181
1182 void UpdateManager::SetWrapMode( Render::Sampler* sampler, unsigned int rWrapMode, unsigned int sWrapMode, unsigned int tWrapMode )
1183 {
1184   typedef MessageValue4< RenderManager, Render::Sampler*, unsigned int, unsigned int, unsigned int > DerivedType;
1185
1186   // Reserve some memory inside the render queue
1187   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1188
1189   // Construct message in the render queue memory; note that delete should not be called on the return value
1190   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::SetWrapMode, sampler, rWrapMode, sWrapMode, tWrapMode );
1191 }
1192
1193 void UpdateManager::AddPropertyBuffer( Render::PropertyBuffer* propertyBuffer )
1194 {
1195   typedef MessageValue1< RenderManager, Render::PropertyBuffer* > DerivedType;
1196
1197   // Reserve some memory inside the render queue
1198   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1199
1200   // Construct message in the render queue memory; note that delete should not be called on the return value
1201   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddPropertyBuffer, propertyBuffer );
1202 }
1203
1204 void UpdateManager::RemovePropertyBuffer( Render::PropertyBuffer* propertyBuffer )
1205 {
1206   typedef MessageValue1< RenderManager, Render::PropertyBuffer* > DerivedType;
1207
1208   // Reserve some memory inside the render queue
1209   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1210
1211   // Construct message in the render queue memory; note that delete should not be called on the return value
1212   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemovePropertyBuffer, propertyBuffer );
1213 }
1214
1215 void UpdateManager::SetPropertyBufferFormat(Render::PropertyBuffer* propertyBuffer, Render::PropertyBuffer::Format* format )
1216 {
1217   typedef MessageValue2< RenderManager, Render::PropertyBuffer*, Render::PropertyBuffer::Format* > DerivedType;
1218
1219   // Reserve some memory inside the render queue
1220   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1221
1222   // Construct message in the render queue memory; note that delete should not be called on the return value
1223   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::SetPropertyBufferFormat, propertyBuffer, format );
1224 }
1225
1226 void UpdateManager::SetPropertyBufferData( Render::PropertyBuffer* propertyBuffer, Dali::Vector<char>* data, size_t size )
1227 {
1228   typedef MessageValue3< RenderManager, Render::PropertyBuffer*, Dali::Vector<char>*, size_t > DerivedType;
1229
1230   // Reserve some memory inside the render queue
1231   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1232
1233   // Construct message in the render queue memory; note that delete should not be called on the return value
1234   new (slot) DerivedType( &mImpl->renderManager, &RenderManager::SetPropertyBufferData, propertyBuffer, data, size );
1235 }
1236
1237 void UpdateManager::AddGeometry( Render::Geometry* geometry )
1238 {
1239   typedef MessageValue1< RenderManager, Render::Geometry* > DerivedType;
1240
1241   // Reserve some memory inside the render queue
1242   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1243
1244   // Construct message in the render queue memory; note that delete should not be called on the return value
1245   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddGeometry, geometry );
1246 }
1247
1248 void UpdateManager::RemoveGeometry( Render::Geometry* geometry )
1249 {
1250   typedef MessageValue1< RenderManager, Render::Geometry* > DerivedType;
1251
1252   // Reserve some memory inside the render queue
1253   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1254
1255   // Construct message in the render queue memory; note that delete should not be called on the return value
1256   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemoveGeometry, geometry );
1257 }
1258
1259 void UpdateManager::SetGeometryType( Render::Geometry* geometry, unsigned int geometryType )
1260 {
1261   typedef MessageValue2< RenderManager, Render::Geometry*, unsigned int > DerivedType;
1262
1263   // Reserve some memory inside the render queue
1264   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1265
1266   // Construct message in the render queue memory; note that delete should not be called on the return value
1267   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::SetGeometryType, geometry, geometryType );
1268 }
1269
1270 void UpdateManager::SetIndexBuffer( Render::Geometry* geometry, Dali::Vector<unsigned short>& indices )
1271 {
1272   typedef IndexBufferMessage< RenderManager > DerivedType;
1273
1274   // Reserve some memory inside the render queue
1275   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1276
1277   // Construct message in the render queue memory; note that delete should not be called on the return value
1278   new (slot) DerivedType( &mImpl->renderManager, geometry, indices );
1279 }
1280
1281 void UpdateManager::RemoveVertexBuffer( Render::Geometry* geometry, Render::PropertyBuffer* propertyBuffer )
1282 {
1283   typedef MessageValue2< RenderManager, Render::Geometry*, Render::PropertyBuffer* > DerivedType;
1284
1285   // Reserve some memory inside the render queue
1286   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1287
1288   // Construct message in the render queue memory; note that delete should not be called on the return value
1289   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemoveVertexBuffer, geometry, propertyBuffer );
1290 }
1291
1292 void UpdateManager::AddVertexBuffer( Render::Geometry* geometry, Render::PropertyBuffer* propertyBuffer )
1293 {
1294   typedef MessageValue2< RenderManager, Render::Geometry*, Render::PropertyBuffer* > DerivedType;
1295
1296   // Reserve some memory inside the render queue
1297   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1298
1299   // Construct message in the render queue memory; note that delete should not be called on the return value
1300   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddVertexBuffer, geometry, propertyBuffer );
1301 }
1302
1303 void UpdateManager::AddTexture( Render::NewTexture* texture )
1304 {
1305   typedef MessageValue1< RenderManager, Render::NewTexture* > DerivedType;
1306
1307   // Reserve some memory inside the render queue
1308   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1309
1310   // Construct message in the render queue memory; note that delete should not be called on the return value
1311   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddTexture, texture );
1312 }
1313
1314 void UpdateManager::RemoveTexture( Render::NewTexture* texture)
1315 {
1316   typedef MessageValue1< RenderManager, Render::NewTexture* > DerivedType;
1317
1318   // Reserve some memory inside the render queue
1319   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1320
1321   // Construct message in the render queue memory; note that delete should not be called on the return value
1322   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemoveTexture, texture );
1323 }
1324
1325 void UpdateManager::UploadTexture( Render::NewTexture* texture, PixelDataPtr pixelData, const NewTexture::UploadParams& params )
1326 {
1327   typedef MessageValue3< RenderManager, Render::NewTexture*, PixelDataPtr, NewTexture::UploadParams > DerivedType;
1328
1329   // Reserve some memory inside the message queue
1330   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1331
1332   // Construct message in the message queue memory; note that delete should not be called on the return value
1333   new (slot) DerivedType( &mImpl->renderManager, &RenderManager::UploadTexture, texture, pixelData, params );
1334 }
1335
1336 void UpdateManager::GenerateMipmaps( Render::NewTexture* texture )
1337 {
1338   typedef MessageValue1< RenderManager, Render::NewTexture* > DerivedType;
1339
1340   // Reserve some memory inside the render queue
1341   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1342
1343   // Construct message in the render queue memory; note that delete should not be called on the return value
1344   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::GenerateMipmaps, texture );
1345 }
1346
1347 void UpdateManager::AddFrameBuffer( Render::FrameBuffer* frameBuffer )
1348 {
1349   typedef MessageValue1< RenderManager, Render::FrameBuffer* > DerivedType;
1350
1351   // Reserve some memory inside the render queue
1352   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1353
1354   // Construct message in the render queue memory; note that delete should not be called on the return value
1355   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AddFrameBuffer, frameBuffer );
1356 }
1357
1358 void UpdateManager::RemoveFrameBuffer( Render::FrameBuffer* frameBuffer)
1359 {
1360   typedef MessageValue1< RenderManager, Render::FrameBuffer* > DerivedType;
1361
1362   // Reserve some memory inside the render queue
1363   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1364
1365   // Construct message in the render queue memory; note that delete should not be called on the return value
1366   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::RemoveFrameBuffer, frameBuffer );
1367 }
1368
1369 void UpdateManager::AttachColorTextureToFrameBuffer( Render::FrameBuffer* frameBuffer, Render::NewTexture* texture, unsigned int mipmapLevel, unsigned int layer )
1370 {
1371   typedef MessageValue4< RenderManager, Render::FrameBuffer*, Render::NewTexture*, unsigned int, unsigned int > DerivedType;
1372
1373   // Reserve some memory inside the render queue
1374   unsigned int* slot = mImpl->renderQueue.ReserveMessageSlot( mSceneGraphBuffers.GetUpdateBufferIndex(), sizeof( DerivedType ) );
1375
1376   // Construct message in the render queue memory; note that delete should not be called on the return value
1377   new (slot) DerivedType( &mImpl->renderManager,  &RenderManager::AttachColorTextureToFrameBuffer, frameBuffer, texture, mipmapLevel, layer );
1378 }
1379
1380 } // namespace SceneGraph
1381
1382 } // namespace Internal
1383
1384 } // namespace Dali