aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/elementary/src/lib/elc_naviframe.c
diff options
context:
space:
mode:
Diffstat (limited to 'libraries/elementary/src/lib/elc_naviframe.c')
-rw-r--r--libraries/elementary/src/lib/elc_naviframe.c1530
1 files changed, 1530 insertions, 0 deletions
diff --git a/libraries/elementary/src/lib/elc_naviframe.c b/libraries/elementary/src/lib/elc_naviframe.c
new file mode 100644
index 0000000..49e838e
--- /dev/null
+++ b/libraries/elementary/src/lib/elc_naviframe.c
@@ -0,0 +1,1530 @@
1#include <Elementary.h>
2#include "elm_priv.h"
3
4typedef struct _Widget_Data Widget_Data;
5typedef struct _Elm_Naviframe_Item Elm_Naviframe_Item;
6typedef struct _Elm_Naviframe_Content_Item_Pair Elm_Naviframe_Content_Item_Pair;
7typedef struct _Elm_Naviframe_Text_Item_Pair Elm_Naviframe_Text_Item_Pair;
8
9struct _Widget_Data
10{
11 Eina_Inlist *stack;
12 Evas_Object *base;
13 Eina_Bool preserve: 1;
14 Eina_Bool auto_pushed: 1;
15 Eina_Bool freeze_events: 1;
16};
17
18struct _Elm_Naviframe_Content_Item_Pair
19{
20 EINA_INLIST;
21 const char *part;
22 Elm_Naviframe_Item *it;
23};
24
25struct _Elm_Naviframe_Text_Item_Pair
26{
27 EINA_INLIST;
28 const char *part;
29};
30
31struct _Elm_Naviframe_Item
32{
33 ELM_WIDGET_ITEM;
34 EINA_INLIST;
35 Eina_Inlist *content_list;
36 Eina_Inlist *text_list;
37 Evas_Object *content;
38 Evas_Object *title_prev_btn;
39 Evas_Object *title_next_btn;
40 Evas_Object *title_icon;
41 const char *style;
42 Evas_Coord minw;
43 Evas_Coord minh;
44 Eina_Bool back_btn: 1;
45 Eina_Bool title_visible: 1;
46 Eina_Bool content_unfocusable : 1;
47};
48
49static const char *widtype = NULL;
50
51//widget signals
52static const char SIG_TRANSITION_FINISHED[] = "transition,finished";
53static const char SIG_TITLE_CLICKED[] = "title,clicked";
54
55static const Evas_Smart_Cb_Description _signals[] = {
56 {SIG_TRANSITION_FINISHED, ""},
57 {SIG_TITLE_CLICKED, ""},
58 {NULL, NULL}
59};
60
61static void _text_set_hook(Evas_Object *obj,
62 const char *part,
63 const char *label);
64static const char *_text_get_hook(const Evas_Object *obj, const char *part);
65static void _content_set_hook(Evas_Object *obj,
66 const char *part,
67 Evas_Object *content);
68static Evas_Object *_content_get_hook(const Evas_Object *obj, const char *part);
69static Evas_Object *_content_unset_hook(Evas_Object *obj, const char *part);
70static void _del_hook(Evas_Object *obj);
71static void _theme_hook(Evas_Object *obj);
72static void _emit_hook(Evas_Object *obj,
73 const char *emission,
74 const char *source);
75static void _disable_hook(Evas_Object *obj);
76static void _item_text_set_hook(Elm_Object_Item *it,
77 const char *part,
78 const char *label);
79static const char *_item_text_get_hook(const Elm_Object_Item *it,
80 const char *part);
81static void _item_content_set_hook(Elm_Object_Item *it,
82 const char *part,
83 Evas_Object *content);
84static Evas_Object *_item_content_get_hook(const Elm_Object_Item *it,
85 const char *part);
86static Evas_Object *_item_content_unset_hook(Elm_Object_Item *it,
87 const char *part);
88static void _item_signal_emit_hook(Elm_Object_Item *it,
89 const char *emission,
90 const char *source);
91static void _item_title_visible_update(Elm_Naviframe_Item *navi_it);
92static void _sizing_eval(Evas_Object *obj);
93static void _move(void *data, Evas *e, Evas_Object *obj, void *event_info);
94static void _resize(void *data,
95 Evas *e,
96 Evas_Object *obj,
97 void *event_info);
98static void _title_clicked(void *data, Evas_Object *obj,
99 const char *emission,
100 const char *source);
101static void _back_btn_clicked(void *data,
102 Evas_Object *obj,
103 void *event_info);
104static Evas_Object *_back_btn_new(Evas_Object *obj);
105static void _item_content_del(void *data,
106 Evas *e,
107 Evas_Object *obj,
108 void *event_info);
109static void _title_content_del(void *data,
110 Evas *e,
111 Evas_Object *obj,
112 void *event_info);
113static void _title_prev_btn_del(void *data,
114 Evas *e,
115 Evas_Object *obj,
116 void *event_info);
117static void _title_next_btn_del(void *data,
118 Evas *e,
119 Evas_Object *obj,
120 void *event_info);
121static void _title_icon_del(void *data,
122 Evas *e,
123 Evas_Object *obj,
124 void *event_info);
125static void _title_content_set(Elm_Naviframe_Item *it,
126 const char *part,
127 Evas_Object *content);
128static void _title_prev_btn_set(Elm_Naviframe_Item *it,
129 Evas_Object *btn,
130 Eina_Bool back_btn);
131static void _title_next_btn_set(Elm_Naviframe_Item *it, Evas_Object *btn);
132static void _title_icon_set(Elm_Naviframe_Item *it, Evas_Object *icon);
133static Evas_Object * _item_content_unset(Elm_Naviframe_Item *it);
134static Evas_Object * _title_prev_btn_unset(Elm_Naviframe_Item *it);
135static Evas_Object * _title_next_btn_unset(Elm_Naviframe_Item *it);
136static Evas_Object * _title_icon_unset(Elm_Naviframe_Item *it);
137static Evas_Object * _title_content_unset(Elm_Naviframe_Item *it,
138 const char *part);
139static void _item_del(Elm_Naviframe_Item *it);
140static Eina_Bool _item_del_pre_hook(Elm_Object_Item *it);
141static void _pushed_finished(void *data,
142 Evas_Object *obj,
143 const char *emission,
144 const char *source);
145static void _popped_finished(void *data,
146 Evas_Object *obj,
147 const char *emission,
148 const char *source);
149static void _show_finished(void *data,
150 Evas_Object *obj,
151 const char *emission,
152 const char *source);
153static void _changed_size_hints(void *data,
154 Evas *e,
155 Evas_Object *obj,
156 void *event_info);
157static void _item_content_set(Elm_Naviframe_Item *navi_it,
158 Evas_Object *content);
159static void _item_style_set(Elm_Naviframe_Item *navi_it,
160 const char *item_style);
161static Elm_Naviframe_Item * _item_new(Evas_Object *obj,
162 const char *title_label,
163 Evas_Object *prev_btn,
164 Evas_Object *next_btn,
165 Evas_Object *content,
166 const char *item_style);
167static Eina_Bool _focus_next_hook(const Evas_Object *obj,
168 Elm_Focus_Direction dir,
169 Evas_Object **next);
170
171static void
172_del_hook(Evas_Object *obj)
173{
174 Widget_Data *wd;
175 Elm_Naviframe_Item *it;
176
177 wd = elm_widget_data_get(obj);
178 if (!wd) return;
179
180 if (wd->stack)
181 {
182 while (wd->stack->last)
183 {
184 it = EINA_INLIST_CONTAINER_GET(wd->stack->last,
185 Elm_Naviframe_Item);
186 wd->stack = eina_inlist_remove(wd->stack, wd->stack->last);
187 _item_del(it);
188 elm_widget_item_free(it);
189 if (!wd->stack) break;
190 }
191 }
192 free(wd);
193}
194
195static void
196_theme_hook(Evas_Object *obj)
197{
198 Widget_Data *wd;
199 Elm_Naviframe_Item *it;
200
201 wd = elm_widget_data_get(obj);
202 if (!wd) return;
203
204 _elm_theme_object_set(obj,
205 wd->base,
206 "naviframe",
207 "base",
208 elm_widget_style_get(obj));
209
210 EINA_INLIST_FOREACH(wd->stack, it)
211 {
212 _item_style_set(it, it->style);
213 _item_title_visible_update(it);
214 }
215}
216
217static void _emit_hook(Evas_Object *obj,
218 const char *emission,
219 const char *source)
220{
221 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
222 if (!it) return;
223 return elm_object_item_signal_emit(it, emission, source);
224}
225
226static void
227_disable_hook(Evas_Object *obj __UNUSED__)
228{
229 //FIXME:
230}
231
232static void
233_item_text_set_hook(Elm_Object_Item *it,
234 const char *part,
235 const char *label)
236{
237 Elm_Naviframe_Text_Item_Pair *pair = NULL;
238 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
239 char buf[1024];
240
241 if (!part || !strcmp(part, "default"))
242 snprintf(buf, sizeof(buf), "elm.text.title");
243 else if (!strcmp("subtitle", part))
244 snprintf(buf, sizeof(buf), "elm.text.subtitle");
245 else
246 snprintf(buf, sizeof(buf), "%s", part);
247
248 EINA_INLIST_FOREACH(navi_it->text_list, pair)
249 if (!strcmp(buf, pair->part)) break;
250
251 if (!pair)
252 {
253 pair = ELM_NEW(Elm_Naviframe_Text_Item_Pair);
254 if (!pair)
255 {
256 ERR("Failed to allocate new text part of the item! : naviframe=%p",
257 WIDGET(navi_it));
258 return;
259 }
260 eina_stringshare_replace(&pair->part, buf);
261 navi_it->text_list = eina_inlist_append(navi_it->text_list,
262 EINA_INLIST_GET(pair));
263 }
264 elm_object_part_text_set(VIEW(navi_it), buf, label);
265
266 if (label)
267 {
268 snprintf(buf, sizeof(buf), "elm,state,%s,show", buf);
269 elm_object_signal_emit(VIEW(navi_it), buf, "elm");
270 }
271 else
272 {
273 snprintf(buf, sizeof(buf), "elm,state,%s,hide", buf);
274 elm_object_signal_emit(VIEW(navi_it), buf, "elm");
275 }
276
277 _sizing_eval(WIDGET(navi_it));
278}
279
280static const char *
281_item_text_get_hook(const Elm_Object_Item *it, const char *part)
282{
283 char buf[1024];
284
285 if (!part || !strcmp(part, "default"))
286 snprintf(buf, sizeof(buf), "elm.text.title");
287 else if (!strcmp("subtitle", part))
288 snprintf(buf, sizeof(buf), "elm.text.subtitle");
289 else
290 snprintf(buf, sizeof(buf), "%s", part);
291
292 return elm_object_part_text_get(VIEW(it), buf);
293}
294
295static void
296_item_content_set_hook(Elm_Object_Item *it,
297 const char *part,
298 Evas_Object *content)
299{
300 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
301
302 //specified parts
303 if (!part || !strcmp("default", part))
304 {
305 _item_content_set(navi_it, content);
306 return;
307 }
308 else if (!strcmp(part, "prev_btn"))
309 {
310 _title_prev_btn_set(navi_it, content, EINA_FALSE);
311 return;
312 }
313 else if (!strcmp(part, "next_btn"))
314 {
315 _title_next_btn_set(navi_it, content);
316 return;
317 }
318 else if (!strcmp(part, "icon"))
319 {
320 _title_icon_set(navi_it, content);
321 return;
322 }
323
324 //common part
325 _title_content_set(navi_it, part, content);
326}
327
328static Evas_Object *
329_item_content_get_hook(const Elm_Object_Item *it, const char *part)
330{
331 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
332
333 //specified parts
334 if (!part || !strcmp("default", part))
335 return navi_it->content;
336 else if (!strcmp(part, "prev_btn"))
337 return navi_it->title_prev_btn;
338 else if (!strcmp(part, "next_btn"))
339 return navi_it->title_next_btn;
340 else if (!strcmp(part, "icon"))
341 return navi_it->title_icon;
342
343 //common parts
344 return elm_object_part_content_get(VIEW(navi_it), part);
345}
346
347static Evas_Object *
348_item_content_unset_hook(Elm_Object_Item *it, const char *part)
349{
350 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
351
352 //specified parts
353 if (!part || !strcmp("default", part))
354 return _item_content_unset(navi_it);
355 else if (!strcmp(part, "prev_btn"))
356 return _title_prev_btn_unset(navi_it);
357 else if (!strcmp(part, "next_btn"))
358 return _title_next_btn_unset(navi_it);
359 else if (!strcmp(part, "icon"))
360 return _title_icon_unset(navi_it);
361
362 return _title_content_unset(navi_it, part);
363}
364
365static void
366_item_signal_emit_hook(Elm_Object_Item *it,
367 const char *emission,
368 const char *source)
369{
370 elm_object_signal_emit(VIEW(it), emission, source);
371}
372
373static void
374_item_title_visible_update(Elm_Naviframe_Item *navi_it)
375{
376 if (navi_it->title_visible)
377 elm_object_signal_emit(VIEW(navi_it), "elm,state,title,show", "elm");
378 else
379 elm_object_signal_emit(VIEW(navi_it), "elm,state,title,hide", "elm");
380}
381
382static void
383_sizing_eval(Evas_Object *obj)
384{
385 Widget_Data *wd;
386 Elm_Naviframe_Item *it;
387 Evas_Coord x, y, w, h;
388 Evas_Coord minw = -1, minh = -1;
389
390 wd = elm_widget_data_get(obj);
391 if (!wd) return;
392
393 evas_object_geometry_get(obj, &x, &y, &w, &h);
394
395 EINA_INLIST_FOREACH(wd->stack, it)
396 {
397 evas_object_move(VIEW(it), x, y);
398 evas_object_resize(VIEW(it), w, h);
399 edje_object_size_min_calc(elm_layout_edje_get(VIEW(it)),
400 &it->minw,
401 &it->minh);
402 if (it->minw > minw) minw = it->minw;
403 if (it->minh > minh) minh = it->minh;
404 }
405 evas_object_size_hint_min_set(obj, minw, minh);
406 evas_object_size_hint_max_set(obj, -1, -1);
407}
408
409static void
410_move(void *data __UNUSED__,
411 Evas *e __UNUSED__,
412 Evas_Object *obj,
413 void *event_info __UNUSED__)
414{
415 _sizing_eval(obj);
416}
417
418static void
419_resize(void *data __UNUSED__,
420 Evas *e __UNUSED__,
421 Evas_Object *obj,
422 void *event_info __UNUSED__)
423{
424 _sizing_eval(obj);
425}
426
427static void
428_title_clicked(void *data,
429 Evas_Object *obj __UNUSED__,
430 const char *emission __UNUSED__,
431 const char *source __UNUSED__)
432{
433 Elm_Naviframe_Item *it = data;
434 evas_object_smart_callback_call(WIDGET(it), SIG_TITLE_CLICKED, it);
435}
436
437static void
438_back_btn_clicked(void *data,
439 Evas_Object *obj,
440 void *event_info __UNUSED__)
441{
442/* Since edje has the event queue, clicked event could be happend multiple times
443 on some heavy environment. This callback del will prevent those scenario and
444 guarantee only one clicked for it's own page. */
445 evas_object_smart_callback_del(obj, "clicked", _back_btn_clicked);
446 elm_naviframe_item_pop(data);
447}
448
449static Evas_Object *
450_back_btn_new(Evas_Object *obj)
451{
452 Evas_Object *btn;
453 char buf[1024];
454 btn = elm_button_add(obj);
455 if (!btn) return NULL;
456 evas_object_smart_callback_add(btn, "clicked", _back_btn_clicked, obj);
457 snprintf(buf, sizeof(buf), "naviframe/back_btn/%s",
458 elm_widget_style_get(obj));
459 elm_object_style_set(btn, buf);
460 return btn;
461}
462
463static void _text_set_hook(Evas_Object *obj,
464 const char *part,
465 const char *label)
466{
467 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
468 if (!it) return;
469 elm_object_item_part_text_set(it, part, label);
470}
471
472static const char *_text_get_hook(const Evas_Object *obj, const char *part)
473{
474 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
475 if (!it) return NULL;
476 return elm_object_item_part_text_get(it, part);
477}
478
479static void
480_content_set_hook(Evas_Object *obj, const char *part, Evas_Object *content)
481{
482 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
483 if (!it) return;
484 elm_object_item_part_content_set(it, part, content);
485}
486
487static Evas_Object *
488_content_unset_hook(Evas_Object *obj, const char *part)
489{
490 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
491 if (!it) return NULL;
492 return elm_object_item_part_content_unset(it, part);
493}
494
495static Evas_Object *
496_content_get_hook(const Evas_Object *obj, const char *part)
497{
498 Elm_Object_Item *it = elm_naviframe_top_item_get(obj);
499 if (!it) return NULL;
500 return elm_object_item_part_content_get(it, part);
501}
502
503static void
504_title_content_del(void *data,
505 Evas *e __UNUSED__,
506 Evas_Object *obj __UNUSED__,
507 void *event_info __UNUSED__)
508{
509 char buf[1024];
510 Elm_Naviframe_Content_Item_Pair *pair = data;
511 Elm_Naviframe_Item *it = pair->it;
512 snprintf(buf, sizeof(buf), "elm,state,%s,hide", pair->part);
513 elm_object_signal_emit(VIEW(it), buf, "elm");
514 it->content_list = eina_inlist_remove(it->content_list,
515 EINA_INLIST_GET(pair));
516 eina_stringshare_del(pair->part);
517 free(pair);
518}
519
520static void
521_title_prev_btn_del(void *data,
522 Evas *e __UNUSED__,
523 Evas_Object *obj __UNUSED__,
524 void *event_info __UNUSED__)
525{
526 Elm_Naviframe_Item *it = data;
527 it->back_btn = EINA_FALSE;
528 it->title_prev_btn = NULL;
529 elm_object_signal_emit(VIEW(it), "elm,state,prev_btn,hide", "elm");
530}
531
532static void
533_title_next_btn_del(void *data,
534 Evas *e __UNUSED__,
535 Evas_Object *obj __UNUSED__,
536 void *event_info __UNUSED__)
537{
538 Elm_Naviframe_Item *it = data;
539 it->title_next_btn = NULL;
540 elm_object_signal_emit(VIEW(it), "elm,state,next_btn,hide", "elm");
541}
542
543static void
544_title_icon_del(void *data,
545 Evas *e __UNUSED__,
546 Evas_Object *obj __UNUSED__,
547 void *event_info __UNUSED__)
548{
549 Elm_Naviframe_Item *it = data;
550 it->title_icon = NULL;
551 elm_object_signal_emit(VIEW(it), "elm,state,icon,hide", "elm");
552}
553
554static void
555_item_content_del(void *data,
556 Evas *e __UNUSED__,
557 Evas_Object *obj __UNUSED__,
558 void *event_info __UNUSED__)
559{
560 Elm_Naviframe_Item *it = data;
561 it->content = NULL;
562 elm_object_signal_emit(VIEW(it), "elm,state,content,hide", "elm");
563}
564
565static void
566_title_content_set(Elm_Naviframe_Item *it,
567 const char *part,
568 Evas_Object *content)
569{
570 char buf[1024];
571 Elm_Naviframe_Content_Item_Pair *pair = NULL;
572 Evas_Object *prev_content = NULL;
573
574 EINA_INLIST_FOREACH(it->content_list, pair)
575 if (!strcmp(part, pair->part)) break;
576
577 if (pair)
578 {
579 prev_content = elm_object_part_content_get(VIEW(it), part);
580 if (prev_content != content)
581 {
582 if (content)
583 {
584 evas_object_event_callback_del(prev_content,
585 EVAS_CALLBACK_DEL,
586 _title_content_del);
587 snprintf(buf, sizeof(buf), "elm,state,%s,hide", part);
588 elm_object_signal_emit(VIEW(it), buf, "elm");
589 }
590 evas_object_del(prev_content);
591 if (!content) return;
592 }
593 }
594 else
595 {
596 if (!content) return;
597 pair = ELM_NEW(Elm_Naviframe_Content_Item_Pair);
598 if (!pair)
599 {
600 ERR("Failed to allocate new content part of the item! : naviframe=%p", WIDGET(it));
601 return;
602 }
603 pair->it = it;
604 eina_stringshare_replace(&pair->part, part);
605 it->content_list = eina_inlist_append(it->content_list,
606 EINA_INLIST_GET(pair));
607 }
608 if (prev_content != content)
609 {
610 evas_object_event_callback_add(content,
611 EVAS_CALLBACK_DEL,
612 _title_content_del,
613 pair);
614 }
615 elm_object_part_content_set(VIEW(it), part, content);
616 snprintf(buf, sizeof(buf), "elm,state,%s,show", part);
617 elm_object_signal_emit(VIEW(it), buf, "elm");
618
619 _sizing_eval(WIDGET(it));
620}
621
622static void
623_title_prev_btn_set(Elm_Naviframe_Item *it,
624 Evas_Object *btn,
625 Eina_Bool back_btn)
626{
627 if (it->title_prev_btn == btn) return;
628 if (it->title_prev_btn) evas_object_del(it->title_prev_btn);
629 it->title_prev_btn = btn;
630 if (!btn) return;
631
632 evas_object_event_callback_add(btn,
633 EVAS_CALLBACK_DEL,
634 _title_prev_btn_del,
635 it);
636 elm_object_part_content_set(VIEW(it), "elm.swallow.prev_btn", btn);
637 elm_object_signal_emit(VIEW(it), "elm,state,prev_btn,show", "elm");
638 it->back_btn = back_btn;
639
640 _sizing_eval(WIDGET(it));
641}
642
643static void
644_title_next_btn_set(Elm_Naviframe_Item *it, Evas_Object *btn)
645{
646 if (it->title_next_btn == btn) return;
647 if (it->title_next_btn) evas_object_del(it->title_next_btn);
648 it->title_next_btn = btn;
649 if (!btn) return;
650
651 evas_object_event_callback_add(btn,
652 EVAS_CALLBACK_DEL,
653 _title_next_btn_del,
654 it);
655 elm_object_part_content_set(VIEW(it), "elm.swallow.next_btn", btn);
656 elm_object_signal_emit(VIEW(it), "elm,state,next_btn,show", "elm");
657
658 _sizing_eval(WIDGET(it));
659}
660
661static void
662_title_icon_set(Elm_Naviframe_Item *it, Evas_Object *icon)
663{
664 if (it->title_icon == icon) return;
665 if (it->title_icon) evas_object_del(it->title_icon);
666 it->title_icon = icon;
667 if (!icon) return;
668
669 evas_object_event_callback_add(icon,
670 EVAS_CALLBACK_DEL,
671 _title_icon_del,
672 it);
673 elm_object_part_content_set(VIEW(it), "elm.swallow.icon", icon);
674 elm_object_signal_emit(VIEW(it), "elm,state,icon,show", "elm");
675
676 _sizing_eval(WIDGET(it));
677}
678
679static Evas_Object *
680_item_content_unset(Elm_Naviframe_Item *it)
681{
682 Evas_Object *content = it->content;
683 if (!content) return NULL;
684
685 elm_object_part_content_unset(VIEW(it), "elm.swallow.content");
686 elm_object_signal_emit(VIEW(it), "elm,state,content,hide", "elm");
687 evas_object_event_callback_del(content,
688 EVAS_CALLBACK_DEL,
689 _item_content_del);
690 _sizing_eval(WIDGET(it));
691
692 it->content = NULL;
693 return content;
694}
695
696static Evas_Object *
697_title_prev_btn_unset(Elm_Naviframe_Item *it)
698{
699 Evas_Object *content = it->title_prev_btn;
700 if (!content) return NULL;
701
702 elm_object_part_content_unset(VIEW(it), "elm.swallow.prev_btn");
703 elm_object_signal_emit(VIEW(it), "elm,state,prev_btn,hide", "elm");
704 evas_object_event_callback_del(content,
705 EVAS_CALLBACK_DEL,
706 _title_prev_btn_del);
707 _sizing_eval(WIDGET(it));
708
709 it->title_prev_btn = NULL;
710 return content;
711}
712
713static Evas_Object *
714_title_next_btn_unset(Elm_Naviframe_Item *it)
715{
716 Evas_Object *content = it->title_next_btn;
717 if (!content) return NULL;
718
719 elm_object_part_content_unset(VIEW(it), "elm.swallow.next_btn");
720 elm_object_signal_emit(VIEW(it), "elm,state,next_btn,hide", "elm");
721 evas_object_event_callback_del(content,
722 EVAS_CALLBACK_DEL,
723 _title_next_btn_del);
724 _sizing_eval(WIDGET(it));
725
726 it->title_next_btn = NULL;
727 return content;
728}
729
730static Evas_Object *
731_title_icon_unset(Elm_Naviframe_Item *it)
732{
733 Evas_Object *content = it->title_icon;
734 if (!content) return NULL;
735
736 elm_object_part_content_unset(VIEW(it), "elm.swallow.icon");
737 elm_object_signal_emit(VIEW(it), "elm,state,icon,hide", "elm");
738 evas_object_event_callback_del(content,
739 EVAS_CALLBACK_DEL,
740 _title_icon_del);
741 _sizing_eval(WIDGET(it));
742 it->title_icon = NULL;
743
744 return content;
745}
746
747static Evas_Object *
748_title_content_unset(Elm_Naviframe_Item *it, const char *part)
749{
750 Elm_Naviframe_Content_Item_Pair *pair = NULL;
751 char buf[1028];
752 Evas_Object *content = NULL;
753
754 EINA_INLIST_FOREACH(it->content_list, pair)
755 {
756 if (!strcmp(part, pair->part))
757 {
758 content = elm_object_part_content_get(VIEW(it), part);
759 eina_stringshare_del(pair->part);
760 it->content_list = eina_inlist_remove(it->content_list,
761 EINA_INLIST_GET(pair));
762 free(pair);
763 break;
764 }
765 }
766
767 if (!content) return NULL;
768
769 elm_object_part_content_unset(VIEW(it), part);
770 snprintf(buf, sizeof(buf), "elm,state,%s,hide", part);
771 elm_object_signal_emit(VIEW(it), buf, "elm");
772 evas_object_event_callback_del(content,
773 EVAS_CALLBACK_DEL,
774 _title_content_del);
775 _sizing_eval(WIDGET(it));
776
777 return content;
778}
779
780static void
781_item_del(Elm_Naviframe_Item *it)
782{
783 Widget_Data *wd;
784 Elm_Naviframe_Content_Item_Pair *content_pair;
785 Elm_Naviframe_Text_Item_Pair *text_pair;
786 Evas_Object *content;
787
788 if (!it) return;
789
790 wd = elm_widget_data_get(WIDGET(it));
791 if (!wd) return;
792
793 while (it->content_list)
794 {
795 content_pair =
796 EINA_INLIST_CONTAINER_GET(it->content_list,
797 Elm_Naviframe_Content_Item_Pair);
798 content = elm_object_part_content_get(VIEW(it), content_pair->part);
799 evas_object_event_callback_del(content,
800 EVAS_CALLBACK_DEL,
801 _title_content_del);
802 eina_stringshare_del(content_pair->part);
803 it->content_list = eina_inlist_remove(it->content_list,
804 it->content_list);
805 free(content_pair);
806 }
807
808 while (it->text_list)
809 {
810 text_pair = EINA_INLIST_CONTAINER_GET(it->text_list,
811 Elm_Naviframe_Text_Item_Pair);
812 eina_stringshare_del(text_pair->part);
813 it->text_list = eina_inlist_remove(it->text_list,
814 it->text_list);
815 free(text_pair);
816 }
817
818 eina_stringshare_del(it->style);
819
820 if (wd->preserve && it->content)
821 {
822 elm_object_part_content_unset(VIEW(it), "elm.swallow.content");
823 evas_object_event_callback_del(it->content,
824 EVAS_CALLBACK_DEL,
825 _item_content_del);
826 }
827}
828
829static Eina_Bool
830_item_del_pre_hook(Elm_Object_Item *it)
831{
832 Elm_Naviframe_Item *navi_it;
833 Widget_Data *wd;
834
835 navi_it =(Elm_Naviframe_Item *)it;
836 wd = elm_widget_data_get(WIDGET(navi_it));
837 if (!wd) return EINA_FALSE;
838
839 if (it == elm_naviframe_top_item_get(WIDGET(navi_it)))
840 {
841 wd->stack = eina_inlist_remove(wd->stack, EINA_INLIST_GET(navi_it));
842 _item_del(navi_it);
843 //If the item is only one, the stack will be empty
844 if (!wd->stack) return EINA_TRUE;
845 navi_it = EINA_INLIST_CONTAINER_GET(wd->stack->last,
846 Elm_Naviframe_Item);
847 evas_object_show(VIEW(navi_it));
848 evas_object_raise(VIEW(navi_it));
849 elm_object_signal_emit(VIEW(navi_it), "elm,state,visible", "elm");
850 }
851 else
852 {
853 wd->stack = eina_inlist_remove(wd->stack, EINA_INLIST_GET(navi_it));
854 _item_del(navi_it);
855 }
856
857 return EINA_TRUE;
858}
859
860static void
861_pushed_finished(void *data,
862 Evas_Object *obj __UNUSED__,
863 const char *emission __UNUSED__,
864 const char *source __UNUSED__)
865{
866 Widget_Data *wd;
867 Elm_Naviframe_Item *it = data;
868 if (!it) return;
869
870 wd = elm_widget_data_get(WIDGET(it));
871 if (!wd) return;
872
873 evas_object_hide(VIEW(it));
874
875 if (it->content)
876 elm_widget_tree_unfocusable_set(it->content, it->content_unfocusable);
877
878 if (wd->freeze_events)
879 evas_object_freeze_events_set(VIEW(it), EINA_FALSE);
880}
881
882static void
883_popped_finished(void *data,
884 Evas_Object *obj __UNUSED__,
885 const char *emission __UNUSED__,
886 const char *source __UNUSED__)
887{
888 Widget_Data *wd;
889 Elm_Naviframe_Item *it = data;
890 if (!it) return;
891
892 wd = elm_widget_data_get(WIDGET(it));
893 if (!wd) return;
894
895 if (wd->preserve && it->content)
896 elm_widget_tree_unfocusable_set(it->content, it->content_unfocusable);
897
898 _item_del(data);
899
900 elm_widget_item_free(data);
901}
902
903static void
904_show_finished(void *data,
905 Evas_Object *obj __UNUSED__,
906 const char *emission __UNUSED__,
907 const char *source __UNUSED__)
908{
909 Elm_Naviframe_Item *it;
910 Widget_Data *wd;
911
912 it = data;
913 if (!it) return;
914 wd = elm_widget_data_get(WIDGET(it));
915 if (!wd) return;
916
917 elm_widget_tree_unfocusable_set(it->content, it->content_unfocusable);
918
919 evas_object_smart_callback_call(WIDGET(it),
920 SIG_TRANSITION_FINISHED,
921 data);
922 if (wd->freeze_events)
923 evas_object_freeze_events_set(VIEW(it), EINA_FALSE);
924}
925
926static void
927_changed_size_hints(void *data,
928 Evas *e __UNUSED__,
929 Evas_Object *obj __UNUSED__,
930 void *event_info __UNUSED__)
931{
932 _sizing_eval(data);
933}
934
935static void
936_item_content_set(Elm_Naviframe_Item *navi_it, Evas_Object *content)
937{
938 if (navi_it->content == content) return;
939 if (navi_it->content) evas_object_del(navi_it->content);
940 elm_object_part_content_set(VIEW(navi_it), "elm.swallow.content", content);
941
942 if (content)
943 elm_object_signal_emit(VIEW(navi_it), "elm,state,content,show", "elm");
944 else
945 elm_object_signal_emit(VIEW(navi_it), "elm,state,content,hide", "elm");
946
947 evas_object_event_callback_add(content,
948 EVAS_CALLBACK_DEL,
949 _item_content_del,
950 navi_it);
951 navi_it->content = content;
952 _sizing_eval(WIDGET(navi_it));
953}
954
955//FIXME: need to handle if this function is called while transition
956static void
957_item_style_set(Elm_Naviframe_Item *navi_it, const char *item_style)
958{
959 Elm_Naviframe_Content_Item_Pair *content_pair;
960 Elm_Naviframe_Text_Item_Pair *text_pair;
961 Widget_Data *wd;
962
963 char buf[256];
964
965 if (!item_style)
966 {
967 strcpy(buf, "item/basic");
968 eina_stringshare_replace(&navi_it->style, "basic");
969 }
970 else
971 {
972 snprintf(buf, sizeof(buf), "item/%s", item_style);
973 eina_stringshare_replace(&navi_it->style, item_style);
974 }
975 elm_layout_theme_set(VIEW(navi_it),
976 "naviframe",
977 buf,
978 elm_widget_style_get(WIDGET(navi_it)));
979 //recover item
980 EINA_INLIST_FOREACH(navi_it->text_list, text_pair)
981 _item_text_set_hook((Elm_Object_Item *) navi_it,
982 text_pair->part,
983 elm_object_part_text_get(VIEW(navi_it),
984 text_pair->part));
985
986 EINA_INLIST_FOREACH(navi_it->content_list, content_pair)
987 _item_content_set_hook((Elm_Object_Item *) navi_it,
988 content_pair->part,
989 elm_object_part_content_get(VIEW(navi_it),
990 content_pair->part));
991 //content
992 if (navi_it->content)
993 elm_object_signal_emit(VIEW(navi_it), "elm,state,content,show", "elm");
994
995 //prev button
996 if (navi_it->title_prev_btn)
997 elm_object_signal_emit(VIEW(navi_it), "elm,state,prev_btn,show", "elm");
998
999 //next button
1000 if (navi_it->title_next_btn)
1001 elm_object_signal_emit(VIEW(navi_it), "elm,state,next_btn,show", "elm");
1002
1003 _sizing_eval(WIDGET(navi_it));
1004
1005 wd = elm_widget_data_get(WIDGET(navi_it));
1006 if (!wd) return;
1007
1008 if (wd->freeze_events)
1009 evas_object_freeze_events_set(VIEW(navi_it), EINA_FALSE);
1010}
1011
1012static Elm_Naviframe_Item *
1013_item_new(Evas_Object *obj,
1014 const char *title_label,
1015 Evas_Object *prev_btn,
1016 Evas_Object *next_btn,
1017 Evas_Object *content,
1018 const char *item_style)
1019{
1020 Widget_Data *wd = elm_widget_data_get(obj);
1021
1022 //create item
1023 Elm_Naviframe_Item *it = elm_widget_item_new(obj, Elm_Naviframe_Item);
1024 if (!it)
1025 {
1026 ERR("Failed to allocate new item! : naviframe=%p", obj);
1027 return NULL;
1028 }
1029
1030 elm_widget_item_del_pre_hook_set(it, _item_del_pre_hook);
1031 elm_widget_item_text_set_hook_set(it, _item_text_set_hook);
1032 elm_widget_item_text_get_hook_set(it, _item_text_get_hook);
1033 elm_widget_item_content_set_hook_set(it, _item_content_set_hook);
1034 elm_widget_item_content_get_hook_set(it, _item_content_get_hook);
1035 elm_widget_item_content_unset_hook_set(it, _item_content_unset_hook);
1036 elm_widget_item_signal_emit_hook_set(it, _item_signal_emit_hook);
1037
1038 //item base layout
1039 VIEW(it) = elm_layout_add(obj);
1040 evas_object_smart_member_add(VIEW(it), obj);
1041
1042 evas_object_event_callback_add(VIEW(it),
1043 EVAS_CALLBACK_CHANGED_SIZE_HINTS,
1044 _changed_size_hints,
1045 obj);
1046 elm_object_signal_callback_add(VIEW(it),
1047 "elm,action,show,finished",
1048 "",
1049 _show_finished, it);
1050 elm_object_signal_callback_add(VIEW(it),
1051 "elm,action,pushed,finished",
1052 "",
1053 _pushed_finished, it);
1054 elm_object_signal_callback_add(VIEW(it),
1055 "elm,action,popped,finished",
1056 "",
1057 _popped_finished, it);
1058 elm_object_signal_callback_add(VIEW(it),
1059 "elm,action,title,clicked",
1060 "",
1061 _title_clicked, it);
1062
1063 _item_style_set(it, item_style);
1064 _item_text_set_hook((Elm_Object_Item *)it, "elm.text.title", title_label);
1065
1066 //title buttons
1067 if ((!prev_btn) && wd->auto_pushed && eina_inlist_count(wd->stack))
1068 {
1069 prev_btn = _back_btn_new(obj);
1070 _title_prev_btn_set(it, prev_btn, EINA_TRUE);
1071 }
1072 else
1073 _title_prev_btn_set(it, prev_btn, EINA_FALSE);
1074
1075 _title_next_btn_set(it, next_btn);
1076 _item_content_set(it, content);
1077 it->title_visible = EINA_TRUE;
1078 return it;
1079}
1080
1081static Eina_Bool
1082_focus_next_hook(const Evas_Object *obj, Elm_Focus_Direction dir, Evas_Object **next)
1083{
1084 Eina_Bool ret;
1085 Elm_Naviframe_Item *top_it;
1086 Eina_List *l = NULL;
1087 Widget_Data *wd = elm_widget_data_get(obj);
1088 void *(*list_data_get)(const Eina_List *list);
1089 if (!wd) return EINA_FALSE;
1090
1091 top_it = (Elm_Naviframe_Item *)elm_naviframe_top_item_get(obj);
1092 if (!top_it) return EINA_FALSE;
1093
1094 list_data_get = eina_list_data_get;
1095
1096 //Forcus order: prev button, next button, contents
1097 if (top_it->title_prev_btn)
1098 l = eina_list_append(l, top_it->title_prev_btn);
1099 if (top_it->title_next_btn)
1100 l = eina_list_append(l, top_it->title_next_btn);
1101 l = eina_list_append(l, VIEW(top_it));
1102
1103 ret = elm_widget_focus_list_next_get(obj, l, list_data_get, dir, next);
1104 eina_list_free(l);
1105 return ret;
1106}
1107
1108EAPI Evas_Object *
1109elm_naviframe_add(Evas_Object *parent)
1110{
1111 Evas_Object *obj;
1112 Evas *e;
1113 Widget_Data *wd;
1114
1115 ELM_WIDGET_STANDARD_SETUP(wd, Widget_Data, parent, e, obj, NULL);
1116 ELM_SET_WIDTYPE(widtype, "naviframe");
1117 elm_widget_type_set(obj, "naviframe");
1118 elm_widget_sub_object_add(parent, obj);
1119 elm_widget_data_set(obj, wd);
1120 elm_widget_del_hook_set(obj, _del_hook);
1121 elm_widget_disable_hook_set(obj, _disable_hook);
1122 elm_widget_theme_hook_set(obj, _theme_hook);
1123 elm_widget_text_set_hook_set(obj, _text_set_hook);
1124 elm_widget_text_get_hook_set(obj, _text_get_hook);
1125 elm_widget_content_set_hook_set(obj, _content_set_hook);
1126 elm_widget_content_get_hook_set(obj, _content_get_hook);
1127 elm_widget_content_unset_hook_set(obj, _content_unset_hook);
1128 elm_widget_signal_emit_hook_set(obj, _emit_hook);
1129 elm_widget_can_focus_set(obj, EINA_FALSE);
1130 elm_widget_focus_next_hook_set(obj, _focus_next_hook);
1131
1132 //base
1133 //FIXME: Is this base layout really needed?
1134 wd->base = elm_layout_add(obj);
1135 evas_object_event_callback_add(wd->base,
1136 EVAS_CALLBACK_CHANGED_SIZE_HINTS,
1137 _changed_size_hints,
1138 obj);
1139 elm_widget_resize_object_set(obj, wd->base);
1140 elm_layout_theme_set(wd->base, "naviframe", "base", "default");
1141
1142 evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _move, obj);
1143 evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, obj);
1144 evas_object_smart_callbacks_descriptions_set(obj, _signals);
1145
1146 wd->auto_pushed = EINA_TRUE;
1147 wd->freeze_events = EINA_TRUE;
1148
1149 return obj;
1150}
1151
1152EAPI Elm_Object_Item *
1153elm_naviframe_item_push(Evas_Object *obj,
1154 const char *title_label,
1155 Evas_Object *prev_btn,
1156 Evas_Object *next_btn,
1157 Evas_Object *content,
1158 const char *item_style)
1159{
1160 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1161 Widget_Data *wd;
1162 Elm_Naviframe_Item *prev_it, *it;
1163
1164 wd = elm_widget_data_get(obj);
1165 if (!wd) return NULL;
1166
1167 it = _item_new(obj, title_label, prev_btn, next_btn, content, item_style);
1168 if (!it) return NULL;
1169
1170 evas_object_show(VIEW(it));
1171
1172 prev_it = (Elm_Naviframe_Item *) elm_naviframe_top_item_get(obj);
1173 if (prev_it)
1174 {
1175 if (wd->freeze_events)
1176 {
1177 evas_object_freeze_events_set(VIEW(it), EINA_TRUE);
1178 evas_object_freeze_events_set(VIEW(prev_it), EINA_TRUE);
1179 }
1180 elm_object_signal_emit(VIEW(prev_it), "elm,state,cur,pushed", "elm");
1181 elm_object_signal_emit(VIEW(it), "elm,state,new,pushed", "elm");
1182 edje_object_message_signal_process(elm_layout_edje_get(VIEW(prev_it)));
1183 if (prev_it->content)
1184 {
1185 prev_it->content_unfocusable = elm_widget_tree_unfocusable_get(prev_it->content);
1186 elm_widget_tree_unfocusable_set(prev_it->content, EINA_TRUE);
1187 }
1188 edje_object_message_signal_process(elm_layout_edje_get(VIEW(it)));
1189 }
1190 wd->stack = eina_inlist_append(wd->stack, EINA_INLIST_GET(it));
1191 _sizing_eval(obj);
1192 return (Elm_Object_Item *)it;
1193}
1194
1195EAPI Elm_Object_Item *
1196elm_naviframe_item_insert_before(Evas_Object *obj,
1197 Elm_Object_Item *before,
1198 const char *title_label,
1199 Evas_Object *prev_btn,
1200 Evas_Object *next_btn,
1201 Evas_Object *content,
1202 const char *item_style)
1203{
1204 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1205 ELM_OBJ_ITEM_CHECK_OR_RETURN(before, NULL);
1206 Elm_Naviframe_Item *it;
1207 Widget_Data *wd;
1208
1209 wd = elm_widget_data_get(obj);
1210 if (!wd) return NULL;
1211
1212 it = _item_new(obj, title_label, prev_btn, next_btn, content, item_style);
1213 if (!it) return NULL;
1214
1215 wd->stack =
1216 eina_inlist_prepend_relative(wd->stack,
1217 EINA_INLIST_GET(it),
1218 EINA_INLIST_GET(((Elm_Naviframe_Item *) before)));
1219 _sizing_eval(obj);
1220 return (Elm_Object_Item *)it;
1221}
1222
1223EAPI Elm_Object_Item *
1224elm_naviframe_item_insert_after(Evas_Object *obj,
1225 Elm_Object_Item *after,
1226 const char *title_label,
1227 Evas_Object *prev_btn,
1228 Evas_Object *next_btn,
1229 Evas_Object *content,
1230 const char *item_style)
1231{
1232 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1233 ELM_OBJ_ITEM_CHECK_OR_RETURN(after, NULL);
1234 Elm_Naviframe_Item *it;
1235 Widget_Data *wd;
1236 Eina_Bool top_inserted;
1237
1238 wd = elm_widget_data_get(obj);
1239 if (!wd) return NULL;
1240
1241 it = _item_new(obj, title_label, prev_btn, next_btn, content, item_style);
1242 if (!it) return NULL;
1243
1244 if (elm_naviframe_top_item_get(obj) == after) top_inserted = EINA_TRUE;
1245
1246 wd->stack =
1247 eina_inlist_append_relative(wd->stack,
1248 EINA_INLIST_GET(it),
1249 EINA_INLIST_GET(((Elm_Naviframe_Item *) after)));
1250 if (top_inserted)
1251 {
1252 evas_object_show(VIEW(it));
1253 evas_object_hide(VIEW(after));
1254 }
1255
1256 _sizing_eval(obj);
1257
1258 return (Elm_Object_Item *)it;
1259}
1260
1261EAPI Evas_Object *
1262elm_naviframe_item_pop(Evas_Object *obj)
1263{
1264 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1265 Elm_Naviframe_Item *it, *prev_it = NULL;
1266 Widget_Data *wd;
1267 Evas_Object *content = NULL;
1268
1269 wd = elm_widget_data_get(obj);
1270 if (!wd) return NULL;
1271
1272 it = (Elm_Naviframe_Item *) elm_naviframe_top_item_get(obj);
1273 if (!it) return NULL;
1274 if (wd->preserve)
1275 content = it->content;
1276
1277 if (it->content)
1278 {
1279 it->content_unfocusable = elm_widget_tree_unfocusable_get(it->content);
1280 elm_widget_tree_unfocusable_set(it->content, EINA_TRUE);
1281 }
1282
1283 if (wd->stack->last->prev)
1284 prev_it = EINA_INLIST_CONTAINER_GET(wd->stack->last->prev,
1285 Elm_Naviframe_Item);
1286 wd->stack = eina_inlist_remove(wd->stack, EINA_INLIST_GET(it));
1287 if (prev_it)
1288 {
1289 if (wd->freeze_events)
1290 {
1291 evas_object_freeze_events_set(VIEW(it), EINA_TRUE);
1292 evas_object_freeze_events_set(VIEW(prev_it), EINA_TRUE);
1293 }
1294 elm_object_signal_emit(VIEW(it), "elm,state,cur,popped", "elm");
1295 evas_object_show(VIEW(prev_it));
1296 elm_object_signal_emit(VIEW(prev_it),
1297 "elm,state,prev,popped",
1298 "elm");
1299 edje_object_message_signal_process(elm_layout_edje_get(VIEW(it)));
1300 edje_object_message_signal_process(elm_layout_edje_get(VIEW(prev_it)));
1301 }
1302 else
1303 {
1304 _item_del(it);
1305 elm_widget_item_free(it);
1306 }
1307
1308 return content;
1309}
1310
1311EAPI void
1312elm_naviframe_item_pop_to(Elm_Object_Item *it)
1313{
1314 ELM_OBJ_ITEM_CHECK_OR_RETURN(it);
1315 Elm_Naviframe_Item *navi_it;
1316 Widget_Data *wd;
1317 Eina_Inlist *l, *prev_l;
1318
1319 navi_it = (Elm_Naviframe_Item *)it;
1320 wd = elm_widget_data_get(WIDGET(navi_it));
1321 if (!wd) return;
1322
1323 if (it == elm_naviframe_top_item_get(WIDGET(navi_it))) return;
1324
1325 l = wd->stack->last->prev;
1326
1327 while (l)
1328 {
1329 if (EINA_INLIST_CONTAINER_GET(l, Elm_Naviframe_Item) ==
1330 ((Elm_Naviframe_Item *)it)) break;
1331 prev_l = l->prev;
1332 wd->stack = eina_inlist_remove(wd->stack, l);
1333 _item_del(EINA_INLIST_CONTAINER_GET(l, Elm_Naviframe_Item));
1334 elm_widget_item_free(EINA_INLIST_CONTAINER_GET(l,
1335 Elm_Naviframe_Item));
1336 l = prev_l;
1337 }
1338 elm_naviframe_item_pop(WIDGET(navi_it));
1339}
1340
1341EAPI void
1342elm_naviframe_item_promote(Elm_Object_Item *it)
1343{
1344 ELM_OBJ_ITEM_CHECK_OR_RETURN(it);
1345 Elm_Naviframe_Item *navi_it;
1346 Elm_Naviframe_Item *prev_it;
1347 Widget_Data *wd;
1348
1349 navi_it = (Elm_Naviframe_Item *)it;
1350 wd = elm_widget_data_get(navi_it->base.widget);
1351 if (!wd) return;
1352
1353 if (it == elm_naviframe_top_item_get(navi_it->base.widget)) return;
1354 wd->stack = eina_inlist_demote(wd->stack, EINA_INLIST_GET(navi_it));
1355 prev_it = EINA_INLIST_CONTAINER_GET(wd->stack->last->prev,
1356 Elm_Naviframe_Item);
1357 if (prev_it->content)
1358 {
1359 prev_it->content_unfocusable = elm_widget_tree_unfocusable_get(prev_it->content);
1360 elm_widget_tree_unfocusable_set(prev_it->content, EINA_TRUE);
1361 }
1362
1363 if (wd->freeze_events)
1364 {
1365 evas_object_freeze_events_set(VIEW(it), EINA_TRUE);
1366 evas_object_freeze_events_set(VIEW(prev_it), EINA_TRUE);
1367 }
1368 elm_object_signal_emit(VIEW(prev_it),
1369 "elm,state,cur,pushed",
1370 "elm");
1371 evas_object_show(VIEW(navi_it));
1372 evas_object_raise(VIEW(navi_it));
1373 elm_object_signal_emit(VIEW(navi_it),
1374 "elm,state,new,pushed",
1375 "elm");
1376 edje_object_message_signal_process(elm_layout_edje_get(VIEW(prev_it)));
1377 edje_object_message_signal_process(elm_layout_edje_get(VIEW(navi_it)));
1378}
1379
1380EAPI void
1381elm_naviframe_item_simple_promote(Evas_Object *obj, Evas_Object *content)
1382{
1383 ELM_CHECK_WIDTYPE(obj, widtype);
1384 Widget_Data *wd = elm_widget_data_get(obj);
1385 if (!wd) return;
1386 Elm_Naviframe_Item *itr;
1387 EINA_INLIST_FOREACH(wd->stack, itr)
1388 {
1389 if (elm_object_item_content_get((Elm_Object_Item *)itr) == content)
1390 {
1391 elm_naviframe_item_promote((Elm_Object_Item *)itr);
1392 break;
1393 }
1394 }
1395}
1396
1397
1398EAPI void
1399elm_naviframe_content_preserve_on_pop_set(Evas_Object *obj, Eina_Bool preserve)
1400{
1401 ELM_CHECK_WIDTYPE(obj, widtype);
1402 Widget_Data *wd = elm_widget_data_get(obj);
1403 if (!wd) return;
1404 wd->preserve = !!preserve;
1405}
1406
1407EAPI Eina_Bool
1408elm_naviframe_content_preserve_on_pop_get(const Evas_Object *obj)
1409{
1410 ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE;
1411 Widget_Data *wd = elm_widget_data_get(obj);
1412 if (!wd) return EINA_FALSE;
1413 return wd->preserve;
1414}
1415
1416EAPI Elm_Object_Item*
1417elm_naviframe_top_item_get(const Evas_Object *obj)
1418{
1419 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1420 Widget_Data *wd = elm_widget_data_get(obj);
1421 if ((!wd) || (!wd->stack)) return NULL;
1422 return (Elm_Object_Item *) (EINA_INLIST_CONTAINER_GET(wd->stack->last,
1423 Elm_Naviframe_Item));
1424}
1425
1426EAPI Elm_Object_Item*
1427elm_naviframe_bottom_item_get(const Evas_Object *obj)
1428{
1429 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1430 Widget_Data *wd = elm_widget_data_get(obj);
1431 if ((!wd) || (!wd->stack)) return NULL;
1432 return (Elm_Object_Item *) (EINA_INLIST_CONTAINER_GET(wd->stack,
1433 Elm_Naviframe_Item));
1434}
1435
1436EAPI void
1437elm_naviframe_item_style_set(Elm_Object_Item *it, const char *item_style)
1438{
1439 ELM_OBJ_ITEM_CHECK_OR_RETURN(it);
1440 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
1441
1442 if (item_style)
1443 if (!strcmp(item_style, navi_it->style)) return;
1444
1445 if (!item_style)
1446 if (!strcmp("basic", navi_it->style)) return;
1447
1448 _item_style_set(navi_it, item_style);
1449 _item_title_visible_update(navi_it);
1450}
1451
1452EAPI const char *
1453elm_naviframe_item_style_get(const Elm_Object_Item *it)
1454{
1455 ELM_OBJ_ITEM_CHECK_OR_RETURN(it, NULL);
1456 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
1457 return navi_it->style;
1458}
1459
1460EAPI void
1461elm_naviframe_item_title_visible_set(Elm_Object_Item *it, Eina_Bool visible)
1462{
1463 ELM_OBJ_ITEM_CHECK_OR_RETURN(it);
1464 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
1465
1466 visible = !!visible;
1467 if (navi_it->title_visible == visible) return;
1468
1469 navi_it->title_visible = visible;
1470 _item_title_visible_update(navi_it);
1471}
1472
1473EAPI Eina_Bool
1474elm_naviframe_item_title_visible_get(const Elm_Object_Item *it)
1475{
1476 ELM_OBJ_ITEM_CHECK_OR_RETURN(it, EINA_FALSE);
1477 Elm_Naviframe_Item *navi_it = (Elm_Naviframe_Item *)it;
1478 return navi_it->title_visible;
1479}
1480
1481EAPI void
1482elm_naviframe_prev_btn_auto_pushed_set(Evas_Object *obj, Eina_Bool auto_pushed)
1483{
1484 ELM_CHECK_WIDTYPE(obj, widtype);
1485 Widget_Data *wd = elm_widget_data_get(obj);
1486 if (!wd) return;
1487 wd->auto_pushed = !!auto_pushed;
1488}
1489
1490EAPI Eina_Bool
1491elm_naviframe_prev_btn_auto_pushed_get(const Evas_Object *obj)
1492{
1493 ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE;
1494 Widget_Data *wd = elm_widget_data_get(obj);
1495 if (!wd) return EINA_FALSE;
1496 return wd->auto_pushed;
1497}
1498
1499EAPI Eina_List *
1500elm_naviframe_items_get(const Evas_Object *obj)
1501{
1502 ELM_CHECK_WIDTYPE(obj, widtype) NULL;
1503 Widget_Data *wd = elm_widget_data_get(obj);
1504 if (!wd) return NULL;
1505 Eina_List *ret = NULL;
1506 Elm_Naviframe_Item *itr;
1507 EINA_INLIST_FOREACH(wd->stack, itr)
1508 ret = eina_list_append(ret, itr);
1509 return ret;
1510}
1511
1512EAPI void
1513elm_naviframe_event_enabled_set(Evas_Object *obj, Eina_Bool enabled)
1514{
1515 ELM_CHECK_WIDTYPE(obj, widtype);
1516 Widget_Data *wd = elm_widget_data_get(obj);
1517 if (!wd) return;
1518 enabled = !!enabled;
1519 if (wd->freeze_events == !enabled) return;
1520 wd->freeze_events = !enabled;
1521}
1522
1523EAPI Eina_Bool
1524elm_naviframe_event_enabled_get(const Evas_Object *obj)
1525{
1526 ELM_CHECK_WIDTYPE(obj, widtype) EINA_FALSE;
1527 Widget_Data *wd = elm_widget_data_get(obj);
1528 if (!wd) return EINA_FALSE;
1529 return !wd->freeze_events;
1530}