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