2 * Copyright (c) 2019 Samsung Electronics Co., Ltd.
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
8 * http://www.apache.org/licenses/LICENSE-2.0
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.
19 #include <dali/internal/adaptor/common/adaptor-impl.h>
20 #include <dali/internal/adaptor/common/adaptor-builder-impl.h>
23 #include <dali/public-api/common/stage.h>
24 #include <dali/public-api/actors/layer.h>
25 #include <dali/public-api/object/any.h>
26 #include <dali/devel-api/actors/actor-devel.h>
27 #include <dali/integration-api/debug.h>
28 #include <dali/integration-api/core.h>
29 #include <dali/integration-api/context-notifier.h>
30 #include <dali/integration-api/profiling.h>
31 #include <dali/integration-api/input-options.h>
32 #include <dali/integration-api/events/touch-event-integ.h>
35 #include <dali/public-api/dali-adaptor-common.h>
36 #include <dali/internal/system/common/thread-controller.h>
37 #include <dali/internal/system/common/performance-interface-factory.h>
38 #include <dali/internal/adaptor/common/lifecycle-observer.h>
40 #include <dali/internal/graphics/gles/egl-graphics-factory.h>
41 #include <dali/internal/graphics/gles/egl-graphics.h> // Temporary until Core is abstracted
43 #include <dali/devel-api/text-abstraction/font-client.h>
45 #include <dali/internal/system/common/callback-manager.h>
46 #include <dali/internal/accessibility/common/tts-player-impl.h>
47 #include <dali/internal/accessibility/common/accessibility-adaptor-impl.h>
48 #include <dali/internal/input/common/gesture-manager.h>
49 #include <dali/internal/window-system/common/event-handler.h>
50 #include <dali/internal/graphics/gles/gl-proxy-implementation.h>
51 #include <dali/internal/graphics/gles/gl-implementation.h>
52 #include <dali/internal/graphics/gles/egl-sync-implementation.h>
53 #include <dali/internal/graphics/common/egl-image-extensions.h>
54 #include <dali/internal/clipboard/common/clipboard-impl.h>
55 #include <dali/internal/graphics/common/vsync-monitor.h>
56 #include <dali/internal/system/common/object-profiler.h>
57 #include <dali/internal/window-system/common/display-connection.h>
58 #include <dali/internal/window-system/common/window-impl.h>
59 #include <dali/internal/window-system/common/window-render-surface.h>
61 #include <dali/internal/system/common/logging.h>
63 #include <dali/internal/system/common/locale-utils.h>
64 #include <dali/internal/imaging/common/image-loader-plugin-proxy.h>
65 #include <dali/internal/imaging/common/image-loader.h>
68 using Dali::TextAbstraction::FontClient;
81 thread_local Adaptor* gThreadLocalAdaptor = NULL; // raw thread specific pointer to allow Adaptor::Get
82 } // unnamed namespace
85 Dali::Adaptor* Adaptor::New( Any nativeWindow, RenderSurface *surface, Dali::Configuration::ContextLoss configuration, EnvironmentOptions* environmentOptions )
87 Dali::Adaptor* adaptor = new Dali::Adaptor;
88 Adaptor* impl = new Adaptor( nativeWindow, *adaptor, surface, environmentOptions );
89 adaptor->mImpl = impl;
91 Dali::Internal::Adaptor::AdaptorBuilder* mAdaptorBuilder = new AdaptorBuilder();
92 auto graphicsFactory = mAdaptorBuilder->GetGraphicsFactory();
94 impl->Initialize( graphicsFactory, configuration );
95 delete mAdaptorBuilder; // Not needed anymore as the graphics interface has now been created
100 Dali::Adaptor* Adaptor::New( Dali::Window window, Dali::Configuration::ContextLoss configuration, EnvironmentOptions* environmentOptions )
102 Any winId = window.GetNativeHandle();
104 Window& windowImpl = Dali::GetImplementation( window );
105 Dali::Adaptor* adaptor = New( winId, windowImpl.GetSurface(), configuration, environmentOptions );
106 windowImpl.SetAdaptor( *adaptor );
110 Dali::Adaptor* Adaptor::New( GraphicsFactory& graphicsFactory, Any nativeWindow, RenderSurface *surface, Dali::Configuration::ContextLoss configuration, EnvironmentOptions* environmentOptions )
112 Dali::Adaptor* adaptor = new Dali::Adaptor; // Public adaptor
113 Adaptor* impl = new Adaptor( nativeWindow, *adaptor, surface, environmentOptions ); // Impl adaptor
114 adaptor->mImpl = impl;
116 impl->Initialize( graphicsFactory, configuration );
121 Dali::Adaptor* Adaptor::New( GraphicsFactory& graphicsFactory, Dali::Window window, Dali::Configuration::ContextLoss configuration, EnvironmentOptions* environmentOptions )
123 Any winId = window.GetNativeHandle();
125 Window& windowImpl = Dali::GetImplementation( window );
126 Dali::Adaptor* adaptor = New( graphicsFactory, winId, windowImpl.GetSurface(), configuration, environmentOptions );
127 windowImpl.SetAdaptor( *adaptor );
131 void Adaptor::Initialize( GraphicsFactory& graphicsFactory, Dali::Configuration::ContextLoss configuration )
133 // all threads here (event, update, and render) will send their logs to TIZEN Platform's LogMessage handler.
134 Dali::Integration::Log::LogFunction logFunction( Dali::TizenPlatform::LogMessage );
135 mEnvironmentOptions->SetLogFunction( logFunction );
136 mEnvironmentOptions->InstallLogFunction(); // install logging for main thread
138 mPlatformAbstraction = new TizenPlatform::TizenPlatformAbstraction;
141 GetDataStoragePath( path );
142 mPlatformAbstraction->SetDataStoragePath( path );
144 ResourcePolicy::DataRetention dataRetentionPolicy = ResourcePolicy::DALI_DISCARDS_ALL_DATA;
145 if( configuration == Dali::Configuration::APPLICATION_DOES_NOT_HANDLE_CONTEXT_LOSS )
147 dataRetentionPolicy = ResourcePolicy::DALI_DISCARDS_ALL_DATA;
150 // Note, Tizen does not use DALI_RETAINS_ALL_DATA, as it can reload images from files automatically.
152 if( mEnvironmentOptions->PerformanceServerRequired() )
154 mPerformanceInterface = PerformanceInterfaceFactory::CreateInterface( *this, *mEnvironmentOptions );
157 mEnvironmentOptions->CreateTraceManager( mPerformanceInterface );
158 mEnvironmentOptions->InstallTraceFunction(); // install tracing for main thread
160 mCallbackManager = CallbackManager::New();
162 WindowPane defaultWindow = mWindowFrame.front();
164 DALI_ASSERT_DEBUG( defaultWindow.surface && "Surface not initialized" );
166 PositionSize size = defaultWindow.surface->GetPositionSize();
168 mGestureManager = new GestureManager(*this, Vector2(size.width, size.height), mCallbackManager, *mEnvironmentOptions);
170 mGraphics = &( graphicsFactory.Create() );
171 mGraphics->Initialize( mEnvironmentOptions );
173 auto eglGraphics = static_cast<EglGraphics *>( mGraphics ); // This interface is temporary until Core has been updated to match
175 GlImplementation& mGLES = eglGraphics->GetGlesInterface();
176 EglSyncImplementation& eglSyncImpl = eglGraphics->GetSyncImplementation();
178 mCore = Integration::Core::New( *this,
179 *mPlatformAbstraction,
183 dataRetentionPolicy ,
184 ( 0u != mEnvironmentOptions->GetRenderToFboInterval() ) ? Integration::RenderToFrameBuffer::TRUE : Integration::RenderToFrameBuffer::FALSE,
185 mGraphics->GetDepthBufferRequired(),
186 mGraphics->GetStencilBufferRequired() );
188 const unsigned int timeInterval = mEnvironmentOptions->GetObjectProfilerInterval();
189 if( 0u < timeInterval )
191 mObjectProfiler = new ObjectProfiler( timeInterval );
194 mNotificationTrigger = mTriggerEventFactory.CreateTriggerEvent( MakeCallback( this, &Adaptor::ProcessCoreEvents ), TriggerEventInterface::KEEP_ALIVE_AFTER_TRIGGER);
196 mVSyncMonitor = new VSyncMonitor;
198 mDisplayConnection = Dali::DisplayConnection::New( *mGraphics, defaultWindow.surface->GetSurfaceType() );
200 mThreadController = new ThreadController( *this, *mEnvironmentOptions );
202 // Should be called after Core creation
203 if( mEnvironmentOptions->GetPanGestureLoggingLevel() )
205 Integration::EnableProfiling( Dali::Integration::PROFILING_TYPE_PAN_GESTURE );
207 if( mEnvironmentOptions->GetPanGesturePredictionMode() >= 0 )
209 Integration::SetPanGesturePredictionMode(mEnvironmentOptions->GetPanGesturePredictionMode());
211 if( mEnvironmentOptions->GetPanGesturePredictionAmount() >= 0 )
213 Integration::SetPanGesturePredictionAmount(mEnvironmentOptions->GetPanGesturePredictionAmount());
215 if( mEnvironmentOptions->GetPanGestureMaximumPredictionAmount() >= 0 )
217 Integration::SetPanGestureMaximumPredictionAmount(mEnvironmentOptions->GetPanGestureMaximumPredictionAmount());
219 if( mEnvironmentOptions->GetPanGestureMinimumPredictionAmount() >= 0 )
221 Integration::SetPanGestureMinimumPredictionAmount(mEnvironmentOptions->GetPanGestureMinimumPredictionAmount());
223 if( mEnvironmentOptions->GetPanGesturePredictionAmountAdjustment() >= 0 )
225 Integration::SetPanGesturePredictionAmountAdjustment(mEnvironmentOptions->GetPanGesturePredictionAmountAdjustment());
227 if( mEnvironmentOptions->GetPanGestureSmoothingMode() >= 0 )
229 Integration::SetPanGestureSmoothingMode(mEnvironmentOptions->GetPanGestureSmoothingMode());
231 if( mEnvironmentOptions->GetPanGestureSmoothingAmount() >= 0.0f )
233 Integration::SetPanGestureSmoothingAmount(mEnvironmentOptions->GetPanGestureSmoothingAmount());
235 if( mEnvironmentOptions->GetPanGestureUseActualTimes() >= 0 )
237 Integration::SetPanGestureUseActualTimes( mEnvironmentOptions->GetPanGestureUseActualTimes() == 0 ? true : false );
239 if( mEnvironmentOptions->GetPanGestureInterpolationTimeRange() >= 0 )
241 Integration::SetPanGestureInterpolationTimeRange( mEnvironmentOptions->GetPanGestureInterpolationTimeRange() );
243 if( mEnvironmentOptions->GetPanGestureScalarOnlyPredictionEnabled() >= 0 )
245 Integration::SetPanGestureScalarOnlyPredictionEnabled( mEnvironmentOptions->GetPanGestureScalarOnlyPredictionEnabled() == 0 ? true : false );
247 if( mEnvironmentOptions->GetPanGestureTwoPointPredictionEnabled() >= 0 )
249 Integration::SetPanGestureTwoPointPredictionEnabled( mEnvironmentOptions->GetPanGestureTwoPointPredictionEnabled() == 0 ? true : false );
251 if( mEnvironmentOptions->GetPanGestureTwoPointInterpolatePastTime() >= 0 )
253 Integration::SetPanGestureTwoPointInterpolatePastTime( mEnvironmentOptions->GetPanGestureTwoPointInterpolatePastTime() );
255 if( mEnvironmentOptions->GetPanGestureTwoPointVelocityBias() >= 0.0f )
257 Integration::SetPanGestureTwoPointVelocityBias( mEnvironmentOptions->GetPanGestureTwoPointVelocityBias() );
259 if( mEnvironmentOptions->GetPanGestureTwoPointAccelerationBias() >= 0.0f )
261 Integration::SetPanGestureTwoPointAccelerationBias( mEnvironmentOptions->GetPanGestureTwoPointAccelerationBias() );
263 if( mEnvironmentOptions->GetPanGestureMultitapSmoothingRange() >= 0 )
265 Integration::SetPanGestureMultitapSmoothingRange( mEnvironmentOptions->GetPanGestureMultitapSmoothingRange() );
268 // Set max texture size
269 if( mEnvironmentOptions->GetMaxTextureSize() > 0 )
271 Dali::TizenPlatform::ImageLoader::SetMaxTextureSize( mEnvironmentOptions->GetMaxTextureSize() );
274 SetupSystemInformation();
279 // Ensure stop status
282 // set to NULL first as we do not want any access to Adaptor as it is being destroyed.
283 gThreadLocalAdaptor = NULL;
285 for ( ObserverContainer::iterator iter = mObservers.begin(), endIter = mObservers.end(); iter != endIter; ++iter )
287 (*iter)->OnDestroy();
290 delete mThreadController; // this will shutdown render thread, which will call Core::ContextDestroyed before exit
291 delete mVSyncMonitor;
292 delete mEventHandler;
293 delete mObjectProfiler;
297 delete mGestureManager;
298 delete mDisplayConnection;
299 delete mPlatformAbstraction;
300 delete mCallbackManager;
301 delete mPerformanceInterface;
303 mGraphics->Destroy();
305 // uninstall it on this thread (main actor thread)
306 Dali::Integration::Log::UninstallLogFunction();
308 // Delete environment options if we own it
309 if( mEnvironmentOptionsOwned )
311 delete mEnvironmentOptions;
315 void Adaptor::Start()
317 // It doesn't support restart after stop at this moment to support restarting, need more testing
318 if( READY != mState )
323 // Start the callback manager
324 mCallbackManager->Start();
326 WindowPane defaultWindow = mWindowFrame.front();
328 // Create event handler
329 mEventHandler = new EventHandler( defaultWindow.surface, *this, *mGestureManager, *this, mDragAndDropDetector );
331 if( mDeferredRotationObserver != NULL )
333 mEventHandler->SetRotationObserver(mDeferredRotationObserver);
334 mDeferredRotationObserver = NULL;
337 unsigned int dpiHor, dpiVer;
340 defaultWindow.surface->GetDpi( dpiHor, dpiVer );
342 // tell core about the DPI value
343 mCore->SetDpi(dpiHor, dpiVer);
345 // set the DPI value for font rendering
346 FontClient fontClient = FontClient::Get();
347 fontClient.SetDpi( dpiHor, dpiVer );
349 // Tell the core the size of the surface just before we start the render-thread
350 PositionSize size = defaultWindow.surface->GetPositionSize();
352 mCore->SurfaceResized( size.width, size.height );
354 // Initialize the thread controller
355 mThreadController->Initialize();
357 ProcessCoreEvents(); // Ensure any startup messages are processed.
359 // Initialize the image loader plugin
360 Internal::Adaptor::ImageLoaderPluginProxy::Initialize();
362 for ( ObserverContainer::iterator iter = mObservers.begin(), endIter = mObservers.end(); iter != endIter; ++iter )
368 // Dali::Internal::Adaptor::Adaptor::Pause
369 void Adaptor::Pause()
371 // Only pause the adaptor if we're actually running.
372 if( RUNNING == mState )
374 // Inform observers that we are about to be paused.
375 for( ObserverContainer::iterator iter = mObservers.begin(), endIter = mObservers.end(); iter != endIter; ++iter )
380 // Reset the event handler when adaptor paused
383 mEventHandler->Pause();
386 mThreadController->Pause();
389 // Ensure any messages queued during pause callbacks are processed by doing another update.
392 DALI_LOG_RELEASE_INFO( "Adaptor::Pause: Paused\n" );
396 DALI_LOG_RELEASE_INFO( "Adaptor::Pause: Not paused [%d]\n", mState );
400 // Dali::Internal::Adaptor::Adaptor::Resume
401 void Adaptor::Resume()
403 // Only resume the adaptor if we are in the suspended state.
404 if( PAUSED == mState )
408 // Reset the event handler when adaptor resumed
411 mEventHandler->Resume();
414 // Inform observers that we have resumed.
415 for( ObserverContainer::iterator iter = mObservers.begin(), endIter = mObservers.end(); iter != endIter; ++iter )
420 // Trigger processing of events queued up while paused
421 mCore->ProcessEvents();
423 // Do at end to ensure our first update/render after resumption includes the processed messages as well
424 mThreadController->Resume();
426 DALI_LOG_RELEASE_INFO( "Adaptor::Resume: Resumed\n");
430 DALI_LOG_RELEASE_INFO( "Adaptor::Resume: Not resumed [%d]\n", mState );
436 if( RUNNING == mState ||
438 PAUSED_WHILE_HIDDEN == mState )
440 for( ObserverContainer::iterator iter = mObservers.begin(), endIter = mObservers.end(); iter != endIter; ++iter )
445 mThreadController->Stop();
447 // Clear out all the handles to Windows
448 mWindowFrame.clear();
450 // Delete the TTS player
451 for(int i =0; i < Dali::TtsPlayer::MODE_NUM; i++)
455 mTtsPlayers[i].Reset();
459 // Destroy the image loader plugin
460 Internal::Adaptor::ImageLoaderPluginProxy::Destroy();
462 delete mEventHandler;
463 mEventHandler = NULL;
465 delete mNotificationTrigger;
466 mNotificationTrigger = NULL;
468 mCallbackManager->Stop();
472 DALI_LOG_RELEASE_INFO( "Adaptor::Stop\n" );
476 void Adaptor::ContextLost()
478 mCore->GetContextNotifier()->NotifyContextLost(); // Inform stage
481 void Adaptor::ContextRegained()
483 // Inform core, so that texture resources can be reloaded
484 mCore->RecoverFromContextLoss();
486 mCore->GetContextNotifier()->NotifyContextRegained(); // Inform stage
489 void Adaptor::FeedTouchPoint( TouchPoint& point, int timeStamp )
491 mEventHandler->FeedTouchPoint( point, timeStamp );
494 void Adaptor::FeedWheelEvent( WheelEvent& wheelEvent )
496 mEventHandler->FeedWheelEvent( wheelEvent );
499 void Adaptor::FeedKeyEvent( KeyEvent& keyEvent )
501 mEventHandler->FeedKeyEvent( keyEvent );
504 void Adaptor::ReplaceSurface( Any nativeWindow, RenderSurface& newSurface )
506 PositionSize positionSize = newSurface.GetPositionSize();
508 // Let the core know the surface size has changed
509 mCore->SurfaceResized( positionSize.width, positionSize.height );
511 mResizedSignal.Emit( mAdaptor );
513 WindowPane newDefaultWindow;
514 newDefaultWindow.nativeWindow = nativeWindow;
515 newDefaultWindow.surface = &newSurface;
517 WindowPane oldDefaultWindow = mWindowFrame.front();
519 // Update WindowFrame
520 std::vector<WindowPane>::iterator iter = mWindowFrame.begin();
521 iter = mWindowFrame.insert( iter, newDefaultWindow );
523 // Flush the event queue to give the update-render thread chance
524 // to start processing messages for new camera setup etc as soon as possible
527 // This method blocks until the render thread has completed the replace.
528 mThreadController->ReplaceSurface( newDefaultWindow.surface );
530 // Must delete the old Window only after the render thread has completed the replace
531 oldDefaultWindow.surface->DestroySurface();
532 oldDefaultWindow.surface = nullptr;
535 RenderSurface& Adaptor::GetSurface() const
537 WindowPane defaultWindow = mWindowFrame.front();
538 return *(defaultWindow.surface);
541 void Adaptor::ReleaseSurfaceLock()
543 WindowPane defaultWindow = mWindowFrame.front();
544 defaultWindow.surface->ReleaseLock();
547 Dali::TtsPlayer Adaptor::GetTtsPlayer(Dali::TtsPlayer::Mode mode)
549 if(!mTtsPlayers[mode])
551 // Create the TTS player when it needed, because it can reduce launching time.
552 mTtsPlayers[mode] = TtsPlayer::New(mode);
555 return mTtsPlayers[mode];
558 bool Adaptor::AddIdle( CallbackBase* callback, bool hasReturnValue, bool forceAdd )
560 bool idleAdded(false);
562 // Only add an idle if the Adaptor is actually running
563 if( RUNNING == mState || READY == mState || forceAdd )
565 idleAdded = mCallbackManager->AddIdleCallback( callback, hasReturnValue );
571 void Adaptor::RemoveIdle( CallbackBase* callback )
573 mCallbackManager->RemoveIdleCallback( callback );
576 void Adaptor::SetPreRenderCallback( CallbackBase* callback )
578 mThreadController->SetPreRenderCallback( callback );
581 bool Adaptor::AddWindow( Dali::Window* childWindow, const std::string& childWindowName, const std::string& childWindowClassName, const bool& childWindowMode )
583 // This is any Window that is not the main (default) one
584 WindowPane additionalWindow;
585 additionalWindow.instance = childWindow;
586 additionalWindow.window_name = childWindowName;
587 additionalWindow.class_name = childWindowClassName;
588 additionalWindow.window_mode = childWindowMode;
590 // Add the new Window to the Frame - the order is not important
591 mWindowFrame.push_back( additionalWindow );
593 Window& windowImpl = Dali::GetImplementation( *childWindow );
594 windowImpl.SetAdaptor( Get() );
599 bool Adaptor::RemoveWindow( Dali::Window* childWindow )
601 for ( WindowFrames::iterator iter = mWindowFrame.begin(); iter != mWindowFrame.end(); ++iter )
603 if( iter->instance == childWindow )
605 mWindowFrame.erase( iter );
613 bool Adaptor::RemoveWindow( std::string childWindowName )
615 for ( WindowFrames::iterator iter = mWindowFrame.begin(); iter != mWindowFrame.end(); ++iter )
617 if( iter->window_name == childWindowName )
619 mWindowFrame.erase( iter );
627 Dali::Adaptor& Adaptor::Get()
629 DALI_ASSERT_ALWAYS( IsAvailable() && "Adaptor not instantiated" );
630 return gThreadLocalAdaptor->mAdaptor;
633 bool Adaptor::IsAvailable()
635 return gThreadLocalAdaptor != NULL;
638 void Adaptor::SceneCreated()
640 mCore->SceneCreated();
643 Dali::Integration::Core& Adaptor::GetCore()
648 void Adaptor::SetRenderRefreshRate( unsigned int numberOfVSyncsPerRender )
650 mThreadController->SetRenderRefreshRate( numberOfVSyncsPerRender );
653 void Adaptor::SetUseHardwareVSync( bool useHardware )
655 mVSyncMonitor->SetUseHardwareVSync( useHardware );
658 Dali::DisplayConnection& Adaptor::GetDisplayConnectionInterface()
660 DALI_ASSERT_DEBUG( mDisplayConnection && "Display connection not created" );
661 return *mDisplayConnection;
664 GraphicsInterface& Adaptor::GetGraphicsInterface()
666 DALI_ASSERT_DEBUG( mGraphics && "Graphics interface not created" );
670 Dali::Integration::PlatformAbstraction& Adaptor::GetPlatformAbstractionInterface()
672 return *mPlatformAbstraction;
675 TriggerEventInterface& Adaptor::GetProcessCoreEventsTrigger()
677 return *mNotificationTrigger;
680 TriggerEventFactoryInterface& Adaptor::GetTriggerEventFactoryInterface()
682 return mTriggerEventFactory;
685 SocketFactoryInterface& Adaptor::GetSocketFactoryInterface()
687 return mSocketFactory;
690 RenderSurface* Adaptor::GetRenderSurfaceInterface()
692 if( !mWindowFrame.empty())
694 WindowPane defaultWindow = mWindowFrame.front();
695 return defaultWindow.surface;
703 VSyncMonitorInterface* Adaptor::GetVSyncMonitorInterface()
705 return mVSyncMonitor;
708 TraceInterface& Adaptor::GetKernelTraceInterface()
710 return mKernelTracer;
713 TraceInterface& Adaptor::GetSystemTraceInterface()
715 return mSystemTracer;
718 PerformanceInterface* Adaptor::GetPerformanceInterface()
720 return mPerformanceInterface;
723 Integration::PlatformAbstraction& Adaptor::GetPlatformAbstraction() const
725 DALI_ASSERT_DEBUG( mPlatformAbstraction && "PlatformAbstraction not created" );
726 return *mPlatformAbstraction;
729 void Adaptor::SetDragAndDropDetector( DragAndDropDetectorPtr detector )
731 mDragAndDropDetector = detector;
735 mEventHandler->SetDragAndDropDetector( detector );
739 void Adaptor::SetRotationObserver( RotationObserver* observer )
743 mEventHandler->SetRotationObserver( observer );
745 else if( mState == READY )
747 // Set once event handler exists
748 mDeferredRotationObserver = observer;
752 void Adaptor::DestroyTtsPlayer(Dali::TtsPlayer::Mode mode)
754 if(mTtsPlayers[mode])
756 mTtsPlayers[mode].Reset();
760 void Adaptor::SetMinimumPinchDistance(float distance)
762 if( mGestureManager )
764 mGestureManager->SetMinimumPinchDistance(distance);
768 Any Adaptor::GetNativeWindowHandle()
770 WindowPane defaultWindow = mWindowFrame.front();
771 return defaultWindow.nativeWindow;
774 Any Adaptor::GetGraphicsDisplay()
780 auto eglGraphics = static_cast<EglGraphics *>( mGraphics ); // This interface is temporary until Core has been updated to match
782 EglImplementation& eglImpl = eglGraphics->GetEglImplementation();
783 display = eglImpl.GetDisplay();
789 void Adaptor::SetUseRemoteSurface(bool useRemoteSurface)
791 mUseRemoteSurface = useRemoteSurface;
794 void Adaptor::AddObserver( LifeCycleObserver& observer )
796 ObserverContainer::iterator match ( find(mObservers.begin(), mObservers.end(), &observer) );
798 if ( match == mObservers.end() )
800 mObservers.push_back( &observer );
804 void Adaptor::RemoveObserver( LifeCycleObserver& observer )
806 ObserverContainer::iterator match ( find(mObservers.begin(), mObservers.end(), &observer) );
808 if ( match != mObservers.end() )
810 mObservers.erase( match );
814 void Adaptor::QueueCoreEvent(const Dali::Integration::Event& event)
818 mCore->QueueEvent(event);
822 void Adaptor::ProcessCoreEvents()
826 if( mPerformanceInterface )
828 mPerformanceInterface->AddMarker( PerformanceInterface::PROCESS_EVENTS_START );
831 mCore->ProcessEvents();
833 if( mPerformanceInterface )
835 mPerformanceInterface->AddMarker( PerformanceInterface::PROCESS_EVENTS_END );
840 void Adaptor::RequestUpdate( bool forceUpdate )
846 mThreadController->RequestUpdate();
850 case PAUSED_WHILE_HIDDEN:
852 // When Dali applications are partially visible behind the lock-screen,
853 // the indicator must be updated (therefore allow updates in the PAUSED state)
856 mThreadController->RequestUpdateOnce();
868 void Adaptor::RequestProcessEventsOnIdle( bool forceProcess )
870 // Only request a notification if the Adaptor is actually running
871 // and we haven't installed the idle notification
872 if( ( ! mNotificationOnIdleInstalled ) && ( RUNNING == mState || READY == mState || forceProcess ) )
874 mNotificationOnIdleInstalled = AddIdleEnterer( MakeCallback( this, &Adaptor::ProcessCoreEventsFromIdle ), forceProcess );
878 void Adaptor::OnWindowShown()
880 if( PAUSED_WHILE_HIDDEN == mState )
882 // Adaptor can now be resumed
887 // Force a render task
892 DALI_LOG_RELEASE_INFO( "Adaptor::OnWindowShown: Adaptor is not paused state.[%d]\n", mState );
896 void Adaptor::OnWindowHidden()
898 if( RUNNING == mState || READY == mState )
900 if( mState == RUNNING )
904 // Adaptor cannot be resumed until the window is shown
905 mState = PAUSED_WHILE_HIDDEN;
907 else // mState is READY
909 // Pause the adaptor after the state gets RUNNING
910 mState = PAUSED_WHILE_INITIALIZING;
915 DALI_LOG_RELEASE_INFO( "Adaptor::OnWindowHidden: Adaptor is not running state.[%d]\n", mState );
919 // Dali::Internal::Adaptor::Adaptor::OnDamaged
920 void Adaptor::OnDamaged( const DamageArea& area )
922 // This is needed for the case where Dali window is partially obscured
923 RequestUpdate( false );
926 void Adaptor::SurfaceResizePrepare( SurfaceSize surfaceSize )
928 // Let the core know the surface size has changed
929 mCore->SurfaceResized( surfaceSize.GetWidth(), surfaceSize.GetHeight() );
931 mResizedSignal.Emit( mAdaptor );
934 void Adaptor::SurfaceResizeComplete( SurfaceSize surfaceSize )
936 // Flush the event queue to give the update-render thread chance
937 // to start processing messages for new camera setup etc as soon as possible
940 mThreadController->ResizeSurface();
943 void Adaptor::NotifySceneCreated()
945 GetCore().SceneCreated();
947 // Start thread controller after the scene has been created
948 mThreadController->Start();
950 // Process after surface is created (registering to remote surface provider if required)
951 SurfaceInitialized();
953 if( mState != PAUSED_WHILE_INITIALIZING )
957 DALI_LOG_RELEASE_INFO( "Adaptor::NotifySceneCreated: Adaptor is running\n" );
965 mState = PAUSED_WHILE_HIDDEN;
967 DALI_LOG_RELEASE_INFO( "Adaptor::NotifySceneCreated: Adaptor is paused\n" );
971 void Adaptor::NotifyLanguageChanged()
973 mLanguageChangedSignal.Emit( mAdaptor );
976 void Adaptor::RenderOnce()
981 const LogFactoryInterface& Adaptor::GetLogFactory()
983 return *mEnvironmentOptions;
986 void Adaptor::RequestUpdateOnce()
988 if( mThreadController )
990 mThreadController->RequestUpdateOnce();
994 void Adaptor::IndicatorSizeChanged(int height)
996 // Let the core know the indicator height is changed
997 mCore->SetTopMargin(height);
1000 bool Adaptor::ProcessCoreEventsFromIdle()
1002 ProcessCoreEvents();
1004 // the idle handle automatically un-installs itself
1005 mNotificationOnIdleInstalled = false;
1010 Adaptor::Adaptor(Any nativeWindow, Dali::Adaptor& adaptor, RenderSurface* surface, EnvironmentOptions* environmentOptions)
1012 mLanguageChangedSignal(),
1013 mAdaptor( adaptor ),
1016 mThreadController( nullptr ),
1017 mVSyncMonitor( nullptr ),
1018 mGraphics( nullptr ),
1019 mDisplayConnection( nullptr ),
1021 mPlatformAbstraction( nullptr ),
1022 mEventHandler( nullptr ),
1023 mCallbackManager( nullptr ),
1024 mNotificationOnIdleInstalled( false ),
1025 mNotificationTrigger( nullptr ),
1026 mGestureManager( nullptr ),
1027 mDaliFeedbackPlugin(),
1028 mFeedbackController( nullptr ),
1031 mDragAndDropDetector(),
1032 mDeferredRotationObserver( nullptr ),
1033 mEnvironmentOptions( environmentOptions ? environmentOptions : new EnvironmentOptions /* Create the options if not provided */),
1034 mPerformanceInterface( nullptr ),
1037 mTriggerEventFactory(),
1038 mObjectProfiler( nullptr ),
1040 mEnvironmentOptionsOwned( environmentOptions ? false : true /* If not provided then we own the object */ ),
1041 mUseRemoteSurface( false )
1043 DALI_ASSERT_ALWAYS( !IsAvailable() && "Cannot create more than one Adaptor per thread" );
1045 WindowPane defaultWindow;
1046 defaultWindow.nativeWindow = nativeWindow;
1047 defaultWindow.surface = surface;
1049 std::vector<WindowPane>::iterator iter = mWindowFrame.begin();
1050 iter = mWindowFrame.insert( iter, defaultWindow );
1052 gThreadLocalAdaptor = this;
1057 void Adaptor::SetViewMode( ViewMode viewMode )
1059 WindowPane defaultWindow = mWindowFrame.front();
1060 defaultWindow.surface->SetViewMode( viewMode );
1062 mCore->SetViewMode( viewMode );
1065 ViewMode Adaptor::GetViewMode() const
1067 return mCore->GetViewMode();
1070 void Adaptor::SetStereoBase( float stereoBase )
1072 mCore->SetStereoBase( stereoBase );
1075 float Adaptor::GetStereoBase() const
1077 return mCore->GetStereoBase();
1080 void Adaptor::SetRootLayoutDirection( std::string locale )
1082 Dali::Stage stage = Dali::Stage::GetCurrent();
1084 stage.GetRootLayer().SetProperty( Dali::Actor::Property::LAYOUT_DIRECTION,
1085 static_cast< LayoutDirection::Type >( Internal::Adaptor::Locale::GetDirection( std::string( locale ) ) ) );
1088 bool Adaptor::AddIdleEnterer( CallbackBase* callback, bool forceAdd )
1090 bool idleAdded( false );
1092 // Only add an idle if the Adaptor is actually running
1093 if( RUNNING == mState || READY == mState || forceAdd )
1095 idleAdded = mCallbackManager->AddIdleEntererCallback( callback );
1101 void Adaptor::RemoveIdleEnterer( CallbackBase* callback )
1103 mCallbackManager->RemoveIdleEntererCallback( callback );
1106 } // namespace Adaptor
1108 } // namespace Internal