Merge "[ATSPI] Sort children using middle line" into devel/master
[platform/core/uifw/dali-adaptor.git] / dali / internal / window-system / common / window-impl.cpp
1 /*
2  * Copyright (c) 2021 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/window-system/common/window-impl.h>
20
21 // EXTERNAL HEADERS
22 #include <dali/devel-api/adaptor-framework/orientation.h>
23 #include <dali/integration-api/core.h>
24 #include <dali/integration-api/events/touch-event-integ.h>
25 #include <dali/public-api/actors/actor.h>
26 #include <dali/public-api/actors/camera-actor.h>
27 #include <dali/public-api/actors/layer.h>
28 #include <dali/public-api/adaptor-framework/window-enumerations.h>
29 #include <dali/public-api/render-tasks/render-task-list.h>
30 #include <dali/public-api/render-tasks/render-task.h>
31 #include <dali/public-api/rendering/frame-buffer.h>
32 #include <thread>
33
34 // INTERNAL HEADERS
35 #include <dali/devel-api/adaptor-framework/accessibility-impl.h>
36 #include <dali/integration-api/adaptor-framework/render-surface-interface.h>
37 #include <dali/internal/graphics/gles/egl-graphics.h>
38 #include <dali/internal/window-system/common/event-handler.h>
39 #include <dali/internal/window-system/common/orientation-impl.h>
40 #include <dali/internal/window-system/common/render-surface-factory.h>
41 #include <dali/internal/window-system/common/window-base.h>
42 #include <dali/internal/window-system/common/window-factory.h>
43 #include <dali/internal/window-system/common/window-render-surface.h>
44 #include <dali/internal/window-system/common/window-system.h>
45 #include <dali/internal/window-system/common/window-visibility-observer.h>
46
47 namespace Dali
48 {
49 namespace Internal
50 {
51 namespace Adaptor
52 {
53 namespace
54 {
55 #if defined(DEBUG_ENABLED)
56 Debug::Filter* gWindowLogFilter = Debug::Filter::New(Debug::NoLogging, false, "LOG_WINDOW");
57 #endif
58
59 } // unnamed namespace
60
61 Window* Window::New(const PositionSize& positionSize, const std::string& name, const std::string& className, Dali::WindowType type, bool isTransparent)
62 {
63   Any surface;
64   return Window::New(surface, positionSize, name, className, type, isTransparent);
65 }
66
67 Window* Window::New(Any surface, const PositionSize& positionSize, const std::string& name, const std::string& className, Dali::WindowType type, bool isTransparent)
68 {
69   Window* window         = new Window();
70   window->mIsTransparent = isTransparent;
71   window->Initialize(surface, positionSize, name, className, type);
72   return window;
73 }
74
75 Window::Window()
76 : mWindowSurface(nullptr),
77   mWindowBase(),
78   mIsTransparent(false),
79   mIsFocusAcceptable(true),
80   mIconified(false),
81   mOpaqueState(false),
82   mWindowRotationAcknowledgement(false),
83   mParentWindow(NULL),
84   mPreferredAngle(static_cast<int>(WindowOrientation::NO_ORIENTATION_PREFERENCE)),
85   mRotationAngle(0),
86   mWindowWidth(0),
87   mWindowHeight(0),
88   mOrientationMode(Internal::Adaptor::Window::OrientationMode::PORTRAIT),
89   mNativeWindowId(-1),
90   mDeleteRequestSignal(),
91   mFocusChangeSignal(),
92   mResizeSignal(),
93   mVisibilityChangedSignal(),
94   mTransitionEffectEventSignal(),
95   mKeyboardRepeatSettingsChangedSignal()
96 {
97 }
98
99 Window::~Window()
100 {
101   if(mAdaptor)
102   {
103     auto bridge     = Accessibility::Bridge::GetCurrentBridge();
104     auto rootLayer  = mScene.GetRootLayer();
105     auto accessible = Accessibility::Accessible::Get(rootLayer);
106     bridge->RemoveTopLevelWindow(accessible);
107
108     mAdaptor->RemoveWindow(this);
109   }
110
111   if(mEventHandler)
112   {
113     mEventHandler->RemoveObserver(*this);
114   }
115 }
116
117 void Window::Initialize(Any surface, const PositionSize& positionSize, const std::string& name, const std::string& className, WindowType type)
118 {
119   // Create a window render surface
120   auto renderSurfaceFactory = Dali::Internal::Adaptor::GetRenderSurfaceFactory();
121   mSurface                  = renderSurfaceFactory->CreateWindowRenderSurface(positionSize, surface, mIsTransparent);
122   mWindowSurface            = static_cast<WindowRenderSurface*>(mSurface.get());
123
124   // Get a window base
125   mWindowBase = mWindowSurface->GetWindowBase();
126
127   // Set Window Type
128   mWindowBase->SetType(type);
129
130   // Initialize for Ime window type
131   if(type == WindowType::IME)
132   {
133     mWindowBase->InitializeIme();
134     mWindowSurface->InitializeImeSurface();
135   }
136
137   // Connect signals
138   mWindowBase->IconifyChangedSignal().Connect(this, &Window::OnIconifyChanged);
139   mWindowBase->FocusChangedSignal().Connect(this, &Window::OnFocusChanged);
140   mWindowBase->DeleteRequestSignal().Connect(this, &Window::OnDeleteRequest);
141   mWindowBase->TransitionEffectEventSignal().Connect(this, &Window::OnTransitionEffectEvent);
142   mWindowBase->KeyboardRepeatSettingsChangedSignal().Connect(this, &Window::OnKeyboardRepeatSettingsChanged);
143   mWindowBase->WindowRedrawRequestSignal().Connect(this, &Window::OnWindowRedrawRequest);
144   mWindowBase->UpdatePositionSizeSignal().Connect(this, &Window::OnUpdatePositionSize);
145
146   mWindowSurface->OutputTransformedSignal().Connect(this, &Window::OnOutputTransformed);
147
148   AddAuxiliaryHint("wm.policy.win.user.geometry", "1");
149
150   SetClass(name, className);
151
152   mOrientation = Orientation::New(this);
153
154   // Get OrientationMode
155   int screenWidth, screenHeight;
156   WindowSystem::GetScreenSize(screenWidth, screenHeight);
157   if(screenWidth > screenHeight)
158   {
159     mOrientationMode = Internal::Adaptor::Window::OrientationMode::LANDSCAPE;
160   }
161   else
162   {
163     mOrientationMode = Internal::Adaptor::Window::OrientationMode::PORTRAIT;
164   }
165   // For Debugging
166   mNativeWindowId = mWindowBase->GetNativeWindowId();
167 }
168
169 void Window::OnAdaptorSet(Dali::Adaptor& adaptor)
170 {
171   mEventHandler = EventHandlerPtr(new EventHandler(mWindowSurface->GetWindowBase(), *mAdaptor));
172   mEventHandler->AddObserver(*this);
173
174   auto bridge     = Accessibility::Bridge::GetCurrentBridge();
175   auto rootLayer  = mScene.GetRootLayer();
176   auto accessible = Accessibility::Accessible::Get(rootLayer, true);
177   bridge->AddTopLevelWindow(accessible);
178
179   // If you call the 'Show' before creating the adaptor, the application cannot know the app resource id.
180   // The show must be called after the adaptor is initialized.
181   Show();
182 }
183
184 void Window::OnSurfaceSet(Dali::RenderSurfaceInterface* surface)
185 {
186   mWindowSurface = static_cast<WindowRenderSurface*>(surface);
187 }
188
189 void Window::SetClass(std::string name, std::string className)
190 {
191   mName      = name;
192   mClassName = className;
193   mWindowBase->SetClass(name, className);
194 }
195
196 std::string Window::GetClassName() const
197 {
198   return mClassName;
199 }
200
201 void Window::Raise()
202 {
203   mWindowBase->Raise();
204
205   mSurface->SetFullSwapNextFrame();
206
207   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Raise() \n", this, mNativeWindowId);
208 }
209
210 void Window::Lower()
211 {
212   mWindowBase->Lower();
213
214   mSurface->SetFullSwapNextFrame();
215
216   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Lower() \n", this, mNativeWindowId);
217 }
218
219 void Window::Activate()
220 {
221   mWindowBase->Activate();
222
223   mSurface->SetFullSwapNextFrame();
224
225   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Activate() \n", this, mNativeWindowId);
226 }
227
228 uint32_t Window::GetLayerCount() const
229 {
230   return mScene.GetLayerCount();
231 }
232
233 Dali::Layer Window::GetLayer(uint32_t depth) const
234 {
235   return mScene.GetLayer(depth);
236 }
237
238 Dali::RenderTaskList Window::GetRenderTaskList() const
239 {
240   return mScene.GetRenderTaskList();
241 }
242
243 void Window::AddAvailableOrientation(WindowOrientation orientation)
244 {
245   if(IsOrientationAvailable(orientation) == false)
246   {
247     return;
248   }
249
250   bool found          = false;
251   int  convertedAngle = ConvertToAngle(orientation);
252   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), AddAvailableOrientation: %d\n", this, mNativeWindowId, convertedAngle);
253   for(std::size_t i = 0; i < mAvailableAngles.size(); i++)
254   {
255     if(mAvailableAngles[i] == convertedAngle)
256     {
257       found = true;
258       break;
259     }
260   }
261
262   if(!found)
263   {
264     mAvailableAngles.push_back(convertedAngle);
265     SetAvailableAnlges(mAvailableAngles);
266   }
267 }
268
269 void Window::RemoveAvailableOrientation(WindowOrientation orientation)
270 {
271   if(IsOrientationAvailable(orientation) == false)
272   {
273     return;
274   }
275
276   int convertedAngle = ConvertToAngle(orientation);
277   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), RemoveAvailableOrientation: %d\n", this, mNativeWindowId, convertedAngle);
278   for(std::vector<int>::iterator iter = mAvailableAngles.begin();
279       iter != mAvailableAngles.end();
280       ++iter)
281   {
282     if(*iter == convertedAngle)
283     {
284       mAvailableAngles.erase(iter);
285       break;
286     }
287   }
288
289   SetAvailableAnlges(mAvailableAngles);
290 }
291
292 void Window::SetPreferredOrientation(WindowOrientation orientation)
293 {
294   if(orientation < WindowOrientation::NO_ORIENTATION_PREFERENCE || orientation > WindowOrientation::LANDSCAPE_INVERSE)
295   {
296     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::CheckOrientation: Invalid input orientation [%d]\n", orientation);
297     return;
298   }
299   mPreferredAngle = ConvertToAngle(orientation);
300   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), SetPreferredOrientation: %d\n", this, mNativeWindowId, mPreferredAngle);
301   mWindowBase->SetPreferredAngle(mPreferredAngle);
302 }
303
304 WindowOrientation Window::GetPreferredOrientation()
305 {
306   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), GetPreferredOrientation: %d\n", this, mNativeWindowId, mPreferredAngle);
307   WindowOrientation preferredOrientation = ConvertToOrientation(mPreferredAngle);
308   return preferredOrientation;
309 }
310
311 void Window::SetPositionSizeWithOrientation(PositionSize positionSize, WindowOrientation orientation)
312 {
313   int angle = ConvertToAngle(orientation);
314   mWindowBase->SetPositionSizeWithAngle(positionSize, angle);
315 }
316
317 void Window::SetAvailableAnlges(const std::vector<int>& angles)
318 {
319   if(angles.size() > 4)
320   {
321     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::SetAvailableAnlges: Invalid vector size! [%d]\n", angles.size());
322     return;
323   }
324
325   mWindowBase->SetAvailableAnlges(angles);
326 }
327
328 int Window::ConvertToAngle(WindowOrientation orientation)
329 {
330   int convertAngle = static_cast<int>(orientation);
331   if(mOrientationMode == Internal::Adaptor::Window::OrientationMode::LANDSCAPE)
332   {
333     switch(orientation)
334     {
335       case WindowOrientation::LANDSCAPE:
336       {
337         convertAngle = 0;
338         break;
339       }
340       case WindowOrientation::PORTRAIT:
341       {
342         convertAngle = 90;
343         break;
344       }
345       case WindowOrientation::LANDSCAPE_INVERSE:
346       {
347         convertAngle = 180;
348         break;
349       }
350       case WindowOrientation::PORTRAIT_INVERSE:
351       {
352         convertAngle = 270;
353         break;
354       }
355       case WindowOrientation::NO_ORIENTATION_PREFERENCE:
356       {
357         convertAngle = -1;
358         break;
359       }
360     }
361   }
362   return convertAngle;
363 }
364
365 WindowOrientation Window::ConvertToOrientation(int angle) const
366 {
367   WindowOrientation orientation = static_cast<WindowOrientation>(angle);
368   if(mOrientationMode == Internal::Adaptor::Window::OrientationMode::LANDSCAPE)
369   {
370     switch(angle)
371     {
372       case 0:
373       {
374         orientation = WindowOrientation::LANDSCAPE;
375         break;
376       }
377       case 90:
378       {
379         orientation = WindowOrientation::PORTRAIT;
380         break;
381       }
382       case 180:
383       {
384         orientation = WindowOrientation::LANDSCAPE_INVERSE;
385         break;
386       }
387       case 270:
388       {
389         orientation = WindowOrientation::PORTRAIT_INVERSE;
390         break;
391       }
392       case -1:
393       {
394         orientation = WindowOrientation::NO_ORIENTATION_PREFERENCE;
395         break;
396       }
397     }
398   }
399   return orientation;
400 }
401
402 bool Window::IsOrientationAvailable(WindowOrientation orientation) const
403 {
404   if(orientation <= WindowOrientation::NO_ORIENTATION_PREFERENCE || orientation > WindowOrientation::LANDSCAPE_INVERSE)
405   {
406     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::IsOrientationAvailable: Invalid input orientation [%d]\n", orientation);
407     return false;
408   }
409   return true;
410 }
411
412 Dali::Any Window::GetNativeHandle() const
413 {
414   return mWindowSurface->GetNativeWindow();
415 }
416
417 void Window::SetAcceptFocus(bool accept)
418 {
419   mIsFocusAcceptable = accept;
420
421   mWindowBase->SetAcceptFocus(accept);
422 }
423
424 bool Window::IsFocusAcceptable() const
425 {
426   return mIsFocusAcceptable;
427 }
428
429 void Window::Show()
430 {
431   mVisible = true;
432
433   mWindowBase->Show();
434
435   if(!mIconified)
436   {
437     Dali::Window handle(this);
438     mVisibilityChangedSignal.Emit(handle, true);
439
440     WindowVisibilityObserver* observer(mAdaptor);
441     observer->OnWindowShown();
442   }
443
444   mSurface->SetFullSwapNextFrame();
445
446   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Show(): iconified = %d, visible = %d\n", this, mNativeWindowId, mIconified, mVisible);
447 }
448
449 void Window::Hide()
450 {
451   mVisible = false;
452
453   mWindowBase->Hide();
454
455   if(!mIconified)
456   {
457     Dali::Window handle(this);
458     mVisibilityChangedSignal.Emit(handle, false);
459
460     WindowVisibilityObserver* observer(mAdaptor);
461     observer->OnWindowHidden();
462   }
463
464   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Hide(): iconified = %d, visible = %d\n", this, mNativeWindowId, mIconified, mVisible);
465 }
466
467 bool Window::IsVisible() const
468 {
469   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), IsVisible(): iconified = %d, visible = %d\n", this, mNativeWindowId, mIconified, mVisible);
470   return mVisible && !mIconified;
471 }
472
473 unsigned int Window::GetSupportedAuxiliaryHintCount() const
474 {
475   return mWindowBase->GetSupportedAuxiliaryHintCount();
476 }
477
478 std::string Window::GetSupportedAuxiliaryHint(unsigned int index) const
479 {
480   return mWindowBase->GetSupportedAuxiliaryHint(index);
481 }
482
483 unsigned int Window::AddAuxiliaryHint(const std::string& hint, const std::string& value)
484 {
485   return mWindowBase->AddAuxiliaryHint(hint, value);
486 }
487
488 bool Window::RemoveAuxiliaryHint(unsigned int id)
489 {
490   return mWindowBase->RemoveAuxiliaryHint(id);
491 }
492
493 bool Window::SetAuxiliaryHintValue(unsigned int id, const std::string& value)
494 {
495   return mWindowBase->SetAuxiliaryHintValue(id, value);
496 }
497
498 std::string Window::GetAuxiliaryHintValue(unsigned int id) const
499 {
500   return mWindowBase->GetAuxiliaryHintValue(id);
501 }
502
503 unsigned int Window::GetAuxiliaryHintId(const std::string& hint) const
504 {
505   return mWindowBase->GetAuxiliaryHintId(hint);
506 }
507
508 void Window::SetInputRegion(const Rect<int>& inputRegion)
509 {
510   Rect<int> convertRegion = RecalculateRect(inputRegion);
511
512   DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window (%p), WinId (%d), SetInputRegion, RecalculateRegion, (%d,%d), (%d x %d)\n", this, mNativeWindowId, convertRegion.x, convertRegion.y, convertRegion.width, convertRegion.height);
513
514   mWindowBase->SetInputRegion(convertRegion);
515 }
516
517 void Window::SetType(WindowType type)
518 {
519   mWindowBase->SetType(type);
520 }
521
522 WindowType Window::GetType() const
523 {
524   return mWindowBase->GetType();
525 }
526
527 WindowOperationResult Window::SetNotificationLevel(WindowNotificationLevel level)
528 {
529   WindowType type = mWindowBase->GetType();
530   if(type != WindowType::NOTIFICATION)
531   {
532     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::SetNotificationLevel: Not supported window type [%d]\n", type);
533     return WindowOperationResult::INVALID_OPERATION;
534   }
535
536   return mWindowBase->SetNotificationLevel(level);
537 }
538
539 WindowNotificationLevel Window::GetNotificationLevel() const
540 {
541   WindowType type = mWindowBase->GetType();
542   if(type != WindowType::NOTIFICATION)
543   {
544     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::GetNotificationLevel: Not supported window type [%d]\n", type);
545     return WindowNotificationLevel::NONE;
546   }
547
548   return mWindowBase->GetNotificationLevel();
549 }
550
551 void Window::SetOpaqueState(bool opaque)
552 {
553   mOpaqueState = opaque;
554
555   mWindowBase->SetOpaqueState(opaque);
556
557   DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::SetOpaqueState: opaque = %d\n", opaque);
558 }
559
560 bool Window::IsOpaqueState() const
561 {
562   return mOpaqueState;
563 }
564
565 WindowOperationResult Window::SetScreenOffMode(WindowScreenOffMode screenOffMode)
566 {
567   return mWindowBase->SetScreenOffMode(screenOffMode);
568 }
569
570 WindowScreenOffMode Window::GetScreenOffMode() const
571 {
572   return mWindowBase->GetScreenOffMode();
573 }
574
575 WindowOperationResult Window::SetBrightness(int brightness)
576 {
577   if(brightness < 0 || brightness > 100)
578   {
579     DALI_LOG_INFO(gWindowLogFilter, Debug::Verbose, "Window::SetBrightness: Invalid brightness value [%d]\n", brightness);
580     return WindowOperationResult::INVALID_OPERATION;
581   }
582
583   return mWindowBase->SetBrightness(brightness);
584 }
585
586 int Window::GetBrightness() const
587 {
588   return mWindowBase->GetBrightness();
589 }
590
591 void Window::SetSize(Dali::Window::WindowSize size)
592 {
593   PositionSize oldRect = mSurface->GetPositionSize();
594
595   mWindowSurface->MoveResize(PositionSize(oldRect.x, oldRect.y, size.GetWidth(), size.GetHeight()));
596
597   PositionSize newRect = mSurface->GetPositionSize();
598
599   // When surface size is updated, inform adaptor of resizing and emit ResizeSignal
600   if((oldRect.width != newRect.width) || (oldRect.height != newRect.height))
601   {
602     Uint16Pair newSize(newRect.width, newRect.height);
603
604     SurfaceResized();
605
606     mAdaptor->SurfaceResizePrepare(mSurface.get(), newSize);
607
608     DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), SetSize(): resize signal [%d x %d]\n", this, mNativeWindowId, newRect.width, newRect.height);
609
610     Dali::Window handle(this);
611     mResizeSignal.Emit(handle, newSize);
612
613     mAdaptor->SurfaceResizeComplete(mSurface.get(), newSize);
614   }
615
616   mSurface->SetFullSwapNextFrame();
617
618   Dali::Accessibility::Accessible::Get(mScene.GetRootLayer(), true)->EmitBoundsChanged(Dali::Rect<>(oldRect.x, oldRect.y, size.GetWidth(), size.GetHeight()));
619 }
620
621 Dali::Window::WindowSize Window::GetSize() const
622 {
623   PositionSize positionSize = mSurface->GetPositionSize();
624
625   return Dali::Window::WindowSize(positionSize.width, positionSize.height);
626 }
627
628 void Window::SetPosition(Dali::Window::WindowPosition position)
629 {
630   PositionSize oldRect = mSurface->GetPositionSize();
631
632   mWindowSurface->MoveResize(PositionSize(position.GetX(), position.GetY(), oldRect.width, oldRect.height));
633
634   mSurface->SetFullSwapNextFrame();
635
636   Dali::Accessibility::Accessible::Get(mScene.GetRootLayer(), true)->EmitBoundsChanged(Dali::Rect<>(position.GetX(), position.GetY(), oldRect.width, oldRect.height));
637 }
638
639 Dali::Window::WindowPosition Window::GetPosition() const
640 {
641   PositionSize positionSize = mSurface->GetPositionSize();
642
643   return Dali::Window::WindowPosition(positionSize.x, positionSize.y);
644 }
645
646 PositionSize Window::GetPositionSize() const
647 {
648   return mSurface->GetPositionSize();
649 }
650
651 void Window::SetPositionSize(PositionSize positionSize)
652 {
653   PositionSize oldRect = mSurface->GetPositionSize();
654
655   mWindowSurface->MoveResize(positionSize);
656
657   PositionSize newRect = mSurface->GetPositionSize();
658
659   // When surface size is updated, inform adaptor of resizing and emit ResizeSignal
660   if((oldRect.width != newRect.width) || (oldRect.height != newRect.height))
661   {
662     Uint16Pair newSize(newRect.width, newRect.height);
663
664     SurfaceResized();
665
666     mAdaptor->SurfaceResizePrepare(mSurface.get(), newSize);
667
668     DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), SetPositionSize():resize signal [%d x %d]\n", this, mNativeWindowId, newRect.width, newRect.height);
669     Dali::Window handle(this);
670     mResizeSignal.Emit(handle, newSize);
671     mAdaptor->SurfaceResizeComplete(mSurface.get(), newSize);
672   }
673
674   mSurface->SetFullSwapNextFrame();
675
676   Dali::Accessibility::Accessible::Get(mScene.GetRootLayer(), true)->EmitBoundsChanged(Dali::Rect<>(positionSize.x, positionSize.y, positionSize.width, positionSize.height));
677 }
678
679 Dali::Layer Window::GetRootLayer() const
680 {
681   return mScene.GetRootLayer();
682 }
683
684 void Window::SetTransparency(bool transparent)
685 {
686   mWindowSurface->SetTransparency(transparent);
687 }
688
689 bool Window::GrabKey(Dali::KEY key, KeyGrab::KeyGrabMode grabMode)
690 {
691   return mWindowBase->GrabKey(key, grabMode);
692 }
693
694 bool Window::UngrabKey(Dali::KEY key)
695 {
696   return mWindowBase->UngrabKey(key);
697 }
698
699 bool Window::GrabKeyList(const Dali::Vector<Dali::KEY>& key, const Dali::Vector<KeyGrab::KeyGrabMode>& grabMode, Dali::Vector<bool>& result)
700 {
701   return mWindowBase->GrabKeyList(key, grabMode, result);
702 }
703
704 bool Window::UngrabKeyList(const Dali::Vector<Dali::KEY>& key, Dali::Vector<bool>& result)
705 {
706   return mWindowBase->UngrabKeyList(key, result);
707 }
708
709 void Window::OnIconifyChanged(bool iconified)
710 {
711   if(iconified)
712   {
713     mIconified = true;
714
715     if(mVisible)
716     {
717       Dali::Window handle(this);
718       mVisibilityChangedSignal.Emit(handle, false);
719
720       WindowVisibilityObserver* observer(mAdaptor);
721       observer->OnWindowHidden();
722     }
723
724     DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Iconified: visible = %d\n", this, mNativeWindowId, mVisible);
725   }
726   else
727   {
728     mIconified = false;
729
730     if(mVisible)
731     {
732       Dali::Window handle(this);
733       mVisibilityChangedSignal.Emit(handle, true);
734
735       WindowVisibilityObserver* observer(mAdaptor);
736       observer->OnWindowShown();
737     }
738
739     DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), Deiconified: visible = %d\n", this, mNativeWindowId, mVisible);
740   }
741
742   mSurface->SetFullSwapNextFrame();
743 }
744
745 void Window::OnFocusChanged(bool focusIn)
746 {
747   Dali::Window handle(this);
748   mFocusChangeSignal.Emit(handle, focusIn);
749
750   mSurface->SetFullSwapNextFrame();
751
752   if(auto bridge = Dali::Accessibility::Bridge::GetCurrentBridge())
753   {
754     if(focusIn)
755     {
756       bridge->WindowShown();
757     }
758     else
759     {
760       bridge->WindowHidden();
761     }
762   }
763 }
764
765 void Window::OnOutputTransformed()
766 {
767   PositionSize positionSize = mSurface->GetPositionSize();
768
769   int orientation = (mRotationAngle + mWindowBase->GetScreenRotationAngle()) % 360;
770   SurfaceRotated(static_cast<float>(positionSize.width), static_cast<float>(positionSize.height), orientation);
771
772   mAdaptor->SurfaceResizePrepare(mSurface.get(), Adaptor::SurfaceSize(positionSize.width, positionSize.height));
773   mAdaptor->SurfaceResizeComplete(mSurface.get(), Adaptor::SurfaceSize(positionSize.width, positionSize.height));
774 }
775
776 void Window::OnDeleteRequest()
777 {
778   mDeleteRequestSignal.Emit();
779 }
780
781 void Window::OnTransitionEffectEvent(WindowEffectState state, WindowEffectType type)
782 {
783   Dali::Window handle(this);
784   mTransitionEffectEventSignal.Emit(handle, state, type);
785 }
786
787 void Window::OnKeyboardRepeatSettingsChanged()
788 {
789   Dali::Window handle(this);
790   mKeyboardRepeatSettingsChangedSignal.Emit();
791 }
792
793 void Window::OnWindowRedrawRequest()
794 {
795   mAdaptor->RenderOnce();
796 }
797
798 void Window::OnUpdatePositionSize(Dali::PositionSize& positionSize)
799 {
800   SetPositionSize(positionSize);
801 }
802
803 void Window::OnTouchPoint(Dali::Integration::Point& point, int timeStamp)
804 {
805   FeedTouchPoint(point, timeStamp);
806 }
807
808 void Window::OnWheelEvent(Dali::Integration::WheelEvent& wheelEvent)
809 {
810   FeedWheelEvent(wheelEvent);
811 }
812
813 void Window::OnKeyEvent(Dali::Integration::KeyEvent& keyEvent)
814 {
815   FeedKeyEvent(keyEvent);
816 }
817
818 void Window::OnRotation(const RotationEvent& rotation)
819 {
820   mRotationAngle = rotation.angle;
821   mWindowWidth   = rotation.width;
822   mWindowHeight  = rotation.height;
823
824   // Notify that the orientation is changed
825   mOrientation->OnOrientationChange(rotation);
826
827   mWindowSurface->RequestRotation(mRotationAngle, mWindowWidth, mWindowHeight);
828
829   int orientation = (mRotationAngle + mWindowBase->GetScreenRotationAngle()) % 360;
830   SurfaceRotated(mWindowWidth, mWindowHeight, orientation);
831
832   mAdaptor->SurfaceResizePrepare(mSurface.get(), Adaptor::SurfaceSize(mWindowWidth, mWindowHeight));
833
834   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), OnRotation(): resize signal emit [%d x %d]\n", this, mNativeWindowId, mWindowWidth, mWindowHeight);
835   // Emit signal
836   Dali::Window handle(this);
837   mResizeSignal.Emit(handle, Dali::Window::WindowSize(mWindowWidth, mWindowHeight));
838
839   mAdaptor->SurfaceResizeComplete(mSurface.get(), Adaptor::SurfaceSize(mWindowWidth, mWindowHeight));
840 }
841
842 void Window::OnPause()
843 {
844   if(mEventHandler)
845   {
846     mEventHandler->Pause();
847   }
848 }
849
850 void Window::OnResume()
851 {
852   if(mEventHandler)
853   {
854     mEventHandler->Resume();
855   }
856
857   mSurface->SetFullSwapNextFrame();
858 }
859
860 void Window::RecalculateTouchPosition(Integration::Point& point)
861 {
862   Vector2 position = point.GetScreenPosition();
863   Vector2 convertedPosition;
864
865   switch(mRotationAngle)
866   {
867     case 90:
868     {
869       convertedPosition.x = static_cast<float>(mWindowWidth) - position.y;
870       convertedPosition.y = position.x;
871       break;
872     }
873     case 180:
874     {
875       convertedPosition.x = static_cast<float>(mWindowWidth) - position.x;
876       convertedPosition.y = static_cast<float>(mWindowHeight) - position.y;
877       break;
878     }
879     case 270:
880     {
881       convertedPosition.x = position.y;
882       convertedPosition.y = static_cast<float>(mWindowHeight) - position.x;
883       break;
884     }
885     default:
886     {
887       convertedPosition = position;
888       break;
889     }
890   }
891
892   point.SetScreenPosition(convertedPosition);
893 }
894
895 Dali::Window Window::Get(Dali::Actor actor)
896 {
897   Internal::Adaptor::Window* windowImpl = nullptr;
898
899   if(Internal::Adaptor::Adaptor::IsAvailable())
900   {
901     Dali::Internal::Adaptor::Adaptor& adaptor = Internal::Adaptor::Adaptor::GetImplementation(Internal::Adaptor::Adaptor::Get());
902     windowImpl                                = dynamic_cast<Internal::Adaptor::Window*>(adaptor.GetWindow(actor));
903     if(windowImpl)
904     {
905       return Dali::Window(windowImpl);
906     }
907   }
908
909   return Dali::Window();
910 }
911
912 void Window::SetParent(Dali::Window& parent)
913 {
914   if(DALI_UNLIKELY(parent))
915   {
916     mParentWindow     = parent;
917     Dali::Window self = Dali::Window(this);
918     // check circular parent window setting
919     if(Dali::DevelWindow::GetParent(parent) == self)
920     {
921       Dali::DevelWindow::Unparent(parent);
922     }
923     mWindowBase->SetParent(GetImplementation(mParentWindow).mWindowBase, false);
924   }
925 }
926
927 void Window::SetParent(Dali::Window& parent, bool belowParent)
928 {
929   if(DALI_UNLIKELY(parent))
930   {
931     mParentWindow     = parent;
932     Dali::Window self = Dali::Window(this);
933     // check circular parent window setting
934     if(Dali::DevelWindow::GetParent(parent) == self)
935     {
936       Dali::DevelWindow::Unparent(parent);
937     }
938     mWindowBase->SetParent(GetImplementation(mParentWindow).mWindowBase, belowParent);
939   }
940 }
941
942 void Window::Unparent()
943 {
944   mWindowBase->SetParent(nullptr, false);
945   mParentWindow.Reset();
946 }
947
948 Dali::Window Window::GetParent()
949 {
950   return mParentWindow;
951 }
952
953 WindowOrientation Window::GetCurrentOrientation() const
954 {
955   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), GetCurrentOrientation(): %d\n", this, mNativeWindowId, mRotationAngle);
956   return ConvertToOrientation(mRotationAngle);
957 }
958
959 int Window::GetPhysicalOrientation() const
960 {
961   return (mRotationAngle + mWindowBase->GetScreenRotationAngle()) % 360;
962 }
963
964 void Window::SetAvailableOrientations(const Dali::Vector<WindowOrientation>& orientations)
965 {
966   Dali::Vector<float>::SizeType count = orientations.Count();
967   for(Dali::Vector<float>::SizeType index = 0; index < count; ++index)
968   {
969     if(IsOrientationAvailable(orientations[index]) == false)
970     {
971       DALI_LOG_ERROR("Window::SetAvailableOrientations, invalid orientation: %d\n", orientations[index]);
972       continue;
973     }
974
975     bool found          = false;
976     int  convertedAngle = ConvertToAngle(orientations[index]);
977
978     for(std::size_t i = 0; i < mAvailableAngles.size(); i++)
979     {
980       if(mAvailableAngles[i] == convertedAngle)
981       {
982         found = true;
983         break;
984       }
985     }
986
987     if(!found)
988     {
989       DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), SetAvailableOrientations: %d\n", this, mNativeWindowId, convertedAngle);
990       mAvailableAngles.push_back(convertedAngle);
991     }
992   }
993   SetAvailableAnlges(mAvailableAngles);
994 }
995
996 int32_t Window::GetNativeId() const
997 {
998   return mWindowBase->GetNativeWindowId();
999 }
1000
1001 void Window::RequestMoveToServer()
1002 {
1003   mWindowBase->RequestMoveToServer();
1004 }
1005
1006 void Window::RequestResizeToServer(WindowResizeDirection direction)
1007 {
1008   mWindowBase->RequestResizeToServer(direction);
1009 }
1010
1011 void Window::EnableFloatingMode(bool enable)
1012 {
1013   mWindowBase->EnableFloatingMode(enable);
1014 }
1015
1016 Rect<int> Window::RecalculateRect(const Rect<int>& rect)
1017 {
1018   Rect<int> newRect;
1019   int screenWidth, screenHeight;
1020
1021   WindowSystem::GetScreenSize(screenWidth, screenHeight);
1022
1023   if(mRotationAngle == 90)
1024   {
1025     newRect.x      = rect.y;
1026     newRect.y      = screenHeight - (rect.x + rect.width);
1027     newRect.width  = rect.height;
1028     newRect.height = rect.width;
1029   }
1030   else if(mRotationAngle == 180)
1031   {
1032     newRect.x      = screenWidth - (rect.x + rect.width);
1033     newRect.y      = screenHeight - (rect.y + rect.height);
1034     newRect.width  = rect.width;
1035     newRect.height = rect.height;
1036   }
1037   else if(mRotationAngle == 270)
1038   {
1039     newRect.x      = screenWidth - (rect.y + rect.height);
1040     newRect.y      = rect.x;
1041     newRect.width  = rect.height;
1042     newRect.height = rect.width;
1043   }
1044   else
1045   {
1046     newRect.x      = rect.x;
1047     newRect.y      = rect.y;
1048     newRect.width  = rect.width;
1049     newRect.height = rect.height;
1050   }
1051   return newRect;
1052 }
1053
1054 void Window::IncludeInputRegion(const Rect<int>& inputRegion)
1055 {
1056   Rect<int> convertRegion = RecalculateRect(inputRegion);
1057
1058   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), IncludeInputRegion, RecalculateRegion, (%d,%d), (%d x %d)\n", this, mNativeWindowId, convertRegion.x, convertRegion.y, convertRegion.width, convertRegion.height);
1059   mWindowBase->IncludeInputRegion(convertRegion);
1060 }
1061
1062 void Window::ExcludeInputRegion(const Rect<int>& inputRegion)
1063 {
1064   Rect<int> convertRegion = RecalculateRect(inputRegion);
1065
1066   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), ExcludeInputRegion, RecalculateRegion, (%d,%d), (%d x %d)\n", this, mNativeWindowId, convertRegion.x, convertRegion.y, convertRegion.width, convertRegion.height);
1067   mWindowBase->ExcludeInputRegion(convertRegion);
1068 }
1069
1070 void Window::SetNeedsRotationCompletedAcknowledgement(bool needAcknowledgement)
1071 {
1072   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), needAcknowledgement(%d) Set needs Rotation Completed Acknowledgement\n", this, mNativeWindowId, needAcknowledgement);
1073   mWindowSurface->SetNeedsRotationCompletedAcknowledgement(needAcknowledgement);
1074   mWindowRotationAcknowledgement = needAcknowledgement;
1075 }
1076
1077 void Window::SendRotationCompletedAcknowledgement()
1078 {
1079   DALI_LOG_RELEASE_INFO("Window (%p), WinId (%d), SendRotationCompletedAcknowledgement(): orientation: %d, mWindowRotationAcknowledgement: %d\n", this, mNativeWindowId, mRotationAngle, mWindowRotationAcknowledgement);
1080   if(mWindowRotationAcknowledgement)
1081   {
1082     SetRotationCompletedAcknowledgement();
1083   }
1084 }
1085
1086 } // namespace Adaptor
1087
1088 } // namespace Internal
1089
1090 } // namespace Dali