[Tizen] Fix to get the logical key to ecore key variable
[platform/core/uifw/dali-adaptor.git] / dali / internal / window-system / ubuntu-x11 / window-base-ecore-x.cpp
1 /*
2  * Copyright (c) 2018 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 // Ecore is littered with C style cast
19 #pragma GCC diagnostic push
20 #pragma GCC diagnostic ignored "-Wold-style-cast"
21
22 // CLASS HEADER
23 #include <dali/internal/window-system/ubuntu-x11/window-base-ecore-x.h>
24
25 // INTERNAL HEADERS
26 #include <dali/internal/window-system/common/window-impl.h>
27 #include <dali/internal/window-system/common/window-render-surface.h>
28 #include <dali/internal/window-system/ubuntu-x11/ecore-x-types.h>
29
30 // EXTERNAL_HEADERS
31 #include <dali/public-api/object/any.h>
32 #include <dali/public-api/events/mouse-button.h>
33 #include <dali/integration-api/debug.h>
34 #include <Ecore_Input.h>
35
36 namespace Dali
37 {
38
39 namespace Internal
40 {
41
42 namespace Adaptor
43 {
44
45 namespace
46 {
47
48 const std::string DEFAULT_DEVICE_NAME = "";
49 const Device::Class::Type DEFAULT_DEVICE_CLASS = Device::Class::NONE;
50 const Device::Subclass::Type DEFAULT_DEVICE_SUBCLASS = Device::Subclass::NONE;
51
52 const unsigned int PRIMARY_TOUCH_BUTTON_ID( 1 );
53
54 #if defined(DEBUG_ENABLED)
55 Debug::Filter* gWindowBaseLogFilter = Debug::Filter::New( Debug::NoLogging, false, "LOG_WINDOW_BASE" );
56 #endif
57
58 /////////////////////////////////////////////////////////////////////////////////////////////////
59 // Window Callbacks
60 /////////////////////////////////////////////////////////////////////////////////////////////////
61
62 static Eina_Bool EcoreEventWindowPropertyChanged( void* data, int type, void* event )
63 {
64   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
65   if( windowBase )
66   {
67     return windowBase->OnWindowPropertyChanged( data, type, event );
68   }
69
70   return ECORE_CALLBACK_PASS_ON;
71 }
72
73 /**
74  * Called when the window receives a delete request
75  */
76 static Eina_Bool EcoreEventWindowDeleteRequest( void* data, int type, void* event )
77 {
78   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
79   if( windowBase )
80   {
81     windowBase->OnDeleteRequest();
82   }
83   return ECORE_CALLBACK_DONE;
84 }
85
86 /**
87  * Called when the window gains focus.
88  */
89 static Eina_Bool EcoreEventWindowFocusIn( void* data, int type, void* event )
90 {
91   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
92   if( windowBase )
93   {
94     windowBase->OnFocusIn( data, type, event );
95   }
96   return ECORE_CALLBACK_PASS_ON;
97 }
98
99 /**
100  * Called when the window loses focus.
101  */
102 static Eina_Bool EcoreEventWindowFocusOut( void* data, int type, void* event )
103 {
104   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
105   if( windowBase )
106   {
107     windowBase->OnFocusOut( data, type, event );
108   }
109   return ECORE_CALLBACK_PASS_ON;
110 }
111
112 /**
113  * Called when the window is damaged.
114  */
115 static Eina_Bool EcoreEventWindowDamaged( void* data, int type, void* event )
116 {
117   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
118   if( windowBase )
119   {
120     windowBase->OnWindowDamaged( data, type, event );
121   }
122
123   return ECORE_CALLBACK_PASS_ON;
124 }
125
126 /////////////////////////////////////////////////////////////////////////////////////////////////
127 // Selection Callbacks
128 /////////////////////////////////////////////////////////////////////////////////////////////////
129
130 /**
131  * Called when the source window notifies us the content in clipboard is selected.
132  */
133 static Eina_Bool EcoreEventSelectionClear( void* data, int type, void* event )
134 {
135   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
136   if( windowBase )
137   {
138     windowBase->OnSelectionClear( data, type, event );
139   }
140   return ECORE_CALLBACK_PASS_ON;
141 }
142
143 /**
144  * Called when the source window sends us about the selected content.
145  * For example, when dragged items are dragged INTO our window or when items are selected in the clipboard.
146  */
147 static Eina_Bool EcoreEventSelectionNotify( void* data, int type, void* event )
148 {
149   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
150   if( windowBase )
151   {
152     windowBase->OnSelectionNotify( data, type, event );
153   }
154   return ECORE_CALLBACK_PASS_ON;
155 }
156
157 /////////////////////////////////////////////////////////////////////////////////////////////////
158 // Touch Callbacks
159 /////////////////////////////////////////////////////////////////////////////////////////////////
160
161 /**
162  * Called when a touch down is received.
163  */
164 static Eina_Bool EcoreEventMouseButtonDown( void* data, int type, void* event )
165 {
166   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
167   if( windowBase )
168   {
169     windowBase->OnMouseButtonDown( data, type, event );
170   }
171   return ECORE_CALLBACK_PASS_ON;
172 }
173
174 /**
175  * Called when a touch up is received.
176  */
177 static Eina_Bool EcoreEventMouseButtonUp( void* data, int type, void* event )
178 {
179   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
180   if( windowBase )
181   {
182     windowBase->OnMouseButtonUp( data, type, event );
183   }
184   return ECORE_CALLBACK_PASS_ON;
185 }
186
187 /**
188  * Called when a touch motion is received.
189  */
190 static Eina_Bool EcoreEventMouseButtonMove( void* data, int type, void* event )
191 {
192   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
193   if( windowBase )
194   {
195     windowBase->OnMouseButtonMove( data, type, event );
196   }
197   return ECORE_CALLBACK_PASS_ON;
198 }
199
200 /////////////////////////////////////////////////////////////////////////////////////////////////
201 // Wheel Callbacks
202 /////////////////////////////////////////////////////////////////////////////////////////////////
203
204 /**
205  * Called when a mouse wheel is received.
206  */
207 static Eina_Bool EcoreEventMouseWheel( void* data, int type, void* event )
208 {
209   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
210   if( windowBase )
211   {
212     windowBase->OnMouseWheel( data, type, event );
213   }
214   return ECORE_CALLBACK_PASS_ON;
215 }
216
217 /////////////////////////////////////////////////////////////////////////////////////////////////
218 // Key Callbacks
219 /////////////////////////////////////////////////////////////////////////////////////////////////
220
221 /**
222  * Called when a key down is received.
223  */
224 static Eina_Bool EcoreEventKeyDown( void* data, int type, void* event )
225 {
226   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
227   if( windowBase )
228   {
229     windowBase->OnKeyDown( data, type, event );
230   }
231   return ECORE_CALLBACK_PASS_ON;
232 }
233
234 /**
235  * Called when a key up is received.
236  */
237 static Eina_Bool EcoreEventKeyUp( void* data, int type, void* event )
238 {
239   WindowBaseEcoreX* windowBase = static_cast< WindowBaseEcoreX* >( data );
240   if( windowBase )
241   {
242     windowBase->OnKeyUp( data, type, event );
243   }
244   return ECORE_CALLBACK_PASS_ON;
245 }
246
247 } // unnamed namespace
248
249 WindowBaseEcoreX::WindowBaseEcoreX( Dali::PositionSize positionSize, Any surface, bool isTransparent )
250 : mEcoreEventHandler(),
251   mEcoreWindow( 0 ),
252   mOwnSurface( false ),
253   mIsTransparent( false ), // Should only be set to true once we actually create a transparent window regardless of what isTransparent is.
254   mRotationAppSet( false )
255 {
256   Initialize( positionSize, surface, isTransparent );
257 }
258
259 WindowBaseEcoreX::~WindowBaseEcoreX()
260 {
261   for( Dali::Vector< Ecore_Event_Handler* >::Iterator iter = mEcoreEventHandler.Begin(), endIter = mEcoreEventHandler.End(); iter != endIter; ++iter )
262   {
263     ecore_event_handler_del( *iter );
264   }
265   mEcoreEventHandler.Clear();
266
267   if( mOwnSurface )
268   {
269     ecore_x_window_free( mEcoreWindow );
270   }
271 }
272
273 void WindowBaseEcoreX::Initialize( PositionSize positionSize, Any surface, bool isTransparent )
274 {
275   // see if there is a surface in Any surface
276   unsigned int surfaceId = GetSurfaceId( surface );
277
278   // if the surface is empty, create a new one.
279   if( surfaceId == 0 )
280   {
281     // we own the surface about to created
282     mOwnSurface = true;
283     CreateWindow( positionSize, isTransparent );
284   }
285   else
286   {
287     // XLib should already be initialized so no point in calling XInitThreads
288     mEcoreWindow = static_cast< Ecore_X_Window >( surfaceId );
289   }
290
291   // set up etc properties to match with ecore-evas
292   char *id = NULL;
293   if( ( id = getenv("DESKTOP_STARTUP_ID") ) )
294   {
295     ecore_x_netwm_startup_id_set( mEcoreWindow, id );
296   }
297
298   ecore_x_icccm_hints_set( mEcoreWindow,
299                            1,                                // accepts_focus
300                            ECORE_X_WINDOW_STATE_HINT_NORMAL, // initial_state
301                            0,                                // icon_pixmap
302                            0,                                // icon_mask
303                            0,                                // icon_window
304                            0,                                // window_group
305                            0 );                              // is_urgent
306
307   // we SHOULD guarantee the x11 window was created in x server.
308   ecore_x_sync();
309
310   ecore_x_input_multi_select( mEcoreWindow );
311
312   // This ensures that we catch the window close (or delete) request
313   ecore_x_icccm_protocol_set( mEcoreWindow, ECORE_X_WM_PROTOCOL_DELETE_REQUEST, EINA_TRUE );
314
315   // Enable Drag & Drop
316   ecore_x_dnd_aware_set( mEcoreWindow, EINA_TRUE );
317
318   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_WINDOW_PROPERTY,       EcoreEventWindowPropertyChanged, this ) );
319   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_WINDOW_DELETE_REQUEST, EcoreEventWindowDeleteRequest,   this ) );
320
321   // Register window focus events
322   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_WINDOW_FOCUS_IN,       EcoreEventWindowFocusIn,   this ) );
323   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_WINDOW_FOCUS_OUT,      EcoreEventWindowFocusOut,  this ) );
324
325   // Register Window damage events
326   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_WINDOW_DAMAGE,         EcoreEventWindowDamaged,   this ) );
327
328   // Register Touch events
329   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_MOUSE_BUTTON_DOWN,       EcoreEventMouseButtonDown, this ) );
330   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_MOUSE_BUTTON_UP,         EcoreEventMouseButtonUp,   this ) );
331   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_MOUSE_MOVE,              EcoreEventMouseButtonMove, this ) );
332   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_MOUSE_OUT,               EcoreEventMouseButtonUp,   this ) ); // process mouse out event like up event
333
334   // Register Mouse wheel events
335   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_MOUSE_WHEEL,             EcoreEventMouseWheel,      this ) );
336
337   // Register Key events
338   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_KEY_DOWN,                EcoreEventKeyDown,         this ) );
339   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_EVENT_KEY_UP,                  EcoreEventKeyUp,           this ) );
340
341   // Register Selection event
342   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_SELECTION_CLEAR,       EcoreEventSelectionClear,  this ) );
343   mEcoreEventHandler.PushBack( ecore_event_handler_add( ECORE_X_EVENT_SELECTION_NOTIFY,      EcoreEventSelectionNotify, this ) );
344 }
345
346 Eina_Bool WindowBaseEcoreX::OnWindowPropertyChanged( void* data, int type, void* event )
347 {
348   Ecore_X_Event_Window_Property* propertyChangedEvent = static_cast< Ecore_X_Event_Window_Property* >( event );
349   Eina_Bool handled( ECORE_CALLBACK_PASS_ON );
350
351   if( propertyChangedEvent->win == mEcoreWindow )
352   {
353     Ecore_X_Window_State_Hint state( ecore_x_icccm_state_get( propertyChangedEvent->win ) );
354
355     switch( state )
356     {
357       case ECORE_X_WINDOW_STATE_HINT_WITHDRAWN:
358       {
359         // Window was hidden.
360         mIconifyChangedSignal.Emit( true );
361         handled = ECORE_CALLBACK_DONE;
362         break;
363       }
364       case ECORE_X_WINDOW_STATE_HINT_ICONIC:
365       {
366         // Window was iconified (minimised).
367         mIconifyChangedSignal.Emit( true );
368         handled = ECORE_CALLBACK_DONE;
369         break;
370       }
371       case ECORE_X_WINDOW_STATE_HINT_NORMAL:
372       {
373         // Window was shown.
374         mIconifyChangedSignal.Emit( false );
375         handled = ECORE_CALLBACK_DONE;
376         break;
377       }
378       default:
379       {
380         // Ignore
381         break;
382       }
383     }
384   }
385
386   return handled;
387 }
388
389 void WindowBaseEcoreX::OnDeleteRequest()
390 {
391   mDeleteRequestSignal.Emit();
392 }
393
394 void WindowBaseEcoreX::OnFocusIn( void* data, int type, void* event )
395 {
396   Ecore_X_Event_Window_Focus_In* focusInEvent = static_cast< Ecore_X_Event_Window_Focus_In* >( event );
397
398   if( focusInEvent->win == mEcoreWindow )
399   {
400     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::General, "Window EcoreEventWindowFocusIn\n" );
401
402     mFocusChangedSignal.Emit( true );
403   }
404 }
405
406 void WindowBaseEcoreX::OnFocusOut( void* data, int type, void* event )
407 {
408   Ecore_X_Event_Window_Focus_Out* focusOutEvent = static_cast< Ecore_X_Event_Window_Focus_Out* >( event );
409
410   // If the window loses focus then hide the keyboard.
411   if( focusOutEvent->win == mEcoreWindow )
412   {
413     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::General, "Window EcoreEventWindowFocusOut\n" );
414
415     mFocusChangedSignal.Emit( false );
416   }
417 }
418
419 void WindowBaseEcoreX::OnWindowDamaged( void* data, int type, void* event )
420 {
421   Ecore_X_Event_Window_Damage* windowDamagedEvent = static_cast< Ecore_X_Event_Window_Damage* >( event );
422
423   if( windowDamagedEvent->win == mEcoreWindow )
424   {
425     DamageArea area;
426     area.x = windowDamagedEvent->x;
427     area.y = windowDamagedEvent->y;
428     area.width = windowDamagedEvent->w;
429     area.height = windowDamagedEvent->h;
430
431     mWindowDamagedSignal.Emit( area );
432   }
433 }
434
435 void WindowBaseEcoreX::OnMouseButtonDown( void* data, int type, void* event )
436 {
437   Ecore_Event_Mouse_Button* touchEvent = static_cast< Ecore_Event_Mouse_Button* >( event );
438
439   if( touchEvent->window == mEcoreWindow )
440   {
441     PointState::Type state ( PointState::DOWN );
442
443     Integration::Point point;
444     point.SetDeviceId( touchEvent->multi.device );
445     point.SetState( state );
446     point.SetScreenPosition( Vector2( touchEvent->x, touchEvent->y ) );
447     point.SetRadius( touchEvent->multi.radius, Vector2( touchEvent->multi.radius_x, touchEvent->multi.radius_y ) );
448     point.SetPressure( touchEvent->multi.pressure );
449     point.SetAngle( Degree( touchEvent->multi.angle ) );
450     if( touchEvent->buttons)
451     {
452       point.SetMouseButton( static_cast< MouseButton::Type >( touchEvent->buttons) );
453     }
454
455     mTouchEventSignal.Emit( point, touchEvent->timestamp );
456   }
457 }
458
459 void WindowBaseEcoreX::OnMouseButtonUp( void* data, int type, void* event )
460 {
461   Ecore_Event_Mouse_Button* touchEvent = static_cast< Ecore_Event_Mouse_Button* >( event );
462
463   if( touchEvent->window == mEcoreWindow )
464   {
465     Integration::Point point;
466     point.SetDeviceId( touchEvent->multi.device );
467     point.SetState( PointState::UP );
468     point.SetScreenPosition( Vector2( touchEvent->x, touchEvent->y ) );
469     point.SetRadius( touchEvent->multi.radius, Vector2( touchEvent->multi.radius_x, touchEvent->multi.radius_y ) );
470     point.SetPressure( touchEvent->multi.pressure );
471     point.SetAngle( Degree( touchEvent->multi.angle ) );
472     if( touchEvent->buttons)
473     {
474       point.SetMouseButton( static_cast< MouseButton::Type >( touchEvent->buttons) );
475     }
476
477     mTouchEventSignal.Emit( point, touchEvent->timestamp );
478   }
479 }
480
481 void WindowBaseEcoreX::OnMouseButtonMove( void* data, int type, void* event )
482 {
483   Ecore_Event_Mouse_Move* touchEvent = static_cast< Ecore_Event_Mouse_Move* >( event );
484
485   if( touchEvent->window == mEcoreWindow )
486   {
487     Integration::Point point;
488     point.SetDeviceId( touchEvent->multi.device );
489     point.SetState( PointState::MOTION );
490     point.SetScreenPosition( Vector2( touchEvent->x, touchEvent->y ) );
491     point.SetRadius( touchEvent->multi.radius, Vector2( touchEvent->multi.radius_x, touchEvent->multi.radius_y ) );
492     point.SetPressure( touchEvent->multi.pressure );
493     point.SetAngle( Degree( touchEvent->multi.angle ) );
494
495     mTouchEventSignal.Emit( point, touchEvent->timestamp );
496   }
497 }
498
499 void WindowBaseEcoreX::OnMouseWheel( void* data, int type, void* event )
500 {
501   Ecore_Event_Mouse_Wheel* mouseWheelEvent = static_cast< Ecore_Event_Mouse_Wheel* >( event );
502
503   if( mouseWheelEvent->window == mEcoreWindow )
504   {
505     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::General, "WindowBaseEcoreX::OnMouseWheel: direction: %d, modifiers: %d, x: %d, y: %d, z: %d\n", mouseWheelEvent->direction, mouseWheelEvent->modifiers, mouseWheelEvent->x, mouseWheelEvent->y, mouseWheelEvent->z );
506
507     WheelEvent wheelEvent( WheelEvent::MOUSE_WHEEL, mouseWheelEvent->direction, mouseWheelEvent->modifiers, Vector2( mouseWheelEvent->x, mouseWheelEvent->y ), mouseWheelEvent->z, mouseWheelEvent->timestamp );
508
509     mWheelEventSignal.Emit( wheelEvent );
510   }
511 }
512
513 void WindowBaseEcoreX::OnKeyDown( void* data, int type, void* event )
514 {
515   Ecore_Event_Key* keyEvent = static_cast< Ecore_Event_Key* >( event );
516
517   if( keyEvent->window == mEcoreWindow )
518   {
519     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::General, "WindowBaseEcoreX::OnKeyDown\n" );
520
521     std::string keyName( keyEvent->keyname );
522     std::string key( "" );
523     std::string keyString( "" );
524     std::string compose( "" );
525
526     // Ensure key compose string is not NULL as keys like SHIFT or arrow have a null string.
527     if( keyEvent->compose )
528     {
529       compose = keyEvent->compose;
530     }
531
532     // Ensure key symbol is not NULL as keys like SHIFT have a null string.
533     if( keyEvent->key )
534     {
535       key = keyEvent->key;
536     }
537
538     int keyCode = ecore_x_keysym_keycode_get( keyEvent->keyname );
539     int modifier( keyEvent->modifiers );
540     unsigned long time = keyEvent->timestamp;
541
542     // Ensure key event string is not NULL as keys like SHIFT have a null string.
543     if( keyEvent->string )
544     {
545       keyString = keyEvent->string;
546     }
547
548     Integration::KeyEvent keyEvent( keyName, key, keyString, keyCode, modifier, time, Integration::KeyEvent::Down, compose, DEFAULT_DEVICE_NAME, DEFAULT_DEVICE_CLASS, DEFAULT_DEVICE_SUBCLASS );
549
550     mKeyEventSignal.Emit( keyEvent );
551   }
552 }
553
554 void WindowBaseEcoreX::OnKeyUp( void* data, int type, void* event )
555 {
556   Ecore_Event_Key* keyEvent = static_cast< Ecore_Event_Key* >( event );
557
558   if ( keyEvent->window == mEcoreWindow )
559   {
560     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::General, " WindowBaseEcoreX::OnKeyUp\n" );
561
562     std::string keyName( keyEvent->keyname );
563     std::string key( "" );
564     std::string keyString( "" );
565     std::string compose( "" );
566
567     // Ensure key compose string is not NULL as keys like SHIFT or arrow have a null string.
568     if( keyEvent->compose )
569     {
570       compose = keyEvent->compose;
571     }
572     // Ensure key symbol is not NULL as keys like SHIFT have a null string.
573     if( keyEvent->key )
574     {
575       key = keyEvent->key;
576     }
577
578     int keyCode = ecore_x_keysym_keycode_get( keyEvent->keyname );
579     int modifier( keyEvent->modifiers );
580     unsigned long time( keyEvent->timestamp );
581
582     // Ensure key event string is not NULL as keys like SHIFT have a null string.
583     if( keyEvent->string )
584     {
585       keyString = keyEvent->string;
586     }
587
588     Integration::KeyEvent keyEvent( keyName, key, keyString, keyCode, modifier, time, Integration::KeyEvent::Up, compose, DEFAULT_DEVICE_NAME, DEFAULT_DEVICE_CLASS, DEFAULT_DEVICE_SUBCLASS );
589
590     mKeyEventSignal.Emit( keyEvent );
591   }
592 }
593
594 void WindowBaseEcoreX::OnSelectionClear( void* data, int type, void* event )
595 {
596   Ecore_X_Event_Selection_Clear* selectionClearEvent = static_cast< Ecore_X_Event_Selection_Clear* >( event );
597
598   if( selectionClearEvent->win == mEcoreWindow )
599   {
600     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::Concise, " WindowBaseEcoreX::OnSelectionClear\n" );
601
602     if( selectionClearEvent->selection == ECORE_X_SELECTION_SECONDARY )
603     {
604       // Request to get the content from Ecore.
605       ecore_x_selection_secondary_request( selectionClearEvent->win, ECORE_X_SELECTION_TARGET_TEXT );
606     }
607   }
608 }
609
610 void WindowBaseEcoreX::OnSelectionNotify( void* data, int type, void* event )
611 {
612   Ecore_X_Event_Selection_Notify* selectionNotifyEvent = static_cast< Ecore_X_Event_Selection_Notify* >( event );
613
614   if( selectionNotifyEvent->win == mEcoreWindow )
615   {
616     DALI_LOG_INFO( gWindowBaseLogFilter, Debug::Concise, " WindowBaseEcoreX::OnSelectionNotify\n" );
617
618     Ecore_X_Selection_Data* selectionData = static_cast< Ecore_X_Selection_Data* >( selectionNotifyEvent->data );
619     if( selectionData->data )
620     {
621       if( selectionNotifyEvent->selection == ECORE_X_SELECTION_SECONDARY )
622       {
623         mSelectionDataReceivedSignal.Emit( event  );
624       }
625     }
626   }
627 }
628
629 Any WindowBaseEcoreX::GetNativeWindow()
630 {
631   return mEcoreWindow;
632 }
633
634 int WindowBaseEcoreX::GetNativeWindowId()
635 {
636   return mEcoreWindow;
637 }
638
639 EGLNativeWindowType WindowBaseEcoreX::CreateEglWindow( int width, int height )
640 {
641   // need to create X handle as in 64bit system ECore handle is 32 bit whereas EGLnative and XWindow are 64 bit
642   XWindow window( mEcoreWindow );
643   return reinterpret_cast< EGLNativeWindowType >( window );
644 }
645
646 void WindowBaseEcoreX::DestroyEglWindow()
647 {
648 }
649
650 void WindowBaseEcoreX::SetEglWindowRotation( int angle )
651 {
652 }
653
654 void WindowBaseEcoreX::SetEglWindowBufferTransform( int angle )
655 {
656 }
657
658 void WindowBaseEcoreX::SetEglWindowTransform( int angle )
659 {
660 }
661
662 void WindowBaseEcoreX::ResizeEglWindow( PositionSize positionSize )
663 {
664 }
665
666 bool WindowBaseEcoreX::IsEglWindowRotationSupported()
667 {
668   return false;
669 }
670
671 void WindowBaseEcoreX::Move( PositionSize positionSize )
672 {
673   ecore_x_window_move( mEcoreWindow, positionSize.x, positionSize.y );
674 }
675
676 void WindowBaseEcoreX::Resize( PositionSize positionSize )
677 {
678   ecore_x_window_resize( mEcoreWindow, positionSize.width, positionSize.height );
679 }
680
681 void WindowBaseEcoreX::MoveResize( PositionSize positionSize )
682 {
683   ecore_x_window_move_resize( mEcoreWindow, positionSize.x, positionSize.y, positionSize.width, positionSize.height );
684 }
685
686 void WindowBaseEcoreX::ShowIndicator( Dali::Window::IndicatorVisibleMode visibleMode, Dali::Window::IndicatorBgOpacity opacityMode )
687 {
688   DALI_LOG_TRACE_METHOD_FMT( gWindowBaseLogFilter, "visible : %d\n", visibleMode );
689
690   if( visibleMode == Dali::Window::VISIBLE )
691   {
692     // when the indicator is visible, set proper mode for indicator server according to bg mode
693     if( opacityMode == Dali::Window::OPAQUE )
694     {
695       ecore_x_e_illume_indicator_opacity_set( mEcoreWindow, ECORE_X_ILLUME_INDICATOR_OPAQUE );
696     }
697     else if( opacityMode == Dali::Window::TRANSLUCENT )
698     {
699       ecore_x_e_illume_indicator_opacity_set( mEcoreWindow, ECORE_X_ILLUME_INDICATOR_TRANSLUCENT );
700     }
701   }
702   else
703   {
704     // when the indicator is not visible, set TRANSPARENT mode for indicator server
705     ecore_x_e_illume_indicator_opacity_set( mEcoreWindow, ECORE_X_ILLUME_INDICATOR_TRANSPARENT ); // it means hidden indicator
706   }
707 }
708
709 void WindowBaseEcoreX::SetIndicatorProperties( bool isShow, Dali::Window::WindowOrientation lastOrientation )
710 {
711   int show_state = static_cast< int >( isShow );
712   ecore_x_window_prop_property_set( mEcoreWindow, ECORE_X_ATOM_E_ILLUME_INDICATOR_STATE,
713                                     ECORE_X_ATOM_CARDINAL, 32, &show_state, 1 );
714
715   if( isShow )
716   {
717     ecore_x_e_illume_indicator_state_set( mEcoreWindow, ECORE_X_ILLUME_INDICATOR_STATE_ON );
718   }
719   else
720   {
721     ecore_x_e_illume_indicator_state_set( mEcoreWindow, ECORE_X_ILLUME_INDICATOR_STATE_OFF );
722   }
723 }
724
725 void WindowBaseEcoreX::IndicatorTypeChanged( IndicatorInterface::Type type )
726 {
727 }
728
729 void WindowBaseEcoreX::SetClass( const std::string& name, const std::string& className )
730 {
731   ecore_x_icccm_title_set( mEcoreWindow, name.c_str() );
732   ecore_x_netwm_name_set( mEcoreWindow, name.c_str() );
733   ecore_x_icccm_name_class_set( mEcoreWindow, name.c_str(), className.c_str() );
734 }
735
736 void WindowBaseEcoreX::Raise()
737 {
738   ecore_x_window_raise( mEcoreWindow );
739 }
740
741 void WindowBaseEcoreX::Lower()
742 {
743   ecore_x_window_lower( mEcoreWindow );
744 }
745
746 void WindowBaseEcoreX::Activate()
747 {
748   ecore_x_netwm_client_active_request( ecore_x_window_root_get( mEcoreWindow ), mEcoreWindow, 1 /* request type, 1:application, 2:pager */, 0 );
749 }
750
751 void WindowBaseEcoreX::SetAvailableOrientations( const std::vector< Dali::Window::WindowOrientation >& orientations )
752 {
753 }
754
755 void WindowBaseEcoreX::SetPreferredOrientation( Dali::Window::WindowOrientation orientation )
756 {
757 }
758
759 void WindowBaseEcoreX::SetAcceptFocus( bool accept )
760 {
761 }
762
763 void WindowBaseEcoreX::Show()
764 {
765   ecore_x_window_show( mEcoreWindow );
766 }
767
768 void WindowBaseEcoreX::Hide()
769 {
770   ecore_x_window_hide( mEcoreWindow );
771 }
772
773 unsigned int WindowBaseEcoreX::GetSupportedAuxiliaryHintCount() const
774 {
775   return 0;
776 }
777
778 std::string WindowBaseEcoreX::GetSupportedAuxiliaryHint( unsigned int index ) const
779 {
780   return std::string();
781 }
782
783 unsigned int WindowBaseEcoreX::AddAuxiliaryHint( const std::string& hint, const std::string& value )
784 {
785   return 0;
786 }
787
788 bool WindowBaseEcoreX::RemoveAuxiliaryHint( unsigned int id )
789 {
790   return false;
791 }
792
793 bool WindowBaseEcoreX::SetAuxiliaryHintValue( unsigned int id, const std::string& value )
794 {
795   return false;
796 }
797
798 std::string WindowBaseEcoreX::GetAuxiliaryHintValue( unsigned int id ) const
799 {
800   return std::string();
801 }
802
803 unsigned int WindowBaseEcoreX::GetAuxiliaryHintId( const std::string& hint ) const
804 {
805   return 0;
806 }
807
808 void WindowBaseEcoreX::SetInputRegion( const Rect< int >& inputRegion )
809 {
810 }
811
812 void WindowBaseEcoreX::SetType( Dali::Window::Type type )
813 {
814 }
815
816 bool WindowBaseEcoreX::SetNotificationLevel( Dali::Window::NotificationLevel::Type level )
817 {
818   return false;
819 }
820
821 Dali::Window::NotificationLevel::Type WindowBaseEcoreX::GetNotificationLevel() const
822 {
823   return Dali::Window::NotificationLevel::NONE;
824 }
825
826 void WindowBaseEcoreX::SetOpaqueState( bool opaque )
827 {
828 }
829
830 bool WindowBaseEcoreX::SetScreenOffMode(Dali::Window::ScreenOffMode::Type screenOffMode)
831 {
832   return false;
833 }
834
835 Dali::Window::ScreenOffMode::Type WindowBaseEcoreX::GetScreenOffMode() const
836 {
837   return Dali::Window::ScreenOffMode::TIMEOUT;
838 }
839
840 bool WindowBaseEcoreX::SetBrightness( int brightness )
841 {
842   return false;
843 }
844
845 int WindowBaseEcoreX::GetBrightness() const
846 {
847   return 0;
848 }
849
850 bool WindowBaseEcoreX::GrabKey( Dali::KEY key, KeyGrab::KeyGrabMode grabMode )
851 {
852   return false;
853 }
854
855 bool WindowBaseEcoreX::UngrabKey( Dali::KEY key )
856 {
857   return false;
858 }
859
860 bool WindowBaseEcoreX::GrabKeyList( const Dali::Vector< Dali::KEY >& key, const Dali::Vector< KeyGrab::KeyGrabMode >& grabMode, Dali::Vector< bool >& result )
861 {
862   return false;
863 }
864
865 bool WindowBaseEcoreX::UngrabKeyList( const Dali::Vector< Dali::KEY >& key, Dali::Vector< bool >& result )
866 {
867   return false;
868 }
869
870 void WindowBaseEcoreX::GetDpi( unsigned int& dpiHorizontal, unsigned int& dpiVertical )
871 {
872   // calculate DPI
873   float xres, yres;
874
875   // 1 inch = 25.4 millimeters
876   xres = ecore_x_dpi_get();
877   yres = ecore_x_dpi_get();
878
879   dpiHorizontal = int( xres + 0.5f );  // rounding
880   dpiVertical   = int( yres + 0.5f );
881 }
882
883 void WindowBaseEcoreX::SetViewMode( ViewMode viewMode )
884 {
885   Ecore_X_Atom viewModeAtom( ecore_x_atom_get( "_E_COMP_3D_APP_WIN" ) );
886
887   if( viewModeAtom != None )
888   {
889     unsigned int value( static_cast< unsigned int >( viewMode ) );
890     ecore_x_window_prop_card32_set( mEcoreWindow, viewModeAtom, &value, 1 );
891   }
892 }
893
894 int WindowBaseEcoreX::GetScreenRotationAngle()
895 {
896   return 0;
897 }
898
899 void WindowBaseEcoreX::SetWindowRotationAngle( int degree )
900 {
901 }
902
903 void WindowBaseEcoreX::WindowRotationCompleted( int degree, int width, int height )
904 {
905 }
906
907 void WindowBaseEcoreX::SetTransparency( bool transparent )
908 {
909 }
910
911 unsigned int WindowBaseEcoreX::GetSurfaceId( Any surface ) const
912 {
913   unsigned int surfaceId = 0;
914
915   if ( surface.Empty() == false )
916   {
917     // check we have a valid type
918     DALI_ASSERT_ALWAYS( ( (surface.GetType() == typeid (XWindow) ) || (surface.GetType() == typeid (Ecore_X_Window) ) )
919                         && "Surface type is invalid" );
920
921     if ( surface.GetType() == typeid (Ecore_X_Window) )
922     {
923       surfaceId = AnyCast< Ecore_X_Window >( surface );
924     }
925     else
926     {
927       surfaceId = AnyCast< XWindow >( surface );
928     }
929   }
930   return surfaceId;
931 }
932
933 void WindowBaseEcoreX::CreateWindow( PositionSize positionSize, bool isTransparent )
934 {
935  if( isTransparent )
936  {
937    // create 32 bit window
938    mEcoreWindow = ecore_x_window_argb_new( 0, positionSize.x, positionSize.y, positionSize.width, positionSize.height );
939    mIsTransparent = true;
940  }
941  else
942  {
943    // create 24 bit window
944    mEcoreWindow = ecore_x_window_new( 0, positionSize.x, positionSize.y, positionSize.width, positionSize.height );
945  }
946
947  if ( mEcoreWindow == 0 )
948  {
949    DALI_ASSERT_ALWAYS( 0 && "Failed to create X window" );
950  }
951 }
952
953 } // namespace Adaptor
954
955 } // namespace Internal
956
957 } // namespace Dali
958
959 #pragma GCC diagnostic pop