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