Merge remote-tracking branch 'origin/tizen' into new_text
[platform/core/uifw/dali-adaptor.git] / adaptors / common / virtual-keyboard-impl.cpp
1 /*
2  * Copyright (c) 2014 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 "virtual-keyboard-impl.h"
20
21 // EXTERNAL INCLUDES
22 #include <algorithm>
23
24 #include <dali/public-api/common/vector-wrapper.h>
25 #include <dali/integration-api/debug.h>
26
27 // INTERNAL INCLUDES
28 #include <adaptor.h>
29 #include <locale-utils.h>
30 #include <imf-manager-impl.h>
31
32
33 namespace Dali
34 {
35
36 namespace Internal
37 {
38
39 namespace Adaptor
40 {
41
42 namespace VirtualKeyboard
43 {
44
45 namespace
46 {
47 #if defined(DEBUG_ENABLED)
48 Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Verbose, false, "LOG_VIRTUAL_KEYBOARD");
49 #endif
50
51 //forward declarations
52 void InputPanelGeometryChangedCallback ( void *data, Ecore_IMF_Context *context, int value );
53 void InputPanelLanguageChangeCallback( void* data, Ecore_IMF_Context* context, int value );
54
55 // Signals
56 Dali::VirtualKeyboard::StatusSignalType gKeyboardStatusSignal;
57 Dali::VirtualKeyboard::VoidSignalType   gKeyboardResizeSignal;
58 Dali::VirtualKeyboard::VoidSignalType   gKeyboardLanguageChangedSignal;
59
60 Dali::VirtualKeyboard::ReturnKeyType gReturnKeyType = Dali::VirtualKeyboard::DEFAULT;  // the currently used return key type.
61
62 void InputPanelStateChangeCallback( void* data, Ecore_IMF_Context* context, int value )
63 {
64   switch (value)
65   {
66     case ECORE_IMF_INPUT_PANEL_STATE_SHOW:
67     {
68       DALI_LOG_INFO( gLogFilter, Debug::General, "VKB ECORE_IMF_INPUT_PANEL_STATE_SHOW\n" );
69
70       gKeyboardStatusSignal.Emit( true );
71
72       break;
73     }
74
75     case ECORE_IMF_INPUT_PANEL_STATE_HIDE:
76     {
77       DALI_LOG_INFO( gLogFilter, Debug::General, "VKB ECORE_IMF_INPUT_PANEL_STATE_HIDE\n" );
78
79       gKeyboardStatusSignal.Emit( false );
80
81       break;
82     }
83
84     case ECORE_IMF_INPUT_PANEL_STATE_WILL_SHOW:
85     default:
86     {
87       // Do nothing
88       break;
89     }
90   }
91 }
92
93 void InputPanelLanguageChangeCallback( void* data, Ecore_IMF_Context* context, int value )
94 {
95   DALI_LOG_INFO( gLogFilter, Debug::General, "VKB InputPanelLanguageChangeCallback" );
96
97   // Emit the signal that the language has changed
98   gKeyboardLanguageChangedSignal.Emit();
99 }
100
101 void InputPanelGeometryChangedCallback ( void *data, Ecore_IMF_Context *context, int value )
102 {
103   DALI_LOG_INFO( gLogFilter, Debug::General, "VKB InputPanelGeometryChangedCallback\n" );
104
105   // Emit signal that the keyboard is resized
106   gKeyboardResizeSignal.Emit();
107 }
108
109 } // unnamed namespace
110
111 void ConnectCallbacks( Ecore_IMF_Context *imfContext )
112 {
113   if( imfContext )
114   {
115     DALI_LOG_INFO( gLogFilter, Debug::General, "VKB ConnectPanelCallbacks\n" );
116
117     ecore_imf_context_input_panel_event_callback_add( imfContext, ECORE_IMF_INPUT_PANEL_STATE_EVENT,    InputPanelStateChangeCallback,     NULL );
118     ecore_imf_context_input_panel_event_callback_add( imfContext, ECORE_IMF_INPUT_PANEL_LANGUAGE_EVENT, InputPanelLanguageChangeCallback,  NULL );
119     ecore_imf_context_input_panel_event_callback_add( imfContext, ECORE_IMF_INPUT_PANEL_GEOMETRY_EVENT, InputPanelGeometryChangedCallback, NULL );
120   }
121 }
122
123 void DisconnectCallbacks( Ecore_IMF_Context *imfContext )
124 {
125   if( imfContext )
126   {
127     DALI_LOG_INFO( gLogFilter, Debug::General, "VKB DisconnectPanelCallbacks\n" );
128
129     ecore_imf_context_input_panel_event_callback_del( imfContext, ECORE_IMF_INPUT_PANEL_STATE_EVENT,    InputPanelStateChangeCallback     );
130     ecore_imf_context_input_panel_event_callback_del( imfContext, ECORE_IMF_INPUT_PANEL_LANGUAGE_EVENT, InputPanelLanguageChangeCallback  );
131     ecore_imf_context_input_panel_event_callback_del( imfContext, ECORE_IMF_INPUT_PANEL_GEOMETRY_EVENT, InputPanelGeometryChangedCallback );
132   }
133 }
134
135 void Show()
136 {
137   Dali::ImfManager imfManager = ImfManager::Get(); // Create ImfManager instance (if required) to show the keyboard
138   Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
139
140   if( imfContext )
141   {
142     ecore_imf_context_input_panel_show( imfContext );
143   }
144 }
145
146 void Hide()
147 {
148   if( ImfManager::IsAvailable() /* We do not want to create an ImfManager instance*/ )
149   {
150     Dali::ImfManager imfManager = ImfManager::Get();
151     Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
152
153     if( imfContext )
154     {
155       ecore_imf_context_input_panel_hide( imfContext );
156     }
157   }
158 }
159
160 bool IsVisible()
161 {
162   if( ImfManager::IsAvailable() /* We do not want to create an ImfManager instance */ )
163   {
164     DALI_LOG_INFO( gLogFilter, Debug::General, "IsVisible\n" );
165
166     Dali::ImfManager imfManager = ImfManager::Get();
167     Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
168
169     if ( imfContext )
170     {
171       if (ecore_imf_context_input_panel_state_get(imfContext) == ECORE_IMF_INPUT_PANEL_STATE_SHOW ||
172           ecore_imf_context_input_panel_state_get(imfContext) == ECORE_IMF_INPUT_PANEL_STATE_WILL_SHOW)
173       {
174         return true;
175       }
176     }
177   }
178
179   return false;
180 }
181
182 void SetReturnKeyType( Dali::VirtualKeyboard::ReturnKeyType type )
183 {
184   Dali::ImfManager imfManager = ImfManager::Get(); // Create ImfManager instance (if required) when setting values
185   Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
186
187   if( imfContext )
188   {
189     DALI_LOG_INFO( gLogFilter, Debug::General, "VKB Retrun key type is changed[%d]\n", type );
190
191     gReturnKeyType = type;
192     ecore_imf_context_input_panel_return_key_type_set( imfContext, static_cast<Ecore_IMF_Input_Panel_Return_Key_Type>( type ) );
193   }
194 }
195
196 Dali::VirtualKeyboard::ReturnKeyType GetReturnKeyType()
197 {
198   return gReturnKeyType;
199 }
200
201 void EnablePrediction(const bool enable)
202 {
203   Dali::ImfManager imfManager = ImfManager::Get(); // Create ImfManager instance (if required) when enabling prediction
204   Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
205
206   if ( imfContext )
207   {
208     ecore_imf_context_prediction_allow_set( imfContext, (enable)? EINA_TRUE : EINA_FALSE);
209   }
210 }
211
212 bool IsPredictionEnabled()
213 {
214   if ( ImfManager::IsAvailable() /* We do not want to create an instance of ImfManger */ )
215   {
216     Dali::ImfManager imfManager = ImfManager::Get();
217     Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
218
219     if ( imfContext )
220     {
221       // predictive text is enabled.
222       if ( ecore_imf_context_input_panel_enabled_get( imfContext ) == EINA_TRUE )
223       {
224         return true;
225       }
226     }
227   }
228
229   return false;
230 }
231
232 Rect<int> GetSizeAndPosition()
233 {
234   int xPos, yPos, width, height;
235
236   width = height = xPos = yPos = 0;
237   Dali::ImfManager imfManager = ImfManager::Get(); // Create ImfManager instance (if required) as we may need to do some size related setup in the application
238   Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
239
240   if( imfContext )
241   {
242     ecore_imf_context_input_panel_geometry_get(imfContext, &xPos, &yPos, &width, &height);
243   }
244   else
245   {
246     DALI_LOG_WARNING("VKB Unable to get IMF Context so GetSize unavailable\n");
247     // return 0 as real size unknown.
248   }
249
250   return Rect<int>(xPos,yPos,width,height);
251 }
252
253 Dali::VirtualKeyboard::StatusSignalType& StatusChangedSignal()
254 {
255   return gKeyboardStatusSignal;
256 }
257
258 Dali::VirtualKeyboard::VoidSignalType& ResizedSignal()
259 {
260   return gKeyboardResizeSignal;
261 }
262
263 Dali::VirtualKeyboard::VoidSignalType& LanguageChangedSignal()
264 {
265   return gKeyboardLanguageChangedSignal;
266 }
267
268 Dali::VirtualKeyboard::TextDirection GetTextDirection()
269 {
270   Dali::VirtualKeyboard::TextDirection direction ( Dali::VirtualKeyboard::LeftToRight );
271
272   if ( ImfManager::IsAvailable() /* We do not want to create an instance of ImfManager */ )
273   {
274     Dali::ImfManager imfManager = ImfManager::Get();
275
276     if ( imfManager )
277     {
278       Ecore_IMF_Context* imfContext = reinterpret_cast<Ecore_IMF_Context*>( imfManager.GetContext() );
279
280       if ( imfContext )
281       {
282         char* locale( NULL );
283         ecore_imf_context_input_panel_language_locale_get( imfContext, &locale );
284
285         if ( locale )
286         {
287           direction = Locale::GetTextDirection( std::string( locale ) );
288           free( locale );
289         }
290       }
291     }
292   }
293   return direction;
294 }
295
296 } // namespace VirtualKeyboard
297
298 } // namespace Adaptor
299
300 } // namespace Internal
301
302 } // namespace Dali