2 #include <Elementary.h>
3 #include <Elementary_Cursor.h>
5 #include "elm_widget_genlist.h"
7 #define GROUP_ITEMS_FEATURE 0
8 // internally allocated
9 #define CLASS_ALLOCATED 0x3a70f11f
11 #define MAX_ITEMS_PER_BLOCK 32
12 #define REORDER_EFFECT_TIME 0.1
13 #define FX_MOVE_TIME 0.5
15 EAPI const char ELM_GENLIST_SMART_NAME[] = "elm_genlist";
16 EAPI const char ELM_GENLIST_PAN_SMART_NAME[] = "elm_genlist_pan";
18 #define ERR_ABORT(_msg) \
20 if (getenv("ELM_ERROR_ABORT")) abort();
22 #define GL_IT(_it) (_it->item)
24 #define IS_ROOT_PARENT_IT(_it) \
25 ((_it->group) || (GL_IT(_it)->items && GL_IT(_it)->expanded_depth == 0)) \
27 static const Evas_Smart_Interface *_smart_interfaces[] =
29 (Evas_Smart_Interface *)&ELM_SCROLLABLE_IFACE, NULL
32 static const char SIG_ACTIVATED[] = "activated";
33 static const char SIG_CLICKED_DOUBLE[] = "clicked,double";
34 static const char SIG_SELECTED[] = "selected";
35 static const char SIG_UNSELECTED[] = "unselected";
36 static const char SIG_EXPANDED[] = "expanded";
37 static const char SIG_CONTRACTED[] = "contracted";
38 static const char SIG_EXPAND_REQUEST[] = "expand,request";
39 static const char SIG_CONTRACT_REQUEST[] = "contract,request";
40 static const char SIG_REALIZED[] = "realized";
41 static const char SIG_UNREALIZED[] = "unrealized";
42 static const char SIG_DRAG_START_UP[] = "drag,start,up";
43 static const char SIG_DRAG_START_DOWN[] = "drag,start,down";
44 static const char SIG_DRAG_START_LEFT[] = "drag,start,left";
45 static const char SIG_DRAG_START_RIGHT[] = "drag,start,right";
46 static const char SIG_DRAG_STOP[] = "drag,stop";
47 static const char SIG_DRAG[] = "drag";
48 static const char SIG_LONGPRESSED[] = "longpressed";
49 static const char SIG_SCROLL_ANIM_START[] = "scroll,anim,start";
50 static const char SIG_SCROLL_ANIM_STOP[] = "scroll,anim,stop";
51 static const char SIG_SCROLL_DRAG_START[] = "scroll,drag,start";
52 static const char SIG_SCROLL_DRAG_STOP[] = "scroll,drag,stop";
53 static const char SIG_EDGE_TOP[] = "edge,top";
54 static const char SIG_EDGE_BOTTOM[] = "edge,bottom";
55 static const char SIG_EDGE_LEFT[] = "edge,left";
56 static const char SIG_EDGE_RIGHT[] = "edge,right";
57 static const char SIG_VBAR_DRAG[] = "vbar,drag";
58 static const char SIG_VBAR_PRESS[] = "vbar,press";
59 static const char SIG_VBAR_UNPRESS[] = "vbar,unpress";
60 static const char SIG_HBAR_DRAG[] = "hbar,drag";
61 static const char SIG_HBAR_PRESS[] = "hbar,press";
62 static const char SIG_HBAR_UNPRESS[] = "hbar,unpress";
63 static const char SIG_MULTI_SWIPE_LEFT[] = "multi,swipe,left";
64 static const char SIG_MULTI_SWIPE_RIGHT[] = "multi,swipe,right";
65 static const char SIG_MULTI_SWIPE_UP[] = "multi,swipe,up";
66 static const char SIG_MULTI_SWIPE_DOWN[] = "multi,swipe,down";
67 static const char SIG_MULTI_PINCH_OUT[] = "multi,pinch,out";
68 static const char SIG_MULTI_PINCH_IN[] = "multi,pinch,in";
69 static const char SIG_SWIPE[] = "swipe";
70 static const char SIG_MOVED[] = "moved";
71 static const char SIG_MOVED_AFTER[] = "moved,after";
72 static const char SIG_MOVED_BEFORE[] = "moved,before";
73 static const char SIG_INDEX_UPDATE[] = "index,update";
74 static const char SIG_TREE_EFFECT_FINISHED [] = "tree,effect,finished";
75 static const char SIG_HIGHLIGHTED[] = "highlighted";
76 static const char SIG_UNHIGHLIGHTED[] = "unhighlighted";
78 static const Evas_Smart_Cb_Description _smart_callbacks[] = {
79 {SIG_CLICKED_DOUBLE, ""},
85 {SIG_EXPAND_REQUEST, ""},
86 {SIG_CONTRACT_REQUEST, ""},
89 {SIG_DRAG_START_UP, ""},
90 {SIG_DRAG_START_DOWN, ""},
91 {SIG_DRAG_START_LEFT, ""},
92 {SIG_DRAG_START_RIGHT, ""},
95 {SIG_LONGPRESSED, ""},
96 {SIG_SCROLL_ANIM_START, ""},
97 {SIG_SCROLL_ANIM_STOP, ""},
98 {SIG_SCROLL_DRAG_START, ""},
99 {SIG_SCROLL_DRAG_STOP, ""},
101 {SIG_EDGE_BOTTOM, ""},
103 {SIG_EDGE_RIGHT, ""},
105 {SIG_VBAR_PRESS, ""},
106 {SIG_VBAR_UNPRESS, ""},
108 {SIG_HBAR_PRESS, ""},
109 {SIG_HBAR_UNPRESS, ""},
110 {SIG_MULTI_SWIPE_LEFT, ""},
111 {SIG_MULTI_SWIPE_RIGHT, ""},
112 {SIG_MULTI_SWIPE_UP, ""},
113 {SIG_MULTI_SWIPE_DOWN, ""},
114 {SIG_MULTI_PINCH_OUT, ""},
115 {SIG_MULTI_PINCH_IN, ""},
118 {SIG_MOVED_AFTER, ""},
119 {SIG_MOVED_BEFORE, ""},
120 {SIG_TREE_EFFECT_FINISHED, ""},
121 {SIG_HIGHLIGHTED, ""},
122 {SIG_UNHIGHLIGHTED, ""},
126 EVAS_SMART_SUBCLASS_IFACE_NEW
127 (ELM_GENLIST_SMART_NAME, _elm_genlist, Elm_Genlist_Smart_Class,
128 Elm_Layout_Smart_Class, elm_layout_smart_class_get, _smart_callbacks,
131 ELM_INTERNAL_SMART_SUBCLASS_NEW
132 (ELM_GENLIST_PAN_SMART_NAME, _elm_genlist_pan, Elm_Genlist_Pan_Smart_Class,
133 Elm_Pan_Smart_Class, elm_pan_smart_class_get, NULL);
135 static void _calc_job(void *);
136 static Eina_Bool _item_block_recalc(Item_Block *, int, Eina_Bool);
137 static void _item_mouse_callbacks_add(Elm_Gen_Item *, Evas_Object *);
138 static void _item_mouse_callbacks_del(Elm_Gen_Item *, Evas_Object *);
139 static void _access_activate_cb(void *data __UNUSED__,
140 Evas_Object *part_obj __UNUSED__,
141 Elm_Object_Item *item);
142 static void _item_select(Elm_Gen_Item *it);
144 static void _expand_toggle_signal_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__);
145 static void _expand_signal_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__);
146 static void _contract_signal_cb(void *data, Evas_Object *obj __UNUSED__, const char *emission __UNUSED__, const char *source __UNUSED__);
147 static void _elm_genlist_item_state_update(Elm_Gen_Item *it);
148 static void _decorate_item_unrealize(Elm_Gen_Item *it);
149 static void _decorate_all_item_unrealize(Elm_Gen_Item *it);
150 static void _decorate_item_set(Elm_Gen_Item *it);
151 static void _changed_job(Elm_Genlist_Smart_Data *sd);
153 #if GENLIST_FX_SUPPORT
154 static Eina_Bool _elm_genlist_fx_capture(Evas_Object *obj, int level);
155 static void _elm_genlist_fx_play(Evas_Object *obj);
156 static void _elm_genlist_fx_clear(Evas_Object *obj, Eina_Bool force);
157 static void _elm_genlist_proxy_item_del(const Elm_Object_Item *item);
160 #if GENLIST_PINCH_ZOOM_SUPPORT
161 EAPI Eina_Bool elm_genlist_pinch_zoom_mode_set(Evas_Object *obj, Elm_Gen_Pinch_Zoom_Mode mode);
165 _item_cache_all_free(Elm_Genlist_Smart_Data *sd)
167 // It would be better not to use
168 // EINA_INLIST_FOREACH or EINA_INLIST_FOREACH_SAFE
169 while (sd->item_cache)
171 Item_Cache *ic = EINA_INLIST_CONTAINER_GET(sd->item_cache->last, Item_Cache);
172 if (ic->spacer) evas_object_del(ic->spacer);
173 if (ic->base_view) evas_object_del(ic->base_view);
174 if (ic->item_style) eina_stringshare_del(ic->item_style);
175 sd->item_cache = eina_inlist_remove(sd->item_cache, EINA_INLIST_GET(ic));
176 // Free should be performed after inlist is poped
179 sd->item_cache = NULL;
180 sd->item_cache_count = 0;
184 _item_cache_push(Elm_Gen_Item *it)
186 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
187 Item_Cache *ic = NULL;
189 if (sd->item_cache_count >= sd->item_cache_max)
191 ic = EINA_INLIST_CONTAINER_GET(sd->item_cache->last, Item_Cache);
192 if (ic->spacer) evas_object_del(ic->spacer);
193 if (ic->base_view) evas_object_del(ic->base_view);
194 eina_stringshare_del(ic->item_style);
195 sd->item_cache = eina_inlist_remove(sd->item_cache,
196 sd->item_cache->last);
197 sd->item_cache_count--;
198 // Free should be performed after inlist is poped
201 //evas_event_freeze(evas_object_evas_get(obj));
203 edje_object_mirrored_set(VIEW(it),
204 elm_widget_mirrored_get(WIDGET(it)));
205 edje_object_scale_set(VIEW(it),
206 elm_widget_scale_get(WIDGET(it))
207 * elm_config_scale_get());
209 // FIXME: other callbacks?
210 edje_object_signal_callback_del_full(VIEW(it), "elm,action,expand,toggle",
211 "elm", _expand_toggle_signal_cb, it);
212 edje_object_signal_callback_del_full(VIEW(it), "elm,action,expand", "elm",
213 _expand_signal_cb, it);
214 edje_object_signal_callback_del_full(VIEW(it), "elm,action,contract", "elm",
215 _contract_signal_cb, it);
216 _item_mouse_callbacks_del(it, VIEW(it));
218 #if GENLIST_FX_SUPPORT
219 if ((it->item->nocache_once) || (it->item->nocache) || (sd->pending_del_items))
221 if ((it->item->nocache_once) || (it->item->nocache))
224 if (VIEW(it)) evas_object_del(VIEW(it));
225 if (it->spacer) evas_object_del(it->spacer);
228 ic = ELM_NEW(Item_Cache);
231 if (VIEW(it)) evas_object_del(VIEW(it));
232 if (it->spacer) evas_object_del(it->spacer);
237 ecore_timer_del(it->long_timer);
238 it->long_timer = NULL;
240 if (it->item->swipe_timer)
242 ecore_timer_del(it->item->swipe_timer);
243 it->item->swipe_timer = NULL;
246 ic->base_view = VIEW(it);
247 ic->spacer = it->spacer;
248 ic->item_style = eina_stringshare_add(it->itc->item_style);
249 if (it->item->type & ELM_GENLIST_ITEM_TREE) ic->tree = 1;
251 ic->selected = it->selected;
252 ic->disabled = elm_widget_item_disabled_get(it);
253 ic->expanded = it->item->expanded;
254 if (it->item->type & ELM_GENLIST_ITEM_TREE) ic->tree = 1;
256 edje_object_signal_emit(ic->base_view, "elm,state,unselected", "elm");
257 evas_object_hide(ic->base_view);
259 sd->item_cache = eina_inlist_prepend(sd->item_cache, EINA_INLIST_GET(ic));
260 sd->item_cache_count++;
266 it->realized = EINA_FALSE;
267 it->want_unrealize = EINA_FALSE;
269 //evas_event_thaw(evas_object_evas_get(obj));
270 //evas_event_thaw_eval(evas_object_evas_get(obj));
274 _item_cache_pop(Elm_Gen_Item *it)
276 Item_Cache *ic = NULL;
279 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
281 if (it->item->nocache_once) {
282 it->item->nocache_once = EINA_FALSE;
285 if (it->item->nocache) return EINA_FALSE;
287 if (it->item->type & ELM_GENLIST_ITEM_TREE) tree = 1;
288 EINA_INLIST_FOREACH_SAFE(sd->item_cache, l, ic)
290 if ((ic->selected) || (ic->disabled) || (ic->expanded))
293 if ((ic->tree == tree) &&
294 (((!it->itc->item_style) && (!ic->item_style)) ||
295 (it->itc->item_style && ic->item_style &&
296 (!strcmp(it->itc->item_style, ic->item_style)))))
299 eina_inlist_remove(sd->item_cache, EINA_INLIST_GET(ic));
300 sd->item_cache_count--;
302 VIEW(it) = ic->base_view;
303 it->spacer = ic->spacer;
305 #if 1 // FIXME: different from upstream
306 // Because of item cache, set state as default after cache item
308 edje_object_signal_emit(VIEW(it),"elm,state,default", "elm");
310 edje_object_signal_callback_add
311 (VIEW(it), "elm,action,expand,toggle", "elm",
312 _expand_toggle_signal_cb, it);
313 edje_object_signal_callback_add
314 (VIEW(it), "elm,action,expand", "elm", _expand_signal_cb, it);
315 edje_object_signal_callback_add
316 (VIEW(it), "elm,action,contract", "elm", _contract_signal_cb, it);
317 _item_mouse_callbacks_add(it, VIEW(it));
319 eina_stringshare_del(ic->item_style);
329 _elm_genlist_pan_smart_pos_set(Evas_Object *obj,
335 ELM_GENLIST_PAN_DATA_GET(obj, psd);
337 if ((x == psd->wsd->pan_x) && (y == psd->wsd->pan_y)) return;
341 EINA_INLIST_FOREACH(psd->wsd->blocks, itb)
343 if ((itb->y + itb->h) > y)
348 EINA_LIST_FOREACH(itb->items, l2, it)
350 if ((itb->y + it->y) >= y)
352 psd->wsd->anchor_item = it;
353 psd->wsd->anchor_y = -(itb->y + it->y - y);
360 if (!psd->wsd->reorder_move_animator) evas_object_smart_changed(obj);
364 _elm_genlist_pan_smart_pos_get(const Evas_Object *obj,
368 ELM_GENLIST_PAN_DATA_GET(obj, psd);
370 if (x) *x = psd->wsd->pan_x;
371 if (y) *y = psd->wsd->pan_y;
375 _elm_genlist_pan_smart_pos_max_get(const Evas_Object *obj,
381 ELM_GENLIST_PAN_DATA_GET(obj, psd);
383 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
384 ow = psd->wsd->minw - ow;
386 oh = psd->wsd->minh - oh;
391 #if GENLIST_PINCH_ZOOM_SUPPORT
392 if (psd->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
394 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
395 if (psd->wsd->pinch_zoom_h > oh)
396 *y = psd->wsd->pinch_zoom_h - oh;
403 _elm_genlist_pan_smart_pos_min_get(const Evas_Object *obj __UNUSED__,
412 _elm_genlist_pan_smart_content_size_get(const Evas_Object *obj,
416 ELM_GENLIST_PAN_DATA_GET(obj, psd);
418 if (w) *w = psd->wsd->minw;
419 if (h) *h = psd->wsd->minh;
423 _elm_genlist_pan_smart_add(Evas_Object *obj)
425 /* here just to allocate our extended data */
426 EVAS_SMART_DATA_ALLOC(obj, Elm_Genlist_Pan_Smart_Data);
428 ELM_PAN_CLASS(_elm_genlist_pan_parent_sc)->base.add(obj);
432 _elm_genlist_pan_smart_del(Evas_Object *obj)
434 ELM_GENLIST_PAN_DATA_GET(obj, psd);
438 ecore_job_del(psd->resize_job);
439 psd->resize_job = NULL;
442 _elm_genlist_pan_parent_sc->base.del(obj);
446 _elm_genlist_pan_smart_move(Evas_Object *obj,
447 Evas_Coord x __UNUSED__,
448 Evas_Coord y __UNUSED__)
450 ELM_GENLIST_PAN_DATA_GET(obj, psd);
452 psd->wsd->pan_changed = EINA_TRUE;
453 evas_object_smart_changed(obj);
454 if (psd->wsd->calc_job) ecore_job_del(psd->wsd->calc_job);
455 psd->wsd->calc_job = NULL;
459 _elm_genlist_pan_smart_resize(Evas_Object *obj,
463 Evas_Coord ow = 0, oh = 0, vw = 0;
465 ELM_GENLIST_PAN_DATA_GET(obj, psd);
467 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
468 if ((ow == w) && (oh == h)) return;
470 psd->wsd->s_iface->content_viewport_size_get(ELM_WIDGET_DATA(psd->wsd)->obj,
472 if (psd->wsd->mode == ELM_LIST_COMPRESS &&
473 vw != psd->wsd->prev_viewport_w)
474 psd->wsd->size_changed = EINA_TRUE;
475 if (vw != 0) psd->wsd->prev_viewport_w = vw;
477 psd->wsd->pan_changed = EINA_TRUE;
478 if (psd->wsd->calc_job) ecore_job_del(psd->wsd->calc_job);
479 psd->wsd->calc_job = ecore_job_add(_calc_job, psd->wsd);
483 _item_scroll(Elm_Genlist_Smart_Data *sd)
486 Elm_Gen_Item *it = NULL;
487 Evas_Coord ow, oh, dx = 0, dy = 0, dw = 0, dh = 0;
489 if (!sd->show_item) return;
491 evas_object_geometry_get(sd->pan_obj, NULL, NULL, &ow, &oh);
493 dx = it->x + it->item->block->x;
494 dy = it->y + it->item->block->y;
495 dw = it->item->block->w;
498 switch (sd->scroll_to_type)
500 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
501 if (it->item->group_item) gith = it->item->group_item->item->h;
505 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
506 dy += ((it->item->h / 2) - (oh / 2));
509 case ELM_GENLIST_ITEM_SCROLLTO_IN:
511 if ((sd->expanded_item) &&
512 ((sd->show_item->y + sd->show_item->item->block->y
513 + sd->show_item->item->h) -
514 (sd->expanded_item->y + sd->expanded_item->item->block->y) > oh))
516 it = sd->expanded_item;
517 if (it->item->group_item) gith = it->item->group_item->item->h;
518 dx = it->x + it->item->block->x;
519 dy = it->y + it->item->block->y - gith;
520 dw = it->item->block->w;
524 if ((it->item->group_item) &&
525 (sd->pan_y > (it->y + it->item->block->y)))
526 gith = it->item->group_item->item->h;
533 sd->s_iface->region_bring_in(ELM_WIDGET_DATA(sd)->obj, dx, dy, dw, dh);
535 sd->s_iface->content_region_show
536 (ELM_WIDGET_DATA(sd)->obj, dx, dy, dw, dh);
538 it->item->show_me = EINA_FALSE;
539 sd->show_item = NULL;
540 sd->auto_scroll_enabled = EINA_FALSE;
541 sd->check_scroll = EINA_FALSE;
545 _item_unrealize(Elm_Gen_Item *it,
548 Evas_Object *content;
552 if (!it->realized) return;
553 if (GL_IT(it)->wsd->reorder_it == it) return;
555 #if GENLIST_FX_SUPPORT
556 if ((GL_IT(it)->has_proxy_it) && (!GL_IT(it)->wsd->genlist_clearing))
558 if (!eina_list_data_find(GL_IT(it)->wsd->pending_unrealized_items, it))
559 GL_IT(it)->wsd->pending_unrealized_items =
560 eina_list_append(GL_IT(it)->wsd->pending_unrealized_items, it);
564 #if GENLIST_ENTRY_SUPPORT
565 if (it->item->unrealize_disabled)
567 evas_object_hide(VIEW(it));
572 //evas_event_freeze(evas_object_evas_get(WIDGET(it)));
574 evas_object_smart_callback_call(WIDGET(it), SIG_UNREALIZED, it);
577 ecore_timer_del(it->long_timer);
578 it->long_timer = NULL;
580 if (it->item->swipe_timer)
582 ecore_timer_del(it->item->swipe_timer);
583 it->item->swipe_timer = NULL;
587 EINA_LIST_FOREACH(it->texts, l, part)
588 edje_object_part_text_set(VIEW(it), part, NULL);
590 elm_widget_stringlist_free(it->texts);
592 elm_widget_stringlist_free(it->contents);
594 elm_widget_stringlist_free(it->states);
596 EINA_LIST_FREE(it->content_objs, content)
598 // FIXME: If parent-child relationship was broken before 'ic'
599 // is deleted, freeze_pop will not be called. ex) elm_slider
600 // If layout is used instead of edje, this problme can be
602 if (0 != elm_widget_scroll_freeze_get(content))
603 elm_widget_scroll_freeze_pop(content);
604 evas_object_del(content);
608 elm_widget_stringlist_free(it->item->flip_contents);
609 it->item->flip_contents = NULL;
610 EINA_LIST_FREE(it->item->flip_content_objs, content)
611 evas_object_del(content);
614 if (_elm_config->access_mode == ELM_ACCESS_MODE_ON)
615 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
617 // unswallow VIEW(it) first then manipulate VIEW(it)
618 _decorate_item_unrealize(it);
619 _decorate_all_item_unrealize(it);
621 edje_object_signal_emit
622 (VIEW(it), "elm,state,decorate,disabled", "elm");
623 edje_object_signal_emit
624 (VIEW(it), "elm,state,reorder,mode_unset", "elm");
625 edje_object_message_signal_process(VIEW(it));
627 it->realized = EINA_FALSE;
628 _item_cache_push(it);
630 #if GENLIST_ENTRY_SUPPORT
631 it->item->unrealize_disabled = EINA_FALSE;
633 it->want_unrealize = EINA_FALSE;
635 //evas_event_thaw(evas_object_evas_get(WIDGET(it)));
636 //evas_event_thaw_eval(evas_object_evas_get(WIDGET(it)));
640 _item_block_unrealize(Item_Block *itb)
644 Eina_Bool dragging = EINA_FALSE;
646 if (!itb->realized) return;
647 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
649 EINA_LIST_FOREACH(itb->items, l, it)
651 if (itb->must_recalc || !it->group)
655 dragging = EINA_TRUE;
656 it->want_unrealize = EINA_TRUE;
659 _item_unrealize(it, EINA_FALSE);
664 itb->realized = EINA_FALSE;
665 itb->want_unrealize = EINA_TRUE;
668 itb->want_unrealize = EINA_FALSE;
669 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
670 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
674 _must_recalc_idler(void *data)
676 Elm_Genlist_Smart_Data *sd = data;
678 if (sd->calc_job) ecore_job_del(sd->calc_job);
679 sd->calc_job = ecore_job_add(_calc_job, sd);
680 sd->must_recalc_idler = NULL;
681 return ECORE_CALLBACK_CANCEL;
685 _calc_job(void *data)
688 Item_Block *itb, *chb = NULL;
689 Evas_Coord pan_w = 0, pan_h = 0;
690 Elm_Genlist_Smart_Data *sd = data;
691 Eina_Bool minw_change = EINA_FALSE;
692 Eina_Bool did_must_recalc = EINA_FALSE;
693 Evas_Coord minw = -1, minh = 0, y = 0, dy = 0, vw = 0;
695 sd->s_iface->content_viewport_size_get(ELM_WIDGET_DATA(sd)->obj, &sd->w, &sd->h);
697 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
698 EINA_INLIST_FOREACH(sd->blocks, itb)
700 Eina_Bool show_me = EINA_FALSE;
703 show_me = itb->show_me;
704 itb->show_me = EINA_FALSE;
707 if (itb->realized) _item_block_unrealize(itb);
709 if ((itb->changed) || ((itb->must_recalc) && (!did_must_recalc)))
711 if (itb->must_recalc)
716 EINA_LIST_FOREACH(itb->items, l, it)
717 if (it->item->mincalcd) it->item->mincalcd = EINA_FALSE;
718 itb->changed = EINA_TRUE;
719 did_must_recalc = EINA_TRUE;
720 if (itb->realized) _item_block_unrealize(itb);
721 itb->must_recalc = EINA_FALSE;
723 show_me = _item_block_recalc(itb, in, EINA_FALSE);
729 if (minw == -1) minw = itb->minw;
730 else if ((!itb->must_recalc) && (minw < itb->minw))
733 minw_change = EINA_TRUE;
735 if ((sd->mode == ELM_LIST_COMPRESS) && (minw > vw))
738 minw_change = EINA_TRUE;
744 if ((show_me) && (sd->show_item) && (!sd->show_item->item->queued))
745 sd->check_scroll = EINA_TRUE;
749 EINA_INLIST_FOREACH(sd->blocks, itb)
755 if ((chb) && (EINA_INLIST_GET(chb)->next))
757 EINA_INLIST_FOREACH(EINA_INLIST_GET(chb)->next, itb)
759 if (itb->realized) _item_block_unrealize(itb);
763 if (minw < sd->w) minw = sd->w;
764 if ((minw != sd->minw) || (minh != sd->minh))
768 evas_object_smart_callback_call(sd->pan_obj, "changed", NULL);
769 elm_layout_sizing_eval(ELM_WIDGET_DATA(sd)->obj);
776 if ((sd->anchor_item) && (sd->anchor_item->item->block)
777 && (!sd->auto_scroll_enabled))
782 it = sd->anchor_item;
784 sd->s_iface->content_pos_set
785 (ELM_WIDGET_DATA(sd)->obj, sd->pan_x, it->item->block->y
786 + it->y + it_y, EINA_TRUE);
787 sd->anchor_item = it;
793 if (!sd->must_recalc_idler)
794 sd->must_recalc_idler = ecore_idler_add(_must_recalc_idler, sd);
796 if (sd->check_scroll)
798 _elm_genlist_pan_smart_content_size_get(sd->pan_obj, &pan_w, &pan_h);
799 if (EINA_INLIST_GET(sd->show_item) == sd->items->last)
800 sd->scroll_to_type = ELM_GENLIST_ITEM_SCROLLTO_IN;
802 switch (sd->scroll_to_type)
804 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
808 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
812 case ELM_GENLIST_ITEM_SCROLLTO_IN:
817 if ((sd->show_item) && (sd->show_item->item->block))
819 if ((pan_w > (sd->show_item->x + sd->show_item->item->block->x))
820 && (pan_h > (sd->show_item->y + sd->show_item->item->block->y
829 evas_object_smart_changed(sd->pan_obj);
830 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
831 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
835 _elm_genlist_smart_sizing_eval(Evas_Object *obj)
837 Evas_Coord minw = 0, minh = 0, maxw = -1, maxh = -1, vw = 0;
839 ELM_GENLIST_DATA_GET(obj, sd);
841 /* parent class' early call */
842 if (!sd->s_iface) return;
843 if (sd->on_sub_del) return;;
845 evas_object_size_hint_min_get(obj, &minw, NULL);
846 evas_object_size_hint_max_get(obj, &maxw, &maxh);
847 edje_object_size_min_calc(ELM_WIDGET_DATA(sd)->resize_obj, &minw, &minh);
849 sd->s_iface->content_viewport_size_get(obj, &vw, NULL);
850 if (vw != 0) sd->prev_viewport_w = vw;
852 if (sd->mode == ELM_LIST_LIMIT)
855 minw = minw + sd->realminw;
858 evas_object_size_hint_min_set(obj, minw, minh);
859 evas_object_size_hint_max_set(obj, maxw, maxh);
863 _item_position(Elm_Gen_Item *it,
871 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
872 evas_object_resize(view, it->item->w, it->item->h);
873 evas_object_move(view, it_x, it_y);
874 evas_object_show(view);
875 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
876 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
880 _item_sub_items_clear(Elm_Gen_Item *it)
883 Elm_Object_Item *it2;
885 EINA_LIST_FOREACH_SAFE(it->item->items, l, ll, it2)
886 elm_widget_item_del(it2);
890 _item_auto_scroll(Elm_Genlist_Smart_Data *sd)
892 Elm_Gen_Item *tmp_item = NULL;
894 #if GENLIST_FX_SUPPORT
895 if (sd->fx_first_captured) return;
897 if ((sd->expanded_item) && (sd->auto_scroll_enabled))
899 tmp_item = eina_list_data_get
900 (eina_list_last(sd->expanded_item->item->items));
901 if (!tmp_item) return;
902 sd->show_item = tmp_item;
903 sd->bring_in = EINA_TRUE;
904 sd->scroll_to_type = ELM_GENLIST_ITEM_SCROLLTO_IN;
905 if ((sd->show_item->item->queued) || (!sd->show_item->item->mincalcd))
907 sd->show_item->item->show_me = EINA_TRUE;
908 sd->auto_scroll_enabled = EINA_FALSE;
916 _elm_genlist_item_odd_even_update(Elm_Gen_Item *it)
918 if (!it->item->nostacking)
920 if ((it->item->order_num_in & 0x1) ^ it->item->stacking_even)
922 if (it->deco_all_view) evas_object_lower(it->deco_all_view);
923 else evas_object_lower(VIEW(it));
927 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
928 else evas_object_raise(VIEW(it));
932 if (it->item->order_num_in & 0x1)
934 edje_object_signal_emit(VIEW(it), "elm,state,odd", "elm");
935 if (it->deco_all_view)
936 edje_object_signal_emit(it->deco_all_view, "elm,state,odd", "elm");
940 edje_object_signal_emit(VIEW(it), "elm,state,even", "elm");
941 if (it->deco_all_view)
942 edje_object_signal_emit(it->deco_all_view, "elm,state,even", "elm");
947 _item_order_update(const Eina_Inlist *l,
950 Elm_Gen_Item *it, *it2;
952 for (it = ELM_GEN_ITEM_FROM_INLIST(l); l; l = l->next,
953 it = ELM_GEN_ITEM_FROM_INLIST(l))
955 it->item->order_num_in = start++;
956 _elm_genlist_item_odd_even_update(it);
957 it2 = ELM_GEN_ITEM_FROM_INLIST(l->next);
958 if (it2 && (it->item->order_num_in != it2->item->order_num_in))
964 _elm_genlist_item_state_update(Elm_Gen_Item *it)
968 if (it->deco_all_view)
969 edje_object_signal_emit
970 (it->deco_all_view, "elm,state,selected", "elm");
971 edje_object_signal_emit
972 (VIEW(it), "elm,state,selected", "elm");
973 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
975 if (elm_widget_item_disabled_get(it))
977 edje_object_signal_emit(VIEW(it), "elm,state,disabled", "elm");
978 if (it->deco_all_view)
979 edje_object_signal_emit
980 (it->deco_all_view, "elm,state,disabled", "elm");
982 if (it->item->expanded)
984 edje_object_signal_emit(VIEW(it), "elm,state,expanded", "elm");
985 if (it->deco_all_view)
986 edje_object_signal_emit
987 (it->deco_all_view, "elm,state,expanded", "elm");
992 _elm_genlist_item_index_update(Elm_Gen_Item *it)
994 if (it->position_update || it->item->block->position_update)
996 evas_object_smart_callback_call(WIDGET(it), SIG_INDEX_UPDATE, it);
997 it->position_update = EINA_FALSE;
1002 _item_text_realize(Elm_Gen_Item *it,
1003 Evas_Object *target,
1007 if (it->itc->func.text_get)
1013 *source = elm_widget_stringlist_get
1014 (edje_object_data_get(target, "texts"));
1015 EINA_LIST_FOREACH(*source, l, key)
1017 if (parts && fnmatch(parts, key, FNM_PERIOD))
1020 char *s = it->itc->func.text_get
1021 ((void *)it->base.data, WIDGET(it), key);
1025 edje_object_part_text_escaped_set(target, key, s);
1030 edje_object_part_text_set(target, key, "");
1037 // FIXME: difference from upstream
1039 _content_focused(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1041 Elm_Gen_Item *it = data;
1042 if (it) it->defer_unrealize = EINA_TRUE;
1046 _content_unfocused(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1048 Elm_Gen_Item *it = data;
1049 if (it) it->defer_unrealize = EINA_FALSE;
1054 _item_mode_content_realize(Elm_Gen_Item *it,
1055 Evas_Object *target,
1058 Eina_List **contents_list)
1060 Eina_List *res = *contents_list;
1062 if (it->itc->func.content_get)
1068 EINA_LIST_FOREACH(*source, l, key)
1070 if (parts && fnmatch(parts, key, FNM_PERIOD))
1073 ic = it->itc->func.content_get
1074 ((void *)it->base.data, WIDGET(it), key);
1078 res = eina_list_append(res, ic);
1079 edje_object_part_swallow(target, key, ic);
1080 evas_object_show(ic);
1081 #if GENLIST_ENTRY_SUPPORT
1084 // For entry or editfield
1085 // 1. Add resize callback for multiline entry.
1086 // 2. Do not unrealize it for focus issue
1087 // ps. Only for entry because of performnace
1088 if (!strcmp("elm_entry", evas_object_type_get(ic)))
1089 it->item->unrealize_disabled = EINA_TRUE;
1093 // FIXME: difference from upstream
1096 // FIXME: if entry calcuates its cursor position correctly and conformant works,
1097 // genlist does not need to handle this focus thing.
1098 evas_object_smart_callback_add(ic, "focused", _content_focused, it);
1099 evas_object_smart_callback_add(ic, "unfocused", _content_unfocused, it);
1102 if (elm_widget_item_disabled_get(it))
1103 elm_widget_disabled_set(ic, EINA_TRUE);
1112 _item_state_realize(Elm_Gen_Item *it,
1113 Evas_Object *target,
1117 if (it->itc->func.state_get)
1124 *source = elm_widget_stringlist_get
1125 (edje_object_data_get(target, "states"));
1126 EINA_LIST_FOREACH(*source, l, key)
1128 if (parts && fnmatch(parts, key, FNM_PERIOD))
1131 Eina_Bool on = it->itc->func.state_get
1132 ((void *)it->base.data, WIDGET(it), key);
1136 snprintf(buf, sizeof(buf), "elm,state,%s,active", key);
1137 edje_object_signal_emit(target, buf, "elm");
1141 snprintf(buf, sizeof(buf), "elm,state,%s,passive", key);
1142 edje_object_signal_emit(target, buf, "elm");
1149 _decorate_item_unrealize(Elm_Gen_Item *it)
1151 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
1152 Evas_Object *content;
1154 if (!it->item->deco_it_view) return;
1156 //evas_event_freeze(evas_object_evas_get(obj));
1157 elm_widget_stringlist_free(it->item->deco_it_texts);
1158 it->item->deco_it_texts = NULL;
1159 elm_widget_stringlist_free(it->item->deco_it_contents);
1160 it->item->deco_it_contents = NULL;
1161 elm_widget_stringlist_free(it->item->deco_it_states);
1163 EINA_LIST_FREE (it->item->deco_it_content_objs, content)
1164 evas_object_del(content);
1166 edje_object_part_unswallow(it->item->deco_it_view, VIEW(it));
1167 evas_object_smart_member_add(VIEW(it), sd->pan_obj);
1168 evas_object_del(it->item->deco_it_view);
1169 it->item->deco_it_view = NULL;
1171 if (sd->mode_item == it) sd->mode_item = NULL;
1172 //evas_event_thaw(evas_object_evas_get(obj));
1173 //evas_event_thaw_eval(evas_object_evas_get(obj));
1178 _decorate_all_item_position(Elm_Gen_Item *it,
1182 evas_object_resize(it->deco_all_view, it->item->w, it->item->h);
1183 evas_object_move(it->deco_all_view, itx, ity);
1187 _decorate_all_item_realize(Elm_Gen_Item *it,
1188 Eina_Bool effect_on)
1191 const char *stacking;
1192 const char *stacking_even;
1194 if ((!it) || (it->item->decorate_all_item_realized)) return;
1196 if (it->item->deco_it_view) _decorate_item_unrealize(it);
1198 it->deco_all_view = edje_object_add(evas_object_evas_get(WIDGET(it)));
1199 edje_object_scale_set(it->deco_all_view, elm_widget_scale_get(WIDGET(it)) *
1200 elm_config_scale_get());
1201 evas_object_smart_member_add(it->deco_all_view, GL_IT(it)->wsd->pan_obj);
1202 elm_widget_sub_object_add(WIDGET(it), it->deco_all_view);
1204 if (it->item->type & ELM_GENLIST_ITEM_TREE)
1205 strncpy(buf, "tree", sizeof(buf));
1206 else strncpy(buf, "item", sizeof(buf));
1207 if (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)
1208 strncat(buf, "_compress", sizeof(buf) - strlen(buf));
1210 strncat(buf, "/", sizeof(buf) - strlen(buf));
1211 strncat(buf, it->itc->decorate_all_item_style, sizeof(buf) - strlen(buf));
1213 elm_widget_theme_object_set(WIDGET(it), it->deco_all_view, "genlist", buf,
1214 elm_widget_style_get(WIDGET(it)));
1216 stacking_even = edje_object_data_get(VIEW(it), "stacking_even");
1217 if (!stacking_even) stacking_even = "above";
1218 it->item->stacking_even = !!strcmp("above", stacking_even);
1220 stacking = edje_object_data_get(VIEW(it), "stacking");
1221 if (!stacking) stacking = "yes";
1222 it->item->nostacking = !!strcmp("yes", stacking);
1224 edje_object_mirrored_set
1225 (it->deco_all_view, elm_widget_mirrored_get(WIDGET(it)));
1227 _elm_genlist_item_odd_even_update(it);
1228 _elm_genlist_item_state_update(it);
1230 #if 1 // FIXME: difference from upstream
1231 if (GL_IT(it)->wsd->reorder_mode)
1232 edje_object_signal_emit
1233 (it->deco_all_view, "elm,state,reorder,mode_set", "elm");
1235 edje_object_signal_emit
1236 (it->deco_all_view, "elm,state,reorder,mode_unset", "elm");
1240 edje_object_signal_emit
1241 (it->deco_all_view, "elm,state,decorate,enabled,effect", "elm");
1242 edje_object_signal_emit
1243 (VIEW(it), "elm,state,decorate,enabled,effect", "elm");
1247 edje_object_signal_emit
1248 (it->deco_all_view, "elm,state,decorate,enabled", "elm");
1249 edje_object_signal_emit
1250 (VIEW(it), "elm,state,decorate,enabled", "elm");
1252 _item_mouse_callbacks_del(it, VIEW(it));
1253 _item_mouse_callbacks_add(it, it->deco_all_view);
1255 _item_text_realize(it, it->deco_all_view, &it->item->deco_all_texts, NULL);
1257 edje_object_signal_emit
1258 (it->deco_all_view, "elm,state,flip,enabled", "elm");
1259 if (!it->item->deco_all_contents)
1260 it->item->deco_all_contents = elm_widget_stringlist_get
1261 (edje_object_data_get(it->deco_all_view, "contents"));
1262 it->item->deco_all_content_objs =
1263 _item_mode_content_realize(it, it->deco_all_view,
1264 &it->item->deco_all_contents, NULL,
1265 &it->item->deco_all_content_objs);
1267 (it, it->deco_all_view, &it->item->deco_all_states, NULL);
1268 edje_object_part_swallow
1269 (it->deco_all_view, "elm.swallow.decorate.content", VIEW(it));
1271 _decorate_all_item_position(it, it->item->scrl_x, it->item->scrl_y);
1272 evas_object_show(it->deco_all_view);
1276 edje_object_signal_emit(it->deco_all_view, "elm,state,selected", "elm");
1277 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
1280 it->item->decorate_all_item_realized = EINA_TRUE;
1281 it->want_unrealize = EINA_FALSE;
1285 _expand_toggle_signal_cb(void *data,
1286 Evas_Object *obj __UNUSED__,
1287 const char *emission __UNUSED__,
1288 const char *source __UNUSED__)
1290 Elm_Gen_Item *it = data;
1292 if (it->item->expanded)
1293 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACT_REQUEST, it);
1295 evas_object_smart_callback_call(WIDGET(it), SIG_EXPAND_REQUEST, it);
1299 _expand_signal_cb(void *data,
1300 Evas_Object *obj __UNUSED__,
1301 const char *emission __UNUSED__,
1302 const char *source __UNUSED__)
1304 Elm_Gen_Item *it = data;
1306 if (!it->item->expanded)
1307 evas_object_smart_callback_call(WIDGET(it), SIG_EXPAND_REQUEST, it);
1311 _contract_signal_cb(void *data,
1312 Evas_Object *obj __UNUSED__,
1313 const char *emission __UNUSED__,
1314 const char *source __UNUSED__)
1316 Elm_Gen_Item *it = data;
1318 if (it->item->expanded)
1319 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACT_REQUEST, it);
1322 #if GENLIST_ENTRY_SUPPORT
1324 _changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1326 Elm_Gen_Item *it = data;
1328 if (it->want_unrealize) return;
1329 GL_IT(it)->wsd->size_changed = EINA_TRUE;
1330 evas_object_smart_changed(GL_IT(it)->wsd->pan_obj);
1335 _item_content_realize(Elm_Gen_Item *it,
1336 Evas_Object *target,
1340 Eina_List *res = it->content_objs;
1342 if (it->itc->func.content_get)
1346 Evas_Object *ic = NULL;
1349 *source = elm_widget_stringlist_get
1350 (edje_object_data_get(target, "contents"));
1352 EINA_LIST_FOREACH(*source, l, key)
1354 if (parts && fnmatch(parts, key, FNM_PERIOD))
1357 if (it->itc->func.content_get)
1358 ic = it->itc->func.content_get
1359 ((void *)it->base.data, WIDGET(it), key);
1362 res = eina_list_append(res, ic);
1363 edje_object_part_swallow(target, key, ic);
1364 evas_object_show(ic);
1366 #if GENLIST_ENTRY_SUPPORT
1367 // For entry or editfield
1368 // 1. Add resize callback for multiline entry.
1369 // 2. Do not unrealize it for focus issue
1370 // ps. Only for entry because of performnace
1371 if (!strcmp("elm_entry", evas_object_type_get(ic)))
1373 if (!elm_entry_single_line_get(ic))
1374 evas_object_event_callback_add
1375 (ic, EVAS_CALLBACK_CHANGED_SIZE_HINTS,
1376 _changed_size_hints, it);
1377 it->item->unrealize_disabled = EINA_TRUE;
1380 #if 0 // FIXME: difference from upstream
1383 // FIXME: if entry calcuates its cursor position correctly and conformant works,
1384 // genlist does not need to handle this focus thing.
1385 evas_object_smart_callback_add(ic, "focused", _content_focused, it);
1386 evas_object_smart_callback_add(ic, "unfocused", _content_unfocused, it);
1389 if (elm_widget_item_disabled_get(it))
1390 elm_widget_disabled_set(ic, EINA_TRUE);
1399 _access_info_cb(void *data, Evas_Object *obj __UNUSED__)
1404 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1405 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
1407 buf = eina_strbuf_new();
1409 if (it->itc->func.text_get)
1414 if (!(it->texts)) it->texts =
1415 elm_widget_stringlist_get(edje_object_data_get(VIEW(it), "texts"));
1417 EINA_LIST_FOREACH(it->texts, l, key)
1419 char *s = it->itc->func.text_get
1420 ((void *)it->base.data, WIDGET(it), key);
1422 s = _elm_util_mkup_to_text(s);
1426 if (eina_strbuf_length_get(buf) > 0) eina_strbuf_append(buf, ", ");
1427 eina_strbuf_append(buf, s);
1433 ret = eina_strbuf_string_steal(buf);
1434 eina_strbuf_free(buf);
1439 _access_state_cb(void *data, Evas_Object *obj __UNUSED__)
1441 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1442 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
1444 if (it->base.disabled)
1445 return strdup(E_("State: Disabled"));
1451 _access_on_highlight_cb(void *data)
1453 Evas_Coord x, y, w, h;
1454 Evas_Coord sx, sy, sw, sh;
1455 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1456 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it);
1458 ELM_GENLIST_DATA_GET(it->base.widget, sd);
1460 evas_object_geometry_get(it->base.view, &x, &y, &w, &h);
1461 // XXX There would be a reason.
1462 if ((w == 0) && (h == 0)) return;
1464 evas_object_geometry_get(ELM_WIDGET_DATA(sd)->obj, &sx, &sy, &sw, &sh);
1465 if ((x < sx) || (y < sy) || ((x + w) > (sx + sw)) || ((y + h) > (sy + sh)))
1466 elm_genlist_item_bring_in((Elm_Object_Item *)it,
1467 ELM_GENLIST_ITEM_SCROLLTO_IN);
1471 _access_widget_item_register(Elm_Gen_Item *it)
1473 Elm_Access_Info *ai;
1475 _elm_access_widget_item_register((Elm_Widget_Item *)it);
1477 ai = _elm_access_object_get(it->base.access_obj);
1479 _elm_access_callback_set(ai, ELM_ACCESS_INFO, _access_info_cb, it);
1480 _elm_access_callback_set(ai, ELM_ACCESS_STATE, _access_state_cb, it);
1481 _elm_access_on_highlight_hook_set(ai, _access_on_highlight_cb, it);
1482 _elm_access_activate_callback_set(ai, _access_activate_cb, it);
1486 _item_realize(Elm_Gen_Item *it,
1490 const char *treesize;
1496 if (it->item->order_num_in != in)
1498 _item_order_update(EINA_INLIST_GET(it), in);
1499 _elm_genlist_item_state_update(it);
1500 _elm_genlist_item_index_update(it);
1504 it->item->order_num_in = in;
1506 if (it->item->nocache_once | it->item->nocache ||
1507 it->item->type == ELM_GENLIST_ITEM_TREE || it->parent ||
1508 !_item_cache_pop(it))
1510 const char *stacking_even;
1511 const char *stacking;
1513 it->item->nocache_once = EINA_FALSE;
1515 VIEW(it) = edje_object_add(evas_object_evas_get(WIDGET(it)));
1516 edje_object_scale_set(VIEW(it),
1517 elm_widget_scale_get(WIDGET(it)) *
1518 elm_config_scale_get());
1519 evas_object_smart_member_add(VIEW(it), GL_IT(it)->wsd->pan_obj);
1520 elm_widget_sub_object_add(WIDGET(it), VIEW(it));
1522 if (it->item->type & ELM_GENLIST_ITEM_TREE)
1523 snprintf(buf, sizeof(buf), "tree%s/%s",
1524 GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS ? "_compress" :
1525 "", it->itc->item_style ? : "default");
1527 snprintf(buf, sizeof(buf), "item%s/%s",
1528 GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS ? "_compress" :
1529 "", it->itc->item_style ? : "default");
1531 elm_widget_theme_object_set
1532 (WIDGET(it), VIEW(it), "genlist", buf,
1533 elm_widget_style_get(WIDGET(it)));
1535 #if 1 // FIXME: difference from upstream
1536 if (it->item->expanded_depth > 0)
1537 edje_object_signal_emit(VIEW(it), "bg_color_change", "elm");
1540 stacking_even = edje_object_data_get(VIEW(it), "stacking_even");
1541 if (!stacking_even) stacking_even = "above";
1542 it->item->stacking_even = !!strcmp("above", stacking_even);
1544 stacking = edje_object_data_get(VIEW(it), "stacking");
1545 if (!stacking) stacking = "yes";
1546 it->item->nostacking = !!strcmp("yes", stacking);
1548 edje_object_mirrored_set
1549 (VIEW(it), elm_widget_mirrored_get(WIDGET(it)));
1551 edje_object_signal_callback_add
1552 (VIEW(it), "elm,action,expand,toggle", "elm",
1553 _expand_toggle_signal_cb, it);
1554 edje_object_signal_callback_add
1555 (VIEW(it), "elm,action,expand", "elm", _expand_signal_cb, it);
1556 edje_object_signal_callback_add
1557 (VIEW(it), "elm,action,contract", "elm", _contract_signal_cb, it);
1558 _item_mouse_callbacks_add(it, VIEW(it));
1562 if (_elm_config->access_mode) _access_widget_item_register(it);
1564 _item_order_update(EINA_INLIST_GET(it), in);
1565 #if 1 // FIXME: difference from upstream
1566 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
1568 if (GL_IT(it)->wsd->reorder_mode)
1569 edje_object_signal_emit
1570 (VIEW(it), "elm,state,reorder,mode_set", "elm");
1572 edje_object_signal_emit
1573 (VIEW(it), "elm,state,reorder,mode_unset", "elm");
1576 treesize = edje_object_data_get(VIEW(it), "treesize");
1577 if (treesize) tsize = atoi(treesize);
1578 if (it->parent && GL_IT(it->parent)->type == ELM_GENLIST_ITEM_TREE &&
1579 !it->spacer && treesize)
1582 evas_object_rectangle_add(evas_object_evas_get(WIDGET(it)));
1583 evas_object_color_set(it->spacer, 0, 0, 0, 0);
1587 evas_object_size_hint_min_set
1588 (it->spacer, (it->item->expanded_depth * tsize) *
1589 elm_config_scale_get(), 1);
1590 edje_object_part_swallow(VIEW(it), "elm.swallow.pad", it->spacer);
1594 if ((GL_IT(it)->wsd->decorate_all_mode) && (!it->deco_all_view) &&
1595 (it->item->type != ELM_GENLIST_ITEM_GROUP) &&
1596 (it->itc->decorate_all_item_style))
1597 _decorate_all_item_realize(it, EINA_FALSE);
1599 _elm_genlist_item_state_update(it);
1600 _elm_genlist_item_index_update(it);
1603 /* homogenous genlist shortcut */
1604 if ((calc) && (GL_IT(it)->wsd->homogeneous) && (!it->item->mincalcd) &&
1605 ((it->group && GL_IT(it)->wsd->group_item_width) ||
1606 (!it->group && GL_IT(it)->wsd->item_width)))
1610 it->item->w = it->item->minw = GL_IT(it)->wsd->group_item_width;
1611 it->item->h = it->item->minh = GL_IT(it)->wsd->group_item_height;
1615 it->item->w = it->item->minw = GL_IT(it)->wsd->item_width;
1616 it->item->h = it->item->minh = GL_IT(it)->wsd->item_height;
1618 it->item->mincalcd = EINA_TRUE;
1622 if (eina_list_count(it->content_objs) != 0)
1623 ERR_ABORT("If you see this error, please notify us and we"
1626 _item_text_realize(it, VIEW(it), &it->texts, NULL);
1628 _item_content_realize(it, VIEW(it), &it->contents, NULL);
1629 _item_state_realize(it, VIEW(it), &it->states, NULL);
1632 edje_object_signal_emit
1633 (VIEW(it), "elm,state,flip,enabled", "elm");
1634 // This is needed before contents are swallowed
1635 edje_object_message_signal_process(VIEW(it));
1637 if (!(it->item->flip_contents))
1638 it->item->flip_contents = elm_widget_stringlist_get
1639 (edje_object_data_get(VIEW(it), "flips"));
1640 it->item->flip_content_objs = _item_mode_content_realize
1641 (it, VIEW(it), &it->item->flip_contents, NULL,
1642 &it->item->flip_content_objs);
1645 /* access: unregister item which have no text and content */
1646 if (_elm_config->access_mode && !it->texts && !it->contents)
1647 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
1650 // FIXME: difference from upstream
1651 if (!it->item->mincalcd || ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) && (it->item->w != it->item->minw)))
1653 if (!it->item->mincalcd)
1656 Evas_Coord mw = 0, mh = 0;
1658 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
1659 elm_coords_finger_size_adjust(1, &mw, 1, &mh);
1660 if ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) &&
1661 (GL_IT(it)->wsd->prev_viewport_w != 0) &&
1662 (mw < GL_IT(it)->wsd->prev_viewport_w))
1663 mw = GL_IT(it)->wsd->prev_viewport_w;
1664 edje_object_size_min_restricted_calc(VIEW(it), &mw, &mh, mw, mh);
1665 if ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) &&
1666 (GL_IT(it)->wsd->prev_viewport_w != 0) &&
1667 (mw > GL_IT(it)->wsd->prev_viewport_w))
1668 mw = GL_IT(it)->wsd->prev_viewport_w;
1671 it->item->w = it->item->minw = mw;
1672 it->item->h = it->item->minh = mh;
1673 it->item->mincalcd = EINA_TRUE;
1675 if ((!GL_IT(it)->wsd->group_item_width) && (it->group))
1677 GL_IT(it)->wsd->group_item_width = mw;
1678 GL_IT(it)->wsd->group_item_height = mh;
1680 else if ((!GL_IT(it)->wsd->item_width) &&
1681 (it->item->type == ELM_GENLIST_ITEM_NONE))
1683 GL_IT(it)->wsd->item_width = mw;
1684 GL_IT(it)->wsd->item_height = mh;
1687 if (!calc) evas_object_show(VIEW(it));
1690 if (it->tooltip.content_cb)
1692 elm_widget_item_tooltip_content_cb_set
1693 (it, it->tooltip.content_cb, it->tooltip.data, NULL);
1694 elm_widget_item_tooltip_style_set(it, it->tooltip.style);
1695 elm_widget_item_tooltip_window_mode_set(it, it->tooltip.free_size);
1698 if (it->mouse_cursor)
1699 elm_widget_item_cursor_set(it, it->mouse_cursor);
1701 it->realized = EINA_TRUE;
1702 it->want_unrealize = EINA_FALSE;
1704 if (!calc || it->item->unrealize_disabled)
1705 evas_object_smart_callback_call(WIDGET(it), SIG_REALIZED, it);
1707 if ((!calc) && (GL_IT(it)->wsd->decorate_all_mode) &&
1708 (it->item->type != ELM_GENLIST_ITEM_GROUP))
1710 if (it->itc->decorate_all_item_style)
1712 if (!it->deco_all_view)
1713 _decorate_all_item_realize(it, EINA_FALSE);
1714 edje_object_message_signal_process(it->deco_all_view);
1717 if ((!calc) && (it->decorate_it_set) &&
1718 (it->item->type != ELM_GENLIST_ITEM_GROUP))
1720 if (it->itc->decorate_item_style)
1722 if (!it->item->deco_it_view)
1723 _decorate_item_set(it);
1724 edje_object_message_signal_process(it->item->deco_it_view);
1727 edje_object_message_signal_process(VIEW(it));
1730 #if GENLIST_PINCH_ZOOM_SUPPORT
1732 _pinch_items_recalc(void *data)
1734 Elm_Genlist_Smart_Data *sd = data;
1739 Evas_Coord tot_y = 0, ox, oy;
1740 evas_object_geometry_get(sd->pan_obj, &ox, &oy, NULL, NULL);
1742 EINA_INLIST_FOREACH(sd->blocks, itb)
1744 EINA_LIST_FOREACH(itb->items, l, it)
1747 if (IS_ROOT_PARENT_IT(it))
1749 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
1751 if (!it->realized) _item_realize(it, 0, EINA_FALSE);
1752 it->item->scrl_y = oy + tot_y - sd->pan_y;
1753 evas_object_resize(VIEW(it), sd->minw, it->item->h);
1754 evas_object_move(VIEW(it), it->item->scrl_x, it->item->scrl_y);
1755 evas_object_show(VIEW(it));
1756 evas_object_raise(VIEW(it));
1757 tot_y += it->item->h;
1758 sd->pinch_zoom_h = tot_y;
1761 else if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND)
1763 evas_object_resize(VIEW(it), sd->minw, it->item->h);
1764 it->item->scrl_y = oy + it->item->pan_scrl_y - sd->pan_y;
1765 evas_object_move(VIEW(it), it->item->scrl_x, it->item->scrl_y);
1774 #if GROUP_ITEMS_FEATURE
1776 _group_items_recalc(void *data)
1780 Elm_Genlist_Smart_Data *sd = data;
1782 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1783 EINA_LIST_FOREACH(sd->group_items, l, git)
1785 if (git->item->want_realize)
1787 if (!git->realized) _item_realize(git, 0, EINA_FALSE);
1788 evas_object_resize(VIEW(git), sd->minw, git->item->h);
1789 evas_object_move(VIEW(git), git->item->scrl_x, git->item->scrl_y);
1790 evas_object_show(VIEW(git));
1791 evas_object_raise(VIEW(git));
1793 else if (!git->item->want_realize)
1796 _item_unrealize(git, EINA_FALSE);
1799 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1800 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1805 _reorder_move_animator_cb(void *data)
1808 Elm_Gen_Item *it = data;
1809 Eina_Bool down = EINA_FALSE;
1812 dy = 6 * elm_config_scale_get();
1813 t = ((0.0 > (t = ecore_loop_time_get()
1814 - GL_IT(it)->wsd->start_time)) ? 0.0 : t);
1816 if (t <= REORDER_EFFECT_TIME)
1817 y = (1 * sin((t / REORDER_EFFECT_TIME) * (M_PI / 2)) * dy);
1820 diff = abs(it->item->old_scrl_y - it->item->scrl_y);
1821 if (diff < dy) y = diff;
1823 if (it->item->old_scrl_y < it->item->scrl_y)
1825 it->item->old_scrl_y += y;
1828 else if (it->item->old_scrl_y > it->item->scrl_y)
1830 it->item->old_scrl_y -= y;
1834 if (it->deco_all_view)
1836 (it, it->deco_all_view, it->item->scrl_x, it->item->old_scrl_y);
1837 else if (it->item->deco_it_view)
1839 (it, it->item->deco_it_view, it->item->scrl_x, it->item->old_scrl_y);
1841 _item_position(it, VIEW(it), it->item->scrl_x, it->item->old_scrl_y);
1843 if ((GL_IT(it)->wsd->reorder_pan_move) ||
1844 (down && it->item->old_scrl_y >= it->item->scrl_y) ||
1845 (!down && it->item->old_scrl_y <= it->item->scrl_y))
1847 it->item->old_scrl_y = it->item->scrl_y;
1848 it->item->move_effect_enabled = EINA_FALSE;
1849 GL_IT(it)->wsd->reorder_move_animator = NULL;
1850 return ECORE_CALLBACK_CANCEL;
1853 return ECORE_CALLBACK_RENEW;
1857 _reorder_item_space_get(Elm_Gen_Item *it)
1859 Elm_Gen_Item *reorder_it = GL_IT(it)->wsd->reorder_it;
1860 Evas_Coord rox, roy, row, roh, oy, oh;
1861 Eina_Bool top = EINA_FALSE;
1863 if (!reorder_it) return 0;
1864 if(it->deco_all_view) evas_object_lower(it->deco_all_view);
1866 evas_object_geometry_get(GL_IT(it)->wsd->pan_obj, NULL, &oy, NULL, &oh);
1867 evas_object_geometry_get
1868 (GL_IT(it)->wsd->VIEW(reorder_it), &rox, &roy, &row, &roh);
1870 if ((GL_IT(it)->wsd->reorder_start_y < it->item->block->y) &&
1871 (roy - oy + (roh / 2) >= it->item->block->y - GL_IT(it)->wsd->pan_y))
1873 it->item->block->reorder_offset =
1874 GL_IT(it)->wsd->reorder_it->item->h * -1;
1875 if (it->item->block->count == 1)
1876 GL_IT(it)->wsd->reorder_rel = it;
1878 else if ((GL_IT(it)->wsd->reorder_start_y >= it->item->block->y) &&
1879 (roy - oy + (roh / 2) <= it->item->block->y -
1880 GL_IT(it)->wsd->pan_y))
1882 it->item->block->reorder_offset = GL_IT(it)->wsd->reorder_it->item->h;
1885 it->item->block->reorder_offset = 0;
1887 it->item->scrl_y += it->item->block->reorder_offset;
1889 top = (ELM_RECTS_INTERSECT
1890 (it->item->scrl_x, it->item->scrl_y, it->item->w, it->item->h,
1891 rox, roy + (roh / 2), row, 1));
1894 GL_IT(it)->wsd->reorder_rel = it;
1895 it->item->scrl_y += GL_IT(it)->wsd->reorder_it->item->h;
1896 return GL_IT(it)->wsd->reorder_it->item->h;
1903 _item_block_position(Item_Block *itb,
1909 Eina_Bool vis = EINA_FALSE;
1910 Evas_Coord y = 0, ox, oy, ow, oh, cvx, cvy, cvw, cvh;
1912 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
1913 evas_object_geometry_get(itb->sd->pan_obj, &ox, &oy, &ow, &oh);
1914 evas_output_viewport_get
1915 (evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj),
1916 &cvx, &cvy, &cvw, &cvh);
1918 EINA_LIST_FOREACH(itb->items, l, it)
1920 if ((GL_IT(it)->wsd->reorder_it == it) && it->highlighted) continue;
1924 it->item->w = itb->w;
1925 it->item->scrl_x = itb->x + it->x - GL_IT(it)->wsd->pan_x + ox;
1926 it->item->scrl_y = itb->y + it->y - GL_IT(it)->wsd->pan_y + oy;
1928 vis = (ELM_RECTS_INTERSECT
1929 (it->item->scrl_x, it->item->scrl_y, it->item->w, it->item->h,
1930 cvx, cvy, cvw, cvh));
1933 if ((itb->realized) && (!it->realized))
1935 if (vis) _item_realize(it, in, EINA_FALSE);
1939 if (vis || it->dragging)
1941 #if GENLIST_ENTRY_SUPPORT
1942 evas_object_show(VIEW(it));
1944 if (GL_IT(it)->wsd->reorder_mode &&
1945 GL_IT(it)->wsd->reorder_it &&
1946 GL_IT(it)->wsd->reorder_it->highlighted)
1947 y += _reorder_item_space_get(it);
1948 git = it->item->group_item;
1951 if (git->item->scrl_y < oy)
1952 git->item->scrl_y = oy;
1953 if ((git->item->scrl_y + git->item->h) >
1954 (it->item->scrl_y + it->item->h))
1955 git->item->scrl_y = (it->item->scrl_y +
1956 it->item->h) - git->item->h;
1957 git->item->scrl_x = it->item->scrl_x;
1958 git->item->want_realize = EINA_TRUE;
1960 if ((GL_IT(it)->wsd->reorder_it) &&
1961 GL_IT(it)->wsd->reorder_it->highlighted &&
1962 (it->item->old_scrl_y != it->item->scrl_y))
1964 if (!it->item->move_effect_enabled)
1966 it->item->move_effect_enabled = EINA_TRUE;
1967 GL_IT(it)->wsd->reorder_move_animator =
1969 _reorder_move_animator_cb, it);
1972 if (!it->item->move_effect_enabled)
1974 if ((GL_IT(it)->wsd->decorate_all_mode) &&
1975 (it->itc->decorate_all_item_style))
1976 _decorate_all_item_position
1977 (it, it->item->scrl_x, it->item->scrl_y);
1980 if (it->item->deco_it_view)
1982 (it, it->item->deco_it_view,
1987 (it, VIEW(it), it->item->scrl_x,
1990 it->item->old_scrl_y = it->item->scrl_y;
1991 #if GENLIST_PINCH_ZOOM_SUPPORT
1992 if (((GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
1993 && (!IS_ROOT_PARENT_IT(it))) || (GL_IT(it)->wsd->sorting))
1995 if (it->deco_all_view) evas_object_hide(it->deco_all_view);
1996 else evas_object_hide(VIEW(it));
2004 if ((GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
2005 && (!IS_ROOT_PARENT_IT(it)))
2007 if (it->deco_all_view) evas_object_hide(it->deco_all_view);
2008 else evas_object_hide(VIEW(it));
2011 _item_unrealize(it, EINA_FALSE);
2018 if (vis) it->item->want_realize = EINA_TRUE;
2022 // FIXME: diffrence from upstream
2023 minh += it->item->minh;
2027 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
2028 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
2032 _item_block_realize(Item_Block *itb)
2034 if (itb->realized) return;
2036 itb->realized = EINA_TRUE;
2037 itb->want_unrealize = EINA_FALSE;
2041 _changed_job(Elm_Genlist_Smart_Data *sd)
2047 Eina_Bool anything_changed = EINA_FALSE;
2048 Eina_Bool width_changed = EINA_FALSE;
2049 Eina_Bool height_changed = EINA_FALSE;
2051 EINA_INLIST_FOREACH(sd->blocks, itb)
2056 width_changed = height_changed = EINA_FALSE;
2057 EINA_LIST_FOREACH(itb->items, l2, it)
2061 Evas_Coord mw = 0, mh = 0;
2063 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
2064 elm_coords_finger_size_adjust(1, &mw, 1, &mh);
2065 if ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) &&
2066 (GL_IT(it)->wsd->prev_viewport_w != 0) &&
2067 (mw < GL_IT(it)->wsd->prev_viewport_w))
2068 mw = GL_IT(it)->wsd->prev_viewport_w;
2069 edje_object_size_min_restricted_calc(VIEW(it), &mw, &mh, mw, mh);
2070 if ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) &&
2071 (GL_IT(it)->wsd->prev_viewport_w != 0) &&
2072 (mw > GL_IT(it)->wsd->prev_viewport_w))
2073 mw = GL_IT(it)->wsd->prev_viewport_w;
2075 if (it->item->minw != mw)
2077 it->item->w = it->item->minw = mw;
2078 width_changed = EINA_TRUE;
2080 if (it->item->minh != mh)
2082 it->item->h = it->item->minh = mh;
2083 height_changed = EINA_TRUE;
2090 if ((!sd->group_item_width) && (it->group))
2092 sd->group_item_width = mw;
2093 sd->group_item_height = mh;
2095 else if ((!sd->item_width) &&
2096 (it->item->type == ELM_GENLIST_ITEM_NONE))
2098 sd->item_width = mw;
2099 sd->item_height = mh;
2106 anything_changed = EINA_TRUE;
2107 itb->changed = EINA_TRUE;
2108 _item_block_recalc(itb, num0, 0);
2109 _item_block_position(itb, num0);
2111 else if (width_changed)
2113 _item_block_position(itb, num0);
2116 if (anything_changed)
2118 if (sd->calc_job) ecore_job_del(sd->calc_job);
2119 sd->calc_job = ecore_job_add(_calc_job, sd);
2124 _elm_genlist_pan_smart_calculate(Evas_Object *obj)
2126 Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh;
2127 Evas_Coord vx = 0, vy = 0, vw = 0, vh = 0;
2133 ELM_GENLIST_PAN_DATA_GET(obj, psd);
2135 //evas_event_freeze(evas_object_evas_get(obj));
2137 #if GENLIST_FX_SUPPORT
2138 if (psd->wsd->fx_playing) return;
2140 if (psd->wsd->pan_changed)
2142 _calc_job(psd->wsd);
2143 psd->wsd->pan_changed = EINA_FALSE;
2146 evas_object_geometry_get(obj, &ox, &oy, &ow, &oh);
2147 evas_output_viewport_get(evas_object_evas_get(obj), &cvx, &cvy, &cvw, &cvh);
2148 EINA_LIST_FOREACH(psd->wsd->group_items, l, git)
2150 #if GROUP_ITEMS_FEATURE
2151 git->item->want_realize = EINA_FALSE;
2153 evas_object_hide(VIEW(git));
2157 EINA_INLIST_FOREACH(psd->wsd->blocks, itb)
2159 itb->w = psd->wsd->minw;
2160 if (ELM_RECTS_INTERSECT(itb->x - psd->wsd->pan_x + ox,
2161 itb->y - psd->wsd->pan_y + oy,
2163 cvx, cvy, cvw, cvh))
2165 if ((!itb->realized) || (itb->changed))
2167 _item_block_realize(itb);
2169 // FIXME: difference from opensource
2170 if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job);
2171 sd->wd->calc_job = NULL;
2175 _item_block_position(itb, in);
2179 if (itb->realized) _item_block_unrealize(itb);
2183 #if GENLIST_PINCH_ZOOM_SUPPORT
2184 if (psd->wsd->pinch_zoom_mode) _pinch_items_recalc(psd->wsd);
2187 #if GROUP_ITEMS_FEATURE
2188 if ((!psd->wsd->reorder_it) || (psd->wsd->reorder_pan_move))
2189 _group_items_recalc(psd->wsd);
2191 if ((psd->wsd->reorder_mode) && (psd->wsd->reorder_it))
2193 if (psd->wsd->pan_y != psd->wsd->reorder_old_pan_y)
2194 psd->wsd->reorder_pan_move = EINA_TRUE;
2195 else psd->wsd->reorder_pan_move = EINA_FALSE;
2197 evas_object_raise(psd->wsd->VIEW(reorder_it));
2198 psd->wsd->reorder_old_pan_y = psd->wsd->pan_y;
2199 psd->wsd->start_time = ecore_loop_time_get();
2201 _item_auto_scroll(psd->wsd);
2203 psd->wsd->s_iface->content_pos_get(ELM_WIDGET_DATA(psd->wsd)->obj, &vx, &vy);
2204 psd->wsd->s_iface->content_viewport_size_get(ELM_WIDGET_DATA(psd->wsd)->obj,
2207 if (psd->wsd->reorder_fast == 1)
2208 psd->wsd->s_iface->content_region_show(ELM_WIDGET_DATA(psd->wsd)->obj,
2209 vx,vy - 10, vw, vh);
2210 else if (psd->wsd->reorder_fast == -1)
2211 psd->wsd->s_iface->content_region_show(ELM_WIDGET_DATA(psd->wsd)->obj,
2212 vx, vy + 10, vw, vh);
2214 if (psd->wsd->size_changed)
2216 _changed_job(psd->wsd);
2217 psd->wsd->size_changed = EINA_FALSE;
2220 #if GENLIST_FX_SUPPORT
2221 psd->wsd->rendered = EINA_TRUE;
2222 if ((psd->wsd->fx_mode) && (!psd->wsd->queue))
2224 if (_elm_genlist_fx_capture(ELM_WIDGET_DATA(psd->wsd)->obj, 1))
2225 _elm_genlist_fx_play(ELM_WIDGET_DATA(psd->wsd)->obj);
2228 #if GENLIST_PINCH_ZOOM_SUPPORT
2229 if (psd->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND)
2230 psd->wsd->pinch_zoom_mode = ELM_GEN_PINCH_ZOOM_NONE;
2232 //evas_event_thaw(evas_object_evas_get(obj));
2233 //evas_event_thaw_eval(evas_object_evas_get(obj));
2237 _elm_genlist_pan_smart_set_user(Elm_Genlist_Pan_Smart_Class *sc)
2239 ELM_PAN_CLASS(sc)->base.add = _elm_genlist_pan_smart_add;
2240 ELM_PAN_CLASS(sc)->base.del = _elm_genlist_pan_smart_del;
2241 ELM_PAN_CLASS(sc)->base.move = _elm_genlist_pan_smart_move;
2242 ELM_PAN_CLASS(sc)->base.resize = _elm_genlist_pan_smart_resize;
2243 ELM_PAN_CLASS(sc)->base.calculate = _elm_genlist_pan_smart_calculate;
2245 ELM_PAN_CLASS(sc)->pos_set = _elm_genlist_pan_smart_pos_set;
2246 ELM_PAN_CLASS(sc)->pos_get = _elm_genlist_pan_smart_pos_get;
2247 ELM_PAN_CLASS(sc)->pos_max_get = _elm_genlist_pan_smart_pos_max_get;
2248 ELM_PAN_CLASS(sc)->pos_min_get = _elm_genlist_pan_smart_pos_min_get;
2249 ELM_PAN_CLASS(sc)->content_size_get =
2250 _elm_genlist_pan_smart_content_size_get;
2254 _item_multi_select_up(Elm_Genlist_Smart_Data *sd)
2256 Elm_Object_Item *prev;
2258 if (!sd->selected) return EINA_FALSE;
2259 if (!sd->multi) return EINA_FALSE;
2261 prev = elm_genlist_item_prev_get(sd->last_selected_item);
2262 if (!prev) return EINA_TRUE;
2264 if (elm_genlist_item_selected_get(prev))
2266 elm_genlist_item_selected_set(sd->last_selected_item, EINA_FALSE);
2267 sd->last_selected_item = prev;
2268 elm_genlist_item_show
2269 (sd->last_selected_item, ELM_GENLIST_ITEM_SCROLLTO_IN);
2273 elm_genlist_item_selected_set(prev, EINA_TRUE);
2274 elm_genlist_item_show(prev, ELM_GENLIST_ITEM_SCROLLTO_IN);
2280 _item_multi_select_down(Elm_Genlist_Smart_Data *sd)
2282 Elm_Object_Item *next;
2284 if (!sd->selected) return EINA_FALSE;
2285 if (!sd->multi) return EINA_FALSE;
2287 next = elm_genlist_item_next_get(sd->last_selected_item);
2288 if (!next) return EINA_TRUE;
2290 if (elm_genlist_item_selected_get(next))
2292 elm_genlist_item_selected_set(sd->last_selected_item, EINA_FALSE);
2293 sd->last_selected_item = next;
2294 elm_genlist_item_show
2295 (sd->last_selected_item, ELM_GENLIST_ITEM_SCROLLTO_IN);
2299 elm_genlist_item_selected_set(next, EINA_TRUE);
2300 elm_genlist_item_show(next, ELM_GENLIST_ITEM_SCROLLTO_IN);
2307 _all_items_deselect(Elm_Genlist_Smart_Data *sd)
2309 if (!sd->selected) return EINA_FALSE;
2311 while (sd->selected)
2312 elm_genlist_item_selected_set(sd->selected->data, EINA_FALSE);
2318 _item_single_select_up(Elm_Genlist_Smart_Data *sd)
2324 prev = ELM_GEN_ITEM_FROM_INLIST(sd->items->last);
2326 prev = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(prev)->prev);
2329 prev = (Elm_Gen_Item *)elm_genlist_item_prev_get
2330 (sd->last_selected_item);
2332 if (!prev) return EINA_FALSE;
2334 _all_items_deselect(sd);
2336 elm_genlist_item_selected_set((Elm_Object_Item *)prev, EINA_TRUE);
2337 elm_genlist_item_show((Elm_Object_Item *)prev, ELM_GENLIST_ITEM_SCROLLTO_IN);
2342 _item_single_select_down(Elm_Genlist_Smart_Data *sd)
2348 next = ELM_GEN_ITEM_FROM_INLIST(sd->items);
2350 next = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(next)->next);
2353 next = (Elm_Gen_Item *)elm_genlist_item_next_get
2354 (sd->last_selected_item);
2356 if (!next) return EINA_FALSE;
2358 _all_items_deselect(sd);
2360 elm_genlist_item_selected_set((Elm_Object_Item *)next, EINA_TRUE);
2361 elm_genlist_item_show
2362 ((Elm_Object_Item *)next, ELM_GENLIST_ITEM_SCROLLTO_IN);
2368 _elm_genlist_smart_event(Evas_Object *obj,
2369 Evas_Object *src __UNUSED__,
2370 Evas_Callback_Type type,
2377 Evas_Coord step_x = 0;
2378 Evas_Coord step_y = 0;
2379 Evas_Coord page_x = 0;
2380 Evas_Coord page_y = 0;
2381 Elm_Object_Item *it;
2382 Evas_Event_Key_Down *ev = event_info;
2383 Evas_Coord pan_max_x = 0, pan_max_y = 0;
2385 ELM_GENLIST_DATA_GET(obj, sd);
2387 if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE;
2388 if (!sd->items) return EINA_FALSE;
2389 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE;
2390 if (elm_widget_disabled_get(obj)) return EINA_FALSE;
2392 sd->s_iface->content_pos_get(obj, &x, &y);
2393 sd->s_iface->step_size_get(obj, &step_x, &step_y);
2394 sd->s_iface->page_size_get(obj, &page_x, &page_y);
2395 sd->s_iface->content_viewport_size_get(obj, &v_w, &v_h);
2397 if ((!strcmp(ev->keyname, "Left")) ||
2398 ((!strcmp(ev->keyname, "KP_Left")) && (!ev->string)))
2402 else if ((!strcmp(ev->keyname, "Right")) ||
2403 ((!strcmp(ev->keyname, "KP_Right")) && (!ev->string)))
2407 else if ((!strcmp(ev->keyname, "Up")) ||
2408 ((!strcmp(ev->keyname, "KP_Up")) && (!ev->string)))
2410 if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) &&
2411 (_item_multi_select_up(sd)))
2412 || (_item_single_select_up(sd)))
2414 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2420 else if ((!strcmp(ev->keyname, "Down")) ||
2421 ((!strcmp(ev->keyname, "KP_Down")) && (!ev->string)))
2423 if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) &&
2424 (_item_multi_select_down(sd)))
2425 || (_item_single_select_down(sd)))
2427 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2433 else if ((!strcmp(ev->keyname, "Home")) ||
2434 ((!strcmp(ev->keyname, "KP_Home")) && (!ev->string)))
2436 it = elm_genlist_first_item_get(obj);
2437 elm_genlist_item_bring_in(it, ELM_GENLIST_ITEM_SCROLLTO_IN);
2438 elm_genlist_item_selected_set(it, EINA_TRUE);
2439 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2442 else if ((!strcmp(ev->keyname, "End")) ||
2443 ((!strcmp(ev->keyname, "KP_End")) && (!ev->string)))
2445 it = elm_genlist_last_item_get(obj);
2446 elm_genlist_item_bring_in(it, ELM_GENLIST_ITEM_SCROLLTO_IN);
2447 elm_genlist_item_selected_set(it, EINA_TRUE);
2448 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2451 else if ((!strcmp(ev->keyname, "Prior")) ||
2452 ((!strcmp(ev->keyname, "KP_Prior")) && (!ev->string)))
2455 y -= -(page_y * v_h) / 100;
2459 else if ((!strcmp(ev->keyname, "Next")) ||
2460 ((!strcmp(ev->keyname, "KP_Next")) && (!ev->string)))
2463 y += -(page_y * v_h) / 100;
2467 else if (!strcmp(ev->keyname, "Escape"))
2469 if (!_all_items_deselect(sd)) return EINA_FALSE;
2470 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2473 else if (((!strcmp(ev->keyname, "Return")) ||
2474 (!strcmp(ev->keyname, "KP_Enter")) ||
2475 (!strcmp(ev->keyname, "space")))
2476 && (!sd->multi) && (sd->selected))
2478 it = elm_genlist_selected_item_get(obj);
2479 elm_genlist_item_expanded_set(it, !elm_genlist_item_expanded_get(it));
2480 evas_object_smart_callback_call(WIDGET(it), SIG_ACTIVATED, it);
2482 else return EINA_FALSE;
2484 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2485 _elm_genlist_pan_smart_pos_max_get(sd->pan_obj, &pan_max_x, &pan_max_y);
2487 if (x > pan_max_x) x = pan_max_x;
2489 if (y > pan_max_y) y = pan_max_y;
2491 sd->s_iface->content_pos_set(obj, x, y, EINA_TRUE);
2497 _elm_genlist_smart_sub_object_add(Evas_Object *obj,
2500 Elm_Widget_Smart_Class *parent_parent;
2502 parent_parent = (Elm_Widget_Smart_Class *)((Evas_Smart_Class *)
2503 _elm_genlist_parent_sc)->parent;
2505 /* skipping layout's code, which registers size hint changing
2506 * callback on sub objects. this is here because items'
2507 * content_get() routines may change hints on the objects after
2508 * creation, thus issuing TOO MANY sizing_eval()'s here. they are
2509 * not needed at here anyway, so let's skip listening to those
2511 if (!parent_parent->sub_object_add(obj, sobj))
2518 _elm_genlist_smart_sub_object_del(Evas_Object *obj,
2521 ELM_GENLIST_DATA_GET(obj, sd);
2523 /* XXX: hack -- also skipping sizing recalculation on
2524 * sub-object-del. genlist's crazy code paths (like groups and
2525 * such) seem to issue a whole lot of deletions and Evas bitches
2526 * about too many recalculations */
2527 sd->on_sub_del = EINA_TRUE;
2529 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->sub_object_del(obj, sobj))
2532 sd->on_sub_del = EINA_FALSE;
2538 _elm_genlist_smart_on_focus(Evas_Object *obj)
2540 ELM_GENLIST_DATA_GET(obj, sd);
2542 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->on_focus(obj))
2545 if (elm_widget_focus_get(obj) && (sd->items) && (sd->selected) &&
2546 (!sd->last_selected_item))
2547 sd->last_selected_item = eina_list_data_get(sd->selected);
2553 _elm_genlist_smart_focus_next(const Evas_Object *obj,
2554 Elm_Focus_Direction dir,
2557 Evas_Coord x, y, w, h;
2558 Evas_Coord sx, sy, sw, sh;
2560 Eina_List *items = NULL;
2561 Eina_Bool done = EINA_FALSE;
2563 ELM_GENLIST_CHECK(obj) EINA_FALSE;
2564 ELM_GENLIST_DATA_GET(obj, sd);
2566 evas_object_geometry_get(ELM_WIDGET_DATA(sd)->obj, &sx, &sy, &sw, &sh);
2568 EINA_INLIST_FOREACH(sd->blocks, itb)
2576 EINA_LIST_FOREACH(itb->items, l, it)
2580 evas_object_geometry_get(it->base.view, &x, &y, &w, &h);
2582 /* check item which displays more than half of its size */
2583 if (ELM_RECTS_INTERSECT
2584 (x + (w / 2), y + (h / 2), 0, 0, sx, sy, sw, sh))
2585 items = eina_list_append(items, it->base.access_obj);
2587 if (!it->base.access_order) continue;
2591 EINA_LIST_FOREACH(it->base.access_order, subl, subo)
2592 items = eina_list_append(items, subo);
2596 else if (done) break;
2599 return elm_widget_focus_list_next_get
2600 (obj, items, eina_list_data_get, dir, next);
2604 _mirrored_set(Evas_Object *obj,
2607 ELM_GENLIST_DATA_GET(obj, sd);
2609 sd->s_iface->mirrored_set(obj, rtl);
2613 _elm_genlist_smart_theme(Evas_Object *obj)
2617 ELM_GENLIST_DATA_GET(obj, sd);
2619 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->theme(obj))
2622 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2623 _item_cache_all_free(sd);
2624 _mirrored_set(obj, elm_widget_mirrored_get(obj));
2627 // FIXME: difference from opensource
2628 elm_layout_theme_set(obj, "genlist", "base", elm_widget_style_get(obj));
2631 sd->item_width = sd->item_height = 0;
2632 sd->group_item_width = sd->group_item_height = 0;
2633 sd->minw = sd->minh = sd->realminw = 0;
2634 EINA_INLIST_FOREACH(sd->blocks, itb)
2639 if (itb->realized) _item_block_unrealize(itb);
2640 EINA_LIST_FOREACH(itb->items, l, it)
2641 it->item->mincalcd = EINA_FALSE;
2643 itb->changed = EINA_TRUE;
2645 if (sd->calc_job) ecore_job_del(sd->calc_job);
2646 sd->calc_job = NULL;
2647 elm_layout_sizing_eval(obj);
2648 sd->pan_changed = EINA_TRUE;
2649 evas_object_smart_changed(sd->pan_obj);
2650 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2651 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2656 /* FIXME: take off later. maybe this show region coords belong in the
2657 * interface (new api functions, set/get)? */
2659 _show_region_hook(void *data,
2662 Evas_Coord x, y, w, h;
2664 ELM_GENLIST_DATA_GET(data, sd);
2666 elm_widget_show_region_get(obj, &x, &y, &w, &h);
2667 //x & y are screen coordinates, Add with pan coordinates
2670 sd->s_iface->content_region_show(obj, x, y, w, h);
2674 _elm_genlist_smart_translate(Evas_Object *obj)
2676 evas_object_smart_callback_call(obj, "language,changed", NULL);
2682 _item_highlight(Elm_Gen_Item *it)
2684 const char *selectraise;
2685 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2687 if (elm_widget_item_disabled_get(it)) return;
2688 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2689 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ) ||
2690 (it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2691 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
2694 if (!sd->highlight || it->highlighted) return;
2695 #if GENLIST_PINCH_ZOOM_SUPPORT
2696 if (sd->pinch_zoom_mode) return;
2699 selectraise = edje_object_data_get(VIEW(it), "selectraise");
2700 if ((selectraise) && (!strcmp(selectraise, "on")))
2702 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
2703 else evas_object_raise(VIEW(it));
2704 if ((it->item->group_item) && (it->item->group_item->realized))
2705 evas_object_raise(it->item->VIEW(group_item));
2707 it->highlighted = EINA_TRUE;
2709 if (it->deco_all_view)
2710 edje_object_signal_emit(it->deco_all_view, "elm,state,selected", "elm");
2711 edje_object_signal_emit(VIEW(it), "elm,state,selected", "elm");
2712 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
2716 _item_unhighlight(Elm_Gen_Item *it)
2718 if (!it->highlighted) return;
2720 if (!it->item->nostacking)
2722 if ((it->item->order_num_in & 0x1) ^ it->item->stacking_even)
2724 if (it->deco_all_view) evas_object_lower(it->deco_all_view);
2725 else evas_object_lower(VIEW(it));
2729 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
2730 else evas_object_raise(VIEW(it));
2733 it->highlighted = EINA_FALSE;
2735 if (it->deco_all_view)
2736 edje_object_signal_emit(it->deco_all_view, "elm,state,unselected", "elm");
2737 edje_object_signal_emit(VIEW(it), "elm,state,unselected", "elm");
2738 evas_object_smart_callback_call(WIDGET(it), SIG_UNHIGHLIGHTED, it);
2742 _item_unselect(Elm_Gen_Item *it)
2744 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2745 _item_unhighlight(it);
2746 if (!it->selected) return;
2748 it->selected = EINA_FALSE;
2749 sd->selected = eina_list_remove(sd->selected, it);
2750 evas_object_smart_callback_call(WIDGET(it), SIG_UNSELECTED, it);
2754 _item_select(Elm_Gen_Item *it)
2756 Evas_Object *obj = WIDGET(it);
2757 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2758 if (elm_widget_item_disabled_get(it)) return;
2759 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2760 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) ||
2761 (it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2762 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
2765 #if GENLIST_PINCH_ZOOM_SUPPORT
2766 if (IS_ROOT_PARENT_IT(it) && (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT))
2768 elm_genlist_pinch_zoom_mode_set(obj, ELM_GEN_PINCH_ZOOM_EXPAND);
2769 elm_genlist_item_show((Elm_Object_Item *)it, ELM_GENLIST_ITEM_SCROLLTO_TOP);
2775 // FIXME: difference from upstream
2776 if ((GL_IT(it)->wsd->last_selected_item) &&
2777 (it != (Elm_Gen_Item *) GL_IT(it)->wsd->last_selected_item))
2778 _item_unfocusable_set
2779 ((Elm_Gen_Item *)GL_IT(it)->wsd->last_selected_item, EINA_TRUE);
2782 // Do not check selected because always select mode can be used
2783 _item_highlight(it);
2784 it->selected = EINA_TRUE;
2785 sd->selected = eina_list_append(sd->selected, it);
2786 sd->last_selected_item = (Elm_Object_Item *)it;
2788 if (it->func.func) it->func.func((void *)it->func.data, obj, it);
2789 if (!EINA_MAGIC_CHECK((Elm_Widget_Item *)it, ELM_WIDGET_ITEM_MAGIC))
2791 evas_object_smart_callback_call(WIDGET(it), SIG_SELECTED, it);
2795 _item_select_unselect(Elm_Gen_Item *it, Eina_Bool selected)
2797 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2798 Evas_Object *obj = ELM_WIDGET_DATA(sd)->obj;
2799 if (elm_widget_item_disabled_get(it)) return;
2801 evas_object_ref(obj);
2804 const Eina_List *l, *ll;
2806 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it2)
2807 if (it2 != it) _item_unselect(it2);
2809 if (selected) _item_select(it);
2810 else _item_unselect(it);
2811 evas_object_unref(obj);
2815 _item_block_position_update(Eina_Inlist *list,
2820 EINA_INLIST_FOREACH(list, tmp)
2822 tmp->position = idx++;
2823 tmp->position_update = EINA_TRUE;
2828 _item_position_update(Eina_List *list,
2834 EINA_LIST_FOREACH(list, l, it)
2836 it->position = idx++;
2837 it->position_update = EINA_TRUE;
2842 _item_block_merge(Item_Block *left,
2848 EINA_LIST_FOREACH(right->items, l, it2)
2850 it2->item->block = left;
2852 left->changed = EINA_TRUE;
2854 left->items = eina_list_merge(left->items, right->items);
2858 _item_block_del(Elm_Gen_Item *it)
2861 Item_Block *itb = it->item->block;
2862 Eina_Bool block_changed = EINA_FALSE;
2864 itb->items = eina_list_remove(itb->items, it);
2866 itb->changed = EINA_TRUE;
2867 if (GL_IT(it)->wsd->calc_job) ecore_job_del(GL_IT(it)->wsd->calc_job);
2868 GL_IT(it)->wsd->calc_job = ecore_job_add(_calc_job, GL_IT(it)->wsd);
2873 il = EINA_INLIST_GET(itb);
2874 itbn = (Item_Block *)(il->next);
2876 it->parent->item->items =
2877 eina_list_remove(it->parent->item->items, it);
2880 _item_block_position_update(il->next, itb->position);
2882 GL_IT(it)->wsd->blocks =
2883 eina_inlist_remove(GL_IT(it)->wsd->blocks, il);
2886 if (itbn) itbn->changed = EINA_TRUE;
2890 if (itb->count < (itb->sd->max_items_per_block / 2))
2895 il = EINA_INLIST_GET(itb);
2896 itbp = (Item_Block *)(il->prev);
2897 itbn = (Item_Block *)(il->next);
2899 /* merge block with previous */
2901 ((itbp->count + itb->count) <
2902 (itb->sd->max_items_per_block +
2903 (itb->sd->max_items_per_block / 2))))
2905 _item_block_merge(itbp, itb);
2906 _item_block_position_update
2907 (EINA_INLIST_GET(itb)->next, itb->position);
2908 GL_IT(it)->wsd->blocks = eina_inlist_remove
2909 (GL_IT(it)->wsd->blocks, EINA_INLIST_GET(itb));
2911 block_changed = EINA_TRUE;
2913 /* merge block with next */
2915 ((itbn->count + itb->count) <
2916 (itb->sd->max_items_per_block +
2917 (itb->sd->max_items_per_block / 2))))
2919 _item_block_merge(itb, itbn);
2920 _item_block_position_update
2921 (EINA_INLIST_GET(itbn)->next, itbn->position);
2922 GL_IT(it)->wsd->blocks =
2923 eina_inlist_remove(GL_IT(it)->wsd->blocks,
2924 EINA_INLIST_GET(itbn));
2926 block_changed = EINA_TRUE;
2933 GL_IT(it)->wsd->pan_changed = EINA_TRUE;
2934 evas_object_smart_changed(GL_IT(it)->wsd->pan_obj);
2935 if (GL_IT(it)->wsd->calc_job) ecore_job_del(GL_IT(it)->wsd->calc_job);
2936 GL_IT(it)->wsd->calc_job = NULL;
2938 #if GENLIST_FX_SUPPORT
2939 it->item->block = NULL;
2944 _decorate_all_item_unrealize(Elm_Gen_Item *it)
2948 if ((!it) || (!it->item->decorate_all_item_realized)) return;
2950 #if GENLIST_FX_SUPPORT
2951 if ((GL_IT(it)->has_proxy_it) && (!GL_IT(it)->wsd->genlist_clearing))
2953 if (!eina_list_data_find(GL_IT(it)->wsd->pending_unrealized_decorate_all_items, it))
2954 GL_IT(it)->wsd->pending_unrealized_decorate_all_items =
2955 eina_list_append(GL_IT(it)->wsd->pending_unrealized_decorate_all_items, it);
2960 edje_object_part_unswallow(it->deco_all_view, VIEW(it));
2961 evas_object_smart_member_add(VIEW(it), GL_IT(it)->wsd->pan_obj);
2962 elm_widget_sub_object_add(WIDGET(it), VIEW(it));
2963 _elm_genlist_item_odd_even_update(it);
2964 _elm_genlist_item_state_update(it);
2966 edje_object_signal_emit
2967 (it->deco_all_view, "elm,state,decorate,disabled", "elm");
2968 edje_object_signal_emit
2969 (VIEW(it), "elm,state,decorate,disabled", "elm");
2970 edje_object_signal_emit
2971 (it->deco_all_view, "elm,state,reorder,mode_unset", "elm");
2972 edje_object_message_signal_process(VIEW(it));
2973 edje_object_message_signal_process(it->deco_all_view);
2975 evas_object_del(it->deco_all_view);
2976 it->deco_all_view = NULL;
2977 elm_widget_stringlist_free(it->item->deco_all_texts);
2978 it->item->deco_all_texts = NULL;
2979 elm_widget_stringlist_free(it->item->deco_all_contents);
2980 it->item->deco_all_contents = NULL;
2981 elm_widget_stringlist_free(it->item->deco_all_states);
2982 it->item->deco_all_states = NULL;
2983 EINA_LIST_FREE (it->item->deco_all_content_objs, icon)
2984 evas_object_del(icon);
2986 _item_mouse_callbacks_del(it, it->deco_all_view);
2987 _item_mouse_callbacks_add(it, VIEW(it));
2989 it->item->decorate_all_item_realized = EINA_FALSE;
2993 _item_free_common(Elm_Gen_Item *it)
2995 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2996 elm_widget_item_pre_notify_del(it);
2997 if (it->itc->func.del)
2998 it->itc->func.del((void *)it->base.data, WIDGET(it));
2999 if (it->tooltip.del_cb)
3000 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
3001 if (it->item->block) _item_block_del(it);
3003 it->parent->item->items =
3004 eina_list_remove(it->parent->item->items, it);
3005 if (it->item->queued) sd->queue = eina_list_remove(sd->queue, it);
3006 if (it->group) sd->group_items = eina_list_remove(sd->group_items, it);
3008 // FIXME: relative will be better to be fixed. it is too harsh.
3010 it->item->rel->item->rel_revs =
3011 eina_list_remove(it->item->rel->item->rel_revs, it);
3012 if (it->item->rel_revs)
3015 EINA_LIST_FREE(it->item->rel_revs, tmp) tmp->item->rel = NULL;
3017 _item_sub_items_clear(it);
3019 #if GENLIST_ENTRY_SUPPORT
3020 it->item->unrealize_disabled = EINA_FALSE;
3023 if (it->selected) sd->selected = eina_list_remove(sd->selected, it);
3024 if (sd->show_item == it) sd->show_item = NULL;
3025 if (sd->anchor_item == it)
3028 ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
3029 if (!sd->anchor_item) sd->anchor_item =
3030 ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
3032 if (sd->expanded_item == it) sd->expanded_item = NULL;
3033 if (sd->expanded_next_item == it) sd->expanded_next_item = NULL;
3034 if (sd->state) eina_inlist_sorted_state_free(sd->state);
3036 if (sd->last_selected_item == (Elm_Object_Item *)it)
3037 sd->last_selected_item = NULL;
3041 ecore_timer_del(it->long_timer);
3042 it->long_timer = NULL;
3044 if (it->item->swipe_timer) ecore_timer_del(it->item->swipe_timer);
3046 sd->items = eina_inlist_remove(sd->items, EINA_INLIST_GET(it));
3051 _item_mouse_move_cb(void *data,
3052 Evas *evas __UNUSED__,
3056 EINA_SAFETY_ON_NULL_RETURN(data);
3057 Elm_Gen_Item *it = data;
3058 Elm_Genlist_Smart_Data *sd;
3059 Evas_Event_Mouse_Move *ev = event_info;
3060 Evas_Coord ox, oy, ow, oh, it_scrl_y, y_pos;
3061 Evas_Coord minw = 0, minh = 0, x, y, dx, dy, adx, ady;
3063 sd = GL_IT(it)->wsd;
3065 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
3067 if (!sd->on_hold) _item_unselect(it);
3068 sd->on_hold = EINA_TRUE;
3070 if (sd->multi_touched)
3072 sd->cur_x = ev->cur.canvas.x;
3073 sd->cur_y = ev->cur.canvas.y;
3076 if ((it->dragging) && (it->down))
3078 if (sd->movements == SWIPE_MOVES)
3079 sd->swipe = EINA_TRUE;
3082 sd->history[sd->movements].x = ev->cur.canvas.x;
3083 sd->history[sd->movements].y = ev->cur.canvas.y;
3084 if (abs((sd->history[sd->movements].x -
3085 sd->history[0].x)) > 40)
3086 sd->swipe = EINA_TRUE;
3092 ecore_timer_del(it->long_timer);
3093 it->long_timer = NULL;
3095 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG, it);
3098 if ((!it->down) || (sd->longpressed))
3102 ecore_timer_del(it->long_timer);
3103 it->long_timer = NULL;
3105 if ((sd->reorder_mode) && (sd->reorder_it))
3107 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
3109 if (ev->cur.canvas.y < (oy + (sd->reorder_it->item->h / 2)))
3110 sd->reorder_fast = 1;
3111 else if (ev->cur.canvas.y > (oy + oh - (sd->reorder_it->item->h / 2)))
3112 sd->reorder_fast = -1;
3113 else sd->reorder_fast = 0;
3115 it_scrl_y = ev->cur.canvas.y - sd->reorder_it->dy;
3117 if (!sd->reorder_start_y)
3118 sd->reorder_start_y = it->item->block->y + it->y;
3122 else if (it_scrl_y + sd->reorder_it->item->h > oy + oh)
3123 y_pos = oy + oh - sd->reorder_it->item->h;
3127 if (it->deco_all_view)
3128 _item_position(it, it->deco_all_view, it->item->scrl_x, y_pos);
3129 else if (it->item->deco_it_view)
3131 (it, it->item->deco_it_view, it->item->scrl_x, y_pos);
3133 _item_position(it, VIEW(it), it->item->scrl_x, y_pos);
3135 if (sd->calc_job) ecore_job_del(sd->calc_job);
3136 sd->calc_job = ecore_job_add(_calc_job, sd);
3140 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
3141 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
3143 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3144 x = ev->cur.canvas.x - x;
3145 y = ev->cur.canvas.y - y;
3148 if (adx < 0) adx = -dx;
3152 if (ady < 0) ady = -dy;
3156 if ((adx > minw) || (ady > minh))
3158 it->dragging = EINA_TRUE;
3161 ecore_timer_del(it->long_timer);
3162 it->long_timer = NULL;
3167 evas_object_smart_callback_call
3168 (WIDGET(it), SIG_DRAG_START_UP, it);
3172 evas_object_smart_callback_call
3173 (WIDGET(it), SIG_DRAG_START_LEFT, it);
3175 evas_object_smart_callback_call
3176 (WIDGET(it), SIG_DRAG_START_RIGHT, it);
3182 evas_object_smart_callback_call
3183 (WIDGET(it), SIG_DRAG_START_DOWN, it);
3187 evas_object_smart_callback_call
3188 (WIDGET(it), SIG_DRAG_START_LEFT, it);
3190 evas_object_smart_callback_call
3191 (WIDGET(it), SIG_DRAG_START_RIGHT, it);
3198 _long_press_cb(void *data)
3200 Elm_Gen_Item *it = data, *it2;
3201 Elm_Genlist_Smart_Data *sd;
3204 sd = GL_IT(it)->wsd;
3206 it->long_timer = NULL;
3207 if (elm_widget_item_disabled_get(it) || (it->dragging) ||
3208 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
3209 return ECORE_CALLBACK_CANCEL;
3211 GL_IT(it)->wsd->longpressed = EINA_TRUE;
3212 evas_object_smart_callback_call(WIDGET(it), SIG_LONGPRESSED, it);
3213 if ((GL_IT(it)->wsd->reorder_mode) && (!it->group))
3215 GL_IT(it)->wsd->reorder_it = it;
3216 GL_IT(it)->wsd->reorder_start_y = 0;
3217 if (it->deco_all_view)
3218 evas_object_raise(it->deco_all_view);
3220 evas_object_raise(VIEW(it));
3222 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_TRUE);
3223 sd->s_iface->bounce_allow_set
3224 (ELM_WIDGET_DATA(sd)->obj, EINA_FALSE, EINA_FALSE);
3226 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it2)
3228 if (it != it2) _item_unselect(it2);
3231 // FIXME: difference from opensource
3232 if (it->item->items)
3234 EINA_LIST_FOREACH(it->item->items, l, it_tmp)
3236 if (elm_genlist_item_expanded_get((Elm_Object_Item *) it_tmp))
3238 elm_genlist_item_expanded_set((Elm_Object_Item *)it_tmp,
3240 return ECORE_CALLBACK_RENEW;
3245 if (elm_genlist_item_expanded_get((Elm_Object_Item *)it))
3247 elm_genlist_item_expanded_set((Elm_Object_Item *)it, EINA_FALSE);
3248 return ECORE_CALLBACK_RENEW;
3251 if (!GL_IT(it)->wsd->decorate_all_mode)
3252 edje_object_signal_emit
3253 (VIEW(it), "elm,state,reorder,enabled", "elm");
3256 return ECORE_CALLBACK_CANCEL;
3260 _swipe_do(Elm_Gen_Item *it)
3265 if ((it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) ||
3266 elm_widget_item_disabled_get(it)) return;
3268 GL_IT(it)->wsd->swipe = EINA_FALSE;
3269 for (i = 0; i < GL_IT(it)->wsd->movements; i++)
3271 sum += GL_IT(it)->wsd->history[i].x;
3272 if (abs(GL_IT(it)->wsd->history[0].y -
3273 GL_IT(it)->wsd->history[i].y) > 10) return;
3276 sum /= GL_IT(it)->wsd->movements;
3277 if (abs(sum - GL_IT(it)->wsd->history[0].x) <= 10) return;
3278 evas_object_smart_callback_call(WIDGET(it), SIG_SWIPE, it);
3282 _swipe_cancel(void *data)
3284 Elm_Gen_Item *it = data;
3286 if (!it) return ECORE_CALLBACK_CANCEL;
3287 GL_IT(it)->wsd->swipe = EINA_FALSE;
3288 GL_IT(it)->wsd->movements = 0;
3290 return ECORE_CALLBACK_RENEW;
3294 _multi_cancel(void *data)
3296 Elm_Genlist_Smart_Data *sd = data;
3298 if (!sd) return ECORE_CALLBACK_CANCEL;
3299 sd->multi_timeout = EINA_TRUE;
3301 return ECORE_CALLBACK_RENEW;
3305 _multi_touch_gesture_eval(void *data)
3307 Elm_Gen_Item *it = data;
3308 Evas_Coord minw = 0, minh = 0;
3309 Evas_Coord off_x, off_y, off_mx, off_my;
3311 GL_IT(it)->wsd->multi_touched = EINA_FALSE;
3312 if (GL_IT(it)->wsd->multi_timer)
3314 ecore_timer_del(GL_IT(it)->wsd->multi_timer);
3315 GL_IT(it)->wsd->multi_timer = NULL;
3317 if (GL_IT(it)->wsd->multi_timeout)
3319 GL_IT(it)->wsd->multi_timeout = EINA_FALSE;
3323 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
3324 off_x = abs(GL_IT(it)->wsd->cur_x - GL_IT(it)->wsd->prev_x);
3325 off_y = abs(GL_IT(it)->wsd->cur_y - GL_IT(it)->wsd->prev_y);
3326 off_mx = abs(GL_IT(it)->wsd->cur_mx - GL_IT(it)->wsd->prev_mx);
3327 off_my = abs(GL_IT(it)->wsd->cur_my - GL_IT(it)->wsd->prev_my);
3329 if (((off_x > minw) || (off_y > minh)) && ((off_mx > minw)
3330 || (off_my > minh)))
3332 if ((off_x + off_mx) > (off_y + off_my))
3334 if ((GL_IT(it)->wsd->cur_x > GL_IT(it)->wsd->prev_x)
3335 && (GL_IT(it)->wsd->cur_mx > GL_IT(it)->wsd->prev_mx))
3336 evas_object_smart_callback_call
3337 (WIDGET(it), SIG_MULTI_SWIPE_RIGHT, it);
3338 else if ((GL_IT(it)->wsd->cur_x < GL_IT(it)->wsd->prev_x)
3339 && (GL_IT(it)->wsd->cur_mx < GL_IT(it)->wsd->prev_mx))
3340 evas_object_smart_callback_call
3341 (WIDGET(it), SIG_MULTI_SWIPE_LEFT, it);
3342 else if (abs(GL_IT(it)->wsd->cur_x - GL_IT(it)->wsd->cur_mx) >
3343 abs(GL_IT(it)->wsd->prev_x - GL_IT(it)->wsd->prev_mx))
3344 evas_object_smart_callback_call
3345 (WIDGET(it), SIG_MULTI_PINCH_OUT, it);
3347 evas_object_smart_callback_call
3348 (WIDGET(it), SIG_MULTI_PINCH_IN, it);
3352 if ((GL_IT(it)->wsd->cur_y > GL_IT(it)->wsd->prev_y)
3353 && (GL_IT(it)->wsd->cur_my > GL_IT(it)->wsd->prev_my))
3354 evas_object_smart_callback_call
3355 (WIDGET(it), SIG_MULTI_SWIPE_DOWN, it);
3356 else if ((GL_IT(it)->wsd->cur_y < GL_IT(it)->wsd->prev_y)
3357 && (GL_IT(it)->wsd->cur_my < GL_IT(it)->wsd->prev_my))
3358 evas_object_smart_callback_call
3359 (WIDGET(it), SIG_MULTI_SWIPE_UP, it);
3360 else if (abs(GL_IT(it)->wsd->cur_y - GL_IT(it)->wsd->cur_my) >
3361 abs(GL_IT(it)->wsd->prev_y - GL_IT(it)->wsd->prev_my))
3363 evas_object_smart_callback_call
3364 (WIDGET(it), SIG_MULTI_PINCH_OUT, it);
3365 #if GENLIST_PINCH_ZOOM_SUPPORT
3366 if (IS_ROOT_PARENT_IT(it) && (GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT))
3368 elm_genlist_pinch_zoom_mode_set(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj, ELM_GEN_PINCH_ZOOM_EXPAND);
3369 elm_genlist_item_show((Elm_Object_Item *)it, ELM_GENLIST_ITEM_SCROLLTO_TOP);
3375 evas_object_smart_callback_call
3376 (WIDGET(it), SIG_MULTI_PINCH_IN, it);
3377 #if GENLIST_PINCH_ZOOM_SUPPORT
3378 elm_genlist_pinch_zoom_mode_set(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj,
3379 ELM_GEN_PINCH_ZOOM_CONTRACT);
3385 GL_IT(it)->wsd->multi_timeout = EINA_FALSE;
3389 _item_multi_down_cb(void *data,
3390 Evas *evas __UNUSED__,
3391 Evas_Object *obj __UNUSED__,
3394 Elm_Gen_Item *it = data;
3395 Evas_Event_Multi_Down *ev = event_info;
3397 if ((GL_IT(it)->wsd->multi_device != 0) || (GL_IT(it)->wsd->multi_touched)
3398 || (GL_IT(it)->wsd->multi_timeout))
3401 GL_IT(it)->wsd->multi_device = ev->device;
3402 GL_IT(it)->wsd->multi_down = EINA_TRUE;
3403 GL_IT(it)->wsd->multi_touched = EINA_TRUE;
3404 GL_IT(it)->wsd->prev_mx = ev->canvas.x;
3405 GL_IT(it)->wsd->prev_my = ev->canvas.y;
3407 if (!GL_IT(it)->wsd->wasselected)
3409 GL_IT(it)->wsd->wasselected = EINA_FALSE;
3413 ecore_timer_del(it->long_timer);
3414 it->long_timer = NULL;
3418 it->dragging = EINA_FALSE;
3419 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG_STOP, it);
3421 if (it->item->swipe_timer)
3423 ecore_timer_del(it->item->swipe_timer);
3424 it->item->swipe_timer = NULL;
3426 GL_IT(it)->wsd->longpressed = EINA_FALSE;
3427 if (GL_IT(it)->wsd->on_hold)
3429 GL_IT(it)->wsd->swipe = EINA_FALSE;
3430 GL_IT(it)->wsd->movements = 0;
3431 GL_IT(it)->wsd->on_hold = EINA_FALSE;
3436 _item_multi_up_cb(void *data,
3437 Evas *evas __UNUSED__,
3438 Evas_Object *obj __UNUSED__,
3441 Elm_Gen_Item *it = data;
3442 Evas_Event_Multi_Up *ev = event_info;
3444 if (GL_IT(it)->wsd->multi_device != ev->device) return;
3445 GL_IT(it)->wsd->multi_device = 0;
3446 GL_IT(it)->wsd->multi_down = EINA_FALSE;
3447 if (GL_IT(it)->wsd->mouse_down) return;
3448 _multi_touch_gesture_eval(data);
3452 _item_multi_move_cb(void *data,
3453 Evas *evas __UNUSED__,
3454 Evas_Object *obj __UNUSED__,
3457 Elm_Gen_Item *it = data;
3458 Evas_Event_Multi_Move *ev = event_info;
3460 if (GL_IT(it)->wsd->multi_device != ev->device) return;
3461 GL_IT(it)->wsd->cur_mx = ev->cur.canvas.x;
3462 GL_IT(it)->wsd->cur_my = ev->cur.canvas.y;
3466 // FIXME: difference from upstream
3468 _item_unfocusable_set(Elm_Gen_Item *it, Eina_Bool unfocus)
3471 Evas_Object *item_obj;
3472 Evas_Object *obj = WIDGET(it);
3476 EINA_LIST_FOREACH(it->content_objs, l, item_obj)
3478 if (unfocus) elm_widget_focused_object_clear(item_obj);
3479 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3481 EINA_LIST_FOREACH(it->item->flip_content_objs, l, item_obj)
3483 if (unfocus) elm_widget_focused_object_clear(item_obj);
3484 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3486 EINA_LIST_FOREACH(it->item->deco_all_content_objs, l, item_obj)
3488 if (unfocus) elm_widget_focused_object_clear(item_obj);
3489 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3491 it->can_focus = !unfocus;
3497 _item_mouse_down_cb(void *data,
3498 Evas *evas __UNUSED__,
3502 Evas_Event_Mouse_Down *ev = event_info;
3503 Elm_Gen_Item *it = data;
3504 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
3507 if (ev->button != 1) return;
3509 _item_unfocusable_set(it, EINA_FALSE);
3511 it->down = EINA_TRUE;
3512 it->dragging = EINA_FALSE;
3513 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3514 it->dx = ev->canvas.x - x;
3515 it->dy = ev->canvas.y - y;
3516 sd->mouse_down = EINA_TRUE;
3517 if (!sd->multi_touched)
3519 sd->prev_x = ev->canvas.x;
3520 sd->prev_y = ev->canvas.y;
3521 sd->multi_timeout = EINA_FALSE;
3522 if (sd->multi_timer) ecore_timer_del(sd->multi_timer);
3523 sd->multi_timer = ecore_timer_add(1, _multi_cancel, sd);
3525 sd->longpressed = EINA_FALSE;
3526 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
3528 sd->on_hold = EINA_TRUE;
3531 else sd->on_hold = EINA_FALSE;
3532 _item_highlight(it);
3533 if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK)
3534 if ((!elm_widget_item_disabled_get(it)) &&
3535 (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
3537 evas_object_smart_callback_call(WIDGET(it), SIG_CLICKED_DOUBLE, it);
3538 evas_object_smart_callback_call(WIDGET(it), SIG_ACTIVATED, it);
3540 if (it->item->swipe_timer) ecore_timer_del(it->item->swipe_timer);
3541 it->item->swipe_timer = ecore_timer_add(0.4, _swipe_cancel, it);
3542 if (it->long_timer) ecore_timer_del(it->long_timer);
3544 it->long_timer = ecore_timer_add
3545 (sd->longpress_timeout, _long_press_cb, it);
3547 it->long_timer = NULL;
3548 sd->swipe = EINA_FALSE;
3553 _item_block_new(Elm_Genlist_Smart_Data *sd,
3558 itb = calloc(1, sizeof(Item_Block));
3559 if (!itb) return NULL;
3563 sd->blocks = eina_inlist_prepend(sd->blocks, EINA_INLIST_GET(itb));
3564 _item_block_position_update(sd->blocks, 0);
3568 sd->blocks = eina_inlist_append(sd->blocks, EINA_INLIST_GET(itb));
3569 itb->position_update = EINA_TRUE;
3570 if (sd->blocks != EINA_INLIST_GET(itb))
3573 ((Item_Block *)(EINA_INLIST_GET(itb)->prev))->position + 1;
3585 _item_block_add(Elm_Genlist_Smart_Data *sd,
3588 Item_Block *itb = NULL;
3595 itb = calloc(1, sizeof(Item_Block));
3596 if (!itb) return EINA_FALSE;
3598 if (!it->item->rel->item->block)
3601 eina_inlist_append(sd->blocks, EINA_INLIST_GET(itb));
3602 itb->items = eina_list_append(itb->items, it);
3603 itb->position_update = EINA_TRUE;
3604 it->position = eina_list_count(itb->items);
3605 it->position_update = EINA_TRUE;
3607 if (sd->blocks != EINA_INLIST_GET(itb))
3611 (EINA_INLIST_GET(itb)->prev))->position + 1;
3622 tmp = eina_list_data_find_list(itb->items, it->item->rel);
3623 if (it->item->before)
3625 sd->blocks = eina_inlist_prepend_relative
3626 (sd->blocks, EINA_INLIST_GET(itb),
3627 EINA_INLIST_GET(it->item->rel->item->block));
3629 eina_list_prepend_relative_list(itb->items, it, tmp);
3631 /* Update index from where we prepended */
3632 _item_position_update
3633 (eina_list_prev(tmp), it->item->rel->position);
3634 _item_block_position_update
3635 (EINA_INLIST_GET(itb),
3636 it->item->rel->item->block->position);
3640 sd->blocks = eina_inlist_append_relative
3641 (sd->blocks, EINA_INLIST_GET(itb),
3642 EINA_INLIST_GET(it->item->rel->item->block));
3644 eina_list_append_relative_list(itb->items, it, tmp);
3646 /* Update block index from where we appended */
3647 _item_position_update
3648 (eina_list_next(tmp), it->item->rel->position + 1);
3649 _item_block_position_update
3650 (EINA_INLIST_GET(itb),
3651 it->item->rel->item->block->position + 1);
3657 if (it->item->before)
3661 itb = (Item_Block *)(sd->blocks);
3662 if (itb->count >= sd->max_items_per_block)
3664 itb = _item_block_new(sd, EINA_TRUE);
3665 if (!itb) return EINA_FALSE;
3670 itb = _item_block_new(sd, EINA_TRUE);
3671 if (!itb) return EINA_FALSE;
3673 itb->items = eina_list_prepend(itb->items, it);
3675 _item_position_update(itb->items, 0);
3681 itb = (Item_Block *)(sd->blocks->last);
3682 if (itb->count >= sd->max_items_per_block)
3684 itb = _item_block_new(sd, EINA_FALSE);
3685 if (!itb) return EINA_FALSE;
3690 itb = _item_block_new(sd, EINA_FALSE);
3691 if (!itb) return EINA_FALSE;
3693 itb->items = eina_list_append(itb->items, it);
3694 it->position = eina_list_count(itb->items);
3702 if (it->item->rel->item->queued)
3704 /* NOTE: for a strange reason eina_list and eina_inlist
3705 don't have the same property on sorted insertion
3706 order, so the queue is not always ordered like the
3707 item list. This lead to issue where we depend on an
3708 item that is not yet created. As a quick work around,
3709 we reschedule the calc of the item and stop reordering
3710 the list to prevent any nasty issue to show up here.
3712 sd->queue = eina_list_append(sd->queue, it);
3713 sd->requeued = EINA_TRUE;
3714 it->item->queued = EINA_TRUE;
3718 itb = it->item->rel->item->block;
3719 if (!itb) goto newblock;
3720 tmp = eina_list_data_find_list(itb->items, it->item->rel);
3721 if (it->item->before)
3723 itb->items = eina_list_prepend_relative_list(itb->items, it, tmp);
3724 _item_position_update
3725 (eina_list_prev(tmp), it->item->rel->position);
3729 itb->items = eina_list_append_relative_list(itb->items, it, tmp);
3730 _item_position_update
3731 (eina_list_next(tmp), it->item->rel->position + 1);
3736 itb->changed = EINA_TRUE;
3737 it->item->block = itb;
3738 if (itb->sd->calc_job) ecore_job_del(itb->sd->calc_job);
3739 itb->sd->calc_job = ecore_job_add(_calc_job, itb->sd);
3741 if (itb->count > itb->sd->max_items_per_block)
3746 Eina_Bool done = EINA_FALSE;
3748 newc = itb->count / 2;
3750 if (EINA_INLIST_GET(itb)->prev)
3752 Item_Block *itbp = (Item_Block *)(EINA_INLIST_GET(itb)->prev);
3754 if (itbp->count + newc < sd->max_items_per_block / 2)
3756 /* moving items to previous block */
3757 while ((itb->count > newc) && (itb->items))
3759 it2 = eina_list_data_get(itb->items);
3760 itb->items = eina_list_remove_list
3761 (itb->items, itb->items);
3764 itbp->items = eina_list_append(itbp->items, it2);
3765 it2->item->block = itbp;
3773 if (!done && EINA_INLIST_GET(itb)->next)
3775 Item_Block *itbn = (Item_Block *)(EINA_INLIST_GET(itb)->next);
3777 if (itbn->count + newc < sd->max_items_per_block / 2)
3779 /* moving items to next block */
3780 while ((itb->count > newc) && (itb->items))
3784 l = eina_list_last(itb->items);
3785 it2 = eina_list_data_get(l);
3786 itb->items = eina_list_remove_list(itb->items, l);
3789 itbn->items = eina_list_prepend(itbn->items, it2);
3790 it2->item->block = itbn;
3800 /* moving items to new block */
3801 itb2 = calloc(1, sizeof(Item_Block));
3802 if (!itb2) return EINA_FALSE;
3805 eina_inlist_append_relative(sd->blocks, EINA_INLIST_GET(itb2),
3806 EINA_INLIST_GET(itb));
3807 itb2->changed = EINA_TRUE;
3808 while ((itb->count > newc) && (itb->items))
3812 l = eina_list_last(itb->items);
3814 itb->items = eina_list_remove_list(itb->items, l);
3817 itb2->items = eina_list_prepend(itb2->items, it2);
3818 it2->item->block = itb2;
3828 _item_process(Elm_Genlist_Smart_Data *sd,
3831 if (!_item_block_add(sd, it)) return 1;
3833 _item_block_realize(it->item->block);
3839 _item_process_post(Elm_Genlist_Smart_Data *sd,
3843 Eina_Bool show_me = EINA_FALSE;
3845 if (it->item->block->changed)
3847 show_me = _item_block_recalc
3848 (it->item->block, it->item->block->num, qadd);
3849 it->item->block->changed = 0;
3850 if (sd->pan_changed)
3852 if (sd->calc_job) ecore_job_del(sd->calc_job);
3853 sd->calc_job = NULL;
3855 sd->pan_changed = EINA_FALSE;
3858 if (show_me) it->item->block->show_me = EINA_TRUE;
3860 /* when prepending, move the scroller along with the first selected
3861 * item to create the illusion that we're watching the selected
3862 * item this prevents the selected item being scrolled off the
3865 if (sd->selected && it->item->before)
3870 it2 = sd->selected->data;
3871 if (!it2->item->block) return;
3872 sd->s_iface->content_pos_get(ELM_WIDGET_DATA(sd)->obj, NULL, &y);
3873 evas_object_geometry_get(sd->pan_obj, NULL, NULL, NULL, &h);
3874 if ((it->y + it->item->block->y > y + h) ||
3875 (it->y + it->item->block->y + it->item->h < y))
3876 /* offscreen, just update */
3877 sd->s_iface->content_region_show
3878 (ELM_WIDGET_DATA(sd)->obj, it2->x + it2->item->block->x, y,
3879 it2->item->block->w, h);
3881 sd->s_iface->content_region_show
3882 (ELM_WIDGET_DATA(sd)->obj, it->x + it->item->block->x,
3883 y + it->item->h, it->item->block->w, h);
3888 _queue_process(Elm_Genlist_Smart_Data *sd)
3893 t0 = ecore_loop_time_get();
3894 for (n = 0; (sd->queue) && (n < 128); n++)
3898 it = eina_list_data_get(sd->queue);
3899 sd->queue = eina_list_remove_list(sd->queue, sd->queue);
3900 it->item->queued = EINA_FALSE;
3901 if (_item_process(sd, it)) continue;
3902 t = ecore_time_get();
3903 _item_process_post(sd, it, EINA_TRUE);
3904 /* same as eina_inlist_count > 1 */
3905 if (sd->blocks && sd->blocks->next)
3907 if ((t - t0) > (ecore_animator_frametime_get())) break;
3914 _item_idle_enterer(void *data)
3916 Elm_Genlist_Smart_Data *sd = data;
3918 if (sd->prev_viewport_w == 0) return ECORE_CALLBACK_RENEW;
3919 if (_queue_process(sd) > 0)
3922 // Job always be alive because idle_enterer should be alive
3923 if (sd->calc_job) ecore_job_del(sd->calc_job);
3924 sd->calc_job = ecore_job_add(_calc_job, sd);
3928 sd->queue_idle_enterer = NULL;
3929 return ECORE_CALLBACK_CANCEL;
3932 #if GENLIST_FX_SUPPORT
3933 _elm_genlist_fx_clear(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
3935 return ECORE_CALLBACK_RENEW;
3939 _item_queue(Elm_Genlist_Smart_Data *sd,
3943 if (it->item->queued) return;
3945 it->item->queued = EINA_TRUE;
3946 if (cb && !sd->requeued)
3947 sd->queue = eina_list_sorted_insert(sd->queue, cb, it);
3949 sd->queue = eina_list_append(sd->queue, it);
3951 if (sd->queue_idle_enterer)
3952 ecore_idle_enterer_del(sd->queue_idle_enterer);
3953 sd->queue_idle_enterer = ecore_idle_enterer_add(_item_idle_enterer, sd);
3955 if (sd->prev_viewport_w != 0)
3957 while ((sd->queue) && ((!sd->blocks) || (!sd->blocks->next)))
3960 while ((sd->queue) && (sd->blocks) &&
3961 (sd->homogeneous) && (sd->mode == ELM_LIST_COMPRESS))
3966 /* If the application wants to know the relative item, use
3967 * elm_genlist_item_prev_get(it)*/
3969 _item_move_after(Elm_Gen_Item *it,
3970 Elm_Gen_Item *after)
3974 if (it == after) return;
3976 GL_IT(it)->wsd->items =
3977 eina_inlist_remove(GL_IT(it)->wsd->items, EINA_INLIST_GET(it));
3978 if (it->item->block) _item_block_del(it);
3980 GL_IT(it)->wsd->items = eina_inlist_append_relative
3981 (GL_IT(it)->wsd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(after));
3982 it->item->rel = after;
3983 after->item->rel_revs = eina_list_append(after->item->rel_revs, it);
3984 it->item->before = EINA_FALSE;
3985 if (after->item->group_item) it->item->group_item = after->item->group_item;
3986 _item_queue(GL_IT(it)->wsd, it, NULL);
3988 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED_AFTER, it);
3992 _access_activate_cb(void *data __UNUSED__,
3993 Evas_Object *part_obj __UNUSED__,
3994 Elm_Object_Item *item)
3996 _item_select_unselect((Elm_Gen_Item *)item, EINA_TRUE);
3999 /* If the application wants to know the relative item, use
4000 * elm_genlist_item_next_get(it)*/
4002 _item_move_before(Elm_Gen_Item *it,
4003 Elm_Gen_Item *before)
4006 if (!before) return;
4007 if (it == before) return;
4009 GL_IT(it)->wsd->items =
4010 eina_inlist_remove(GL_IT(it)->wsd->items, EINA_INLIST_GET(it));
4011 if (it->item->block) _item_block_del(it);
4012 GL_IT(it)->wsd->items = eina_inlist_prepend_relative
4013 (GL_IT(it)->wsd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(before));
4014 it->item->rel = before;
4015 before->item->rel_revs = eina_list_append(before->item->rel_revs, it);
4016 it->item->before = EINA_TRUE;
4017 if (before->item->group_item)
4018 it->item->group_item = before->item->group_item;
4019 _item_queue(GL_IT(it)->wsd, it, NULL);
4021 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED_BEFORE, it);
4025 _item_mouse_up_cb(void *data,
4026 Evas *evas __UNUSED__,
4027 Evas_Object *obj __UNUSED__,
4030 Evas_Event_Mouse_Up *ev = event_info;
4031 Eina_Bool dragged = EINA_FALSE;
4032 Elm_Genlist_Smart_Data *sd;
4033 Elm_Gen_Item *it = data;
4035 if (ev->button != 1) return;
4036 it->down = EINA_FALSE;
4037 sd = GL_IT(it)->wsd;
4039 sd->mouse_down = EINA_FALSE;
4040 if (sd->multi_touched)
4042 if ((!sd->multi) && (!it->selected) && (it->highlighted))
4043 _item_unhighlight(it);
4044 if (sd->multi_down) return;
4045 _multi_touch_gesture_eval(data);
4050 ecore_timer_del(it->long_timer);
4051 it->long_timer = NULL;
4055 it->dragging = EINA_FALSE;
4056 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG_STOP, it);
4059 if (it->item->swipe_timer)
4061 ecore_timer_del(it->item->swipe_timer);
4062 it->item->swipe_timer = NULL;
4064 if (sd->multi_timer)
4066 ecore_timer_del(sd->multi_timer);
4067 sd->multi_timer = NULL;
4068 sd->multi_timeout = EINA_FALSE;
4070 sd->on_hold = EINA_FALSE;
4071 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
4073 if (sd->swipe) _swipe_do(data);
4074 sd->longpressed = EINA_FALSE;
4077 if ((sd->reorder_mode) && (sd->reorder_it))
4079 Evas_Coord it_scrl_y = ev->canvas.y - sd->reorder_it->dy;
4080 sd->reorder_fast = 0;
4082 if (sd->reorder_rel &&
4083 (sd->reorder_it->parent == sd->reorder_rel->parent))
4085 if (it_scrl_y <= sd->reorder_rel->item->scrl_y)
4086 _item_move_before(sd->reorder_it, sd->reorder_rel);
4088 _item_move_after(sd->reorder_it, sd->reorder_rel);
4089 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED, it);
4093 if (sd->calc_job) ecore_job_del(sd->calc_job);
4094 sd->calc_job = ecore_job_add(_calc_job, sd);
4096 edje_object_signal_emit(VIEW(it), "elm,state,reorder,disabled", "elm");
4097 sd->reorder_it = sd->reorder_rel = NULL;
4098 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
4099 sd->s_iface->bounce_allow_set
4100 (ELM_WIDGET_DATA(sd)->obj, sd->h_bounce, sd->v_bounce);
4104 if (it->want_unrealize && !(it->item->unrealize_disabled))
4106 _item_unrealize(it, EINA_FALSE);
4107 if (it->item->block->want_unrealize)
4108 _item_block_unrealize(it->item->block);
4113 if (!sd->longpressed)
4114 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_ALWAYS) ||
4115 (it->select_mode == ELM_OBJECT_SELECT_MODE_ALWAYS))
4116 _item_select_unselect(it, EINA_TRUE);
4117 else _item_select_unselect(it, !it->selected);
4119 _item_unhighlight(it);
4123 _item_mouse_callbacks_add(Elm_Gen_Item *it,
4126 evas_object_event_callback_add
4127 (view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb, it);
4128 evas_object_event_callback_add
4129 (view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4130 evas_object_event_callback_add
4131 (view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb, it);
4132 evas_object_event_callback_add
4133 (view, EVAS_CALLBACK_MULTI_DOWN, _item_multi_down_cb, it);
4134 evas_object_event_callback_add
4135 (view, EVAS_CALLBACK_MULTI_UP, _item_multi_up_cb, it);
4136 evas_object_event_callback_add
4137 (view, EVAS_CALLBACK_MULTI_MOVE, _item_multi_move_cb, it);
4141 _item_mouse_callbacks_del(Elm_Gen_Item *it,
4144 evas_object_event_callback_del_full
4145 (view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb, it);
4146 evas_object_event_callback_del_full
4147 (view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4148 evas_object_event_callback_del_full
4149 (view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb, it);
4150 evas_object_event_callback_del_full
4151 (view, EVAS_CALLBACK_MULTI_DOWN, _item_multi_down_cb, it);
4152 evas_object_event_callback_del_full
4153 (view, EVAS_CALLBACK_MULTI_UP, _item_multi_up_cb, it);
4154 evas_object_event_callback_del_full
4155 (view, EVAS_CALLBACK_MULTI_MOVE, _item_multi_move_cb, it);
4159 _scroll_hold_timer_cb(void *data)
4161 Elm_Genlist_Smart_Data *sd = data;
4163 if (!data) return ECORE_CALLBACK_CANCEL;
4165 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
4166 sd->scr_hold_timer = NULL;
4168 return ECORE_CALLBACK_CANCEL;
4172 _decorate_item_finished_signal_cb(void *data,
4174 const char *emission __UNUSED__,
4175 const char *source __UNUSED__)
4177 Elm_Gen_Item *it = data;
4180 if (!data || !obj) return;
4181 if ((!it->realized) || (!it->item->deco_it_view)) return;
4183 it->item->nocache_once = EINA_FALSE;
4184 _decorate_item_unrealize(it);
4185 if (it->item->group_item)
4186 evas_object_raise(it->item->VIEW(group_item));
4188 snprintf(buf, sizeof(buf), "elm,state,%s,passive,finished",
4189 GL_IT(it)->wsd->decorate_it_type);
4190 edje_object_signal_callback_del_full
4191 (obj, buf, "elm", _decorate_item_finished_signal_cb, it);
4195 _item_mode_content_unrealize(Elm_Gen_Item *it,
4196 Evas_Object *target,
4199 Eina_List **contents_list)
4201 Eina_List *res = *contents_list;
4203 if (it->itc->func.content_get)
4207 Evas_Object *ic = NULL;
4209 EINA_LIST_FOREACH(*source, l, key)
4211 if (parts && fnmatch(parts, key, FNM_PERIOD))
4214 ic = edje_object_part_swallow_get(target, key);
4217 res = eina_list_remove(res, ic);
4218 edje_object_part_unswallow(target, ic);
4219 evas_object_del(ic);
4228 _item_content_unrealize(Elm_Gen_Item *it,
4229 Evas_Object *target,
4233 Eina_List *res = it->content_objs;
4235 if (it->itc->func.content_get)
4239 Evas_Object *ic = NULL;
4241 EINA_LIST_FOREACH(*source, l, key)
4243 if (parts && fnmatch(parts, key, FNM_PERIOD))
4246 ic = edje_object_part_swallow_get(target, key);
4249 res = eina_list_remove(res, ic);
4250 edje_object_part_unswallow(target, ic);
4251 // FIXME: If parent-child relationship was broken before 'ic'
4252 // is deleted, freeze_pop will not be called. ex) elm_slider
4253 // If layout is used instead of edje, this problme can be
4255 if (0 != elm_widget_scroll_freeze_get(ic))
4256 elm_widget_scroll_freeze_pop(ic);
4257 evas_object_del(ic);
4266 _item_block_recalc(Item_Block *itb,
4270 const Eina_List *l, *ll;
4272 Evas_Coord minw = 0, minh = 0;
4273 Eina_Bool show_me = EINA_FALSE, changed = EINA_FALSE;
4277 EINA_LIST_FOREACH_SAFE(itb->items, l, ll, it)
4279 show_me |= it->item->show_me;
4284 if (!it->item->mincalcd) changed = EINA_TRUE;
4287 _item_realize(it, in, EINA_TRUE);
4288 _item_unrealize(it, EINA_TRUE);
4293 if ((itb->sd->homogeneous) &&
4294 (itb->sd->mode == ELM_LIST_COMPRESS))
4298 it->item->w = it->item->minw =
4299 GL_IT(it)->wsd->group_item_width;
4300 it->item->h = it->item->minh =
4301 GL_IT(it)->wsd->group_item_height;
4305 it->item->w = it->item->minw =
4306 GL_IT(it)->wsd->item_width;
4307 it->item->h = it->item->minh =
4308 GL_IT(it)->wsd->item_height;
4313 _item_realize(it, in, EINA_TRUE);
4314 _item_unrealize(it, EINA_TRUE);
4320 if (!it->item->mincalcd) changed = EINA_TRUE;
4321 _item_realize(it, in, EINA_FALSE);
4323 minh += it->item->minh;
4324 if (minw < it->item->minw) minw = it->item->minw;
4328 #if GENLIST_PINCH_ZOOM_SUPPORT
4329 if (IS_ROOT_PARENT_IT(it))
4330 it->item->pan_scrl_y = itb->y + it->y;
4334 if (changed) itb->sd->pan_changed = changed;
4337 itb->changed = EINA_FALSE;
4338 itb->position_update = EINA_FALSE;
4344 _update_job(void *data)
4346 Eina_Bool position = EINA_FALSE, recalc = EINA_FALSE;
4347 Elm_Genlist_Smart_Data *sd = data;
4352 sd->update_job = NULL;
4355 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4356 EINA_INLIST_FOREACH(sd->blocks, itb)
4358 Evas_Coord itminw, itminh;
4365 _item_block_position(itb, num);
4369 recalc = EINA_FALSE;
4370 EINA_LIST_FOREACH(itb->items, l2, it)
4372 if (it->item->updateme)
4374 itminw = it->item->minw;
4375 itminh = it->item->minh;
4377 it->item->updateme = EINA_FALSE;
4380 _item_unrealize(it, EINA_FALSE);
4381 _item_realize(it, num, EINA_FALSE);
4382 position = EINA_TRUE;
4386 _item_realize(it, num, EINA_TRUE);
4387 _item_unrealize(it, EINA_TRUE);
4389 if ((it->item->minw != itminw) || (it->item->minh != itminh))
4394 itb->updateme = EINA_FALSE;
4397 position = EINA_TRUE;
4398 itb->changed = EINA_TRUE;
4399 _item_block_recalc(itb, num0, EINA_FALSE);
4400 _item_block_position(itb, num0);
4405 if (sd->calc_job) ecore_job_del(sd->calc_job);
4406 sd->calc_job = ecore_job_add(_calc_job, sd);
4408 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4409 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4413 _scroll_animate_start_cb(Evas_Object *obj,
4414 void *data __UNUSED__)
4416 #if GENLIST_FX_SUPPORT
4417 _elm_genlist_fx_clear(obj, EINA_FALSE);
4419 evas_object_smart_callback_call(obj, SIG_SCROLL_ANIM_START, NULL);
4423 _scroll_animate_stop_cb(Evas_Object *obj,
4424 void *data __UNUSED__)
4426 #if GENLIST_FX_SUPPORT
4427 _elm_genlist_fx_clear(obj, EINA_FALSE);
4429 evas_object_smart_callback_call(obj, SIG_SCROLL_ANIM_STOP, NULL);
4433 _scroll_drag_start_cb(Evas_Object *obj,
4434 void *data __UNUSED__)
4436 evas_object_smart_callback_call(obj, SIG_SCROLL_DRAG_START, NULL);
4440 _scroll_drag_stop_cb(Evas_Object *obj,
4441 void *data __UNUSED__)
4443 evas_object_smart_callback_call(obj, SIG_SCROLL_DRAG_STOP, NULL);
4447 _edge_left_cb(Evas_Object *obj,
4448 void *data __UNUSED__)
4450 evas_object_smart_callback_call(obj, SIG_EDGE_LEFT, NULL);
4454 _edge_right_cb(Evas_Object *obj,
4455 void *data __UNUSED__)
4457 evas_object_smart_callback_call(obj, SIG_EDGE_RIGHT, NULL);
4461 _edge_top_cb(Evas_Object *obj,
4462 void *data __UNUSED__)
4464 evas_object_smart_callback_call(obj, SIG_EDGE_TOP, NULL);
4468 _edge_bottom_cb(Evas_Object *obj,
4469 void *data __UNUSED__)
4471 evas_object_smart_callback_call(obj, SIG_EDGE_BOTTOM, NULL);
4475 _vbar_drag_cb(Evas_Object *obj,
4476 void *data __UNUSED__)
4478 evas_object_smart_callback_call(obj, SIG_VBAR_DRAG, NULL);
4482 _vbar_press_cb(Evas_Object *obj,
4483 void *data __UNUSED__)
4485 evas_object_smart_callback_call(obj, SIG_VBAR_PRESS, NULL);
4489 _vbar_unpress_cb(Evas_Object *obj,
4490 void *data __UNUSED__)
4492 evas_object_smart_callback_call(obj, SIG_VBAR_UNPRESS, NULL);
4496 _hbar_drag_cb(Evas_Object *obj,
4497 void *data __UNUSED__)
4499 evas_object_smart_callback_call(obj, SIG_HBAR_DRAG, NULL);
4503 _hbar_press_cb(Evas_Object *obj,
4504 void *data __UNUSED__)
4506 evas_object_smart_callback_call(obj, SIG_HBAR_PRESS, NULL);
4510 _hbar_unpress_cb(Evas_Object *obj,
4511 void *data __UNUSED__)
4513 evas_object_smart_callback_call(obj, SIG_HBAR_UNPRESS, NULL);
4517 _decorate_item_realize(Elm_Gen_Item *it)
4520 if (it->item->deco_it_view) return;
4522 //evas_event_freeze(evas_object_evas_get(obj));
4523 it->item->deco_it_view = edje_object_add(evas_object_evas_get(WIDGET(it)));
4524 edje_object_scale_set
4525 (it->item->deco_it_view, elm_widget_scale_get(WIDGET(it)) *
4526 elm_config_scale_get());
4527 evas_object_smart_member_add
4528 (it->item->deco_it_view, GL_IT(it)->wsd->pan_obj);
4529 elm_widget_sub_object_add(WIDGET(it), it->item->deco_it_view);
4531 strncpy(buf, "item", sizeof(buf));
4532 if (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)
4533 strncat(buf, "_compress", sizeof(buf) - strlen(buf));
4535 if (it->item->order_num_in & 0x1)
4536 strncat(buf, "_odd", sizeof(buf) - strlen(buf));
4537 strncat(buf, "/", sizeof(buf) - strlen(buf));
4538 strncat(buf, it->itc->decorate_item_style, sizeof(buf) - strlen(buf));
4540 elm_widget_theme_object_set
4541 (WIDGET(it), it->item->deco_it_view, "genlist", buf,
4542 elm_widget_style_get(WIDGET(it)));
4543 edje_object_mirrored_set
4544 (it->item->deco_it_view, elm_widget_mirrored_get(WIDGET(it)));
4546 /* signal callback add */
4547 evas_object_event_callback_add
4548 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb,
4550 evas_object_event_callback_add
4551 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4552 evas_object_event_callback_add
4553 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb,
4556 if (eina_list_count(it->item->deco_it_content_objs) != 0)
4557 ERR_ABORT("If you see this error, please notify us and we"
4560 /* text_get, content_get, state_get */
4562 (it, it->item->deco_it_view, &it->item->deco_it_texts, NULL);
4563 if (!it->item->deco_it_contents)
4564 it->item->deco_it_contents =
4565 elm_widget_stringlist_get
4566 (edje_object_data_get(it->item->deco_it_view, "contents"));
4567 it->item->deco_it_content_objs =
4568 _item_mode_content_realize
4569 (it, it->item->deco_it_view, &it->item->deco_it_contents, NULL,
4570 &it->item->deco_it_content_objs);
4572 (it, it->item->deco_it_view, &it->item->deco_it_states, NULL);
4573 edje_object_part_swallow
4574 (it->item->deco_it_view,
4575 edje_object_data_get(it->item->deco_it_view, "mode_part"), VIEW(it));
4577 it->want_unrealize = EINA_FALSE;
4578 //evas_event_thaw(evas_object_evas_get(obj));
4579 //evas_event_thaw_eval(evas_object_evas_get(obj));
4583 _decorate_item_set(Elm_Gen_Item *it)
4585 Elm_Genlist_Smart_Data *sd;
4590 sd = GL_IT(it)->wsd;
4593 it->item->nocache_once = EINA_TRUE;
4595 if (sd->scr_hold_timer)
4597 ecore_timer_del(sd->scr_hold_timer);
4598 sd->scr_hold_timer = NULL;
4600 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_TRUE);
4601 sd->scr_hold_timer = ecore_timer_add(0.1, _scroll_hold_timer_cb, sd);
4603 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4604 _decorate_item_realize(it);
4605 if (it->item->group_item)
4606 evas_object_raise(it->item->VIEW(group_item));
4608 (it, it->item->deco_it_view, it->item->scrl_x, it->item->scrl_y);
4609 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4610 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4612 snprintf(buf, sizeof(buf), "elm,state,%s,active", sd->decorate_it_type);
4613 edje_object_signal_emit(it->item->deco_it_view, buf, "elm");
4617 _decorate_item_unset(Elm_Genlist_Smart_Data *sd)
4619 char buf[1024], buf2[1024];
4622 if (!sd->mode_item) return;
4625 it->item->nocache_once = EINA_TRUE;
4627 snprintf(buf, sizeof(buf), "elm,state,%s,passive", sd->decorate_it_type);
4628 snprintf(buf2, sizeof(buf2), "elm,state,%s,passive,finished",
4629 sd->decorate_it_type);
4630 edje_object_signal_emit(it->item->deco_it_view, buf, "elm");
4631 edje_object_signal_callback_add
4632 (it->item->deco_it_view, buf2, "elm", _decorate_item_finished_signal_cb,
4634 sd->mode_item = NULL;
4638 // FIXME: difference from upstream
4640 _mouse_down_scroller(void *data,
4641 Evas *evas __UNUSED__,
4642 Evas_Object *obj __UNUSED__,
4643 void *event_info __UNUSED__)
4645 Widget_Data *wd = elm_widget_data_get(data);
4648 wd->drag_started = EINA_FALSE;
4652 _mouse_up_scroller(void *data,
4653 Evas *evas __UNUSED__,
4654 Evas_Object *obj __UNUSED__,
4655 void *event_info __UNUSED__)
4657 Widget_Data *wd = elm_widget_data_get(data);
4660 wd->drag_started = EINA_FALSE;
4664 _mouse_move_scroller(void *data,
4665 Evas *evas __UNUSED__,
4666 Evas_Object *obj __UNUSED__,
4669 Widget_Data *wd = elm_widget_data_get(data);
4670 Evas_Event_Mouse_Move *ev = event_info;
4671 Evas_Coord minw = 0, minh = 0, dx, dy, adx, ady;
4674 if (wd->drag_started) return;
4676 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
4677 dx = ev->cur.canvas.x - ev->prev.canvas.x;
4678 dy = ev->cur.canvas.y - ev->prev.canvas.y;
4681 if (adx < 0) adx = -dx;
4682 if (ady < 0) ady = -dy;
4683 if (((ady < minh) && (ady > minh / 2)) && (ady > adx))
4687 evas_object_smart_callback_call(data, SIG_DRAG_START_UP, NULL);
4688 wd->drag_started = EINA_TRUE;
4692 evas_object_smart_callback_call(data, SIG_DRAG_START_DOWN, NULL);
4693 wd->drag_started = EINA_TRUE;
4700 _elm_genlist_smart_add(Evas_Object *obj)
4702 Evas_Coord minw, minh;
4703 Elm_Genlist_Pan_Smart_Data *pan_data;
4705 EVAS_SMART_DATA_ALLOC(obj, Elm_Genlist_Smart_Data);
4707 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.add(obj);
4709 priv->hit_rect = evas_object_rectangle_add(evas_object_evas_get(obj));
4710 evas_object_smart_member_add(priv->hit_rect, obj);
4711 elm_widget_sub_object_add(obj, priv->hit_rect);
4713 /* common scroller hit rectangle setup */
4714 evas_object_color_set(priv->hit_rect, 0, 0, 0, 0);
4715 evas_object_show(priv->hit_rect);
4716 evas_object_repeat_events_set(priv->hit_rect, EINA_TRUE);
4718 elm_widget_can_focus_set(obj, EINA_TRUE);
4719 elm_widget_on_show_region_hook_set(obj, _show_region_hook, obj);
4721 elm_layout_theme_set(obj, "genlist", "base", elm_widget_style_get(obj));
4723 /* interface's add() routine issued AFTER the object's smart_add() */
4724 priv->s_iface = evas_object_smart_interface_get
4725 (obj, ELM_SCROLLABLE_IFACE_NAME);
4727 priv->s_iface->objects_set
4728 (obj, ELM_WIDGET_DATA(priv)->resize_obj, priv->hit_rect);
4730 priv->s_iface->bounce_allow_set
4731 (obj, EINA_FALSE, _elm_config->thumbscroll_bounce_enable);
4732 priv->v_bounce = _elm_config->thumbscroll_bounce_enable;
4734 priv->s_iface->animate_start_cb_set(obj, _scroll_animate_start_cb);
4735 priv->s_iface->animate_stop_cb_set(obj, _scroll_animate_stop_cb);
4736 priv->s_iface->drag_start_cb_set(obj, _scroll_drag_start_cb);
4737 priv->s_iface->drag_stop_cb_set(obj, _scroll_drag_stop_cb);
4738 priv->s_iface->edge_left_cb_set(obj, _edge_left_cb);
4739 priv->s_iface->edge_right_cb_set(obj, _edge_right_cb);
4740 priv->s_iface->edge_top_cb_set(obj, _edge_top_cb);
4741 priv->s_iface->edge_bottom_cb_set(obj, _edge_bottom_cb);
4742 priv->s_iface->vbar_drag_cb_set(obj, _vbar_drag_cb);
4743 priv->s_iface->vbar_press_cb_set(obj, _vbar_press_cb);
4744 priv->s_iface->vbar_unpress_cb_set(obj, _vbar_unpress_cb);
4745 priv->s_iface->hbar_drag_cb_set(obj, _hbar_drag_cb);
4746 priv->s_iface->hbar_press_cb_set(obj, _hbar_press_cb);
4747 priv->s_iface->hbar_unpress_cb_set(obj, _hbar_unpress_cb);
4749 priv->mode = ELM_LIST_SCROLL;
4750 priv->max_items_per_block = MAX_ITEMS_PER_BLOCK;
4751 priv->item_cache_max = priv->max_items_per_block * 2;
4752 priv->longpress_timeout = _elm_config->longpress_timeout;
4753 priv->highlight = EINA_TRUE;
4755 #if GENLIST_FX_SUPPORT
4756 priv->fx_mode = EINA_FALSE;
4757 priv->rendered = EINA_FALSE;
4758 priv->fx_first_captured = EINA_FALSE;
4759 priv->fx_playing = EINA_FALSE;
4760 priv->fx_items_deleted = EINA_FALSE;
4761 priv->genlist_clearing = EINA_FALSE;
4764 priv->pan_obj = evas_object_smart_add
4765 (evas_object_evas_get(obj), _elm_genlist_pan_smart_class_new());
4766 pan_data = evas_object_smart_data_get(priv->pan_obj);
4767 pan_data->wsd = priv;
4770 // FIXME: difference from upstream
4771 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_DOWN,
4772 _mouse_down_scroller, obj);
4773 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_UP,
4774 _mouse_up_scroller, obj);
4775 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_MOVE,
4776 _mouse_move_scroller, obj);
4779 priv->s_iface->extern_pan_set(obj, priv->pan_obj);
4781 edje_object_size_min_calc(ELM_WIDGET_DATA(priv)->resize_obj, &minw, &minh);
4782 evas_object_size_hint_min_set(obj, minw, minh);
4784 _item_cache_all_free(priv);
4785 _mirrored_set(obj, elm_widget_mirrored_get(obj));
4787 elm_layout_sizing_eval(obj);
4791 _elm_genlist_smart_del(Evas_Object *obj)
4793 ELM_GENLIST_DATA_GET(obj, sd);
4795 elm_genlist_clear(obj);
4796 if (sd->calc_job) ecore_job_del(sd->calc_job);
4797 if (sd->update_job) ecore_job_del(sd->update_job);
4798 if (sd->queue_idle_enterer) ecore_idle_enterer_del(sd->queue_idle_enterer);
4799 if (sd->must_recalc_idler) ecore_idler_del(sd->must_recalc_idler);
4800 if (sd->multi_timer) ecore_timer_del(sd->multi_timer);
4801 if (sd->decorate_it_type) eina_stringshare_del(sd->decorate_it_type);
4802 if (sd->scr_hold_timer) ecore_timer_del(sd->scr_hold_timer);
4804 evas_object_del(sd->pan_obj);
4805 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.del(obj);
4809 _elm_genlist_smart_move(Evas_Object *obj,
4813 ELM_GENLIST_DATA_GET(obj, sd);
4815 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.move(obj, x, y);
4817 evas_object_move(sd->hit_rect, x, y);
4821 _elm_genlist_smart_resize(Evas_Object *obj,
4825 ELM_GENLIST_DATA_GET(obj, sd);
4827 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.resize(obj, w, h);
4829 evas_object_resize(sd->hit_rect, w, h);
4833 _elm_genlist_smart_member_add(Evas_Object *obj,
4834 Evas_Object *member)
4836 ELM_GENLIST_DATA_GET(obj, sd);
4838 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.member_add(obj, member);
4841 evas_object_raise(sd->hit_rect);
4845 _access_obj_process(Elm_Genlist_Smart_Data *sd, Eina_Bool is_access)
4848 Eina_Bool done = EINA_FALSE;
4850 EINA_INLIST_FOREACH(sd->blocks, itb)
4858 EINA_LIST_FOREACH(itb->items, l, it)
4860 if (!it->realized) continue;
4861 if (is_access) _access_widget_item_register(it);
4863 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
4866 else if (done) break;
4871 _elm_genlist_smart_access(Evas_Object *obj, Eina_Bool is_access)
4873 ELM_GENLIST_CHECK(obj);
4874 ELM_GENLIST_DATA_GET(obj, sd);
4877 ELM_WIDGET_CLASS(ELM_WIDGET_DATA(sd)->api)->focus_next =
4878 _elm_genlist_smart_focus_next;
4880 ELM_WIDGET_CLASS(ELM_WIDGET_DATA(sd)->api)->focus_next = NULL;
4881 _access_obj_process(sd, is_access);
4885 _elm_genlist_smart_set_user(Elm_Genlist_Smart_Class *sc)
4887 ELM_WIDGET_CLASS(sc)->base.add = _elm_genlist_smart_add;
4888 ELM_WIDGET_CLASS(sc)->base.del = _elm_genlist_smart_del;
4889 ELM_WIDGET_CLASS(sc)->base.move = _elm_genlist_smart_move;
4890 ELM_WIDGET_CLASS(sc)->base.resize = _elm_genlist_smart_resize;
4891 ELM_WIDGET_CLASS(sc)->base.member_add = _elm_genlist_smart_member_add;
4893 ELM_WIDGET_CLASS(sc)->sub_object_add = _elm_genlist_smart_sub_object_add;
4894 ELM_WIDGET_CLASS(sc)->sub_object_del = _elm_genlist_smart_sub_object_del;
4895 ELM_WIDGET_CLASS(sc)->on_focus = _elm_genlist_smart_on_focus;
4896 ELM_WIDGET_CLASS(sc)->theme = _elm_genlist_smart_theme;
4897 ELM_WIDGET_CLASS(sc)->event = _elm_genlist_smart_event;
4898 ELM_WIDGET_CLASS(sc)->translate = _elm_genlist_smart_translate;
4900 /* not a 'focus chain manager' */
4901 ELM_WIDGET_CLASS(sc)->focus_next = NULL;
4902 ELM_WIDGET_CLASS(sc)->focus_direction = NULL;
4904 ELM_LAYOUT_CLASS(sc)->sizing_eval = _elm_genlist_smart_sizing_eval;
4907 if (_elm_config->access_mode == ELM_ACCESS_MODE_ON)
4908 ELM_WIDGET_CLASS(sc)->focus_next = _elm_genlist_smart_focus_next;
4910 ELM_WIDGET_CLASS(sc)->access = _elm_genlist_smart_access;
4913 EAPI const Elm_Genlist_Smart_Class *
4914 elm_genlist_smart_class_get(void)
4916 static Elm_Genlist_Smart_Class _sc =
4917 ELM_GENLIST_SMART_CLASS_INIT_NAME_VERSION(ELM_GENLIST_SMART_NAME);
4918 static const Elm_Genlist_Smart_Class *class = NULL;
4919 Evas_Smart_Class *esc = (Evas_Smart_Class *)&_sc;
4924 _elm_genlist_smart_set(&_sc);
4925 esc->callbacks = _smart_callbacks;
4932 elm_genlist_add(Evas_Object *parent)
4936 EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL);
4938 obj = elm_widget_add(_elm_genlist_smart_class_new(), parent);
4939 if (!obj) return NULL;
4941 if (!elm_widget_sub_object_add(parent, obj))
4942 ERR("could not add %p as sub object of %p", obj, parent);
4948 static Evas_Object *
4949 _item_content_get_hook(Elm_Gen_Item *it,
4952 Evas_Object *ret = NULL;
4953 if (it->deco_all_view)
4954 ret = edje_object_part_swallow_get(it->deco_all_view, part);
4955 else if (it->decorate_it_set)
4956 ret = edje_object_part_swallow_get(it->item->deco_it_view, part);
4958 ret = edje_object_part_swallow_get(VIEW(it), part);
4963 _item_text_get_hook(Elm_Gen_Item *it,
4966 if (!it->itc->func.text_get) return NULL;
4967 const char *ret = NULL;
4968 if (it->deco_all_view)
4969 ret = edje_object_part_text_get(it->deco_all_view, part);
4970 else if (it->decorate_it_set)
4971 ret = edje_object_part_text_get(it->item->deco_it_view, part);
4973 ret = edje_object_part_text_get(VIEW(it), part);
4978 _item_disable_hook(Elm_Object_Item *item)
4982 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
4985 elm_genlist_item_selected_set(item, EINA_FALSE);
4989 if (elm_widget_item_disabled_get(it))
4991 edje_object_signal_emit(VIEW(it), "elm,state,disabled", "elm");
4992 if (it->deco_all_view)
4993 edje_object_signal_emit
4994 (it->deco_all_view, "elm,state,disabled", "elm");
4998 edje_object_signal_emit(VIEW(it), "elm,state,enabled", "elm");
4999 if (it->deco_all_view)
5000 edje_object_signal_emit
5001 (it->deco_all_view, "elm,state,enabled", "elm");
5003 EINA_LIST_FOREACH(it->content_objs, l, obj)
5004 elm_widget_disabled_set(obj, elm_widget_item_disabled_get(it));
5009 _item_free(Elm_Gen_Item *it)
5011 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
5013 #if GENLIST_FX_SUPPORT
5014 if (sd->fx_mode) GL_IT(it)->has_proxy_it = EINA_FALSE;
5015 _elm_genlist_proxy_item_del((Elm_Object_Item *)it);
5016 if ((!sd->fx_mode) || (sd->genlist_clearing))
5019 _item_free_common(it);
5021 _item_unrealize(it, EINA_FALSE);
5022 elm_genlist_item_class_unref((Elm_Genlist_Item_Class *)it->itc);
5025 if (sd->calc_job) ecore_job_del(sd->calc_job);
5026 sd->calc_job = ecore_job_add(_calc_job, sd);
5029 #if GENLIST_FX_SUPPORT
5031 _item_del_pre_fx_process(Elm_Gen_Item *it)
5033 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
5035 sd->fx_items_deleted = EINA_TRUE;
5036 _elm_genlist_fx_capture(ELM_WIDGET_DATA(sd)->obj, 0);
5037 if (!eina_list_data_find(sd->pending_del_items, it))
5038 sd->pending_del_items = eina_list_append(sd->pending_del_items, it);
5040 _item_free_common(it);
5046 _item_del_pre_hook(Elm_Object_Item *item)
5048 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5050 #if GENLIST_FX_SUPPORT
5051 if ((GL_IT(it)->wsd->fx_mode) && (!GL_IT(it)->wsd->genlist_clearing))
5053 _item_del_pre_fx_process(it);
5062 _item_signal_emit_hook(Elm_Object_Item *it,
5063 const char *emission,
5066 edje_object_signal_emit(VIEW(it), emission, source);
5069 static Elm_Gen_Item *
5070 _elm_genlist_item_new(Elm_Genlist_Smart_Data *sd,
5071 const Elm_Genlist_Item_Class *itc,
5073 Elm_Gen_Item *parent,
5074 Elm_Genlist_Item_Type type,
5076 const void *func_data)
5078 Elm_Gen_Item *it, *it2;
5081 if (!itc) return NULL;
5083 it = elm_widget_item_new(ELM_WIDGET_DATA(sd)->obj, Elm_Gen_Item);
5084 if (!it) return NULL;
5087 elm_genlist_item_class_ref((Elm_Genlist_Item_Class *)itc);
5089 it->base.data = data;
5090 it->parent = parent;
5091 it->func.func = func;
5092 it->func.data = func_data;
5094 elm_widget_item_content_get_hook_set(it, _item_content_get_hook);
5095 elm_widget_item_text_get_hook_set(it, _item_text_get_hook);
5096 elm_widget_item_disable_hook_set(it, _item_disable_hook);
5097 elm_widget_item_del_pre_hook_set(it, _item_del_pre_hook);
5098 elm_widget_item_signal_emit_hook_set(it, _item_signal_emit_hook);
5100 #if 0 // FIXME: difference from upstream
5101 it->can_focus = EINA_TRUE;
5103 //it->del_cb = (Ecore_Cb)_item_free;
5104 //it->highlight_cb = (Ecore_Cb)_item_highlight;
5105 //it->unhighlight_cb = (Ecore_Cb)_item_unhighlight;
5106 //it->sel_cb = (Ecore_Cb)_item_select;
5107 //it->unsel_cb = (Ecore_Cb)_item_unselect;
5108 //it->unrealize_cb = (Ecore_Cb)_item_unrealize_cb;
5110 GL_IT(it) = ELM_NEW(Elm_Gen_Item_Type);
5111 GL_IT(it)->wsd = sd;
5112 GL_IT(it)->type = type;
5113 if (type & ELM_GENLIST_ITEM_GROUP) it->group++;
5117 if (it->parent->group)
5118 GL_IT(it)->group_item = parent;
5119 else if (GL_IT(it->parent)->group_item)
5120 GL_IT(it)->group_item = GL_IT(it->parent)->group_item;
5122 for (it2 = it, depth = 0; it2->parent; it2 = it2->parent)
5124 if (!it2->parent->group) depth += 1;
5126 GL_IT(it)->expanded_depth = depth;
5129 #if GENLIST_FX_SUPPORT
5130 it->item->num = sd->item_count;
5133 sd->fx_items_deleted = EINA_FALSE;
5134 _elm_genlist_fx_capture(ELM_WIDGET_DATA(sd)->obj, 0);
5141 _elm_genlist_item_compare(const void *data,
5144 const Elm_Gen_Item *it, *item1;
5146 it = ELM_GEN_ITEM_FROM_INLIST(data);
5147 item1 = ELM_GEN_ITEM_FROM_INLIST(data1);
5148 return GL_IT(it)->wsd->item_compare_cb(it, item1);
5152 _elm_genlist_item_list_compare(const void *data,
5155 const Elm_Gen_Item *it = data;
5156 const Elm_Gen_Item *item1 = data1;
5158 return GL_IT(it)->wsd->item_compare_cb(it, item1);
5162 elm_genlist_items_count(const Evas_Object *obj)
5164 ELM_GENLIST_CHECK(obj) 0;
5165 ELM_GENLIST_DATA_GET(obj, sd);
5167 return sd->item_count;
5170 EAPI Elm_Object_Item *
5171 elm_genlist_item_append(Evas_Object *obj,
5172 const Elm_Genlist_Item_Class *itc,
5174 Elm_Object_Item *parent,
5175 Elm_Genlist_Item_Type type,
5177 const void *func_data)
5181 ELM_GENLIST_CHECK(obj) NULL;
5182 ELM_GENLIST_DATA_GET(obj, sd);
5184 ELM_WIDGET_ITEM_RETURN_IF_ONDEL(((Elm_Widget_Item *)parent),NULL);
5186 it = _elm_genlist_item_new
5187 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5188 if (!it) return NULL;
5193 sd->group_items = eina_list_append(sd->group_items, it);
5194 sd->items = eina_inlist_append(sd->items, EINA_INLIST_GET(it));
5195 it->item->rel = NULL;
5199 Elm_Gen_Item *it2 = NULL;
5200 Eina_List *ll = eina_list_last(it->parent->item->items);
5202 if (ll) it2 = ll->data;
5203 it->parent->item->items =
5204 eina_list_append(it->parent->item->items, it);
5205 if (!it2) it2 = it->parent;
5206 sd->items = eina_inlist_append_relative
5207 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(it2));
5208 it->item->rel = it2;
5209 it2->item->rel_revs = eina_list_append(it2->item->rel_revs, it);
5211 it->item->before = EINA_FALSE;
5212 _item_queue(sd, it, NULL);
5214 return (Elm_Object_Item *)it;
5217 EAPI Elm_Object_Item *
5218 elm_genlist_item_prepend(Evas_Object *obj,
5219 const Elm_Genlist_Item_Class *itc,
5221 Elm_Object_Item *parent,
5222 Elm_Genlist_Item_Type type,
5224 const void *func_data)
5228 ELM_GENLIST_CHECK(obj) NULL;
5229 ELM_GENLIST_DATA_GET(obj, sd);
5230 it = _elm_genlist_item_new
5231 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5232 if (!it) return NULL;
5237 sd->group_items = eina_list_prepend(sd->group_items, it);
5238 sd->items = eina_inlist_prepend(sd->items, EINA_INLIST_GET(it));
5239 it->item->rel = NULL;
5243 Elm_Gen_Item *it2 = NULL;
5244 Eina_List *ll = it->parent->item->items;
5246 if (ll) it2 = ll->data;
5247 it->parent->item->items =
5248 eina_list_prepend(it->parent->item->items, it);
5249 if (!it2) it2 = it->parent;
5250 sd->items = eina_inlist_prepend_relative
5251 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(it2));
5252 it->item->rel = it2;
5253 it2->item->rel_revs = eina_list_append(it2->item->rel_revs, it);
5255 it->item->before = EINA_TRUE;
5256 _item_queue(sd, it, NULL);
5258 return (Elm_Object_Item *)it;
5261 EAPI Elm_Object_Item *
5262 elm_genlist_item_insert_after(Evas_Object *obj,
5263 const Elm_Genlist_Item_Class *itc,
5265 Elm_Object_Item *parent,
5266 Elm_Object_Item *after_it,
5267 Elm_Genlist_Item_Type type,
5269 const void *func_data)
5271 Elm_Gen_Item *after = (Elm_Gen_Item *)after_it;
5274 ELM_GENLIST_CHECK(obj) NULL;
5275 ELM_GENLIST_ITEM_CHECK_OR_RETURN(after_it, NULL);
5276 ELM_GENLIST_DATA_GET(obj, sd);
5278 /* It makes no sense to insert after in an empty list with after !=
5279 * NULL, something really bad is happening in your app. */
5280 EINA_SAFETY_ON_NULL_RETURN_VAL(sd->items, NULL);
5282 it = _elm_genlist_item_new
5283 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5284 if (!it) return NULL;
5288 if ((it->group) && (after->group))
5289 sd->group_items = eina_list_append_relative
5290 (sd->group_items, it, after);
5294 it->parent->item->items =
5295 eina_list_append_relative(it->parent->item->items, it, after);
5297 sd->items = eina_inlist_append_relative
5298 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(after));
5300 it->item->rel = after;
5301 after->item->rel_revs = eina_list_append(after->item->rel_revs, it);
5302 it->item->before = EINA_FALSE;
5303 _item_queue(sd, it, NULL);
5305 return (Elm_Object_Item *)it;
5308 EAPI Elm_Object_Item *
5309 elm_genlist_item_insert_before(Evas_Object *obj,
5310 const Elm_Genlist_Item_Class *itc,
5312 Elm_Object_Item *parent,
5313 Elm_Object_Item *before_it,
5314 Elm_Genlist_Item_Type type,
5316 const void *func_data)
5318 Elm_Gen_Item *before = (Elm_Gen_Item *)before_it;
5321 ELM_GENLIST_CHECK(obj) NULL;
5322 ELM_GENLIST_ITEM_CHECK_OR_RETURN(before_it, NULL);
5323 ELM_GENLIST_DATA_GET(obj, sd);
5325 /* It makes no sense to insert before in an empty list with before
5326 * != NULL, something really bad is happening in your app. */
5327 EINA_SAFETY_ON_NULL_RETURN_VAL(sd->items, NULL);
5329 it = _elm_genlist_item_new
5330 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5331 if (!it) return NULL;
5335 if (it->group && before->group)
5337 eina_list_prepend_relative(sd->group_items, it, before);
5341 it->parent->item->items =
5342 eina_list_prepend_relative(it->parent->item->items, it, before);
5344 sd->items = eina_inlist_prepend_relative
5345 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(before));
5347 it->item->rel = before;
5348 before->item->rel_revs = eina_list_append(before->item->rel_revs, it);
5349 it->item->before = EINA_TRUE;
5350 _item_queue(sd, it, NULL);
5352 return (Elm_Object_Item *)it;
5355 EAPI Elm_Object_Item *
5356 elm_genlist_item_sorted_insert(Evas_Object *obj,
5357 const Elm_Genlist_Item_Class *itc,
5359 Elm_Object_Item *parent,
5360 Elm_Genlist_Item_Type type,
5361 Eina_Compare_Cb comp,
5363 const void *func_data)
5365 Elm_Gen_Item *rel = NULL;
5368 ELM_GENLIST_CHECK(obj) NULL;
5369 ELM_GENLIST_DATA_GET(obj, sd);
5371 it = _elm_genlist_item_new
5372 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5373 if (!it) return NULL;
5375 sd->item_compare_cb = comp;
5382 l = eina_list_search_sorted_near_list
5383 (it->parent->item->items, _elm_genlist_item_list_compare, it,
5387 rel = eina_list_data_get(l);
5391 if (cmp_result >= 0)
5393 it->parent->item->items = eina_list_prepend_relative_list
5394 (it->parent->item->items, it, l);
5395 sd->items = eina_inlist_prepend_relative
5396 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(rel));
5397 it->item->before = EINA_FALSE;
5399 else if (cmp_result < 0)
5401 it->parent->item->items = eina_list_append_relative_list
5402 (it->parent->item->items, it, l);
5403 sd->items = eina_inlist_append_relative
5404 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(rel));
5405 it->item->before = EINA_TRUE;
5412 sd->state = eina_inlist_sorted_state_new();
5413 eina_inlist_sorted_state_init(sd->state, sd->items);
5414 sd->requeued = EINA_FALSE;
5418 sd->group_items = eina_list_append(sd->group_items, it);
5420 sd->items = eina_inlist_sorted_state_insert
5421 (sd->items, EINA_INLIST_GET(it), _elm_genlist_item_compare,
5424 if (EINA_INLIST_GET(it)->next)
5426 rel = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
5427 it->item->before = EINA_TRUE;
5429 else if (EINA_INLIST_GET(it)->prev)
5431 rel = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
5432 it->item->before = EINA_FALSE;
5438 it->item->rel = rel;
5439 rel->item->rel_revs = eina_list_append(rel->item->rel_revs, it);
5442 _item_queue(sd, it, _elm_genlist_item_list_compare);
5444 return (Elm_Object_Item *)it;
5448 _elm_genlist_fx_clear(Evas_Object *obj, Eina_Bool force)
5450 ELM_GENLIST_DATA_GET(obj, sd);
5452 Elm_Gen_FX_Item *fi;
5456 if ((!force) && (!sd->fx_first_captured)) return;
5458 EINA_LIST_FREE(sd->capture_before_items, pi)
5460 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
5461 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
5462 if (pi->proxy) evas_object_del(pi->proxy);
5465 EINA_LIST_FREE(sd->capture_after_items, pi)
5467 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
5468 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
5469 if (pi->proxy) evas_object_del(pi->proxy);
5473 EINA_LIST_FREE(sd->fx_items, fi)
5475 if (fi->trans) elm_transit_del(fi->trans);
5479 EINA_LIST_FREE (sd->pending_unrealized_items, it)
5480 _item_unrealize(it, EINA_FALSE);
5482 EINA_LIST_FREE (sd->pending_unrealized_decorate_all_items, it)
5483 _decorate_all_item_unrealize(it);
5485 EINA_LIST_FREE (sd->pending_del_items, it)
5488 _elm_widget_item_free((Elm_Widget_Item *)it);
5490 if (sd->alpha_bg) evas_object_del(sd->alpha_bg);
5491 sd->alpha_bg = NULL;
5492 if (sd->fx_timer) ecore_timer_del(sd->fx_timer);
5493 sd->fx_timer = NULL;
5495 sd->genlist_clearing = EINA_TRUE;
5496 sd->fx_playing = EINA_FALSE;
5497 sd->sorting = EINA_FALSE;
5498 sd->fx_first_captured = EINA_FALSE;
5499 sd->fx_items_deleted = EINA_FALSE;
5503 elm_genlist_clear(Evas_Object *obj)
5505 ELM_GENLIST_CHECK(obj);
5506 ELM_GENLIST_DATA_GET(obj, sd);
5511 eina_inlist_sorted_state_free(sd->state);
5515 #if GENLIST_FX_SUPPORT
5518 _elm_genlist_fx_clear(obj, EINA_TRUE);
5519 sd->genlist_clearing = EINA_TRUE;
5520 sd->rendered = EINA_FALSE;
5523 #if GENLIST_PINCH_ZOOM_SUPPORT
5524 sd->pinch_zoom_h = 0;
5525 sd->realized_top_item = NULL;
5526 sd->pinch_zoom_mode = ELM_GEN_PINCH_ZOOM_NONE;
5529 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5531 // Do not use EINA_INLIST_FOREACH or EINA_INLIST_FOREACH_SAFE
5532 // because sd->items can be modified inside elm_widget_item_del()
5535 it = EINA_INLIST_CONTAINER_GET(sd->items->last, Elm_Gen_Item);
5536 it->item->nocache_once = EINA_TRUE;
5537 elm_widget_item_del(it);
5541 _item_cache_all_free(sd);
5543 sd->pan_changed = EINA_TRUE;
5544 if (sd->selected) sd->selected = eina_list_free(sd->selected);
5545 sd->selected = NULL;
5547 sd->anchor_item = NULL;
5548 if (sd->multi_timer)
5550 ecore_timer_del(sd->multi_timer);
5551 sd->multi_timer = NULL;
5555 ecore_job_del(sd->update_job);
5556 sd->update_job = NULL;
5560 ecore_job_del(sd->calc_job);
5561 sd->calc_job = NULL;
5563 if (sd->queue_idle_enterer)
5565 ecore_idle_enterer_del(sd->queue_idle_enterer);
5566 sd->queue_idle_enterer = NULL;
5568 if (sd->must_recalc_idler)
5570 ecore_idler_del(sd->must_recalc_idler);
5571 sd->must_recalc_idler = NULL;
5573 if (sd->queue) sd->queue = eina_list_free(sd->queue);
5574 if (sd->reorder_move_animator)
5576 ecore_animator_del(sd->reorder_move_animator);
5577 sd->reorder_move_animator = NULL;
5579 sd->show_item = NULL;
5580 sd->reorder_old_pan_y = 0;
5587 if (sd->alpha_bg) evas_object_del(sd->alpha_bg);
5588 sd->alpha_bg = NULL;
5592 evas_object_size_hint_min_set(sd->pan_obj, sd->minw, sd->minh);
5593 evas_object_smart_callback_call(sd->pan_obj, "changed", NULL);
5595 elm_layout_sizing_eval(ELM_WIDGET_DATA(sd)->obj);
5596 sd->s_iface->content_region_show(obj, 0, 0, 0, 0);
5598 #if GENLIST_FX_SUPPORT
5599 sd->genlist_clearing = EINA_FALSE;
5601 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5602 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5606 elm_genlist_multi_select_set(Evas_Object *obj,
5609 ELM_GENLIST_CHECK(obj);
5610 ELM_GENLIST_DATA_GET(obj, sd);
5612 sd->multi = !!multi;
5616 elm_genlist_multi_select_get(const Evas_Object *obj)
5618 ELM_GENLIST_CHECK(obj) EINA_FALSE;
5619 ELM_GENLIST_DATA_GET(obj, sd);
5624 EAPI Elm_Object_Item *
5625 elm_genlist_selected_item_get(const Evas_Object *obj)
5627 ELM_GENLIST_CHECK(obj) NULL;
5628 ELM_GENLIST_DATA_GET(obj, sd);
5631 return sd->selected->data;
5637 elm_genlist_selected_items_get(const Evas_Object *obj)
5639 ELM_GENLIST_CHECK(obj) NULL;
5640 ELM_GENLIST_DATA_GET(obj, sd);
5642 return sd->selected;
5646 elm_genlist_realized_items_get(const Evas_Object *obj)
5649 Eina_List *list = NULL;
5650 Eina_Bool done = EINA_FALSE;
5652 ELM_GENLIST_CHECK(obj) NULL;
5653 ELM_GENLIST_DATA_GET(obj, sd);
5655 EINA_INLIST_FOREACH(sd->blocks, itb)
5663 EINA_LIST_FOREACH(itb->items, l, it)
5665 if (it->realized) list = eina_list_append(list, it);
5676 EAPI Elm_Object_Item *
5677 elm_genlist_at_xy_item_get(const Evas_Object *obj,
5682 Evas_Coord ox, oy, ow, oh;
5686 ELM_GENLIST_CHECK(obj) NULL;
5687 ELM_GENLIST_DATA_GET(obj, sd);
5689 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
5691 EINA_INLIST_FOREACH(sd->blocks, itb)
5696 if (!ELM_RECTS_INTERSECT(ox + itb->x - itb->sd->pan_x,
5697 oy + itb->y - itb->sd->pan_y,
5698 itb->w, itb->h, x, y, 1, 1))
5700 EINA_LIST_FOREACH(itb->items, l, it)
5702 Evas_Coord itx, ity;
5704 itx = ox + itb->x + it->x - itb->sd->pan_x;
5705 ity = oy + itb->y + it->y - itb->sd->pan_y;
5706 if (ELM_RECTS_INTERSECT
5707 (itx, ity, it->item->w, it->item->h, x, y, 1, 1))
5711 if (y <= (ity + (it->item->h / 4))) *posret = -1;
5712 else if (y >= (ity + it->item->h - (it->item->h / 4)))
5717 return (Elm_Object_Item *)it;
5719 lasty = ity + it->item->h;
5724 if (y > lasty) *posret = 1;
5731 EAPI Elm_Object_Item *
5732 elm_genlist_first_item_get(const Evas_Object *obj)
5734 Elm_Gen_Item *tit, *it = NULL;
5736 ELM_GENLIST_CHECK(obj) NULL;
5737 ELM_GENLIST_DATA_GET(obj, sd);
5739 EINA_INLIST_REVERSE_FOREACH(sd->items, tit) it = tit;
5741 return (Elm_Object_Item *)it;
5744 EAPI Elm_Object_Item *
5745 elm_genlist_last_item_get(const Evas_Object *obj)
5749 ELM_GENLIST_CHECK(obj) NULL;
5750 ELM_GENLIST_DATA_GET(obj, sd);
5751 if (!sd->items) return NULL;
5753 it = ELM_GEN_ITEM_FROM_INLIST(sd->items->last);
5754 return (Elm_Object_Item *)it;
5757 EAPI Elm_Object_Item *
5758 elm_genlist_item_next_get(const Elm_Object_Item *item)
5762 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
5764 it = (Elm_Gen_Item *)item;
5767 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
5771 return (Elm_Object_Item *)it;
5774 EAPI Elm_Object_Item *
5775 elm_genlist_item_prev_get(const Elm_Object_Item *item)
5779 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
5781 it = (Elm_Gen_Item *)item;
5784 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
5788 return (Elm_Object_Item *)it;
5791 EAPI Elm_Object_Item *
5792 elm_genlist_item_parent_get(const Elm_Object_Item *it)
5794 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
5796 return (Elm_Object_Item *)((Elm_Gen_Item *)it)->parent;
5800 elm_genlist_item_subitems_clear(Elm_Object_Item *item)
5802 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5804 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5805 _item_sub_items_clear(it);
5809 elm_genlist_item_selected_set(Elm_Object_Item *item,
5812 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5813 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5815 if (elm_widget_item_disabled_get(it)) return;
5816 selected = !!selected;
5817 if (it->selected == selected) return;
5819 _item_select_unselect(it, selected);
5823 elm_genlist_item_selected_get(const Elm_Object_Item *it)
5825 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, EINA_FALSE);
5827 return ((Elm_Gen_Item *)it)->selected;
5830 static Elm_Gen_Item *
5831 _elm_genlist_expanded_next_item_get(Elm_Gen_Item *it)
5835 if (it->item->expanded)
5837 it2 = (Elm_Gen_Item *)elm_genlist_item_next_get((Elm_Object_Item *)it);
5841 it2 = (Elm_Gen_Item *)elm_genlist_item_next_get((Elm_Object_Item *)it);
5844 if (it->item->expanded_depth >= it2->item->expanded_depth) break;
5845 it2 = (Elm_Gen_Item *)
5846 elm_genlist_item_next_get((Elm_Object_Item *)it2);
5852 static Evas_Object *
5853 _tray_alpha_bg_create(const Evas_Object *obj)
5855 Evas_Object *bg = NULL;
5856 Evas_Coord ox, oy, ow, oh;
5858 ELM_GENLIST_CHECK(obj) NULL;
5859 ELM_GENLIST_DATA_GET(obj, sd);
5861 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
5862 bg = evas_object_rectangle_add
5863 (evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5864 evas_object_color_set(bg, 0, 0, 0, 0);
5865 evas_object_resize(bg, ow, oh);
5866 evas_object_move(bg, ox, oy);
5872 elm_genlist_item_expanded_set(Elm_Object_Item *item,
5875 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5877 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5879 expanded = !!expanded;
5880 if (it->item->expanded == expanded) return;
5881 if (it->item->type != ELM_GENLIST_ITEM_TREE) return;
5882 it->item->expanded = expanded;
5883 GL_IT(it)->wsd->expanded_item = it;
5884 GL_IT(it)->wsd->expanded_next_item =
5885 _elm_genlist_expanded_next_item_get(it);
5887 if (it->item->expanded)
5890 edje_object_signal_emit(VIEW(it), "elm,state,expanded", "elm");
5891 evas_object_smart_callback_call(WIDGET(it), SIG_EXPANDED, it);
5892 GL_IT(it)->wsd->auto_scroll_enabled = EINA_TRUE;
5897 edje_object_signal_emit(VIEW(it), "elm,state,contracted", "elm");
5898 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACTED, it);
5899 GL_IT(it)->wsd->auto_scroll_enabled = EINA_FALSE;
5904 elm_genlist_item_expanded_get(const Elm_Object_Item *it)
5906 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, EINA_FALSE);
5908 return ((Elm_Gen_Item *)it)->item->expanded;
5912 elm_genlist_item_expanded_depth_get(const Elm_Object_Item *it)
5914 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, 0);
5916 return ((Elm_Gen_Item *)it)->item->expanded_depth;
5920 _elm_genlist_item_coordinates_calc(Elm_Object_Item *item,
5921 Elm_Genlist_Item_Scrollto_Type type,
5928 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5929 Evas_Coord gith = 0;
5931 if (!((GL_IT(it)->wsd->homogeneous) &&
5932 (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)))
5934 if ((it->item->queued) || (!it->item->mincalcd))
5936 GL_IT(it)->wsd->show_item = it;
5937 GL_IT(it)->wsd->bring_in = bring_in;
5938 GL_IT(it)->wsd->scroll_to_type = type;
5939 it->item->show_me = EINA_TRUE;
5943 if (GL_IT(it)->wsd->show_item)
5945 GL_IT(it)->wsd->show_item->item->show_me = EINA_FALSE;
5946 GL_IT(it)->wsd->show_item = NULL;
5949 evas_object_geometry_get(GL_IT(it)->wsd->pan_obj, NULL, NULL, w, h);
5952 case ELM_GENLIST_ITEM_SCROLLTO_IN:
5953 if ((it->item->group_item) &&
5954 (GL_IT(it)->wsd->pan_y > (it->y + it->item->block->y)))
5955 gith = it->item->group_item->item->h;
5957 *y = it->y + it->item->block->y - gith;
5960 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
5961 if (it->item->group_item) gith = it->item->group_item->item->h;
5962 *y = it->y + it->item->block->y - gith;
5965 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
5966 *y = it->y + it->item->block->y - (*h / 2) + (it->item->h / 2);
5973 *x = it->x + it->item->block->x;
5974 *w = it->item->block->w;
5980 elm_genlist_item_promote(Elm_Object_Item *item)
5982 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5983 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5985 (it, (Elm_Gen_Item *)elm_genlist_first_item_get(WIDGET(it)));
5989 elm_genlist_item_demote(Elm_Object_Item *item)
5991 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5992 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5993 _item_move_after(it, (Elm_Gen_Item *)elm_genlist_last_item_get(WIDGET(it)));
5997 elm_genlist_item_show(Elm_Object_Item *item,
5998 Elm_Genlist_Item_Scrollto_Type type)
6000 Evas_Coord x, y, w, h;
6001 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6002 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6004 if (_elm_genlist_item_coordinates_calc
6005 (item, type, EINA_FALSE, &x, &y, &w, &h))
6006 GL_IT(it)->wsd->s_iface->content_region_show(WIDGET(item), x, y, w, h);
6010 elm_genlist_item_bring_in(Elm_Object_Item *item,
6011 Elm_Genlist_Item_Scrollto_Type type)
6013 Evas_Coord x, y, w, h;
6014 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6015 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6017 if (_elm_genlist_item_coordinates_calc
6018 (item, type, EINA_TRUE, &x, &y, &w, &h))
6019 GL_IT(it)->wsd->s_iface->region_bring_in(WIDGET(item), x, y, w, h);
6023 elm_genlist_item_all_contents_unset(Elm_Object_Item *item,
6026 Evas_Object *content;
6028 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6029 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6031 EINA_LIST_FREE (it->content_objs, content)
6033 evas_object_smart_member_del(content);
6034 evas_object_hide(content);
6035 if (l) *l = eina_list_append(*l, content);
6040 elm_genlist_item_update(Elm_Object_Item *item)
6042 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6043 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6045 if (!it->item->block) return;
6046 it->item->mincalcd = EINA_FALSE;
6047 it->item->updateme = EINA_TRUE;
6048 it->item->block->updateme = EINA_TRUE;
6049 #if GENLIST_ENTRY_SUPPORT
6050 it->item->unrealize_disabled = EINA_FALSE;
6053 #if GENLIST_FX_SUPPORT
6054 _elm_genlist_fx_clear(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj, EINA_FALSE);
6057 if (GL_IT(it)->wsd->update_job) ecore_job_del(GL_IT(it)->wsd->update_job);
6058 GL_IT(it)->wsd->update_job = ecore_job_add(_update_job, GL_IT(it)->wsd);
6062 elm_genlist_item_fields_update(Elm_Object_Item *item,
6064 Elm_Genlist_Item_Field_Type itf)
6066 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6067 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6069 if (!it->item->block) return;
6071 #if GENLIST_ENTRY_SUPPORT
6072 it->item->unrealize_disabled = EINA_FALSE;
6074 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_TEXT))
6076 _item_text_realize(it, VIEW(it), &it->texts, parts);
6078 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_CONTENT))
6080 it->content_objs = _item_content_unrealize(it, VIEW(it),
6081 &it->contents, parts);
6082 it->content_objs = _item_content_realize(it, VIEW(it),
6083 &it->contents, parts);
6087 it->item->flip_content_objs =
6088 _item_mode_content_unrealize(it, VIEW(it),
6089 &it->item->flip_contents, parts,
6090 &it->item->flip_content_objs);
6091 it->item->flip_content_objs =
6092 _item_mode_content_realize(it, VIEW(it),
6093 &it->item->flip_contents, parts,
6094 &it->item->flip_content_objs);
6096 if (it->item->deco_it_view)
6098 it->item->deco_it_content_objs =
6099 _item_mode_content_unrealize(it, it->item->deco_it_view,
6100 &it->item->deco_it_contents, parts,
6101 &it->item->deco_it_content_objs);
6102 it->item->deco_it_content_objs =
6103 _item_mode_content_realize(it, it->item->deco_it_view,
6104 &it->item->deco_it_contents, parts,
6105 &it->item->deco_it_content_objs);
6107 if (GL_IT(it)->wsd->decorate_all_mode)
6109 it->item->deco_all_content_objs =
6110 _item_mode_content_unrealize
6111 (it, it->deco_all_view, &it->item->deco_all_contents, parts,
6112 &it->item->deco_all_content_objs);
6113 it->item->deco_all_content_objs =
6114 _item_mode_content_realize(it, it->deco_all_view,
6115 &it->item->deco_all_contents, parts,
6116 &it->item->deco_all_content_objs);
6120 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_STATE))
6121 _item_state_realize(it, VIEW(it), &it->states, parts);
6125 elm_genlist_item_item_class_update(Elm_Object_Item *item,
6126 const Elm_Genlist_Item_Class *itc)
6128 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6129 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6131 if (!it->item->block) return;
6132 EINA_SAFETY_ON_NULL_RETURN(itc);
6134 it->item->nocache_once = EINA_TRUE;
6136 elm_widget_stringlist_free(it->texts);
6138 elm_widget_stringlist_free(it->contents);
6139 it->contents = NULL;
6140 elm_widget_stringlist_free(it->states);
6145 elm_widget_stringlist_free(it->item->flip_contents);
6146 it->item->flip_contents = NULL;
6148 if (it->item->deco_it_view)
6150 elm_widget_stringlist_free(it->item->deco_it_texts);
6151 it->item->deco_it_texts = NULL;
6152 elm_widget_stringlist_free(it->item->deco_it_contents);
6153 it->item->deco_it_contents = NULL;
6155 if (GL_IT(it)->wsd->decorate_all_mode)
6157 elm_widget_stringlist_free(it->item->deco_all_texts);
6158 it->item->deco_all_texts = NULL;
6159 elm_widget_stringlist_free(it->item->deco_all_contents);
6160 it->item->deco_all_contents = NULL;
6163 elm_genlist_item_update(item);
6166 EAPI const Elm_Genlist_Item_Class *
6167 elm_genlist_item_item_class_get(const Elm_Object_Item *item)
6169 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
6170 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6174 static Evas_Object *
6175 _elm_genlist_item_label_create(void *data,
6176 Evas_Object *obj __UNUSED__,
6177 Evas_Object *tooltip,
6178 void *it __UNUSED__)
6180 Evas_Object *label = elm_label_add(tooltip);
6185 elm_object_style_set(label, "tooltip");
6186 elm_object_text_set(label, data);
6192 _elm_genlist_item_label_del_cb(void *data,
6193 Evas_Object *obj __UNUSED__,
6194 void *event_info __UNUSED__)
6196 eina_stringshare_del(data);
6200 elm_genlist_item_tooltip_text_set(Elm_Object_Item *it,
6203 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it);
6205 text = eina_stringshare_add(text);
6206 elm_genlist_item_tooltip_content_cb_set
6207 (it, _elm_genlist_item_label_create, text,
6208 _elm_genlist_item_label_del_cb);
6212 elm_genlist_item_tooltip_content_cb_set(Elm_Object_Item *item,
6213 Elm_Tooltip_Item_Content_Cb func,
6215 Evas_Smart_Cb del_cb)
6217 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6219 ELM_GENLIST_ITEM_CHECK_OR_GOTO(item, error);
6221 if ((it->tooltip.content_cb == func) && (it->tooltip.data == data))
6224 if (it->tooltip.del_cb)
6225 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
6227 it->tooltip.content_cb = func;
6228 it->tooltip.data = data;
6229 it->tooltip.del_cb = del_cb;
6233 elm_widget_item_tooltip_content_cb_set
6234 (it, it->tooltip.content_cb, it->tooltip.data, NULL);
6235 elm_widget_item_tooltip_style_set(it, it->tooltip.style);
6236 elm_widget_item_tooltip_window_mode_set(it, it->tooltip.free_size);
6242 if (del_cb) del_cb((void *)data, NULL, NULL);
6246 elm_genlist_item_tooltip_unset(Elm_Object_Item *item)
6248 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6250 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6252 if ((VIEW(it)) && (it->tooltip.content_cb))
6253 elm_widget_item_tooltip_unset(it);
6255 if (it->tooltip.del_cb)
6256 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
6257 it->tooltip.del_cb = NULL;
6258 it->tooltip.content_cb = NULL;
6259 it->tooltip.data = NULL;
6260 it->tooltip.free_size = EINA_FALSE;
6261 if (it->tooltip.style)
6262 elm_genlist_item_tooltip_style_set(item, NULL);
6266 elm_genlist_item_tooltip_style_set(Elm_Object_Item *item,
6269 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6271 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6273 eina_stringshare_replace(&it->tooltip.style, style);
6274 if (VIEW(it)) elm_widget_item_tooltip_style_set(it, style);
6278 elm_genlist_item_tooltip_style_get(const Elm_Object_Item *it)
6280 return elm_object_item_tooltip_style_get(it);
6284 elm_genlist_item_tooltip_window_mode_set(Elm_Object_Item *item,
6287 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6289 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, EINA_FALSE);
6291 it->tooltip.free_size = disable;
6292 if (VIEW(it)) return elm_widget_item_tooltip_window_mode_set(it, disable);
6298 elm_genlist_item_tooltip_window_mode_get(const Elm_Object_Item *it)
6300 return elm_object_tooltip_window_mode_get(VIEW(it));
6304 elm_genlist_item_cursor_set(Elm_Object_Item *item,
6307 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6309 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6310 eina_stringshare_replace(&it->mouse_cursor, cursor);
6311 if (VIEW(it)) elm_widget_item_cursor_set(it, cursor);
6315 elm_genlist_item_cursor_get(const Elm_Object_Item *it)
6317 return elm_widget_item_cursor_get(it);
6321 elm_genlist_item_cursor_unset(Elm_Object_Item *item)
6323 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6325 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6327 if (!it->mouse_cursor) return;
6329 if (VIEW(it)) elm_widget_item_cursor_unset(it);
6331 eina_stringshare_del(it->mouse_cursor);
6332 it->mouse_cursor = NULL;
6336 elm_genlist_item_cursor_style_set(Elm_Object_Item *it,
6339 elm_widget_item_cursor_style_set(it, style);
6343 elm_genlist_item_cursor_style_get(const Elm_Object_Item *it)
6345 return elm_widget_item_cursor_style_get(it);
6349 elm_genlist_item_cursor_engine_only_set(Elm_Object_Item *it,
6350 Eina_Bool engine_only)
6352 elm_widget_item_cursor_engine_only_set(it, engine_only);
6356 elm_genlist_item_cursor_engine_only_get(const Elm_Object_Item *it)
6358 return elm_widget_item_cursor_engine_only_get(it);
6362 elm_genlist_item_index_get(const Elm_Object_Item *item)
6366 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6368 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, -1);
6370 EINA_INLIST_FOREACH(GL_IT(it)->wsd->items, tmp)
6372 if (tmp == it) break;
6379 elm_genlist_mode_set(Evas_Object *obj,
6382 ELM_GENLIST_CHECK(obj);
6383 ELM_GENLIST_DATA_GET(obj, sd);
6385 if (sd->mode == mode) return;
6387 elm_layout_sizing_eval(obj);
6391 elm_genlist_mode_get(const Evas_Object *obj)
6393 ELM_GENLIST_CHECK(obj) ELM_LIST_LAST;
6394 ELM_GENLIST_DATA_GET(obj, sd);
6400 elm_genlist_bounce_set(Evas_Object *obj,
6404 ELM_GENLIST_CHECK(obj);
6405 ELM_GENLIST_DATA_GET(obj, sd);
6407 sd->h_bounce = !!h_bounce;
6408 sd->v_bounce = !!v_bounce;
6409 sd->s_iface->bounce_allow_set(obj, sd->h_bounce, sd->v_bounce);
6413 elm_genlist_bounce_get(const Evas_Object *obj,
6414 Eina_Bool *h_bounce,
6415 Eina_Bool *v_bounce)
6417 ELM_GENLIST_CHECK(obj);
6418 ELM_GENLIST_DATA_GET(obj, sd);
6420 if (h_bounce) *h_bounce = sd->h_bounce;
6421 if (v_bounce) *v_bounce = sd->v_bounce;
6425 elm_genlist_homogeneous_set(Evas_Object *obj,
6426 Eina_Bool homogeneous)
6428 ELM_GENLIST_CHECK(obj);
6429 ELM_GENLIST_DATA_GET(obj, sd);
6431 sd->homogeneous = !!homogeneous;
6435 elm_genlist_homogeneous_get(const Evas_Object *obj)
6437 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6438 ELM_GENLIST_DATA_GET(obj, sd);
6440 return sd->homogeneous;
6444 elm_genlist_block_count_set(Evas_Object *obj,
6447 ELM_GENLIST_CHECK(obj);
6448 ELM_GENLIST_DATA_GET(obj, sd);
6449 EINA_SAFETY_ON_TRUE_RETURN(count < 1);
6451 sd->max_items_per_block = count;
6452 sd->item_cache_max = sd->max_items_per_block * 2;
6453 _item_cache_all_free(sd);
6457 elm_genlist_block_count_get(const Evas_Object *obj)
6459 ELM_GENLIST_CHECK(obj) 0;
6460 ELM_GENLIST_DATA_GET(obj, sd);
6462 return sd->max_items_per_block;
6466 elm_genlist_longpress_timeout_set(Evas_Object *obj,
6469 ELM_GENLIST_CHECK(obj);
6470 ELM_GENLIST_DATA_GET(obj, sd);
6472 sd->longpress_timeout = timeout;
6476 elm_genlist_longpress_timeout_get(const Evas_Object *obj)
6478 ELM_GENLIST_CHECK(obj) 0;
6479 ELM_GENLIST_DATA_GET(obj, sd);
6481 return sd->longpress_timeout;
6485 elm_genlist_scroller_policy_set(Evas_Object *obj,
6486 Elm_Scroller_Policy policy_h,
6487 Elm_Scroller_Policy policy_v)
6489 ELM_GENLIST_CHECK(obj);
6490 ELM_GENLIST_DATA_GET(obj, sd);
6492 if ((policy_h >= ELM_SCROLLER_POLICY_LAST) ||
6493 (policy_v >= ELM_SCROLLER_POLICY_LAST))
6496 sd->s_iface->policy_set(obj, policy_h, policy_v);
6500 elm_genlist_scroller_policy_get(const Evas_Object *obj,
6501 Elm_Scroller_Policy *policy_h,
6502 Elm_Scroller_Policy *policy_v)
6504 Elm_Scroller_Policy s_policy_h, s_policy_v;
6506 ELM_GENLIST_CHECK(obj);
6507 ELM_GENLIST_DATA_GET(obj, sd);
6509 sd->s_iface->policy_get(obj, &s_policy_h, &s_policy_v);
6510 if (policy_h) *policy_h = (Elm_Scroller_Policy)s_policy_h;
6511 if (policy_v) *policy_v = (Elm_Scroller_Policy)s_policy_v;
6515 elm_genlist_realized_items_update(Evas_Object *obj)
6517 Eina_List *list, *l;
6518 Elm_Object_Item *it;
6520 ELM_GENLIST_CHECK(obj);
6522 list = elm_genlist_realized_items_get(obj);
6523 EINA_LIST_FOREACH(list, l, it)
6524 elm_genlist_item_update(it);
6528 elm_genlist_item_decorate_mode_set(Elm_Object_Item *item,
6529 const char *decorate_it_type,
6530 Eina_Bool decorate_it_set)
6532 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6533 Elm_Genlist_Smart_Data *sd;
6535 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6536 sd = GL_IT(it)->wsd;
6538 if (elm_widget_item_disabled_get(it)) return;
6539 if (!decorate_it_type) return;
6540 if (sd->decorate_all_mode) return;
6542 if ((sd->mode_item == it) &&
6543 (!strcmp(decorate_it_type, sd->decorate_it_type)) &&
6546 if (!it->itc->decorate_item_style) return;
6547 it->decorate_it_set = decorate_it_set;
6550 if (((sd->decorate_it_type)
6551 && (strcmp(decorate_it_type, sd->decorate_it_type))) ||
6552 (decorate_it_set) || ((it == sd->mode_item) && (!decorate_it_set)))
6553 _decorate_item_unset(sd);
6555 eina_stringshare_replace(&sd->decorate_it_type, decorate_it_type);
6556 if (decorate_it_set) _decorate_item_set(it);
6560 elm_genlist_item_decorate_mode_get(const Elm_Object_Item *item)
6562 Elm_Gen_Item *i = (Elm_Gen_Item *)item;
6564 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
6565 return GL_IT(i)->wsd->decorate_it_type;
6568 EAPI Elm_Object_Item *
6569 elm_genlist_decorated_item_get(const Evas_Object *obj)
6571 ELM_GENLIST_CHECK(obj) NULL;
6572 ELM_GENLIST_DATA_GET(obj, sd);
6574 return (Elm_Object_Item *)sd->mode_item;
6578 elm_genlist_decorate_mode_get(const Evas_Object *obj)
6580 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6581 ELM_GENLIST_DATA_GET(obj, sd);
6583 return sd->decorate_all_mode;
6587 elm_genlist_decorate_mode_set(Evas_Object *obj,
6588 Eina_Bool decorated)
6591 Eina_List *list, *l;
6593 ELM_GENLIST_CHECK(obj);
6594 ELM_GENLIST_DATA_GET(obj, sd);
6596 decorated = !!decorated;
6597 if (sd->decorate_all_mode == decorated) return;
6598 // decorate_all_mode should be set first
6599 // because content_get func. will be called after this
6600 // and user can check whether deocrate_all_mode is enabeld.
6601 sd->decorate_all_mode = decorated;
6603 list = elm_genlist_realized_items_get(obj);
6604 if (!sd->decorate_all_mode)
6606 EINA_LIST_FOREACH(list, l, it)
6608 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6609 _decorate_all_item_unrealize(it);
6611 _item_cache_all_free(sd);
6615 EINA_LIST_FOREACH(list, l, it)
6617 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6619 if (it->itc->decorate_all_item_style)
6620 _decorate_all_item_realize(it, EINA_TRUE);
6624 #if GENLIST_FX_SUPPORT
6625 _elm_genlist_fx_clear(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
6627 if (sd->calc_job) ecore_job_del(sd->calc_job);
6628 sd->calc_job = ecore_job_add(_calc_job, sd);
6632 elm_genlist_reorder_mode_set(Evas_Object *obj,
6633 Eina_Bool reorder_mode)
6635 #if 1 // FIXME: difference from upstream
6636 Eina_List *list, *l;
6639 ELM_GENLIST_CHECK(obj);
6640 ELM_GENLIST_DATA_GET(obj, sd);
6642 if (sd->reorder_mode == !!reorder_mode) return;
6643 sd->reorder_mode = !!reorder_mode;
6644 #if 1 // FIXME: difference from upstream
6645 list = elm_genlist_realized_items_get(obj);
6646 EINA_LIST_FOREACH(list, l, it)
6648 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6650 if (sd->reorder_mode)
6651 edje_object_signal_emit
6652 (VIEW(it), "elm,state,reorder,mode_set", "elm");
6654 edje_object_signal_emit
6655 (VIEW(it), "elm,state,reorder,mode_unset", "elm");
6657 if (sd->decorate_all_mode)
6659 if (sd->reorder_mode)
6660 edje_object_signal_emit
6661 (it->deco_all_view, "elm,state,reorder,mode_set", "elm");
6663 edje_object_signal_emit
6664 (it->deco_all_view, "elm,state,reorder,mode_unset", "elm");
6667 eina_list_free(list);
6672 elm_genlist_reorder_mode_get(const Evas_Object *obj)
6674 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6675 ELM_GENLIST_DATA_GET(obj, sd);
6677 return sd->reorder_mode;
6680 EAPI Elm_Genlist_Item_Type
6681 elm_genlist_item_type_get(const Elm_Object_Item *item)
6683 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6685 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, ELM_GENLIST_ITEM_MAX);
6687 return it->item->type;
6690 EAPI Elm_Genlist_Item_Class *
6691 elm_genlist_item_class_new(void)
6693 Elm_Genlist_Item_Class *itc = ELM_NEW(Elm_Genlist_Item_Class);
6694 EINA_SAFETY_ON_NULL_RETURN_VAL(itc, NULL);
6696 itc->version = CLASS_ALLOCATED;
6698 itc->delete_me = EINA_FALSE;
6704 elm_genlist_item_class_free(Elm_Genlist_Item_Class *itc)
6706 if (itc && (itc->version == CLASS_ALLOCATED))
6708 if (!itc->delete_me) itc->delete_me = EINA_TRUE;
6709 if (itc->refcount > 0) elm_genlist_item_class_unref(itc);
6719 elm_genlist_item_class_ref(Elm_Genlist_Item_Class *itc)
6721 if (itc && (itc->version == CLASS_ALLOCATED))
6724 if (itc->refcount == 0) itc->refcount--;
6729 elm_genlist_item_class_unref(Elm_Genlist_Item_Class *itc)
6731 if (itc && (itc->version == CLASS_ALLOCATED))
6733 if (itc->refcount > 0) itc->refcount--;
6734 if (itc->delete_me && (!itc->refcount))
6735 elm_genlist_item_class_free(itc);
6740 elm_genlist_item_flip_set(Elm_Object_Item *item,
6743 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6744 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6745 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
6748 if (it->flipped == flip) return;
6750 it->item->unrealize_disabled = EINA_FALSE;
6754 _item_unrealize(it, EINA_FALSE);
6755 it->flipped = EINA_TRUE;
6756 it->item->nocache = EINA_TRUE;
6760 _item_unrealize(it, EINA_FALSE);
6761 it->flipped = EINA_FALSE;
6762 it->item->nocache = EINA_FALSE;
6764 if (sd->calc_job) ecore_job_del(sd->calc_job);
6765 sd->calc_job = ecore_job_add(_calc_job, sd);
6769 elm_genlist_item_flip_get(const Elm_Object_Item *item)
6771 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6773 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, EINA_FALSE);
6779 elm_genlist_select_mode_set(Evas_Object *obj,
6780 Elm_Object_Select_Mode mode)
6782 ELM_GENLIST_CHECK(obj);
6783 ELM_GENLIST_DATA_GET(obj, sd);
6785 if (mode >= ELM_OBJECT_SELECT_MODE_MAX || (sd->select_mode == mode))
6788 sd->select_mode = mode;
6789 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
6790 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
6794 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it)
6799 EAPI Elm_Object_Select_Mode
6800 elm_genlist_select_mode_get(const Evas_Object *obj)
6802 ELM_GENLIST_CHECK(obj) ELM_OBJECT_SELECT_MODE_MAX;
6803 ELM_GENLIST_DATA_GET(obj, sd);
6805 return sd->select_mode;
6809 elm_genlist_highlight_mode_set(Evas_Object *obj,
6810 Eina_Bool highlight)
6812 ELM_GENLIST_CHECK(obj);
6813 ELM_GENLIST_DATA_GET(obj, sd);
6815 sd->highlight = !!highlight;
6819 elm_genlist_highlight_mode_get(const Evas_Object *obj)
6821 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6822 ELM_GENLIST_DATA_GET(obj, sd);
6824 return sd->highlight;
6828 elm_genlist_item_select_mode_set(Elm_Object_Item *item,
6829 Elm_Object_Select_Mode mode)
6831 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6833 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6835 if (mode >= ELM_OBJECT_SELECT_MODE_MAX)
6837 if (it->select_mode != mode)
6838 it->select_mode = mode;
6840 if ((it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
6841 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
6844 if (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
6846 it->item->mincalcd = EINA_FALSE;
6847 it->item->updateme = EINA_TRUE;
6848 if (it->item->block) it->item->block->updateme = EINA_TRUE;
6849 if (GL_IT(it)->wsd->update_job)
6850 ecore_job_del(GL_IT(it)->wsd->update_job);
6851 GL_IT(it)->wsd->update_job =
6852 ecore_job_add(_update_job, GL_IT(it)->wsd);
6854 // reset homogeneous item size
6855 if (GL_IT(it)->wsd->homogeneous)
6858 GL_IT(it)->wsd->group_item_width =
6859 GL_IT(it)->wsd->group_item_height = 0;
6861 GL_IT(it)->wsd->item_width = GL_IT(it)->wsd->item_height = 0;
6866 EAPI Elm_Object_Select_Mode
6867 elm_genlist_item_select_mode_get(const Elm_Object_Item *item)
6869 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6871 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, ELM_OBJECT_SELECT_MODE_MAX);
6873 if (!it) return ELM_OBJECT_SELECT_MODE_MAX;
6875 return it->select_mode;
6878 // will be deprecated
6880 elm_genlist_tree_effect_enabled_set(Evas_Object *obj __UNUSED__,
6881 Eina_Bool enabled __UNUSED__)
6883 ELM_GENLIST_CHECK(obj);
6886 // will be deprecated
6888 elm_genlist_tree_effect_enabled_get(const Evas_Object *obj __UNUSED__)
6890 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6895 EAPI Elm_Object_Item *
6896 elm_genlist_nth_item_get(const Evas_Object *obj, unsigned int nth)
6898 Elm_Gen_Item *it = NULL;
6902 ELM_GENLIST_CHECK(obj) NULL;
6903 ELM_GENLIST_DATA_GET(obj, sd);
6905 if (!sd->items) return NULL;
6907 a = eina_inlist_accessor_new(sd->items);
6908 if (!a) return NULL;
6909 if (eina_accessor_data_get(a, nth, &data))
6910 it = ELM_GEN_ITEM_FROM_INLIST(data);
6911 eina_accessor_free(a);
6912 return (Elm_Object_Item *)it;
6915 #if GENLIST_FX_SUPPORT
6917 elm_genlist_fx_mode_set(Evas_Object *obj, Eina_Bool mode)
6919 ELM_GENLIST_CHECK(obj);
6920 ELM_GENLIST_DATA_GET(obj, sd);
6926 elm_genlist_fx_mode_get(const Evas_Object *obj)
6928 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6929 ELM_GENLIST_DATA_GET(obj, sd);
6935 _elm_genlist_proxy_item_del(const Elm_Object_Item *item)
6937 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6938 if ((!it) || (!it->item)) return;
6940 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
6944 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
6945 if (pi->it == it) pi->it = NULL;
6947 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
6948 if (pi->it == it) pi->it = NULL;
6952 _elm_genlist_proxy_item_new(const Elm_Object_Item *item)
6954 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6955 if ((!it) || (!it->item)) return EINA_FALSE;
6958 Proxy_Item *pi = NULL;
6959 pi = calloc(1, sizeof(Proxy_Item));
6960 if (!pi) return NULL;
6962 pi->proxy = evas_object_image_filled_add
6963 (evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
6964 if (!pi->proxy) return EINA_FALSE;
6965 evas_object_clip_set(pi->proxy, evas_object_clip_get(GL_IT(it)->wsd->pan_obj));
6966 evas_object_smart_member_add(pi->proxy, GL_IT(it)->wsd->pan_obj);
6967 evas_object_hide(pi->proxy);
6969 if ((GL_IT(it)->wsd->decorate_all_mode) && (it->deco_all_view))
6970 evas_object_image_source_set(pi->proxy, it->deco_all_view);
6972 evas_object_image_source_set(pi->proxy, VIEW(it));
6974 GL_IT(it)->has_proxy_it = EINA_TRUE;
6976 pi->num = it->item->num;
6977 pi->x = it->item->scrl_x;
6978 pi->y = it->item->scrl_y;
6979 pi->w = it->item->w;
6980 pi->h = it->item->h;
6982 evas_object_geometry_get(VIEW(it), NULL, NULL, &w, &h);
6984 if (w <= 0 || h <= 0)
6986 evas_object_size_hint_min_get(VIEW(it), &w, &h);
6987 evas_object_size_hint_min_set(pi->proxy, w, h);
6989 else evas_object_resize(pi->proxy, w, h);
6995 _elm_genlist_fx_capture(Evas_Object *obj, int level)
6997 ELM_GENLIST_DATA_GET(obj, sd);
7001 Eina_Bool done = EINA_FALSE;
7004 Evas_Coord ox, oy, ow, oh;
7008 if ((!sd->rendered) || (sd->fx_playing)) return EINA_FALSE;
7009 if ((!level) && (sd->fx_first_captured)) return EINA_FALSE;
7010 if ((level) && (!sd->fx_first_captured)) return EINA_FALSE;
7012 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7016 sd->fx_first_captured = EINA_TRUE;
7017 EINA_LIST_FREE(sd->capture_before_items, pi)
7019 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
7020 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
7021 if (pi->proxy) evas_object_del(pi->proxy);
7027 EINA_LIST_FREE(sd->capture_after_items, pi)
7029 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
7030 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
7031 if (pi->proxy) evas_object_del(pi->proxy);
7035 EINA_INLIST_FOREACH(sd->blocks, itb)
7039 EINA_LIST_FOREACH(itb->items, l, it)
7041 if (it->realized && it->item->scrl_y >= oy)
7043 sd->realized_top_item = it;
7048 if (sd->realized_top_item) break;
7052 #if GENLIST_PINCH_ZOOM_SUPPORT
7053 if (sd->pinch_zoom_mode)
7055 EINA_INLIST_FOREACH(sd->blocks, itb)
7057 EINA_LIST_FOREACH(itb->items, l, it)
7060 if (IS_ROOT_PARENT_IT(it) && it->realized
7061 && (GL_IT(it)->scrl_y + GL_IT(it)->h >= oy && GL_IT(it)->scrl_y <= oy + oh))
7063 pi = _elm_genlist_proxy_item_new((Elm_Object_Item *)it);
7064 if (!level) sd->capture_before_items = eina_list_append(sd->capture_before_items, pi);
7065 else sd->capture_after_items = eina_list_append(sd->capture_after_items, pi);
7069 if ((sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT) && (level)) return EINA_TRUE;
7070 if ((sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND) && (!level)) return EINA_TRUE;
7074 EINA_INLIST_FOREACH(sd->blocks, itb)
7079 EINA_LIST_FOREACH(itb->items, l, it)
7081 #if GENLIST_PINCH_ZOOM_SUPPORT
7082 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7086 pi = _elm_genlist_proxy_item_new((Elm_Object_Item *)it);
7089 sd->capture_before_items = eina_list_append(sd->capture_before_items, pi);
7091 sd->capture_after_items = eina_list_append(sd->capture_after_items, pi);
7095 else if (done) break;
7100 static Elm_Gen_FX_Item *
7101 _elm_genlist_fx_item_find(const Elm_Object_Item *item)
7103 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
7104 if (!it) return EINA_FALSE;
7106 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
7107 if (!sd) return NULL;
7109 Elm_Gen_FX_Item *fi = NULL;
7112 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7114 if (fi->it == it) return fi;
7119 static Elm_Gen_FX_Item *
7120 _elm_genlist_fx_item_new(const Proxy_Item *pi)
7122 if ((!pi) || (!pi->it)) return NULL;
7124 Elm_Gen_FX_Item *fi = NULL;
7125 fi = calloc(1, sizeof(Elm_Gen_FX_Item));
7126 if (!fi) return NULL;
7129 GL_IT(fi->it)->fi = fi;
7130 fi->proxy = pi->proxy;
7132 fi->from.x = fi->to.x = pi->x;
7133 fi->from.y = fi->to.y = pi->y;
7134 fi->from.w = fi->to.w = pi->w;
7135 fi->from.h = fi->to.h = pi->h;
7136 fi->update = EINA_FALSE;
7141 static Elm_Object_Item *
7142 _elm_genlist_fx_item_prev_get(const Elm_Object_Item *item)
7145 it = (Elm_Gen_Item *)item;
7146 if (!it) return NULL;
7147 if (GL_IT(it)->wsd->pinch_zoom_mode) return NULL;
7151 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
7155 return (Elm_Object_Item *)it;
7159 _elm_genlist_fx_items_make(Evas_Object *obj)
7161 ELM_GENLIST_CHECK(obj) EINA_FALSE;
7162 ELM_GENLIST_DATA_GET(obj, sd);
7164 Elm_Gen_FX_Item *fi;
7167 Elm_Gen_Item *prev = NULL;
7168 Evas_Coord ox, oy, ow, oh, mv_dist, max_mv_dist = 0;
7170 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7172 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
7174 fi = _elm_genlist_fx_item_new(pi);
7175 if (fi) sd->fx_items = eina_list_append(sd->fx_items, fi);
7178 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
7180 fi = _elm_genlist_fx_item_find((Elm_Object_Item *)pi->it);
7182 if (fi) // pi exists in both before and after capture items
7184 fi->type = ELM_GEN_ITEM_FX_TYPE_SAME;
7185 fi->update = EINA_TRUE;
7191 // find the max distance between before and after capture items
7192 mv_dist = abs(fi->to.y - fi->from.y);
7193 if (max_mv_dist < mv_dist) max_mv_dist = mv_dist;
7195 else // pi only exists in after capture items
7197 fi = _elm_genlist_fx_item_new(pi);
7200 fi->type = ELM_GEN_ITEM_FX_TYPE_ADD;
7201 fi->update = EINA_TRUE;
7202 sd->fx_items = eina_list_append(sd->fx_items, fi);
7207 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7209 // find deleted items
7210 if (!fi->update) // pi only exists in before capture items
7212 fi->type = ELM_GEN_ITEM_FX_TYPE_DEL;
7213 fi->update = EINA_TRUE;
7215 prev = (Elm_Gen_Item *)_elm_genlist_fx_item_prev_get((Elm_Object_Item *)fi->it);
7216 if ((prev) && (GL_IT(prev)->fi))
7218 fi->to.y = GL_IT(prev)->fi->to.y + GL_IT(prev)->fi->to.h;
7221 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_ADD)
7223 prev = (Elm_Gen_Item *)_elm_genlist_fx_item_prev_get((Elm_Object_Item *)fi->it);
7224 if ((prev) && (prev->realized) && (GL_IT(prev)->fi))
7226 fi->from.y = GL_IT(prev)->fi->from.y + GL_IT(prev)->fi->from.h;
7230 if (sd->realized_top_item)
7233 if (fi->num <= sd->realized_top_item->item->num)
7234 fi->from.y -= max_mv_dist;
7236 fi->from.y += max_mv_dist;
7242 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7244 if ((GL_IT(fi->it)->items) && (GL_IT(fi->it)->expanded_depth == 0))
7246 #if GENLIST_PINCH_ZOOM_SUPPORT
7247 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
7249 fi->from.y = oy + GL_IT(fi->it)->pan_scrl_y - sd->pinch_pan_y;
7252 if (fi->type == ELM_GEN_ITEM_FX_TYPE_DEL)
7254 if (sd->realized_top_item)
7256 if (fi->num <= sd->realized_top_item->item->num)
7257 fi->to.y = oy - fi->from.h;
7268 static Elm_Gen_FX_Item *
7269 _fx_cover_item_get(const Elm_Gen_FX_Item *fi)
7271 Elm_Gen_FX_Item *cover_fi;
7273 if (!fi) return NULL;
7275 Elm_Genlist_Smart_Data *sd = GL_IT(fi->it)->wsd;
7276 Evas_Coord ox, oy, ow, oh;
7277 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7279 EINA_LIST_FOREACH(sd->fx_items, l, cover_fi)
7281 if (fi == cover_fi) continue;
7282 if (sd->fx_items_deleted)
7284 if ((cover_fi->from.y >= oy+oh || cover_fi->from.y > fi->to.y) && (cover_fi->from.y - cover_fi->to.y > 0))
7289 if ((cover_fi->to.y > fi->to.y) && (cover_fi->from.y - cover_fi->to.y < 0))
7297 _item_fx_op(Elm_Transit_Effect *data, Elm_Transit *transit __UNUSED__, double progress __UNUSED__)
7299 Elm_Gen_FX_Item *fi = data, *cover_it;
7300 Elm_Genlist_Smart_Data *sd = GL_IT(fi->it)->wsd;
7301 Evas_Coord fi_ox, fi_oy, cover_it_ox, cover_it_oy, ox, oy, ow, oh;
7303 evas_object_show(VIEW(fi->it));
7304 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7305 evas_object_geometry_get(fi->proxy, &fi_ox, &fi_oy, NULL, NULL);
7306 evas_object_move(fi->proxy, ox, fi_oy);
7307 evas_object_show(fi->proxy);
7308 #if GENLIST_PINCH_ZOOM_SUPPORT
7309 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(fi->it))) evas_object_raise(fi->proxy);
7312 if ((!sd->expanded_next_item) || (sd->expanded_next_item == fi->it)) goto raise_event_block;
7313 if (fi->type == ELM_GEN_ITEM_FX_TYPE_SAME) goto raise_event_block;
7315 // find the closest item that cover current item when deleting
7316 cover_it = _fx_cover_item_get(fi);
7319 evas_object_geometry_get(cover_it->proxy, &cover_it_ox, &cover_it_oy, NULL, NULL);
7321 if (sd->fx_items_deleted)
7324 && (fi_oy + fi->to.h >= cover_it_oy + cover_it->to.h ) && (fi->from.y < cover_it->from.y))
7325 evas_object_hide(fi->proxy);
7327 else if (cover_it_oy && (fi_oy >= cover_it_oy))
7328 evas_object_hide(fi->proxy);
7330 evas_object_show(fi->proxy);
7334 evas_object_raise(sd->alpha_bg);
7341 _item_fx_done(Elm_Transit_Effect *data, Elm_Transit *transit __UNUSED__)
7343 Elm_Gen_FX_Item *fx_done_it = data;
7344 Elm_Genlist_Smart_Data *sd = GL_IT(fx_done_it->it)->wsd;
7346 if ((!fx_done_it) || (!fx_done_it->it) || (!sd)) return;
7348 evas_object_image_source_visible_set(fx_done_it->proxy, EINA_TRUE);
7349 evas_object_lower(fx_done_it->proxy);
7351 if ((sd->decorate_all_mode) && (fx_done_it->it->deco_all_view))
7352 evas_object_move(fx_done_it->it->deco_all_view, fx_done_it->to.x, fx_done_it->to.y);
7354 evas_object_move(VIEW(fx_done_it->it), fx_done_it->to.x, fx_done_it->to.y);
7355 GL_IT(fx_done_it->it)->has_proxy_it = EINA_FALSE;
7357 evas_object_clip_unset(fx_done_it->proxy);
7361 _item_fx_del_cb(void *data, Elm_Transit *transit __UNUSED__)
7363 Elm_Gen_FX_Item *fx_done_it = data;
7364 Elm_Gen_Item *it = NULL;
7365 Proxy_Item *pi = NULL;
7367 Elm_Genlist_Smart_Data *sd = GL_IT(fx_done_it->it)->wsd;
7369 if ((!fx_done_it) || (!fx_done_it->it) || (!sd)) return;
7371 sd->fx_items = eina_list_remove(sd->fx_items, fx_done_it);
7372 GL_IT(fx_done_it->it)->fi = NULL;
7375 if (!eina_list_count(sd->fx_items))
7377 EINA_LIST_FREE (sd->pending_unrealized_items, it)
7379 if (GL_IT(it)) GL_IT(it)->has_proxy_it = EINA_FALSE;
7380 #if GENLIST_PINCH_ZOOM_SUPPORT
7381 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7383 _item_unrealize(it, EINA_FALSE);
7385 EINA_LIST_FREE (sd->pending_unrealized_decorate_all_items, it)
7387 if (GL_IT(it)) GL_IT(it)->has_proxy_it = EINA_FALSE;
7388 #if GENLIST_PINCH_ZOOM_SUPPORT
7389 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7391 _decorate_all_item_unrealize(it);
7394 EINA_LIST_FREE (sd->pending_del_items, it)
7397 _elm_widget_item_free((Elm_Widget_Item *)it);
7400 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
7401 evas_object_hide(pi->proxy);
7402 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
7403 evas_object_hide(pi->proxy);
7405 sd->fx_playing = EINA_FALSE;
7406 sd->sorting = EINA_FALSE;
7407 sd->fx_first_captured = EINA_FALSE;
7408 evas_object_hide(sd->alpha_bg);
7410 sd->realized_top_item = NULL;
7411 sd->pan_changed = EINA_TRUE;
7412 evas_object_smart_changed(sd->pan_obj);
7417 _sorting_effect_animator_cb(void *data)
7419 Elm_Genlist_Smart_Data *sd = data;
7420 Elm_Gen_FX_Item *fi;
7423 Evas_Coord ox, oy, ow, oh;
7424 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7426 sd->fx_timer = NULL;
7427 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7431 fi->changed = EINA_TRUE;
7432 evas_object_resize(fi->proxy, ow, fi->to.h);
7434 fi->trans = elm_transit_add();
7435 elm_transit_object_add(fi->trans, fi->proxy);
7436 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7437 elm_transit_tween_mode_set(fi->trans, ELM_TRANSIT_TWEEN_MODE_DECELERATE);
7439 elm_transit_effect_translation_add(fi->trans, fi->to.x, fi->to.y - 30 * elm_config_scale_get(), fi->to.x, fi->to.y);
7440 elm_transit_effect_color_add(fi->trans,0, 0, 0, 0, 255,255,255,255);
7442 elm_transit_effect_add(fi->trans, _item_fx_op, fi, _item_fx_done);
7443 elm_transit_del_cb_set(fi->trans, _item_fx_del_cb, fi);
7444 elm_transit_duration_set(fi->trans,0.3);
7445 elm_transit_objects_final_state_keep_set(fi->trans, EINA_FALSE);
7446 elm_transit_go(fi->trans);
7448 return ECORE_CALLBACK_RENEW;
7451 return ECORE_CALLBACK_CANCEL;
7455 _elm_genlist_fx_play(Evas_Object *obj)
7457 ELM_GENLIST_CHECK(obj);
7458 ELM_GENLIST_DATA_GET(obj, sd);
7460 Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh;
7461 Elm_Gen_FX_Item *fi;
7464 if (!sd->fx_mode) return;
7466 EINA_LIST_FREE(sd->fx_items, fi)
7468 if (fi->trans) elm_transit_del(fi->trans);
7471 _item_cache_all_free(sd);
7473 _elm_genlist_fx_items_make(obj);
7474 if (!eina_list_count(sd->fx_items) || (sd->queue))
7476 _elm_genlist_fx_clear(obj, EINA_TRUE);
7480 sd->fx_playing = EINA_TRUE;
7482 if (!sd->alpha_bg) sd->alpha_bg = _tray_alpha_bg_create(obj);
7483 evas_object_show(sd->alpha_bg);
7485 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7486 evas_output_viewport_get(evas_object_evas_get(obj), &cvx, &cvy, &cvw, &cvh);
7490 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7491 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7492 if (sd->fx_timer) ecore_timer_del(sd->fx_timer);
7493 sd->fx_timer = ecore_timer_add(0.05, _sorting_effect_animator_cb, sd);
7497 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7499 if (!fi->proxy) continue;
7501 if ((fi->from.y <= oy) || (fi->from.y + fi->from.h >= oy + oh))
7503 if ((sd->decorate_all_mode) && (fi->it->deco_all_view))
7504 evas_object_move(fi->it->deco_all_view, cvx, fi->to.y);
7506 evas_object_move(VIEW(fi->it), cvx, fi->to.y);
7508 else if ((fi->to.y <= oy) || (fi->to.y + fi->to.h >= oy + oh))
7510 if ((sd->decorate_all_mode) && (fi->it->deco_all_view))
7511 evas_object_move(fi->it->deco_all_view, cvx, fi->from.y);
7513 evas_object_move(VIEW(fi->it), cvx, fi->from.y);
7516 evas_object_resize(fi->proxy, ow, fi->to.h);
7517 evas_object_show(fi->proxy);
7519 fi->trans = elm_transit_add();
7520 elm_transit_object_add(fi->trans, fi->proxy);
7522 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7523 elm_transit_tween_mode_set(fi->trans, ELM_TRANSIT_TWEEN_MODE_DECELERATE);
7525 if (fi->type == ELM_GEN_ITEM_FX_TYPE_SAME)
7527 evas_object_raise(fi->proxy);
7528 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7531 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_ADD)
7533 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7534 elm_transit_effect_color_add(fi->trans, 0, 0, 0, 0, 255, 255, 255, 255);
7536 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_DEL)
7538 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7539 elm_transit_effect_color_add(fi->trans, 255, 255, 255, 255, 0, 0, 0, 0);
7541 elm_transit_effect_add(fi->trans, _item_fx_op, fi, _item_fx_done);
7542 elm_transit_del_cb_set(fi->trans, _item_fx_del_cb, fi);
7544 elm_transit_duration_set(fi->trans, FX_MOVE_TIME);
7545 elm_transit_objects_final_state_keep_set(fi->trans, EINA_FALSE);
7546 elm_transit_go(fi->trans);
7551 #if GENLIST_PINCH_ZOOM_SUPPORT
7553 elm_genlist_pinch_zoom_mode_set(Evas_Object *obj, Elm_Gen_Pinch_Zoom_Mode mode)
7555 ELM_GENLIST_DATA_GET(obj, sd);
7560 Eina_Bool done = EINA_FALSE;
7562 if ((sd->queue) || (!sd->rendered) || (sd->queue_idle_enterer)) return EINA_FALSE;
7564 EINA_INLIST_FOREACH(sd->blocks, itb)
7566 EINA_LIST_FOREACH(itb->items, l, it)
7569 if (IS_ROOT_PARENT_IT(it))
7577 if (!done) return EINA_FALSE;
7579 sd->pinch_zoom_mode = mode;
7581 _item_cache_all_free(sd);
7582 _elm_genlist_fx_capture(obj, 0);
7584 sd->pinch_pan_y = sd->pan_y;
7586 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
7587 sd->s_iface->content_region_show(obj, 0,0,0,0);
7589 sd->pan_changed = EINA_TRUE;
7590 evas_object_smart_changed(sd->pan_obj);
7597 eina_list_sort_merge(Eina_List *a, Eina_List *b, Eina_Compare_Cb func)
7599 Eina_List *first, *last;
7601 if (func(a->data, b->data) > 0)
7603 _item_move_after(a->data, b->data);
7604 a = (last = first = a)->next;
7608 b = (last = first = b)->next;
7611 if (func(a->data, b->data) > 0)
7613 _item_move_after(a->data, b->data);
7614 a = (last = last->next = a)->next;
7617 b = (last = last->next = b)->next;
7619 last->next = a ? a : b;
7625 elm_genlist_sort(Evas_Object *obj, Eina_Compare_Cb func)
7627 ELM_GENLIST_CHECK(obj) NULL;
7628 ELM_GENLIST_DATA_GET(obj, sd);
7629 Eina_List *list = NULL;
7630 Elm_Gen_Item *it, *next;
7631 unsigned int limit = 0, i = 0, n = 0;
7632 Eina_List *tail = NULL, *unsort = NULL, *stack[32], *prev = NULL;
7634 sd->sorting = EINA_TRUE;
7636 it = (Elm_Gen_Item*)elm_genlist_first_item_get(obj);
7639 list = eina_list_append(list, it);
7640 next = (Elm_Gen_Item*)elm_genlist_item_next_get((Elm_Object_Item *)it);
7648 limit = eina_list_count(list);
7652 (limit > list->accounting->count))
7653 limit = list->accounting->count;
7655 if (limit != list->accounting->count)
7657 unsort = eina_list_nth_list(list, limit);
7659 unsort->prev->next = NULL;
7664 unsigned int idx, tmp;
7666 Eina_List *a = tail;
7667 Eina_List *b = tail->next;
7677 if (func(a->data, b->data) > 0)
7678 ((stack[i++] = a)->next = b)->next = 0;
7680 ((stack[i++] = b)->next = a)->next = 0;
7683 for (idx = n ^ tmp; idx &= idx - 1; i--)
7684 stack[i - 2] = eina_list_sort_merge(stack[i - 2], stack[i - 1], func);
7688 stack[i - 1] = eina_list_sort_merge(stack[i - 1], stack[i], func);
7692 for (; stack[0]; stack[0] = stack[0]->next)
7694 stack[0]->prev = prev;
7701 tail->next = unsort;
7702 unsort->prev = tail;
7705 list->accounting->last = tail;
7707 if (!sd->fx_mode) sd->sorting = EINA_FALSE;
7708 if (sd->decorate_all_mode) sd->sorting = EINA_FALSE;
7709 sd->s_iface->content_region_show(obj, 0,0,0,0);
7710 sd->pan_changed = EINA_TRUE;
7711 evas_object_smart_changed(sd->pan_obj);