modify license, permission and remove ^M char
[platform/framework/native/uifw.git] / src / ui / FUi_UiBuilder.cpp
1 //
2 // Open Service Platform
3 // Copyright (c) 2012-2013 Samsung Electronics Co., Ltd.
4 //
5 // Licensed under the Apache License, Version 2.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 //     http://www.apache.org/licenses/LICENSE-2.0/
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an ”AS IS” BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17
18 /**
19 * @file         FUi_UiBuilder.cpp
20 * @brief                This is the implementation file for _UiBuilder class.
21 */
22
23 #include <new>
24 #include <FAppApp.h>
25 #include <FUiIOrientationEventListener.h>
26 #include <FUi_ControlImplManager.h>
27 #include <FBaseSysLog.h>
28 #include "FUiCtrl_FrameImpl.h"
29 #include "FUi_UiBuilder.h"
30 #include "FUi_UiBuilderXmlHandler.h"
31 #include "FUi_ControlManager.h"
32
33 using namespace Tizen::Base;
34 using namespace Tizen::Base::Collection;
35 using namespace Tizen::Io;
36 using namespace Tizen::Ui;
37 using namespace Tizen::Ui::Controls;
38 using namespace Tizen::Media;
39 using namespace Tizen::Graphics;
40
41 namespace Tizen { namespace Ui
42 {
43 _UiBuilder::_UiBuilder(void)
44         : __version(0)
45         , __lastIndex(0)
46         , __logicalResolution(0)
47         , __pUiBuilderControlList(null)
48         , __pContainer(null)
49         , __rotate(UIBUIDER_SCREEN_NONE)
50         , __pTransform(null)
51         , __xmlFile(L"")
52 {
53 }
54
55 _UiBuilder::~_UiBuilder(void)
56 {
57         if (__pUiBuilderControlList)
58         {
59                 _UiBuilderControl* pUiBuilderControl = null;
60                 int controlCount = __pUiBuilderControlList->GetCount();
61                 for (int i = 0; i < controlCount; i++)
62                 {
63                         __pUiBuilderControlList->GetAt(i, pUiBuilderControl);
64                         delete pUiBuilderControl;
65                 }
66                 __pUiBuilderControlList->RemoveAll();
67                 delete __pUiBuilderControlList;
68                 __pUiBuilderControlList = null;
69         }
70 }
71
72 _UiBuilderControl*
73 _UiBuilder::GetControl(int index) const
74 {
75         SysTryReturn(NID_UI, index >= 0 && index < UIBUILDER_CONTROL_MAX_COUNT, null, E_INVALID_ARG,
76                                 "[E_INVALID_ARG] Index is over than max control count");
77
78         _UiBuilderControl* pUiBuilderControl = null;
79         __pUiBuilderControlList->GetAt(index, pUiBuilderControl);
80         if (pUiBuilderControl == null)
81         {
82                 SysLogException(NID_UI, GetLastResult(), "Failed to GetControl()");
83                 return null;
84         }
85
86         return pUiBuilderControl;
87 }
88
89 _UiBuilderControl*
90 _UiBuilder::GetControl(const Tizen::Base::String& id) const
91 {
92         IEnumeratorT<_UiBuilderControl*>* pEnum = __pUiBuilderControlList->GetEnumeratorN();
93         SysTryReturn(NID_UI, pEnum != null, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Unable to get IEnumeratorT.");
94         _UiBuilderControl* pUiBuilderControl = null;
95
96         while (pEnum->MoveNext() == E_SUCCESS)
97         {
98                 pEnum->GetCurrent(pUiBuilderControl);
99                 String controlId = pUiBuilderControl->GetId();
100
101                 if (controlId.Equals(id, false))
102                 {
103                         delete pEnum;
104                         return pUiBuilderControl;
105                 }
106         }
107         delete pEnum;
108         return null;
109
110 }
111
112 void
113 _UiBuilder::SetVersion(int xmlVersion)
114 {
115         __version = xmlVersion;
116 }
117
118 int
119 _UiBuilder::GetVersion(void) const
120 {
121         return __version;
122 }
123
124 result
125 _UiBuilder::Construct(const String& xmlFile, Container* pContainer)
126 {
127         result r = E_SUCCESS;
128
129         __pContainer =  pContainer;
130         __xmlFile = xmlFile;
131         __pUiBuilderControlList = new (std::nothrow) ArrayListT<_UiBuilderControl*>;
132         SysTryCatch(NID_UI, __pUiBuilderControlList != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Unable to create __pUiBuilderControlList.");
133
134         return r;
135
136         CATCH:
137
138         delete __pUiBuilderControlList;
139         return r;
140 }
141
142 result
143 _UiBuilder::MakeUI(_UiBuilderControl* pControl)
144 {
145         result r = E_SUCCESS;
146
147         _UiBuilderControlTableManager* pUiBuilderControlTableManager = _UiBuilderControlTableManager::GetInstance();
148         if(pUiBuilderControlTableManager == null)
149         {
150                 return E_OUT_OF_MEMORY;
151         }
152
153         for (int i = 0; i < UIBUILDER_CONTROL_MAX_COUNT; i++)
154         {
155                 if (pUiBuilderControlTableManager->GetName(i).IsEmpty())
156                 {
157                         break;
158                 }
159
160                 if (pControl->GetType().Equals(pUiBuilderControlTableManager->GetName(i), false))
161                 {
162                         _UiBuilderControlMakerFunctionPointer pControlMakerFunctionPointer = pUiBuilderControlTableManager->GetControlMaker(i);
163                         if (pControlMakerFunctionPointer != null)
164                         {
165                                 _UiBuilderControlMaker* pMaker = pControlMakerFunctionPointer(this);
166                                 r = pMaker->MakeControl(pControl);
167
168                                 delete pMaker;
169                                 return r;
170                         }
171                 }
172
173         }
174
175         return E_OPERATION_FAILED;
176 }
177
178 result
179 _UiBuilder::Parse(void)
180 {
181         File file;
182         ByteBuffer buffer;
183         FileAttributes attrib;
184         int readCount = 0;
185         byte* pXmlContents = null;
186         result r = E_SUCCESS;
187         bool findPath = false;
188         int size = 0;
189         String xmlFilePath(L"");
190         String temp;
191         String homePath;
192
193         __logicalResolution = _CoordinateSystem::GetInstance()->GetLogicalResolutionInt();
194
195         xmlFilePath.Append(__xmlFile);
196         xmlFilePath.Append(L".xml");
197
198         _ControlManager* pControlManager = _ControlManager::GetInstance();
199         SysTryReturn(NID_UI, pControlManager != null, E_OPERATION_FAILED, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Unable to get the control manager");
200
201     FloatDimension screenSize = pControlManager->GetScreenSizeF();
202
203         // find xml file with device deviceResolution
204
205         temp = xmlFilePath;
206         r = temp.Insert("/", 0);
207         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
208         r = temp.Insert(screenSize.height, 0);
209         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
210         r = temp.Insert("x", 0);
211         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
212         r = temp.Insert(screenSize.width, 0);
213         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
214         r = temp.Insert("res/", 0);
215         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
216
217         homePath = Tizen::App::App::GetInstance()->GetAppRootPath();
218         r = temp.Insert(homePath, 0);
219         SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
220         SysLog(NID_IO, "[UiBuilder] ui builder res path: %ls", temp.GetPointer());
221
222         // find device deviceResolution directory
223         if (!File::IsFileExist(temp))
224         {
225                 temp = xmlFilePath;
226                 r = temp.Insert("res/screen-size-normal/", 0);
227                 SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
228
229                 homePath = Tizen::App::App::GetInstance()->GetAppRootPath();
230                 r = temp.Insert(homePath, 0);
231                 SysTryReturn(NID_UI, r == E_SUCCESS, E_OPERATION_FAILED, E_OPERATION_FAILED, "[%s] Propagated.", GetErrorMessage(r));
232                 SysLog(NID_IO, "[UiBuilder] ui builder home path: %ls, res path: %ls", homePath.GetPointer(), temp.GetPointer());
233
234                 if (!pControlManager->IsCoordinateSystemLogical() || !File::IsFileExist(temp))         // if autoscale on, find ScreenSize normal
235                 {
236                         findPath = false;
237                         SysLogException(NID_UI, E_FILE_NOT_FOUND, "[E_FILE_NOT_FOUND] Parse failed -- %ls file not found.", temp.GetPointer());
238                         return E_FILE_NOT_FOUND;
239                 }
240         }
241
242         findPath = true;
243         xmlFilePath = temp;
244         r = file.Construct(xmlFilePath, L"r");
245         if (IsFailed(r))
246         {
247                 SysLogException(NID_UI, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Parse Failed -- XML file Construct.");
248                 return E_OPERATION_FAILED;
249         }
250
251         r = Tizen::Io::File::GetAttributes(xmlFilePath, attrib);
252         if (IsFailed(r))
253         {
254                 SysLogException(NID_UI, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Parse Failed -- XML file GetAttributes.");
255                 return E_OPERATION_FAILED;
256         }
257         size = (int) attrib.GetFileSize();
258
259         r = buffer.Construct(size);
260         if (IsFailed(r))
261         {
262                 SysLogException(NID_UI, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Parse Failed - Buffer Construct Failed.");
263                 return E_OPERATION_FAILED;
264         }
265
266         r = file.Read(buffer);
267         if (IsFailed(r))
268         {
269                 SysLogException(NID_UI, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Parse Failed -- can't read the file.");
270                 return E_OPERATION_FAILED;
271         }
272
273         readCount = buffer.GetPosition();
274         pXmlContents = new (std::nothrow) byte[readCount];
275         SysTryReturn(NID_UI, pXmlContents != null, E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Unable to create XmlContents.");
276         buffer.Flip();
277
278         r = buffer.GetArray(pXmlContents, 0, readCount);
279         if (IsFailed(r))
280         {
281                 SysLogException(NID_UI, E_OPERATION_FAILED, "[E_OPERATION_FAILED] Parse Failed -- buffer.GetArray is Failed.");
282                 delete[] pXmlContents;
283                 return E_OPERATION_FAILED;
284         }
285
286         _UiBuilderXmlHandler xmlHandler;
287         bool returnValue = false;
288         char* pXmlBuffer = (char*) pXmlContents;
289
290
291         returnValue = xmlHandler.Construct(this);
292         if (returnValue ==  false)
293         {
294                 delete[] pXmlContents;
295                 return E_OPERATION_FAILED;
296         }
297
298         r = xmlHandler.ParseXml(pXmlBuffer, readCount);
299         if (r != E_SUCCESS)
300         {
301                 SysLogException(NID_UI, r, "[%s] Propagation.", GetErrorMessage(r));
302                 return r;
303         }
304
305         if (__pTransform != null)
306         {
307                 _UiBuilderControl* pUiBuilderControl;
308                 for (int i = 0; i < UIBUILDER_CONTROL_MAX_COUNT; i++)
309                 {
310                         pUiBuilderControl = GetControl(i);
311                         if (pUiBuilderControl != null)
312                         {
313                                 _UiBuilderControlLayout* pUiBuilderControlLayoutPortrait;
314                                 _UiBuilderControlLayout* pUiBuilderControlLayoutLandscape;
315
316                                 pUiBuilderControlLayoutPortrait = pUiBuilderControl->GetAttribute(UIBUILDER_ATTRIBUTE_PORTRAIT);
317                 FloatRectangle rect =   pUiBuilderControlLayoutPortrait->GetRectF();
318                 FloatRectangle realBounds = __pTransform->Transform(rect);
319                                 pUiBuilderControlLayoutPortrait->SetRect(realBounds.x, realBounds.y, realBounds.width, realBounds.height);
320
321                                 pUiBuilderControlLayoutLandscape = pUiBuilderControl->GetAttribute(UIBUILDER_ATTRIBUTE_LANDSCAPE);
322                 rect = pUiBuilderControlLayoutLandscape->GetRectF();
323                                 realBounds = __pTransform->Transform(rect);
324                                 pUiBuilderControlLayoutLandscape->SetRect(realBounds.x, realBounds.y, realBounds.width,         realBounds.height);
325                         }
326                         else
327                         {
328                                 break;
329                         }
330                 }
331
332         }
333
334         //Make UiControls with UiBuilderControls
335         IEnumeratorT<_UiBuilderControl*>* pEnum = __pUiBuilderControlList->GetEnumeratorN();
336         SysTryCatch(NID_UI, pEnum != null, , E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Unable to get IEnumeratorT.");
337
338         while (pEnum->MoveNext() == E_SUCCESS)
339         {
340                 _UiBuilderControl* pUiBuilderControl = null;
341                 pEnum->GetCurrent(pUiBuilderControl);
342                 if (pUiBuilderControl != null)
343                 {
344                         r = MakeUI(pUiBuilderControl);
345                         SysTryCatch(NID_UI, r == E_SUCCESS, , r, "[UiBuilder] Failed to create control %ls", pUiBuilderControl->GetType().GetPointer());
346                         delete pUiBuilderControl;
347                 }
348         }
349
350         if (__pUiBuilderControlList)
351         {
352                 __pUiBuilderControlList->RemoveAll();
353                 delete __pUiBuilderControlList;
354                 __pUiBuilderControlList = null;
355         }
356
357         if (__pTransform)
358         {
359                 delete __pTransform;
360                 __pTransform = null;
361         }
362         delete[] pXmlContents;
363         delete pEnum;
364         return E_SUCCESS;
365
366         CATCH:
367         if (__pTransform)
368         {
369                 delete __pTransform;
370                 __pTransform = null;
371         }
372         delete[] pXmlContents;
373         delete pEnum;
374         return r;
375
376 }
377
378 _UiBuilderControl*
379 _UiBuilder::CreateControl(void)
380 {
381         if (__pUiBuilderControlList == null)
382         {
383                 __pUiBuilderControlList = new (std::nothrow) ArrayListT<_UiBuilderControl*>;
384                 SysTryReturn(NID_UI, __pUiBuilderControlList != null, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Unable to create __pUiBuilderControlList.");
385         }
386
387         _UiBuilderControl* pUiBuilderControl = null;
388         pUiBuilderControl = new (std::nothrow) _UiBuilderControl;
389         if (pUiBuilderControl != null)
390         {
391                 __pUiBuilderControlList->Add(pUiBuilderControl);
392         }
393         else
394         {
395                 SysLogException(NID_UI, E_OUT_OF_MEMORY, "Failed to CreateControl()");
396                 return null;
397         }
398
399         return  pUiBuilderControl;
400 }
401
402 Tizen::Ui::Container*
403 _UiBuilder::GetContainer() const
404 {
405         return __pContainer;
406 }
407
408 void
409 _UiBuilder::SetUiBuilderRotateState(_UiBuilderScreenRotate rotate)
410 {
411         __rotate = rotate;
412 }
413
414 _UiBuilderScreenRotate
415 _UiBuilder::GetUiBuilderRotateState() const
416 {
417         return __rotate;
418 }
419
420 result
421 _UiBuilder::SetFormXmlResolution(int formXmlResoluton)
422 {
423         result r = E_SUCCESS;
424
425         if (__pTransform == null)
426         {
427                 if (formXmlResoluton == 720 && __logicalResolution == 480)
428                 {
429                         __pTransform = _CoordinateSystem::GetTransformerN(720, _CoordinateSystem::GetInstance()->GetLogicalBaseScreenSize(), Dimension(480, 800), _CoordinateSystem::GetInstance()->GetPhysicalBaseScreenSize());
430                         SysTryReturn(NID_UI, __pTransform != null, null, GetLastResult(),
431                                                         "Failed to get Transformer");
432                 }
433                 if (formXmlResoluton == 480 && __logicalResolution == 720)
434                 {
435                         __pTransform = _CoordinateSystem::GetTransformerN(480, _CoordinateSystem::GetInstance()->GetLogicalBaseScreenSize(), Dimension(720, 1280), _CoordinateSystem::GetInstance()->GetPhysicalBaseScreenSize());
436                         SysTryReturn(NID_UI, __pTransform != null, GetLastResult(), GetLastResult(),
437                                                         "Failed to get Transformer");
438                 }
439         }
440         else
441         {
442                 SysLog(NID_UI, "__pTransform is already exists");
443                 r = E_SYSTEM;
444         }
445         return r;
446 }
447
448 void
449 _UiBuilder::SetLayoutOrientation(_UiBuilderControl* pUiBuilderControl, Tizen::Ui::Control* pControl)
450 {
451         _ControlImpl* pControlImpl = _ControlImpl::GetInstance(*pControl);
452         _UiBuilderControlLayout* pLayout = null;
453     FloatRectangle rect;
454
455         pLayout = pUiBuilderControl->GetAttribute(UIBUILDER_ATTRIBUTE_PORTRAIT);
456     rect = pLayout->GetRectF();
457     pControlImpl->SetBuilderBounds(_CONTROL_ORIENTATION_PORTRAIT, rect);
458
459         pLayout = pUiBuilderControl->GetAttribute(UIBUILDER_ATTRIBUTE_LANDSCAPE);
460     rect = pLayout->GetRectF();
461     pControlImpl->SetBuilderBounds(_CONTROL_ORIENTATION_LANDSCAPE, rect);
462 }
463
464 _ICoordinateSystemTransformer*
465 _UiBuilder::GetTransformer() const
466 {
467         return __pTransform;
468 }
469
470 } }  // Tizen::Ui