Merge branch 'tizen_2.1' into devgfx
[platform/framework/native/uifw.git] / src / ui / FUi_GridLayoutImpl.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  * @file                FUi_GridLayoutImpl.cpp
19  * @brief       This is the implementation file for _GridLayoutImpl class.
20  *
21  * This file contains the implementation of _GridLayoutImpl class.
22  */
23
24 #include "FUi_GridLayoutImpl.h"
25 #include "FUi_CoordinateSystemUtils.h"
26
27 namespace Tizen { namespace Ui
28 {
29
30 // _GridLayoutImpl implementation
31 _GridLayoutImpl::_GridLayoutImpl(GridLayout* pPublicLayout, _Layout::TableLayout* pCoreLayout)
32         : _LayoutImpl(pPublicLayout, pCoreLayout)
33         , __maxRow(0)
34         , __maxColumn(0)
35 {
36 }
37
38 _GridLayoutImpl::~_GridLayoutImpl()
39 {
40 }
41
42 Tizen::Ui::LayoutType
43 _GridLayoutImpl::GetLayoutType(void) const
44 {
45         return LAYOUT_GRID;
46 }
47
48 _GridLayoutImpl*
49 _GridLayoutImpl::CreateGridLayoutImplN(GridLayout* pPublicLayout, int maxRow, int maxColumn)
50 {
51         ClearLastResult();
52
53         _Layout::TableLayout* pCoreLayout = null;
54         _GridLayoutImpl* pImplLayout = null;
55         result r = E_SUCCESS;
56
57         pCoreLayout = _Layout::TableLayout::CreateTableLayoutN();
58         r = GetLastResult();
59         SysTryReturn(NID_UI, pCoreLayout != null, null, r, "[%s] Propagating.", GetErrorMessage(r));
60
61         pImplLayout = new (std::nothrow) _GridLayoutImpl(pPublicLayout, pCoreLayout);
62         r = CheckConstruction(pCoreLayout, pImplLayout);
63         SysTryReturn(NID_UI, r == E_SUCCESS, null, r, "[%s] Propagating.", GetErrorMessage(r));
64
65         r = pImplLayout->Construct(maxRow, maxColumn);
66         if (r != E_SUCCESS)
67         {
68                 delete pImplLayout;
69                 SysTryReturn(NID_UI, false, null, r, "[%s] Propagating.", GetErrorMessage(r));
70         }
71
72         return pImplLayout;
73 }
74
75 const char*
76 _GridLayoutImpl::GetPublicClassName(void) const
77 {
78         return "Tizen::Ui::GridLayout";
79 }
80
81 const GridLayout&
82 _GridLayoutImpl::GetPublic(void) const
83 {
84         return static_cast <const GridLayout&>(_LayoutImpl::GetPublic());
85 }
86
87 GridLayout&
88 _GridLayoutImpl::GetPublic(void)
89 {
90         return static_cast <GridLayout&>(_LayoutImpl::GetPublic());
91 }
92
93 const _Layout::TableLayout&
94 _GridLayoutImpl::GetCore(void) const
95 {
96         return static_cast <const _Layout::TableLayout&>(_LayoutImpl::GetCore());
97 }
98
99 _Layout::TableLayout&
100 _GridLayoutImpl::GetCore(void)
101 {
102         return static_cast <_Layout::TableLayout&>(_LayoutImpl::GetCore());
103 }
104
105 const _GridLayoutImpl*
106 _GridLayoutImpl::GetInstance(const GridLayout& layout)
107 {
108         return static_cast <const _GridLayoutImpl*>(_LayoutImpl::GetInstance(layout));
109 }
110
111 _GridLayoutImpl*
112 _GridLayoutImpl::GetInstance(GridLayout& layout)
113 {
114         return static_cast <_GridLayoutImpl*>(_LayoutImpl::GetInstance(layout));
115 }
116
117 result
118 _GridLayoutImpl::Construct(int maxRow, int maxColumn)
119 {
120         ClearLastResult();
121
122         result r = GetCore().CreateTable(maxRow, maxColumn);
123         SysTryReturn(NID_UI, r == E_SUCCESS, r, r, "[%s] Propagating.", GetErrorMessage(r));
124
125         __maxRow = maxRow;
126         __maxColumn = maxColumn;
127
128         return E_SUCCESS;
129 }
130
131 result
132 _GridLayoutImpl::SetColumnStretchable(int columnIndex, bool stretchable)
133 {
134         ClearLastResult();
135
136         return GetCore().SetColumnStretchable(columnIndex, stretchable);
137 }
138
139 result
140 _GridLayoutImpl::SetColumnShrinkable(int columnIndex, bool shrinkable)
141 {
142         ClearLastResult();
143
144         return GetCore().SetColumnShrinkable(columnIndex, shrinkable);
145 }
146
147 result
148 _GridLayoutImpl::SetColumnCollapsed(int columnIndex, bool collapsed)
149 {
150         ClearLastResult();
151
152         return GetCore().SetColumnCollapsed(columnIndex, collapsed);
153 }
154
155 result
156 _GridLayoutImpl::SetAllColumnsStretchable(bool stretchable)
157 {
158         ClearLastResult();
159
160         result r = E_SUCCESS;
161         bool* pOldStretchable = new (std::nothrow) bool[__maxColumn];
162         SysTryReturn(NID_UI, pOldStretchable != null, E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Memory shortage.");
163         memset(pOldStretchable, 0, sizeof(bool) * __maxColumn);
164
165         int col = 0;
166         for (col = 0; col < __maxColumn; col++)
167         {
168                 pOldStretchable[col] = GetCore().GetColumnStretchable(col);
169                 r = GetLastResult();
170                 if (r != E_SUCCESS)
171                 {
172                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max column is invalid value.");
173                         goto CATCH;
174                 }
175
176                 r = GetCore().SetColumnStretchable(col, stretchable);
177                 if (r != E_SUCCESS)
178                 {
179                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max column is invalid value.");
180                         goto CATCH;
181                 }
182         }
183
184         delete[] pOldStretchable;
185
186         return r;
187
188 CATCH:
189         for (int colIndex = 0; colIndex < col; colIndex++)
190         {
191                 GetCore().SetColumnStretchable(colIndex, pOldStretchable[colIndex]);
192         }
193
194         delete[] pOldStretchable;
195
196         return r;
197 }
198
199 result
200 _GridLayoutImpl::SetAllColumnsShrinkable(bool shrinkable)
201 {
202         ClearLastResult();
203
204         result r = E_SUCCESS;
205         bool* pOldShrinkable = new (std::nothrow) bool[__maxColumn];
206         SysTryReturn(NID_UI, pOldShrinkable != null, E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Memory shortage.");
207         memset(pOldShrinkable, 0, sizeof(bool) * __maxColumn);
208
209         int col = 0;
210         for (col = 0; col < __maxColumn; col++)
211         {
212                 pOldShrinkable[col] = GetCore().GetColumnShrinkable(col);
213                 r = GetLastResult();
214                 if (r != E_SUCCESS)
215                 {
216                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max column is invalid value.");
217                         goto CATCH;
218                 }
219
220                 r = GetCore().SetColumnShrinkable(col, shrinkable);
221                 if (r != E_SUCCESS)
222                 {
223                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max column is invalid value.");
224                         goto CATCH;
225                 }
226         }
227
228         delete[] pOldShrinkable;
229
230         return r;
231
232 CATCH:
233         for (int colIndex = 0; colIndex < col; colIndex++)
234         {
235                 GetCore().SetColumnShrinkable(colIndex, pOldShrinkable[colIndex]);
236         }
237
238         delete[] pOldShrinkable;
239
240         return r;
241 }
242
243 result
244 _GridLayoutImpl::SetColumnSpacing(int columnIndex, float space)
245 {
246         ClearLastResult();
247
248         return GetCore().SetColumnSpacing(columnIndex, space);
249 }
250
251 result
252 _GridLayoutImpl::SetRowStretchable(int rowIndex, bool stretchable)
253 {
254         ClearLastResult();
255
256         return GetCore().SetRowStretchable(rowIndex, stretchable);
257 }
258
259 result
260 _GridLayoutImpl::SetRowShrinkable(int rowIndex, bool shrinkable)
261 {
262         ClearLastResult();
263
264         return GetCore().SetRowShrinkable(rowIndex, shrinkable);
265 }
266
267 result
268 _GridLayoutImpl::SetRowCollapsed(int rowIndex, bool collapsed)
269 {
270         ClearLastResult();
271
272         return GetCore().SetRowCollapsed(rowIndex, collapsed);
273 }
274
275 result
276 _GridLayoutImpl::SetAllRowsStretchable(bool stretchable)
277 {
278         ClearLastResult();
279
280         result r = E_SUCCESS;
281         bool* pOldStretchable = new (std::nothrow) bool[__maxRow];
282         SysTryReturn(NID_UI, pOldStretchable != null, E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Memory shortage.");
283         memset(pOldStretchable, 0, sizeof(bool) * __maxRow);
284
285
286         int row = 0;
287         for (row = 0; row < __maxRow; row++)
288         {
289                 pOldStretchable[row] = GetCore().GetRowStretchable(row);
290                 r = GetLastResult();
291                 if (r != E_SUCCESS)
292                 {
293                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max row is invalid value.");
294                         goto CATCH;
295                 }
296
297                 r = GetCore().SetRowStretchable(row, stretchable);
298                 if (r != E_SUCCESS)
299                 {
300                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max row is invalid value.");
301                         goto CATCH;
302                 }
303         }
304
305         delete[] pOldStretchable;
306
307         return r;
308
309 CATCH:
310         for (int rowIndex = 0; rowIndex < row; rowIndex++)
311         {
312                 GetCore().SetRowStretchable(rowIndex, pOldStretchable[rowIndex]);
313         }
314
315         delete[] pOldStretchable;
316
317         return r;
318 }
319
320 result
321 _GridLayoutImpl::SetAllRowsShrinkable(bool shrinkable)
322 {
323         ClearLastResult();
324
325         result r = E_SUCCESS;
326         bool* pOldShrinkable = new (std::nothrow) bool[__maxRow];
327         SysTryReturn(NID_UI, pOldShrinkable != null, E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Memory shortage.");
328         memset(pOldShrinkable, 0, sizeof(bool) * __maxRow);
329
330         int row = 0;
331         for (row = 0; row < __maxRow; row++)
332         {
333                 pOldShrinkable[row] = GetCore().GetRowShrinkable(row);
334                 r = GetLastResult();
335                 if (r != E_SUCCESS)
336                 {
337                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max row is invalid value.");
338                         goto CATCH;
339                 }
340
341                 r = GetCore().SetRowShrinkable(row, shrinkable);
342                 if (r != E_SUCCESS)
343                 {
344                         SysLogException(NID_UI, E_INVALID_ARG, "[E_INVALID_ARG] max row is invalid value.");
345                         goto CATCH;
346                 }
347         }
348
349         delete[] pOldShrinkable;
350
351         return r;
352
353 CATCH:
354         for (int rowIndex = 0; rowIndex < row; rowIndex++)
355         {
356                 GetCore().SetRowShrinkable(rowIndex, pOldShrinkable[rowIndex]);
357         }
358         delete[] pOldShrinkable;
359
360         return r;
361 }
362
363 result
364 _GridLayoutImpl::SetRowSpacing(int rowIndex, float space)
365 {
366         ClearLastResult();
367
368         return GetCore().SetRowSpacing(rowIndex, space);
369 }
370
371 result
372 _GridLayoutImpl::SetPosition(_ControlImpl& control, int row, int column, int rowSpan, int columnSpan)
373 {
374         ClearLastResult();
375
376         _Layout::LayoutItem& layoutItem = control.GetLayoutContainer();
377
378         result r = E_SUCCESS;
379         int rowSize = 1;
380         int colSize = 1;
381
382         SysTryReturn(NID_UI, GetCore().ItemExists(layoutItem), E_INVALID_ARG, E_INVALID_ARG,
383                                 "[E_INVALID_ARG] The control is not belong to layout");
384
385         SysTryReturn(NID_UI, row >= 0, E_OUT_OF_RANGE, E_OUT_OF_RANGE,
386                                 "[E_OUT_OF_RANGE] Negative input argument : row(%d)", row);
387         SysTryReturn(NID_UI, row < __maxRow, E_OUT_OF_RANGE, E_OUT_OF_RANGE,
388                                 "[E_OUT_OF_RANGE]  Input Argument row over the max row : row(%d), maxRow(%d)", row, __maxRow);
389         SysTryReturn(NID_UI, column >= 0, E_OUT_OF_RANGE, E_OUT_OF_RANGE,
390                                 "[E_OUT_OF_RANGE] Negative input argument : column(%d)", column);
391         SysTryReturn(NID_UI, column < __maxColumn, E_OUT_OF_RANGE, E_OUT_OF_RANGE,
392                                 "[E_OUT_OF_RANGE]  Input Argument column over the max column : column(%d), maxColumn(%d)", column, __maxColumn);
393
394         SysTryReturn(NID_UI, rowSpan >= 0, E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The row span is negative value.");
395         SysTryReturn(NID_UI, columnSpan >= 0, E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The column span is negative value.");
396
397         SysTryReturn(NID_UI, (row + rowSpan - 1) < __maxRow, E_OUT_OF_RANGE, E_OUT_OF_RANGE, "[E_OUT_OF_RANGE] Out of range.");
398         SysTryReturn(NID_UI, (column + columnSpan - 1) < __maxColumn, E_OUT_OF_RANGE, E_OUT_OF_RANGE,
399                                 "[E_OUT_OF_RANGE] Out of range.");
400
401         r = GetCore().GetMergeSize(row, column, rowSize, colSize);
402         SysTryReturn(NID_UI, (r == E_SUCCESS), r, r,
403                                 "The specified span tries to include a cell which is already included in another span.");
404
405         _Layout::LayoutItem* prevItem = GetCore().GetItem(row, column);
406         if (prevItem)
407         {
408                 if (prevItem != &layoutItem)
409                 {
410                         r = GetCore().SwapItemPosition(layoutItem, *prevItem);
411                 }
412         }
413         else
414         {
415                 r = GetCore().SetItemPosition(layoutItem, row, column);
416         }
417         GetCore().SetFillCell(row, column, false, false);
418
419         if (r != E_SUCCESS)
420         {
421                 return r;
422         }
423
424         if (rowSpan != rowSize || columnSpan != colSize)
425         {
426                 for (int y = 0; y < rowSpan; y++)
427                 {
428                         for (int x = 0; x < columnSpan; x++)
429                         {
430                                 r = GetCore().Unmerge(row + y, column + x);
431                                 if (r == E_SYSTEM)
432                                 {
433                                         return r;
434                                 }
435                         }
436                 }
437
438                 r = GetCore().Merge(row, column, row + rowSpan - 1, column + columnSpan - 1);
439                 GetCore().SetFillCell(row, column, true, true);
440         }
441
442         return r;
443 }
444
445 int
446 _GridLayoutImpl::GetRowCount() const
447 {
448         return __maxRow;
449 }
450
451 int
452 _GridLayoutImpl::GetColumnCount() const
453 {
454         return __maxColumn;
455 }
456
457 }} // Tizen::Ui