2 * Copyright (c) 2021 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/application-impl.h>
22 #include <dali/devel-api/common/singleton-service.h>
23 #include <dali/integration-api/debug.h>
24 #include <dali/public-api/object/object-registry.h>
27 #include <dali/devel-api/adaptor-framework/accessibility-impl.h>
28 #include <dali/devel-api/adaptor-framework/style-monitor.h>
29 #include <dali/devel-api/text-abstraction/font-client.h>
30 #include <dali/internal/adaptor/common/adaptor-impl.h>
31 #include <dali/internal/adaptor/common/framework.h>
32 #include <dali/internal/adaptor/common/lifecycle-controller-impl.h>
33 #include <dali/internal/system/common/command-line-options.h>
34 #include <dali/internal/window-system/common/render-surface-factory.h>
35 #include <dali/internal/window-system/common/window-impl.h>
36 #include <dali/internal/window-system/common/window-render-surface.h>
37 #include <dali/internal/window-system/common/window-system.h>
39 // To disable a macro with the same name from one of OpenGL headers
44 namespace TizenPlatform
46 class TizenPlatformAbstraction;
58 ApplicationPtr Application::gPreInitializedApplication(NULL);
60 ApplicationPtr Application::New(
63 const std::string& stylesheet,
64 Dali::Application::WINDOW_MODE windowMode,
65 const PositionSize& positionSize,
66 Framework::Type applicationType,
69 ApplicationPtr application(new Application(argc, argv, stylesheet, windowMode, positionSize, applicationType, type));
73 void Application::PreInitialize(int* argc, char** argv[])
75 if(!gPreInitializedApplication)
77 Dali::TextAbstraction::FontClientPreInitialize();
79 gPreInitializedApplication = new Application(argc, argv, "", Dali::Application::OPAQUE, PositionSize(), Framework::NORMAL, WindowType::NORMAL);
80 gPreInitializedApplication->CreateWindow(); // Only create window
81 gPreInitializedApplication->mLaunchpadState = Launchpad::PRE_INITIALIZED;
85 Application::Application(int* argc, char** argv[], const std::string& stylesheet, Dali::Application::WINDOW_MODE windowMode, const PositionSize& positionSize, Framework::Type applicationType, WindowType type)
92 mLanguageChangedSignal(),
93 mRegionChangedSignal(),
96 mCommandLineOptions(nullptr),
97 mAdaptorBuilder(nullptr),
100 mMainWindowMode(windowMode),
102 mStylesheet(stylesheet),
103 mEnvironmentOptions(),
104 mWindowPositionSize(positionSize),
105 mLaunchpadState(Launchpad::NONE),
106 mDefaultWindowType(type),
109 // Get mName from environment options
110 mMainWindowName = mEnvironmentOptions.GetWindowName();
111 if(mMainWindowName.empty() && argc && (*argc > 0))
113 // Set mName from command-line args if environment option not set
114 mMainWindowName = (*argv)[0];
117 mCommandLineOptions = new CommandLineOptions(argc, argv);
118 mFramework = new Framework(*this, argc, argv, applicationType);
119 mUseRemoteSurface = (applicationType == Framework::WATCH);
122 Application::~Application()
124 SingletonService service = SingletonService::Get();
125 // Note this can be false i.e. if Application has never created a Core instance
128 service.UnregisterAll();
133 delete mAdaptorBuilder;
134 delete mCommandLineOptions;
138 void Application::StoreWindowPositionSize(PositionSize positionSize)
140 mWindowPositionSize = positionSize;
143 void Application::ChangePreInitializedWindowSize()
145 int screenWidth, screenHeight;
146 Dali::Internal::Adaptor::WindowSystem::GetScreenSize(screenWidth, screenHeight);
148 if(mWindowPositionSize != PositionSize(0, 0, 0, 0))
150 Dali::DevelWindow::SetPositionSize(mMainWindow, mWindowPositionSize);
152 else if(mCommandLineOptions->stageWidth > 0 && mCommandLineOptions->stageHeight > 0)
154 // Command line options override environment options and full screen
155 mWindowPositionSize.width = mCommandLineOptions->stageWidth;
156 mWindowPositionSize.height = mCommandLineOptions->stageHeight;
157 mMainWindow.SetSize(Dali::Window::WindowSize(mWindowPositionSize.width, mWindowPositionSize.height));
159 else if(mEnvironmentOptions.GetWindowWidth() && mEnvironmentOptions.GetWindowHeight())
161 // Environment options override full screen functionality if command line arguments not provided
162 mWindowPositionSize.width = mEnvironmentOptions.GetWindowWidth();
163 mWindowPositionSize.height = mEnvironmentOptions.GetWindowHeight();
164 mMainWindow.SetSize(Dali::Window::WindowSize(mWindowPositionSize.width, mWindowPositionSize.height));
166 else if(screenWidth != mWindowPositionSize.width || screenHeight != mWindowPositionSize.height)
168 //Some apps can receive screen size differently after launching by specifying size in manifest.
169 mWindowPositionSize.width = screenWidth;
170 mWindowPositionSize.height = screenHeight;
171 mMainWindow.SetSize(Dali::Window::WindowSize(mWindowPositionSize.width, mWindowPositionSize.height));
175 void Application::CreateWindow()
177 if(mWindowPositionSize.width == 0 && mWindowPositionSize.height == 0)
179 if(mCommandLineOptions->stageWidth > 0 && mCommandLineOptions->stageHeight > 0)
181 // Command line options override environment options and full screen
182 mWindowPositionSize.width = mCommandLineOptions->stageWidth;
183 mWindowPositionSize.height = mCommandLineOptions->stageHeight;
185 else if(mEnvironmentOptions.GetWindowWidth() && mEnvironmentOptions.GetWindowHeight())
187 // Environment options override full screen functionality if command line arguments not provided
188 mWindowPositionSize.width = mEnvironmentOptions.GetWindowWidth();
189 mWindowPositionSize.height = mEnvironmentOptions.GetWindowHeight();
193 const std::string& windowClassName = mEnvironmentOptions.GetWindowClassName();
195 Internal::Adaptor::Window* window = Internal::Adaptor::Window::New(mWindowPositionSize, mMainWindowName, windowClassName, mDefaultWindowType, mMainWindowMode == Dali::Application::TRANSPARENT);
196 mMainWindow = Dali::Window(window);
198 // Quit the application when the window is closed
199 GetImplementation(mMainWindow).DeleteRequestSignal().Connect(mSlotDelegate, &Application::Quit);
202 void Application::CreateAdaptor()
204 DALI_ASSERT_ALWAYS(mMainWindow && "Window required to create adaptor");
206 auto graphicsFactory = mAdaptorBuilder->GetGraphicsFactory();
208 Integration::SceneHolder sceneHolder = Integration::SceneHolder(&Dali::GetImplementation(mMainWindow));
210 mAdaptor = Adaptor::New(graphicsFactory, sceneHolder, &mEnvironmentOptions);
212 Adaptor::GetImplementation(*mAdaptor).SetUseRemoteSurface(mUseRemoteSurface);
215 void Application::CreateAdaptorBuilder()
217 mAdaptorBuilder = new AdaptorBuilder(mEnvironmentOptions);
220 void Application::MainLoop()
222 // Run the application
226 void Application::Lower()
228 // Lower the application without quitting it.
232 void Application::Quit()
234 // Actually quit the application.
235 // Force a call to Quit even if adaptor is not running.
236 Internal::Adaptor::Adaptor::GetImplementation(*mAdaptor).AddIdle(MakeCallback(this, &Application::QuitFromMainLoop), false, true);
239 void Application::QuitFromMainLoop()
241 Accessibility::Bridge::GetCurrentBridge()->ApplicationHidden();
242 Accessibility::Bridge::GetCurrentBridge()->Terminate();
247 // This will trigger OnTerminate(), below, after the main loop has completed.
250 void Application::OnInit()
252 mFramework->AddAbortCallback(MakeCallback(this, &Application::QuitFromMainLoop));
254 CreateAdaptorBuilder();
255 // If an application was pre-initialized, a window was made in advance
256 if(mLaunchpadState == Launchpad::NONE)
263 if(mLaunchpadState == Launchpad::PRE_INITIALIZED)
265 ChangePreInitializedWindowSize();
270 Accessibility::Accessible::SetObjectRegistry(mAdaptor->GetObjectRegistry());
272 if(!mStylesheet.empty())
274 Dali::StyleMonitor::Get().SetTheme(mStylesheet);
277 // Wire up the LifecycleController
278 Dali::LifecycleController lifecycleController = Dali::LifecycleController::Get();
280 InitSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnInit);
281 TerminateSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnTerminate);
282 PauseSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnPause);
283 ResumeSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnResume);
284 ResetSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnReset);
285 LanguageChangedSignal().Connect(&GetImplementation(lifecycleController), &LifecycleController::OnLanguageChanged);
287 Dali::Application application(this);
288 mInitSignal.Emit(application);
290 mAdaptor->NotifySceneCreated();
293 void Application::OnTerminate()
295 // We've been told to quit by AppCore, ecore_x_destroy has been called, need to quit synchronously
296 // delete the window as ecore_x has been destroyed by AppCore
298 Dali::Application application(this);
299 mTerminateSignal.Emit(application);
303 // Ensure that the render-thread is not using the surface(window) after we delete it
307 mMainWindow.Reset(); // This only resets (clears) the default Window
310 void Application::OnPause()
312 // A DALi app should handle Pause/Resume events.
313 // DALi just delivers the framework Pause event to the application, but not actually pause DALi core.
314 // Pausing DALi core only occurs on the Window Hidden framework event
315 Dali::Application application(this);
316 mPauseSignal.Emit(application);
319 void Application::OnResume()
321 // Emit the signal first so the application can queue any messages before we do an update/render
322 // This ensures we do not just redraw the last frame before pausing if that's not required
323 Dali::Application application(this);
324 mResumeSignal.Emit(application);
326 // DALi just delivers the framework Resume event to the application.
327 // Resuming DALi core only occurs on the Window Show framework event
329 // Trigger processing of events queued up while paused
330 CoreEventInterface& coreEventInterface = Internal::Adaptor::Adaptor::GetImplementation(GetAdaptor());
331 coreEventInterface.ProcessCoreEvents();
334 void Application::OnReset()
337 * usually, reset callback was called when a caller request to launch this application via aul.
338 * because Application class already handled initialization in OnInit(), OnReset do nothing.
340 Dali::Application application(this);
341 mResetSignal.Emit(application);
344 void Application::OnAppControl(void* data)
346 Dali::Application application(this);
347 mAppControlSignal.Emit(application, data);
350 void Application::OnLanguageChanged()
352 mAdaptor->NotifyLanguageChanged();
353 Dali::Application application(this);
354 mLanguageChangedSignal.Emit(application);
357 void Application::OnRegionChanged()
359 Dali::Application application(this);
360 mRegionChangedSignal.Emit(application);
363 void Application::OnBatteryLow(Dali::DeviceStatus::Battery::Status status)
365 Dali::Application application(this);
366 mLowBatterySignal.Emit(status);
369 void Application::OnMemoryLow(Dali::DeviceStatus::Memory::Status status)
371 Dali::Application application(this);
372 mLowMemorySignal.Emit(status);
375 void Application::OnSurfaceCreated(Any newSurface)
377 void* newWindow = AnyCast<void*>(newSurface);
378 void* oldWindow = AnyCast<void*>(mMainWindow.GetNativeHandle());
379 if(oldWindow != newWindow)
381 auto renderSurfaceFactory = Dali::Internal::Adaptor::GetRenderSurfaceFactory();
382 std::unique_ptr<WindowRenderSurface> newSurfacePtr = renderSurfaceFactory->CreateWindowRenderSurface(PositionSize(), newSurface, true);
384 mAdaptor->ReplaceSurface(mMainWindow, *newSurfacePtr.release());
388 void Application::OnSurfaceDestroyed(Any surface)
392 bool Application::AddIdle(CallbackBase* callback, bool hasReturnValue)
394 return mAdaptor->AddIdle(callback, hasReturnValue);
397 std::string Application::GetRegion() const
399 return mFramework->GetRegion();
402 std::string Application::GetLanguage() const
404 return mFramework->GetLanguage();
407 Dali::ObjectRegistry Application::GetObjectRegistry() const
409 Dali::ObjectRegistry objectRegistry;
412 objectRegistry = mAdaptor->GetObjectRegistry();
414 return objectRegistry;
417 Dali::Adaptor& Application::GetAdaptor()
422 Dali::Window Application::GetWindow()
427 std::string Application::GetResourcePath()
429 return Internal::Adaptor::Framework::GetResourcePath();
432 std::string Application::GetDataPath()
434 return Internal::Adaptor::Framework::GetDataPath();
437 void Application::SetStyleSheet(const std::string& stylesheet)
439 mStylesheet = stylesheet;
442 void Application::SetCommandLineOptions(int* argc, char** argv[])
444 delete mCommandLineOptions;
446 mCommandLineOptions = new CommandLineOptions(argc, argv);
448 mFramework->SetCommandLineOptions(argc, argv);
451 void Application::SetDefaultWindowType(WindowType type)
453 mDefaultWindowType = type;
454 mMainWindow.SetType(type);
457 ApplicationPtr Application::GetPreInitializedApplication()
459 return gPreInitializedApplication;
462 Graphics::Controller& Application::GetController()
464 auto& adaptor = Internal::Adaptor::Adaptor::GetImplementation(*mAdaptor);
465 return adaptor.GetGraphicsInterface().GetController();
468 } // namespace Adaptor
470 } // namespace Internal