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, Item_Cache *ic);
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);
152 #if GENLIST_FX_SUPPORT
153 static Eina_Bool _elm_genlist_fx_capture(Evas_Object *obj, int level);
154 static void _elm_genlist_fx_play(Evas_Object *obj);
155 static void _elm_genlist_fx_clear(Evas_Object *obj);
156 static void _elm_genlist_proxy_item_del(const Elm_Object_Item *item);
159 #if GENLIST_PINCH_ZOOM_SUPPORT
160 EAPI Eina_Bool elm_genlist_pinch_zoom_mode_set(Evas_Object *obj, Elm_Gen_Pinch_Zoom_Mode mode);
164 _item_cache_all_free(Elm_Genlist_Smart_Data *sd)
166 // It would be better not to use
167 // EINA_INLIST_FOREACH or EINA_INLIST_FOREACH_SAFE
168 while (sd->item_cache)
170 Item_Cache *ic = EINA_INLIST_CONTAINER_GET(sd->item_cache->last, Item_Cache);
171 if (ic->spacer) evas_object_del(ic->spacer);
172 if (ic->base_view) evas_object_del(ic->base_view);
173 if (ic->item_style) eina_stringshare_del(ic->item_style);
174 sd->item_cache = eina_inlist_remove(sd->item_cache, EINA_INLIST_GET(ic));
175 // Free should be performed after inlist is poped
178 sd->item_cache = NULL;
179 sd->item_cache_count = 0;
183 _item_cache_push(Elm_Gen_Item *it)
185 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
186 Item_Cache *ic = NULL;
188 if (sd->item_cache_count >= sd->item_cache_max)
190 ic = EINA_INLIST_CONTAINER_GET(sd->item_cache->last, Item_Cache);
191 if (ic->spacer) evas_object_del(ic->spacer);
192 if (ic->base_view) evas_object_del(ic->base_view);
193 eina_stringshare_del(ic->item_style);
194 sd->item_cache = eina_inlist_remove(sd->item_cache,
195 sd->item_cache->last);
196 sd->item_cache_count--;
197 // Free should be performed after inlist is poped
200 //evas_event_freeze(evas_object_evas_get(obj));
202 edje_object_mirrored_set(VIEW(it),
203 elm_widget_mirrored_get(WIDGET(it)));
204 edje_object_scale_set(VIEW(it),
205 elm_widget_scale_get(WIDGET(it))
206 * elm_config_scale_get());
208 // FIXME: other callbacks?
209 edje_object_signal_callback_del_full(VIEW(it), "elm,action,expand,toggle",
210 "elm", _expand_toggle_signal_cb, it);
211 edje_object_signal_callback_del_full(VIEW(it), "elm,action,expand", "elm",
212 _expand_signal_cb, it);
213 edje_object_signal_callback_del_full(VIEW(it), "elm,action,contract", "elm",
214 _contract_signal_cb, it);
215 _item_mouse_callbacks_del(it, VIEW(it));
217 #if GENLIST_FX_SUPPORT
218 if ((it->item->nocache_once) || (it->item->nocache) || (sd->pending_del_items))
220 if ((it->item->nocache_once) || (it->item->nocache))
223 if (VIEW(it)) evas_object_del(VIEW(it));
224 if (it->spacer) evas_object_del(it->spacer);
227 ic = ELM_NEW(Item_Cache);
230 if (VIEW(it)) evas_object_del(VIEW(it));
231 if (it->spacer) evas_object_del(it->spacer);
236 ecore_timer_del(it->long_timer);
237 it->long_timer = NULL;
239 if (it->item->swipe_timer)
241 ecore_timer_del(it->item->swipe_timer);
242 it->item->swipe_timer = NULL;
245 ic->base_view = VIEW(it);
246 ic->spacer = it->spacer;
247 ic->item_style = eina_stringshare_add(it->itc->item_style);
248 if (it->item->type & ELM_GENLIST_ITEM_TREE) ic->tree = 1;
250 ic->selected = it->selected;
251 ic->disabled = elm_widget_item_disabled_get(it);
252 ic->expanded = it->item->expanded;
253 if (it->item->type & ELM_GENLIST_ITEM_TREE) ic->tree = 1;
255 edje_object_signal_emit(ic->base_view, "elm,state,unselected", "elm");
256 evas_object_hide(ic->base_view);
258 sd->item_cache = eina_inlist_prepend(sd->item_cache, EINA_INLIST_GET(ic));
259 sd->item_cache_count++;
265 it->realized = EINA_FALSE;
266 it->want_unrealize = EINA_FALSE;
268 //evas_event_thaw(evas_object_evas_get(obj));
269 //evas_event_thaw_eval(evas_object_evas_get(obj));
273 _item_cache_pop(Elm_Gen_Item *it)
275 Item_Cache *ic = NULL;
278 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
280 if (it->item->nocache_once) {
281 it->item->nocache_once = EINA_FALSE;
284 if (it->item->nocache) return EINA_FALSE;
286 if (it->item->type & ELM_GENLIST_ITEM_TREE) tree = 1;
287 EINA_INLIST_FOREACH_SAFE(sd->item_cache, l, ic)
289 if ((ic->selected) || (ic->disabled) || (ic->expanded))
292 if ((ic->tree == tree) &&
293 (((!it->itc->item_style) && (!ic->item_style)) ||
294 (it->itc->item_style && ic->item_style &&
295 (!strcmp(it->itc->item_style, ic->item_style)))))
298 eina_inlist_remove(sd->item_cache, EINA_INLIST_GET(ic));
299 sd->item_cache_count--;
301 VIEW(it) = ic->base_view;
302 it->spacer = ic->spacer;
304 #if 1 // FIXME: different from upstream
305 // Because of item cache, set state as default after cache item
307 edje_object_signal_emit(VIEW(it),"elm,state,default", "elm");
309 edje_object_signal_callback_add
310 (VIEW(it), "elm,action,expand,toggle", "elm",
311 _expand_toggle_signal_cb, it);
312 edje_object_signal_callback_add
313 (VIEW(it), "elm,action,expand", "elm", _expand_signal_cb, it);
314 edje_object_signal_callback_add
315 (VIEW(it), "elm,action,contract", "elm", _contract_signal_cb, it);
316 _item_mouse_callbacks_add(it, VIEW(it));
318 eina_stringshare_del(ic->item_style);
328 _elm_genlist_pan_smart_pos_set(Evas_Object *obj,
334 ELM_GENLIST_PAN_DATA_GET(obj, psd);
336 if ((x == psd->wsd->pan_x) && (y == psd->wsd->pan_y)) return;
340 EINA_INLIST_FOREACH(psd->wsd->blocks, itb)
342 if ((itb->y + itb->h) > y)
347 EINA_LIST_FOREACH(itb->items, l2, it)
349 if ((itb->y + it->y) >= y)
351 psd->wsd->anchor_item = it;
352 psd->wsd->anchor_y = -(itb->y + it->y - y);
359 if (!psd->wsd->reorder_move_animator) evas_object_smart_changed(obj);
363 _elm_genlist_pan_smart_pos_get(const Evas_Object *obj,
367 ELM_GENLIST_PAN_DATA_GET(obj, psd);
369 if (x) *x = psd->wsd->pan_x;
370 if (y) *y = psd->wsd->pan_y;
374 _elm_genlist_pan_smart_pos_max_get(const Evas_Object *obj,
380 ELM_GENLIST_PAN_DATA_GET(obj, psd);
382 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
383 ow = psd->wsd->minw - ow;
385 oh = psd->wsd->minh - oh;
390 #if GENLIST_PINCH_ZOOM_SUPPORT
391 if (psd->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
393 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
394 if (psd->wsd->pinch_zoom_h > oh)
395 *y = psd->wsd->pinch_zoom_h - oh;
402 _elm_genlist_pan_smart_pos_min_get(const Evas_Object *obj __UNUSED__,
411 _elm_genlist_pan_smart_content_size_get(const Evas_Object *obj,
415 ELM_GENLIST_PAN_DATA_GET(obj, psd);
417 if (w) *w = psd->wsd->minw;
418 if (h) *h = psd->wsd->minh;
422 _elm_genlist_pan_smart_add(Evas_Object *obj)
424 /* here just to allocate our extended data */
425 EVAS_SMART_DATA_ALLOC(obj, Elm_Genlist_Pan_Smart_Data);
427 ELM_PAN_CLASS(_elm_genlist_pan_parent_sc)->base.add(obj);
431 _elm_genlist_pan_smart_del(Evas_Object *obj)
433 ELM_GENLIST_PAN_DATA_GET(obj, psd);
437 ecore_job_del(psd->resize_job);
438 psd->resize_job = NULL;
441 _elm_genlist_pan_parent_sc->base.del(obj);
445 _elm_genlist_pan_smart_move(Evas_Object *obj,
446 Evas_Coord x __UNUSED__,
447 Evas_Coord y __UNUSED__)
449 ELM_GENLIST_PAN_DATA_GET(obj, psd);
451 psd->wsd->pan_changed = EINA_TRUE;
452 evas_object_smart_changed(obj);
453 if (psd->wsd->calc_job) ecore_job_del(psd->wsd->calc_job);
454 psd->wsd->calc_job = NULL;
458 _elm_genlist_pan_smart_resize_job(void *data)
460 Elm_Genlist_Pan_Smart_Data *psd = data;
462 elm_layout_sizing_eval(ELM_WIDGET_DATA(psd->wsd)->obj);
463 psd->resize_job = NULL;
467 _elm_genlist_pan_smart_resize(Evas_Object *obj,
473 ELM_GENLIST_PAN_DATA_GET(obj, psd);
475 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
476 if ((ow == w) && (oh == h)) return;
477 if ((psd->wsd->mode == ELM_LIST_COMPRESS) && (ow != w))
480 if (psd->resize_job) ecore_job_del(psd->resize_job);
482 ecore_job_add(_elm_genlist_pan_smart_resize_job, psd);
484 psd->wsd->pan_changed = EINA_TRUE;
485 evas_object_smart_changed(obj);
486 if (psd->wsd->calc_job) ecore_job_del(psd->wsd->calc_job);
487 // if the widht changed we may have to resize content if scrollbar went
488 // away or appesared to queue a job to deal with it. it should settle in
489 // the end to a steady-state
491 psd->wsd->calc_job = ecore_job_add(_calc_job, psd->wsd);
493 psd->wsd->calc_job = NULL;
497 _item_scroll(Elm_Genlist_Smart_Data *sd)
500 Elm_Gen_Item *it = NULL;
501 Evas_Coord ow, oh, dx = 0, dy = 0, dw = 0, dh = 0;
503 if (!sd->show_item) return;
505 evas_object_geometry_get(sd->pan_obj, NULL, NULL, &ow, &oh);
507 dx = it->x + it->item->block->x;
508 dy = it->y + it->item->block->y;
509 dw = it->item->block->w;
512 switch (sd->scroll_to_type)
514 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
515 if (it->item->group_item) gith = it->item->group_item->item->h;
519 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
520 dy += ((it->item->h / 2) - (oh / 2));
523 case ELM_GENLIST_ITEM_SCROLLTO_IN:
525 if ((sd->expanded_item) &&
526 ((sd->show_item->y + sd->show_item->item->block->y
527 + sd->show_item->item->h) -
528 (sd->expanded_item->y + sd->expanded_item->item->block->y) > oh))
530 it = sd->expanded_item;
531 if (it->item->group_item) gith = it->item->group_item->item->h;
532 dx = it->x + it->item->block->x;
533 dy = it->y + it->item->block->y - gith;
534 dw = it->item->block->w;
538 if ((it->item->group_item) &&
539 (sd->pan_y > (it->y + it->item->block->y)))
540 gith = it->item->group_item->item->h;
547 sd->s_iface->region_bring_in(ELM_WIDGET_DATA(sd)->obj, dx, dy, dw, dh);
549 sd->s_iface->content_region_show
550 (ELM_WIDGET_DATA(sd)->obj, dx, dy, dw, dh);
552 it->item->show_me = EINA_FALSE;
553 sd->show_item = NULL;
554 sd->auto_scroll_enabled = EINA_FALSE;
555 sd->check_scroll = EINA_FALSE;
559 _item_unrealize(Elm_Gen_Item *it,
562 Evas_Object *content;
566 if (!it->realized) return;
567 if (GL_IT(it)->wsd->reorder_it == it) return;
569 #if GENLIST_FX_SUPPORT
570 if ((GL_IT(it)->has_proxy_it) && (!GL_IT(it)->wsd->genlist_clearing))
572 if (!eina_list_data_find(GL_IT(it)->wsd->pending_unrealized_items, it))
573 GL_IT(it)->wsd->pending_unrealized_items =
574 eina_list_append(GL_IT(it)->wsd->pending_unrealized_items, it);
578 #if GENLIST_ENTRY_SUPPORT
579 if (it->item->unrealize_disabled)
581 evas_object_hide(VIEW(it));
586 //evas_event_freeze(evas_object_evas_get(WIDGET(it)));
588 evas_object_smart_callback_call(WIDGET(it), SIG_UNREALIZED, it);
591 ecore_timer_del(it->long_timer);
592 it->long_timer = NULL;
594 if (it->item->swipe_timer)
596 ecore_timer_del(it->item->swipe_timer);
597 it->item->swipe_timer = NULL;
601 EINA_LIST_FOREACH(it->texts, l, part)
602 edje_object_part_text_set(VIEW(it), part, NULL);
604 elm_widget_stringlist_free(it->texts);
606 elm_widget_stringlist_free(it->contents);
608 elm_widget_stringlist_free(it->states);
610 EINA_LIST_FREE(it->content_objs, content)
612 // FIXME: If parent-child relationship was broken before 'ic'
613 // is deleted, freeze_pop will not be called. ex) elm_slider
614 // If layout is used instead of edje, this problme can be
616 if (0 != elm_widget_scroll_freeze_get(content))
617 elm_widget_scroll_freeze_pop(content);
618 evas_object_del(content);
622 elm_widget_stringlist_free(it->item->flip_contents);
623 it->item->flip_contents = NULL;
624 EINA_LIST_FREE(it->item->flip_content_objs, content)
625 evas_object_del(content);
628 if (_elm_config->access_mode == ELM_ACCESS_MODE_ON)
629 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
631 // unswallow VIEW(it) first then manipulate VIEW(it)
632 _decorate_item_unrealize(it);
633 _decorate_all_item_unrealize(it);
635 it->realized = EINA_FALSE;
636 _item_cache_push(it);
638 #if GENLIST_ENTRY_SUPPORT
639 it->item->unrealize_disabled = EINA_FALSE;
641 it->want_unrealize = EINA_FALSE;
643 //evas_event_thaw(evas_object_evas_get(WIDGET(it)));
644 //evas_event_thaw_eval(evas_object_evas_get(WIDGET(it)));
648 _item_block_unrealize(Item_Block *itb)
652 Eina_Bool dragging = EINA_FALSE;
654 if (!itb->realized) return;
655 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
657 EINA_LIST_FOREACH(itb->items, l, it)
659 if (itb->must_recalc || !it->group)
663 dragging = EINA_TRUE;
664 it->want_unrealize = EINA_TRUE;
667 _item_unrealize(it, EINA_FALSE);
672 itb->realized = EINA_FALSE;
673 itb->want_unrealize = EINA_TRUE;
676 itb->want_unrealize = EINA_FALSE;
677 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
678 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
682 _must_recalc_idler(void *data)
684 Elm_Genlist_Smart_Data *sd = data;
686 if (sd->calc_job) ecore_job_del(sd->calc_job);
687 sd->calc_job = ecore_job_add(_calc_job, sd);
688 sd->must_recalc_idler = NULL;
689 return ECORE_CALLBACK_CANCEL;
693 _calc_job(void *data)
696 Item_Block *itb, *chb = NULL;
697 Evas_Coord pan_w = 0, pan_h = 0;
698 Elm_Genlist_Smart_Data *sd = data;
699 Eina_Bool minw_change = EINA_FALSE;
700 Eina_Bool did_must_recalc = EINA_FALSE;
701 Evas_Coord minw = -1, minh = 0, y = 0, ow, dy = 0, vw = 0;
703 evas_object_geometry_get(sd->pan_obj, NULL, NULL, &ow, &sd->h);
704 if (sd->mode == ELM_LIST_COMPRESS)
705 sd->s_iface->content_viewport_size_get(ELM_WIDGET_DATA(sd)->obj, &vw, NULL);
707 if (sd->w != ow) sd->w = ow;
709 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
710 EINA_INLIST_FOREACH(sd->blocks, itb)
712 Eina_Bool show_me = EINA_FALSE;
715 show_me = itb->show_me;
716 itb->show_me = EINA_FALSE;
719 if (itb->realized) _item_block_unrealize(itb);
721 if ((itb->changed) || ((itb->must_recalc) && (!did_must_recalc)))
723 if (itb->must_recalc)
728 EINA_LIST_FOREACH(itb->items, l, it)
729 if (it->item->mincalcd) it->item->mincalcd = EINA_FALSE;
730 itb->changed = EINA_TRUE;
731 did_must_recalc = EINA_TRUE;
732 if (itb->realized) _item_block_unrealize(itb);
733 itb->must_recalc = EINA_FALSE;
735 show_me = _item_block_recalc(itb, in, EINA_FALSE);
741 if (minw == -1) minw = itb->minw;
742 else if ((!itb->must_recalc) && (minw < itb->minw))
745 minw_change = EINA_TRUE;
747 if ((sd->mode == ELM_LIST_COMPRESS) && (minw > vw))
750 minw_change = EINA_TRUE;
756 if ((show_me) && (sd->show_item) && (!sd->show_item->item->queued))
757 sd->check_scroll = EINA_TRUE;
761 EINA_INLIST_FOREACH(sd->blocks, itb)
767 if ((chb) && (EINA_INLIST_GET(chb)->next))
769 EINA_INLIST_FOREACH(EINA_INLIST_GET(chb)->next, itb)
771 if (itb->realized) _item_block_unrealize(itb);
775 if (minw < sd->w) minw = sd->w;
776 if ((minw != sd->minw) || (minh != sd->minh))
780 evas_object_smart_callback_call(sd->pan_obj, "changed", NULL);
781 elm_layout_sizing_eval(ELM_WIDGET_DATA(sd)->obj);
788 if ((sd->anchor_item) && (sd->anchor_item->item->block)
789 && (!sd->auto_scroll_enabled))
794 it = sd->anchor_item;
796 sd->s_iface->content_pos_set
797 (ELM_WIDGET_DATA(sd)->obj, sd->pan_x, it->item->block->y
798 + it->y + it_y, EINA_TRUE);
799 sd->anchor_item = it;
805 if (!sd->must_recalc_idler)
806 sd->must_recalc_idler = ecore_idler_add(_must_recalc_idler, sd);
808 if (sd->check_scroll)
810 _elm_genlist_pan_smart_content_size_get(sd->pan_obj, &pan_w, &pan_h);
811 if (EINA_INLIST_GET(sd->show_item) == sd->items->last)
812 sd->scroll_to_type = ELM_GENLIST_ITEM_SCROLLTO_IN;
814 switch (sd->scroll_to_type)
816 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
820 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
824 case ELM_GENLIST_ITEM_SCROLLTO_IN:
829 if ((sd->show_item) && (sd->show_item->item->block))
831 if ((pan_w > (sd->show_item->x + sd->show_item->item->block->x))
832 && (pan_h > (sd->show_item->y + sd->show_item->item->block->y
841 evas_object_smart_changed(sd->pan_obj);
842 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
843 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
847 _elm_genlist_smart_sizing_eval(Evas_Object *obj)
849 Evas_Coord minw = -1, minh = -1, maxw = -1, maxh = -1;
850 Evas_Coord vmw = 0, vmh = 0;
852 ELM_GENLIST_DATA_GET(obj, sd);
854 /* parent class' early call */
855 if (!sd->s_iface) return;
857 if (sd->on_sub_del) return;;
859 evas_object_size_hint_min_get(obj, &minw, NULL);
860 evas_object_size_hint_max_get(obj, &maxw, &maxh);
862 edje_object_size_min_calc(ELM_WIDGET_DATA(sd)->resize_obj, &vmw, &vmh);
864 if (sd->mode == ELM_LIST_COMPRESS)
868 sd->s_iface->content_viewport_size_get(obj, &vw, &vh);
869 if ((vw != 0) && (vw != sd->prev_viewport_w))
873 sd->prev_viewport_w = vw;
875 EINA_INLIST_FOREACH(sd->blocks, itb)
877 itb->must_recalc = EINA_TRUE;
879 if (sd->calc_job) ecore_job_del(sd->calc_job);
880 sd->calc_job = ecore_job_add(_calc_job, sd);
885 else if (sd->mode == ELM_LIST_LIMIT)
888 minw = vmw + sd->realminw;
896 evas_object_size_hint_min_set(obj, minw, minh);
897 evas_object_size_hint_max_set(obj, maxw, maxh);
901 _item_position(Elm_Gen_Item *it,
909 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
910 evas_object_resize(view, it->item->w, it->item->h);
911 evas_object_move(view, it_x, it_y);
912 evas_object_show(view);
913 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
914 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
918 _item_sub_items_clear(Elm_Gen_Item *it)
921 Elm_Object_Item *it2;
923 // FIXME: this can be removed after tree effect is remove in the upstream
924 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it);
926 EINA_LIST_FOREACH_SAFE(it->item->items, l, ll, it2)
927 elm_widget_item_del(it2);
931 _item_auto_scroll(Elm_Genlist_Smart_Data *sd)
933 Elm_Gen_Item *tmp_item = NULL;
935 #if GENLIST_FX_SUPPORT
936 if (sd->fx_first_captured) return;
938 if ((sd->expanded_item) && (sd->auto_scroll_enabled))
940 tmp_item = eina_list_data_get
941 (eina_list_last(sd->expanded_item->item->items));
942 if (!tmp_item) return;
943 sd->show_item = tmp_item;
944 sd->bring_in = EINA_TRUE;
945 sd->scroll_to_type = ELM_GENLIST_ITEM_SCROLLTO_IN;
946 if ((sd->show_item->item->queued) || (!sd->show_item->item->mincalcd))
948 sd->show_item->item->show_me = EINA_TRUE;
949 sd->auto_scroll_enabled = EINA_FALSE;
957 _elm_genlist_item_odd_even_update(Elm_Gen_Item *it)
959 if (!it->item->nostacking)
961 if ((it->item->order_num_in & 0x1) ^ it->item->stacking_even)
963 if (it->deco_all_view) evas_object_lower(it->deco_all_view);
964 else evas_object_lower(VIEW(it));
968 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
969 else evas_object_raise(VIEW(it));
973 if (it->item->order_num_in & 0x1)
975 edje_object_signal_emit(VIEW(it), "elm,state,odd", "elm");
976 if (it->deco_all_view)
977 edje_object_signal_emit(it->deco_all_view, "elm,state,odd", "elm");
981 edje_object_signal_emit(VIEW(it), "elm,state,even", "elm");
982 if (it->deco_all_view)
983 edje_object_signal_emit(it->deco_all_view, "elm,state,even", "elm");
988 _item_order_update(const Eina_Inlist *l,
991 Elm_Gen_Item *it, *it2;
993 for (it = ELM_GEN_ITEM_FROM_INLIST(l); l; l = l->next,
994 it = ELM_GEN_ITEM_FROM_INLIST(l))
996 it->item->order_num_in = start++;
997 _elm_genlist_item_odd_even_update(it);
998 it2 = ELM_GEN_ITEM_FROM_INLIST(l->next);
999 if (it2 && (it->item->order_num_in != it2->item->order_num_in))
1005 _elm_genlist_item_state_update(Elm_Gen_Item *it,
1010 if (it->selected != itc->selected)
1014 if (it->deco_all_view)
1015 edje_object_signal_emit
1016 (it->deco_all_view, "elm,state,selected", "elm,nosound");
1017 edje_object_signal_emit
1018 (VIEW(it), "elm,state,selected", "elm,nosound");
1019 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
1022 if (elm_widget_item_disabled_get(it) != itc->disabled)
1024 if (elm_widget_item_disabled_get(it))
1025 edje_object_signal_emit(VIEW(it), "elm,state,disabled", "elm");
1026 if (it->deco_all_view)
1027 edje_object_signal_emit
1028 (it->deco_all_view, "elm,state,disabled", "elm");
1030 if (it->item->expanded != itc->expanded)
1032 if (it->item->expanded)
1033 edje_object_signal_emit(VIEW(it), "elm,state,expanded", "elm");
1034 if (it->deco_all_view)
1035 edje_object_signal_emit
1036 (it->deco_all_view, "elm,state,expanded", "elm");
1043 if (it->deco_all_view)
1044 edje_object_signal_emit
1045 (it->deco_all_view, "elm,state,selected", "elm,nosound");
1046 edje_object_signal_emit
1047 (VIEW(it), "elm,state,selected", "elm,nosound");
1048 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
1050 if (elm_widget_item_disabled_get(it))
1052 edje_object_signal_emit(VIEW(it), "elm,state,disabled", "elm");
1053 if (it->deco_all_view)
1054 edje_object_signal_emit
1055 (it->deco_all_view, "elm,state,disabled", "elm");
1057 if (it->item->expanded)
1059 edje_object_signal_emit(VIEW(it), "elm,state,expanded", "elm");
1060 if (it->deco_all_view)
1061 edje_object_signal_emit
1062 (it->deco_all_view, "elm,state,expanded", "elm");
1068 _elm_genlist_item_index_update(Elm_Gen_Item *it)
1070 if (it->position_update || it->item->block->position_update)
1072 evas_object_smart_callback_call(WIDGET(it), SIG_INDEX_UPDATE, it);
1073 it->position_update = EINA_FALSE;
1078 _item_text_realize(Elm_Gen_Item *it,
1079 Evas_Object *target,
1083 if (it->itc->func.text_get)
1089 *source = elm_widget_stringlist_get
1090 (edje_object_data_get(target, "texts"));
1091 EINA_LIST_FOREACH(*source, l, key)
1093 if (parts && fnmatch(parts, key, FNM_PERIOD))
1096 char *s = it->itc->func.text_get
1097 ((void *)it->base.data, WIDGET(it), key);
1101 edje_object_part_text_escaped_set(target, key, s);
1106 edje_object_part_text_set(target, key, "");
1113 // FIXME: difference from upstream
1115 _content_focused(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1117 Elm_Gen_Item *it = data;
1118 if (it) it->defer_unrealize = EINA_TRUE;
1122 _content_unfocused(void *data, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1124 Elm_Gen_Item *it = data;
1125 if (it) it->defer_unrealize = EINA_FALSE;
1130 _item_mode_content_realize(Elm_Gen_Item *it,
1131 Evas_Object *target,
1134 Eina_List **contents_list)
1136 Eina_List *res = *contents_list;
1138 if (it->itc->func.content_get)
1144 EINA_LIST_FOREACH(*source, l, key)
1146 if (parts && fnmatch(parts, key, FNM_PERIOD))
1149 ic = it->itc->func.content_get
1150 ((void *)it->base.data, WIDGET(it), key);
1154 res = eina_list_append(res, ic);
1155 edje_object_part_swallow(target, key, ic);
1156 evas_object_show(ic);
1157 #if GENLIST_ENTRY_SUPPORT
1160 // For entry or editfield
1161 // 1. Add resize callback for multiline entry.
1162 // 2. Do not unrealize it for focus issue
1163 // ps. Only for entry because of performnace
1164 if (!strcmp("elm_layout", evas_object_type_get(ic)))
1166 // If editfield style, it can have entry.
1168 edje_object_file_get(elm_layout_edje_get(ic), NULL, &group);
1169 if (group && !strncmp("elm/layout/editfield/", group, 20))
1170 it->item->unrealize_disabled = EINA_TRUE;
1172 else if (!strcmp("elm_entry", evas_object_type_get(ic)))
1173 it->item->unrealize_disabled = EINA_TRUE;
1177 // FIXME: difference from upstream
1180 // FIXME: if entry calcuates its cursor position correctly and conformant works,
1181 // genlist does not need to handle this focus thing.
1182 evas_object_smart_callback_add(ic, "focused", _content_focused, it);
1183 evas_object_smart_callback_add(ic, "unfocused", _content_unfocused, it);
1186 if (elm_widget_item_disabled_get(it))
1187 elm_widget_disabled_set(ic, EINA_TRUE);
1196 _item_state_realize(Elm_Gen_Item *it,
1197 Evas_Object *target,
1201 if (it->itc->func.state_get)
1208 *source = elm_widget_stringlist_get
1209 (edje_object_data_get(target, "states"));
1210 EINA_LIST_FOREACH(*source, l, key)
1212 if (parts && fnmatch(parts, key, FNM_PERIOD))
1215 Eina_Bool on = it->itc->func.state_get
1216 ((void *)it->base.data, WIDGET(it), key);
1220 snprintf(buf, sizeof(buf), "elm,state,%s,active", key);
1221 edje_object_signal_emit(target, buf, "elm");
1225 snprintf(buf, sizeof(buf), "elm,state,%s,passive", key);
1226 edje_object_signal_emit(target, buf, "elm");
1233 _decorate_item_unrealize(Elm_Gen_Item *it)
1235 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
1236 Evas_Object *content;
1238 if (!it->item->deco_it_view) return;
1240 //evas_event_freeze(evas_object_evas_get(obj));
1241 elm_widget_stringlist_free(it->item->deco_it_texts);
1242 it->item->deco_it_texts = NULL;
1243 elm_widget_stringlist_free(it->item->deco_it_contents);
1244 it->item->deco_it_contents = NULL;
1245 elm_widget_stringlist_free(it->item->deco_it_states);
1247 EINA_LIST_FREE (it->item->deco_it_content_objs, content)
1248 evas_object_del(content);
1250 edje_object_part_unswallow(it->item->deco_it_view, VIEW(it));
1251 evas_object_smart_member_add(VIEW(it), sd->pan_obj);
1252 evas_object_del(it->item->deco_it_view);
1253 it->item->deco_it_view = NULL;
1255 if (sd->mode_item == it) sd->mode_item = NULL;
1256 //evas_event_thaw(evas_object_evas_get(obj));
1257 //evas_event_thaw_eval(evas_object_evas_get(obj));
1262 _decorate_all_item_position(Elm_Gen_Item *it,
1266 evas_object_resize(it->deco_all_view, it->item->w, it->item->h);
1267 evas_object_move(it->deco_all_view, itx, ity);
1271 _decorate_all_item_realize(Elm_Gen_Item *it,
1272 Eina_Bool effect_on)
1275 const char *stacking;
1276 const char *stacking_even;
1278 if ((!it) || (it->item->decorate_all_item_realized)) return;
1280 if (it->item->deco_it_view) _decorate_item_unrealize(it);
1282 it->deco_all_view = edje_object_add(evas_object_evas_get(WIDGET(it)));
1283 edje_object_scale_set(it->deco_all_view, elm_widget_scale_get(WIDGET(it)) *
1284 elm_config_scale_get());
1285 evas_object_smart_member_add(it->deco_all_view, GL_IT(it)->wsd->pan_obj);
1286 elm_widget_sub_object_add(WIDGET(it), it->deco_all_view);
1288 if (it->item->type & ELM_GENLIST_ITEM_TREE)
1289 strncpy(buf, "tree", sizeof(buf));
1290 else strncpy(buf, "item", sizeof(buf));
1291 if (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)
1292 strncat(buf, "_compress", sizeof(buf) - strlen(buf));
1294 strncat(buf, "/", sizeof(buf) - strlen(buf));
1295 strncat(buf, it->itc->decorate_all_item_style, sizeof(buf) - strlen(buf));
1297 elm_widget_theme_object_set(WIDGET(it), it->deco_all_view, "genlist", buf,
1298 elm_widget_style_get(WIDGET(it)));
1300 stacking_even = edje_object_data_get(VIEW(it), "stacking_even");
1301 if (!stacking_even) stacking_even = "above";
1302 it->item->stacking_even = !!strcmp("above", stacking_even);
1304 stacking = edje_object_data_get(VIEW(it), "stacking");
1305 if (!stacking) stacking = "yes";
1306 it->item->nostacking = !!strcmp("yes", stacking);
1308 edje_object_mirrored_set
1309 (it->deco_all_view, elm_widget_mirrored_get(WIDGET(it)));
1311 _elm_genlist_item_odd_even_update(it);
1312 _elm_genlist_item_state_update(it, NULL);
1314 #if 1 // FIXME: difference from upstream
1315 if (GL_IT(it)->wsd->reorder_mode)
1317 edje_object_signal_emit
1318 (VIEW(it), "elm,state,reorder,mode_unset", "elm");
1319 edje_object_signal_emit
1320 (it->deco_all_view, "elm,state,reorder,mode_set", "elm");
1325 edje_object_signal_emit
1326 (it->deco_all_view, "elm,state,decorate,enabled,effect", "elm");
1327 edje_object_signal_emit
1328 (VIEW(it), "elm,state,decorate,enabled,effect", "elm");
1332 edje_object_signal_emit
1333 (it->deco_all_view, "elm,state,decorate,enabled", "elm");
1334 edje_object_signal_emit
1335 (VIEW(it), "elm,state,decorate,enabled", "elm");
1337 _item_mouse_callbacks_del(it, VIEW(it));
1338 _item_mouse_callbacks_add(it, it->deco_all_view);
1340 _item_text_realize(it, it->deco_all_view, &it->item->deco_all_texts, NULL);
1342 edje_object_signal_emit
1343 (it->deco_all_view, "elm,state,flip,enabled", "elm");
1344 if (!it->item->deco_all_contents)
1345 it->item->deco_all_contents = elm_widget_stringlist_get
1346 (edje_object_data_get(it->deco_all_view, "contents"));
1347 it->item->deco_all_content_objs =
1348 _item_mode_content_realize(it, it->deco_all_view,
1349 &it->item->deco_all_contents, NULL,
1350 &it->item->deco_all_content_objs);
1352 (it, it->deco_all_view, &it->item->deco_all_states, NULL);
1353 edje_object_part_swallow
1354 (it->deco_all_view, "elm.swallow.decorate.content", VIEW(it));
1356 _decorate_all_item_position(it, it->item->scrl_x, it->item->scrl_y);
1357 evas_object_show(it->deco_all_view);
1361 edje_object_signal_emit(it->deco_all_view, "elm,state,selected", "elm");
1362 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
1365 it->item->decorate_all_item_realized = EINA_TRUE;
1366 it->want_unrealize = EINA_FALSE;
1370 _expand_toggle_signal_cb(void *data,
1371 Evas_Object *obj __UNUSED__,
1372 const char *emission __UNUSED__,
1373 const char *source __UNUSED__)
1375 Elm_Gen_Item *it = data;
1377 if (it->item->expanded)
1378 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACT_REQUEST, it);
1380 evas_object_smart_callback_call(WIDGET(it), SIG_EXPAND_REQUEST, it);
1384 _expand_signal_cb(void *data,
1385 Evas_Object *obj __UNUSED__,
1386 const char *emission __UNUSED__,
1387 const char *source __UNUSED__)
1389 Elm_Gen_Item *it = data;
1391 if (!it->item->expanded)
1392 evas_object_smart_callback_call(WIDGET(it), SIG_EXPAND_REQUEST, it);
1396 _contract_signal_cb(void *data,
1397 Evas_Object *obj __UNUSED__,
1398 const char *emission __UNUSED__,
1399 const char *source __UNUSED__)
1401 Elm_Gen_Item *it = data;
1403 if (it->item->expanded)
1404 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACT_REQUEST, it);
1407 #if GENLIST_ENTRY_SUPPORT
1409 _changed_size_hints(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
1411 Elm_Gen_Item *it = data;
1413 if (it->want_unrealize) return;
1414 it->item->mincalcd = EINA_FALSE;
1415 it->item->block->changeme = EINA_TRUE;
1416 GL_IT(it)->wsd->size_changed = EINA_TRUE;
1417 evas_object_smart_changed(GL_IT(it)->wsd->pan_obj);
1422 _item_content_realize(Elm_Gen_Item *it,
1423 Evas_Object *target,
1427 Eina_List *res = it->content_objs;
1429 if (it->itc->func.content_get)
1433 Evas_Object *ic = NULL;
1436 *source = elm_widget_stringlist_get
1437 (edje_object_data_get(target, "contents"));
1439 EINA_LIST_FOREACH(*source, l, key)
1441 if (parts && fnmatch(parts, key, FNM_PERIOD))
1444 if (it->itc->func.content_get)
1445 ic = it->itc->func.content_get
1446 ((void *)it->base.data, WIDGET(it), key);
1449 res = eina_list_append(res, ic);
1450 edje_object_part_swallow(target, key, ic);
1451 evas_object_show(ic);
1453 #if GENLIST_ENTRY_SUPPORT
1454 // For entry or editfield
1455 // 1. Add resize callback for multiline entry.
1456 // 2. Do not unrealize it for focus issue
1457 // ps. Only for entry because of performnace
1458 if (!strcmp("elm_layout", evas_object_type_get(ic)))
1460 // If editfield style, it can have entry.
1462 edje_object_file_get(elm_layout_edje_get(ic), NULL, &group);
1463 if (group && !strncmp("elm/layout/editfield/", group, 20))
1465 evas_object_event_callback_add
1466 (ic, EVAS_CALLBACK_CHANGED_SIZE_HINTS,
1467 _changed_size_hints, it);
1468 it->item->unrealize_disabled = EINA_TRUE;
1472 else if (!strcmp("elm_entry", evas_object_type_get(ic)))
1474 evas_object_event_callback_add
1475 (ic, EVAS_CALLBACK_CHANGED_SIZE_HINTS,
1476 _changed_size_hints, it);
1477 it->item->unrealize_disabled = EINA_TRUE;
1480 #if 0 // FIXME: difference from upstream
1483 // FIXME: if entry calcuates its cursor position correctly and conformant works,
1484 // genlist does not need to handle this focus thing.
1485 evas_object_smart_callback_add(ic, "focused", _content_focused, it);
1486 evas_object_smart_callback_add(ic, "unfocused", _content_unfocused, it);
1489 if (elm_widget_item_disabled_get(it))
1490 elm_widget_disabled_set(ic, EINA_TRUE);
1499 _access_info_cb(void *data, Evas_Object *obj __UNUSED__)
1504 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1505 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
1507 buf = eina_strbuf_new();
1509 if (it->itc->func.text_get)
1514 if (!(it->texts)) it->texts =
1515 elm_widget_stringlist_get(edje_object_data_get(VIEW(it), "texts"));
1517 EINA_LIST_FOREACH(it->texts, l, key)
1519 char *s = it->itc->func.text_get
1520 ((void *)it->base.data, WIDGET(it), key);
1522 s = _elm_util_mkup_to_text(s);
1526 if (eina_strbuf_length_get(buf) > 0) eina_strbuf_append(buf, ", ");
1527 eina_strbuf_append(buf, s);
1533 ret = eina_strbuf_string_steal(buf);
1534 eina_strbuf_free(buf);
1539 _access_state_cb(void *data, Evas_Object *obj __UNUSED__)
1541 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1542 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
1544 if (it->base.disabled)
1545 return strdup(E_("State: Disabled"));
1551 _access_on_highlight_cb(void *data)
1553 Evas_Coord x, y, w, h;
1554 Evas_Coord sx, sy, sw, sh;
1555 Elm_Gen_Item *it = (Elm_Gen_Item *)data;
1556 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it);
1558 ELM_GENLIST_DATA_GET(it->base.widget, sd);
1560 evas_object_geometry_get(it->base.view, &x, &y, &w, &h);
1561 // XXX There would be a reason.
1562 if ((w == 0) && (h == 0)) return;
1564 evas_object_geometry_get(ELM_WIDGET_DATA(sd)->obj, &sx, &sy, &sw, &sh);
1565 if ((x < sx) || (y < sy) || ((x + w) > (sx + sw)) || ((y + h) > (sy + sh)))
1566 elm_genlist_item_bring_in((Elm_Object_Item *)it,
1567 ELM_GENLIST_ITEM_SCROLLTO_IN);
1571 _access_widget_item_register(Elm_Gen_Item *it)
1573 Elm_Access_Info *ai;
1575 _elm_access_widget_item_register((Elm_Widget_Item *)it);
1577 ai = _elm_access_object_get(it->base.access_obj);
1579 _elm_access_callback_set(ai, ELM_ACCESS_INFO, _access_info_cb, it);
1580 _elm_access_callback_set(ai, ELM_ACCESS_STATE, _access_state_cb, it);
1581 _elm_access_on_highlight_hook_set(ai, _access_on_highlight_cb, it);
1582 _elm_access_activate_callback_set(ai, _access_activate_cb, it);
1586 _item_realize(Elm_Gen_Item *it,
1590 Item_Cache *itc = NULL;
1591 const char *treesize;
1597 if (it->item->order_num_in != in)
1599 _item_order_update(EINA_INLIST_GET(it), in);
1600 _elm_genlist_item_state_update(it, NULL);
1601 _elm_genlist_item_index_update(it);
1605 it->item->order_num_in = in;
1607 if (it->item->nocache_once | it->item->nocache ||
1608 it->item->type == ELM_GENLIST_ITEM_TREE || it->parent ||
1609 !_item_cache_pop(it))
1611 const char *stacking_even;
1612 const char *stacking;
1614 it->item->nocache_once = EINA_FALSE;
1616 VIEW(it) = edje_object_add(evas_object_evas_get(WIDGET(it)));
1617 edje_object_scale_set(VIEW(it),
1618 elm_widget_scale_get(WIDGET(it)) *
1619 elm_config_scale_get());
1620 evas_object_smart_member_add(VIEW(it), GL_IT(it)->wsd->pan_obj);
1621 elm_widget_sub_object_add(WIDGET(it), VIEW(it));
1623 if (it->item->type & ELM_GENLIST_ITEM_TREE)
1624 snprintf(buf, sizeof(buf), "tree%s/%s",
1625 GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS ? "_compress" :
1626 "", it->itc->item_style ? : "default");
1628 snprintf(buf, sizeof(buf), "item%s/%s",
1629 GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS ? "_compress" :
1630 "", it->itc->item_style ? : "default");
1632 elm_widget_theme_object_set
1633 (WIDGET(it), VIEW(it), "genlist", buf,
1634 elm_widget_style_get(WIDGET(it)));
1636 #if 1 // FIXME: difference from upstream
1637 if (it->item->expanded_depth > 0)
1638 edje_object_signal_emit(VIEW(it), "bg_color_change", "elm");
1641 stacking_even = edje_object_data_get(VIEW(it), "stacking_even");
1642 if (!stacking_even) stacking_even = "above";
1643 it->item->stacking_even = !!strcmp("above", stacking_even);
1645 stacking = edje_object_data_get(VIEW(it), "stacking");
1646 if (!stacking) stacking = "yes";
1647 it->item->nostacking = !!strcmp("yes", stacking);
1649 edje_object_mirrored_set
1650 (VIEW(it), elm_widget_mirrored_get(WIDGET(it)));
1652 edje_object_signal_callback_add
1653 (VIEW(it), "elm,action,expand,toggle", "elm",
1654 _expand_toggle_signal_cb, it);
1655 edje_object_signal_callback_add
1656 (VIEW(it), "elm,action,expand", "elm", _expand_signal_cb, it);
1657 edje_object_signal_callback_add
1658 (VIEW(it), "elm,action,contract", "elm", _contract_signal_cb, it);
1659 _item_mouse_callbacks_add(it, VIEW(it));
1663 if (_elm_config->access_mode) _access_widget_item_register(it);
1665 _item_order_update(EINA_INLIST_GET(it), in);
1666 #if 1 // FIXME: difference from upstream
1667 if (!(it->deco_all_view) && (it->item->type != ELM_GENLIST_ITEM_GROUP))
1669 if (GL_IT(it)->wsd->reorder_mode)
1670 edje_object_signal_emit
1671 (VIEW(it), "elm,state,reorder,mode_set", "elm");
1673 edje_object_signal_emit
1674 (VIEW(it), "elm,state,reorder,mode_unset", "elm");
1677 treesize = edje_object_data_get(VIEW(it), "treesize");
1678 if (treesize) tsize = atoi(treesize);
1679 if (it->parent && GL_IT(it->parent)->type == ELM_GENLIST_ITEM_TREE &&
1680 !it->spacer && treesize)
1683 evas_object_rectangle_add(evas_object_evas_get(WIDGET(it)));
1684 evas_object_color_set(it->spacer, 0, 0, 0, 0);
1688 evas_object_size_hint_min_set
1689 (it->spacer, (it->item->expanded_depth * tsize) *
1690 elm_config_scale_get(), 1);
1691 edje_object_part_swallow(VIEW(it), "elm.swallow.pad", it->spacer);
1695 if ((GL_IT(it)->wsd->decorate_all_mode) && (!it->deco_all_view) &&
1696 (it->item->type != ELM_GENLIST_ITEM_GROUP) &&
1697 (it->itc->decorate_all_item_style))
1698 _decorate_all_item_realize(it, EINA_FALSE);
1700 _elm_genlist_item_state_update(it, itc);
1701 _elm_genlist_item_index_update(it);
1704 /* homogenous genlist shortcut */
1705 if ((calc) && (GL_IT(it)->wsd->homogeneous) && (!it->item->mincalcd) &&
1706 ((it->group && GL_IT(it)->wsd->group_item_width) ||
1707 (!it->group && GL_IT(it)->wsd->item_width)))
1711 it->item->w = it->item->minw = GL_IT(it)->wsd->group_item_width;
1712 it->item->h = it->item->minh = GL_IT(it)->wsd->group_item_height;
1716 it->item->w = it->item->minw = GL_IT(it)->wsd->item_width;
1717 it->item->h = it->item->minh = GL_IT(it)->wsd->item_height;
1719 it->item->mincalcd = EINA_TRUE;
1723 if (eina_list_count(it->content_objs) != 0)
1724 ERR_ABORT("If you see this error, please notify us and we"
1727 _item_text_realize(it, VIEW(it), &it->texts, NULL);
1729 _item_content_realize(it, VIEW(it), &it->contents, NULL);
1730 _item_state_realize(it, VIEW(it), &it->states, NULL);
1733 edje_object_signal_emit
1734 (VIEW(it), "elm,state,flip,enabled", "elm");
1735 // This is needed before contents are swallowed
1736 edje_object_message_signal_process(VIEW(it));
1738 if (!(it->item->flip_contents))
1739 it->item->flip_contents = elm_widget_stringlist_get
1740 (edje_object_data_get(VIEW(it), "flips"));
1741 it->item->flip_content_objs = _item_mode_content_realize
1742 (it, VIEW(it), &it->item->flip_contents, NULL,
1743 &it->item->flip_content_objs);
1746 /* access: unregister item which have no text and content */
1747 if (_elm_config->access_mode && !it->texts && !it->contents)
1748 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
1751 // FIXME: difference from upstream
1752 if (!it->item->mincalcd || ((GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS) && (it->item->w != it->item->minw)))
1754 if (!it->item->mincalcd)
1757 Evas_Coord mw = -1, mh = -1;
1759 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
1760 elm_coords_finger_size_adjust(1, &mw, 1, &mh);
1761 if (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)
1762 mw = GL_IT(it)->wsd->prev_viewport_w;
1763 edje_object_size_min_restricted_calc(VIEW(it), &mw, &mh, mw, mh);
1765 it->item->w = it->item->minw = mw;
1766 it->item->h = it->item->minh = mh;
1767 it->item->mincalcd = EINA_TRUE;
1769 if ((!GL_IT(it)->wsd->group_item_width) && (it->group))
1771 GL_IT(it)->wsd->group_item_width = mw;
1772 GL_IT(it)->wsd->group_item_height = mh;
1774 else if ((!GL_IT(it)->wsd->item_width) &&
1775 (it->item->type == ELM_GENLIST_ITEM_NONE))
1777 GL_IT(it)->wsd->item_width = mw;
1778 GL_IT(it)->wsd->item_height = mh;
1781 if (!calc) evas_object_show(VIEW(it));
1784 if (it->tooltip.content_cb)
1786 elm_widget_item_tooltip_content_cb_set
1787 (it, it->tooltip.content_cb, it->tooltip.data, NULL);
1788 elm_widget_item_tooltip_style_set(it, it->tooltip.style);
1789 elm_widget_item_tooltip_window_mode_set(it, it->tooltip.free_size);
1792 if (it->mouse_cursor)
1793 elm_widget_item_cursor_set(it, it->mouse_cursor);
1795 it->realized = EINA_TRUE;
1796 it->want_unrealize = EINA_FALSE;
1798 if (!calc || it->item->unrealize_disabled)
1799 evas_object_smart_callback_call(WIDGET(it), SIG_REALIZED, it);
1801 if ((!calc) && (GL_IT(it)->wsd->decorate_all_mode) &&
1802 (it->item->type != ELM_GENLIST_ITEM_GROUP))
1804 if (it->itc->decorate_all_item_style)
1806 if (!it->deco_all_view)
1807 _decorate_all_item_realize(it, EINA_FALSE);
1808 edje_object_message_signal_process(it->deco_all_view);
1811 if ((!calc) && (it->decorate_it_set) &&
1812 (it->item->type != ELM_GENLIST_ITEM_GROUP))
1814 if (it->itc->decorate_item_style)
1816 if (!it->item->deco_it_view)
1817 _decorate_item_set(it);
1818 edje_object_message_signal_process(it->item->deco_it_view);
1821 edje_object_message_signal_process(VIEW(it));
1824 #if GENLIST_PINCH_ZOOM_SUPPORT
1826 _pinch_items_recalc(void *data)
1828 Elm_Genlist_Smart_Data *sd = data;
1833 Evas_Coord tot_y = 0, ox, oy;
1834 evas_object_geometry_get(sd->pan_obj, &ox, &oy, NULL, NULL);
1836 EINA_INLIST_FOREACH(sd->blocks, itb)
1838 EINA_LIST_FOREACH(itb->items, l, it)
1841 if (IS_ROOT_PARENT_IT(it))
1843 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
1845 if (!it->realized) _item_realize(it, 0, EINA_FALSE);
1846 it->item->scrl_y = oy + tot_y - sd->pan_y;
1847 evas_object_resize(VIEW(it), sd->minw, it->item->h);
1848 evas_object_move(VIEW(it), it->item->scrl_x, it->item->scrl_y);
1849 evas_object_show(VIEW(it));
1850 evas_object_raise(VIEW(it));
1851 tot_y += it->item->h;
1852 sd->pinch_zoom_h = tot_y;
1855 else if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND)
1857 evas_object_resize(VIEW(it), sd->minw, it->item->h);
1858 it->item->scrl_y = oy + it->item->pan_scrl_y - sd->pan_y;
1859 evas_object_move(VIEW(it), it->item->scrl_x, it->item->scrl_y);
1868 #if GROUP_ITEMS_FEATURE
1870 _group_items_recalc(void *data)
1874 Elm_Genlist_Smart_Data *sd = data;
1876 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1877 EINA_LIST_FOREACH(sd->group_items, l, git)
1879 if (git->item->want_realize)
1881 if (!git->realized) _item_realize(git, 0, EINA_FALSE);
1882 evas_object_resize(VIEW(git), sd->minw, git->item->h);
1883 evas_object_move(VIEW(git), git->item->scrl_x, git->item->scrl_y);
1884 evas_object_show(VIEW(git));
1885 evas_object_raise(VIEW(git));
1887 else if (!git->item->want_realize)
1890 _item_unrealize(git, EINA_FALSE);
1893 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1894 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
1899 _reorder_move_animator_cb(void *data)
1902 Elm_Gen_Item *it = data;
1903 Eina_Bool down = EINA_FALSE;
1906 dy = 6 * elm_config_scale_get();
1907 t = ((0.0 > (t = ecore_loop_time_get()
1908 - GL_IT(it)->wsd->start_time)) ? 0.0 : t);
1910 if (t <= REORDER_EFFECT_TIME)
1911 y = (1 * sin((t / REORDER_EFFECT_TIME) * (M_PI / 2)) * dy);
1914 diff = abs(it->item->old_scrl_y - it->item->scrl_y);
1915 if (diff < dy) y = diff;
1917 if (it->item->old_scrl_y < it->item->scrl_y)
1919 it->item->old_scrl_y += y;
1922 else if (it->item->old_scrl_y > it->item->scrl_y)
1924 it->item->old_scrl_y -= y;
1928 if (it->deco_all_view)
1930 (it, it->deco_all_view, it->item->scrl_x, it->item->old_scrl_y);
1931 else if (it->item->deco_it_view)
1933 (it, it->item->deco_it_view, it->item->scrl_x, it->item->old_scrl_y);
1935 _item_position(it, VIEW(it), it->item->scrl_x, it->item->old_scrl_y);
1937 if ((GL_IT(it)->wsd->reorder_pan_move) ||
1938 (down && it->item->old_scrl_y >= it->item->scrl_y) ||
1939 (!down && it->item->old_scrl_y <= it->item->scrl_y))
1941 it->item->old_scrl_y = it->item->scrl_y;
1942 it->item->move_effect_enabled = EINA_FALSE;
1943 GL_IT(it)->wsd->reorder_move_animator = NULL;
1944 return ECORE_CALLBACK_CANCEL;
1947 return ECORE_CALLBACK_RENEW;
1951 _reorder_item_space_get(Elm_Gen_Item *it)
1953 Elm_Gen_Item *reorder_it = GL_IT(it)->wsd->reorder_it;
1954 Evas_Coord rox, roy, row, roh, oy, oh;
1955 Eina_Bool top = EINA_FALSE;
1957 if (!reorder_it) return 0;
1958 if(it->deco_all_view) evas_object_lower(it->deco_all_view);
1960 evas_object_geometry_get(GL_IT(it)->wsd->pan_obj, NULL, &oy, NULL, &oh);
1961 evas_object_geometry_get
1962 (GL_IT(it)->wsd->VIEW(reorder_it), &rox, &roy, &row, &roh);
1964 if ((GL_IT(it)->wsd->reorder_start_y < it->item->block->y) &&
1965 (roy - oy + (roh / 2) >= it->item->block->y - GL_IT(it)->wsd->pan_y))
1967 it->item->block->reorder_offset =
1968 GL_IT(it)->wsd->reorder_it->item->h * -1;
1969 if (it->item->block->count == 1)
1970 GL_IT(it)->wsd->reorder_rel = it;
1972 else if ((GL_IT(it)->wsd->reorder_start_y >= it->item->block->y) &&
1973 (roy - oy + (roh / 2) <= it->item->block->y -
1974 GL_IT(it)->wsd->pan_y))
1976 it->item->block->reorder_offset = GL_IT(it)->wsd->reorder_it->item->h;
1979 it->item->block->reorder_offset = 0;
1981 it->item->scrl_y += it->item->block->reorder_offset;
1983 top = (ELM_RECTS_INTERSECT
1984 (it->item->scrl_x, it->item->scrl_y, it->item->w, it->item->h,
1985 rox, roy + (roh / 2), row, 1));
1988 GL_IT(it)->wsd->reorder_rel = it;
1989 it->item->scrl_y += GL_IT(it)->wsd->reorder_it->item->h;
1990 return GL_IT(it)->wsd->reorder_it->item->h;
1997 _item_block_position(Item_Block *itb,
2003 Eina_Bool vis = EINA_FALSE;
2004 Evas_Coord y = 0, ox, oy, ow, oh, cvx, cvy, cvw, cvh;
2006 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
2007 evas_object_geometry_get(itb->sd->pan_obj, &ox, &oy, &ow, &oh);
2008 evas_output_viewport_get
2009 (evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj),
2010 &cvx, &cvy, &cvw, &cvh);
2012 EINA_LIST_FOREACH(itb->items, l, it)
2014 if ((GL_IT(it)->wsd->reorder_it == it) && it->highlighted) continue;
2018 it->item->w = itb->w;
2019 it->item->scrl_x = itb->x + it->x - GL_IT(it)->wsd->pan_x + ox;
2020 it->item->scrl_y = itb->y + it->y - GL_IT(it)->wsd->pan_y + oy;
2022 vis = (ELM_RECTS_INTERSECT
2023 (it->item->scrl_x, it->item->scrl_y, it->item->w, it->item->h,
2024 cvx, cvy, cvw, cvh));
2027 if ((itb->realized) && (!it->realized))
2029 if (vis) _item_realize(it, in, EINA_FALSE);
2033 if (vis || it->dragging)
2035 #if GENLIST_ENTRY_SUPPORT
2036 evas_object_show(VIEW(it));
2038 if (GL_IT(it)->wsd->reorder_mode &&
2039 GL_IT(it)->wsd->reorder_it &&
2040 GL_IT(it)->wsd->reorder_it->highlighted)
2041 y += _reorder_item_space_get(it);
2042 git = it->item->group_item;
2045 if (git->item->scrl_y < oy)
2046 git->item->scrl_y = oy;
2047 if ((git->item->scrl_y + git->item->h) >
2048 (it->item->scrl_y + it->item->h))
2049 git->item->scrl_y = (it->item->scrl_y +
2050 it->item->h) - git->item->h;
2051 git->item->scrl_x = it->item->scrl_x;
2052 git->item->want_realize = EINA_TRUE;
2054 if ((GL_IT(it)->wsd->reorder_it) &&
2055 GL_IT(it)->wsd->reorder_it->highlighted &&
2056 (it->item->old_scrl_y != it->item->scrl_y))
2058 if (!it->item->move_effect_enabled)
2060 it->item->move_effect_enabled = EINA_TRUE;
2061 GL_IT(it)->wsd->reorder_move_animator =
2063 _reorder_move_animator_cb, it);
2066 if (!it->item->move_effect_enabled)
2068 if ((GL_IT(it)->wsd->decorate_all_mode) &&
2069 (it->itc->decorate_all_item_style))
2070 _decorate_all_item_position
2071 (it, it->item->scrl_x, it->item->scrl_y);
2074 if (it->item->deco_it_view)
2076 (it, it->item->deco_it_view,
2081 (it, VIEW(it), it->item->scrl_x,
2084 it->item->old_scrl_y = it->item->scrl_y;
2085 #if GENLIST_PINCH_ZOOM_SUPPORT
2086 if (((GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
2087 && (!IS_ROOT_PARENT_IT(it))) || (GL_IT(it)->wsd->sorting))
2089 if (it->deco_all_view) evas_object_hide(it->deco_all_view);
2090 else evas_object_hide(VIEW(it));
2098 if ((GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
2099 && (!IS_ROOT_PARENT_IT(it)))
2101 if (it->deco_all_view) evas_object_hide(it->deco_all_view);
2102 else evas_object_hide(VIEW(it));
2105 _item_unrealize(it, EINA_FALSE);
2112 if (vis) it->item->want_realize = EINA_TRUE;
2116 // FIXME: diffrence from upstream
2117 minh += it->item->minh;
2121 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
2122 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(itb->sd)->obj));
2126 _item_block_realize(Item_Block *itb)
2128 if (itb->realized) return;
2130 itb->realized = EINA_TRUE;
2131 itb->want_unrealize = EINA_FALSE;
2134 #if GENLIST_ENTRY_SUPPORT
2136 _changed_job(Elm_Genlist_Smart_Data *sd)
2142 Eina_Bool anything_changed = EINA_FALSE;
2143 Eina_Bool width_changed = EINA_FALSE;
2144 Eina_Bool height_changed = EINA_FALSE;
2145 sd->size_changed = EINA_FALSE;
2147 EINA_INLIST_FOREACH(sd->blocks, itb)
2154 if (anything_changed)
2155 _item_block_position(itb, num);
2159 width_changed = height_changed = EINA_FALSE;
2160 EINA_LIST_FOREACH(itb->items, l2, it)
2162 if ((!it->item->mincalcd) && (it->realized))
2164 Evas_Coord fw = -1, fh = -1;
2165 Evas_Coord mw = -1, mh = -1;
2167 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
2168 elm_coords_finger_size_adjust(1, &fw, 1, &fh);
2170 // FIXME: why compressmode do this?
2171 if (sd->mode == ELM_LIST_COMPRESS) mw = sd->prev_viewport_w;
2173 edje_object_size_min_restricted_calc(VIEW(it), &mw, &mh, fw, fh);
2175 if (it->item->w != mw)
2177 it->item->w = it->item->minw = mw;
2178 width_changed = EINA_TRUE;
2180 if (it->item->h != mh)
2182 it->item->h = it->item->minh = mh;
2183 height_changed = EINA_TRUE;
2190 it->item->mincalcd = EINA_TRUE;
2192 if ((!sd->group_item_width) && (it->group))
2194 sd->group_item_width = mw;
2195 sd->group_item_height = mh;
2197 else if ((!sd->item_width) && (it->item->type == ELM_GENLIST_ITEM_NONE))
2199 sd->item_width = mw;
2200 sd->item_height = mh;
2205 itb->changeme = EINA_FALSE;
2208 anything_changed = EINA_TRUE;
2209 itb->changed = EINA_TRUE;
2210 _item_block_recalc(itb, num0, 0);
2211 _item_block_position(itb, num0);
2213 else if (width_changed)
2215 _item_block_position(itb, num0);
2218 if (anything_changed)
2220 if (sd->calc_job) ecore_job_del(sd->calc_job);
2221 sd->calc_job = ecore_job_add(_calc_job, sd);
2227 _elm_genlist_pan_smart_calculate(Evas_Object *obj)
2229 Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh;
2230 Evas_Coord vx = 0, vy = 0, vw = 0, vh = 0;
2236 ELM_GENLIST_PAN_DATA_GET(obj, psd);
2238 //evas_event_freeze(evas_object_evas_get(obj));
2240 #if GENLIST_FX_SUPPORT
2241 if (psd->wsd->fx_playing) return;
2243 if (psd->wsd->pan_changed)
2245 _calc_job(psd->wsd);
2246 psd->wsd->pan_changed = EINA_FALSE;
2249 evas_object_geometry_get(obj, &ox, &oy, &ow, &oh);
2250 evas_output_viewport_get(evas_object_evas_get(obj), &cvx, &cvy, &cvw, &cvh);
2251 EINA_LIST_FOREACH(psd->wsd->group_items, l, git)
2253 #if GROUP_ITEMS_FEATURE
2254 git->item->want_realize = EINA_FALSE;
2256 _item_unrealize(git, EINA_TRUE);
2260 EINA_INLIST_FOREACH(psd->wsd->blocks, itb)
2262 itb->w = psd->wsd->minw;
2263 if (ELM_RECTS_INTERSECT(itb->x - psd->wsd->pan_x + ox,
2264 itb->y - psd->wsd->pan_y + oy,
2266 cvx, cvy, cvw, cvh))
2268 if ((!itb->realized) || (itb->changed))
2270 _item_block_realize(itb);
2272 // FIXME: difference from opensource
2273 if (sd->wd->calc_job) ecore_job_del(sd->wd->calc_job);
2274 sd->wd->calc_job = NULL;
2278 _item_block_position(itb, in);
2282 if (itb->realized) _item_block_unrealize(itb);
2286 #if GENLIST_PINCH_ZOOM_SUPPORT
2287 if (psd->wsd->pinch_zoom_mode) _pinch_items_recalc(psd->wsd);
2290 #if GROUP_ITEMS_FEATURE
2291 if ((!psd->wsd->reorder_it) || (psd->wsd->reorder_pan_move))
2292 _group_items_recalc(psd->wsd);
2294 if ((psd->wsd->reorder_mode) && (psd->wsd->reorder_it))
2296 if (psd->wsd->pan_y != psd->wsd->reorder_old_pan_y)
2297 psd->wsd->reorder_pan_move = EINA_TRUE;
2298 else psd->wsd->reorder_pan_move = EINA_FALSE;
2300 evas_object_raise(psd->wsd->VIEW(reorder_it));
2301 psd->wsd->reorder_old_pan_y = psd->wsd->pan_y;
2302 psd->wsd->start_time = ecore_loop_time_get();
2304 _item_auto_scroll(psd->wsd);
2306 psd->wsd->s_iface->content_pos_get(ELM_WIDGET_DATA(psd->wsd)->obj, &vx, &vy);
2307 psd->wsd->s_iface->content_viewport_size_get(ELM_WIDGET_DATA(psd->wsd)->obj,
2310 if (psd->wsd->reorder_fast == 1)
2311 psd->wsd->s_iface->content_region_show(ELM_WIDGET_DATA(psd->wsd)->obj,
2312 vx,vy - 10, vw, vh);
2313 else if (psd->wsd->reorder_fast == -1)
2314 psd->wsd->s_iface->content_region_show(ELM_WIDGET_DATA(psd->wsd)->obj,
2315 vx, vy + 10, vw, vh);
2317 #if GENLIST_ENTRY_SUPPORT
2318 if (psd->wsd->size_changed) _changed_job(psd->wsd);
2321 #if GENLIST_FX_SUPPORT
2322 psd->wsd->rendered = EINA_TRUE;
2323 if ((psd->wsd->fx_mode) && (!psd->wsd->queue))
2325 if (_elm_genlist_fx_capture(ELM_WIDGET_DATA(psd->wsd)->obj, 1))
2326 _elm_genlist_fx_play(ELM_WIDGET_DATA(psd->wsd)->obj);
2329 #if GENLIST_PINCH_ZOOM_SUPPORT
2330 if (psd->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND)
2331 psd->wsd->pinch_zoom_mode = ELM_GEN_PINCH_ZOOM_NONE;
2333 //evas_event_thaw(evas_object_evas_get(obj));
2334 //evas_event_thaw_eval(evas_object_evas_get(obj));
2338 _elm_genlist_pan_smart_set_user(Elm_Genlist_Pan_Smart_Class *sc)
2340 ELM_PAN_CLASS(sc)->base.add = _elm_genlist_pan_smart_add;
2341 ELM_PAN_CLASS(sc)->base.del = _elm_genlist_pan_smart_del;
2342 ELM_PAN_CLASS(sc)->base.move = _elm_genlist_pan_smart_move;
2343 ELM_PAN_CLASS(sc)->base.resize = _elm_genlist_pan_smart_resize;
2344 ELM_PAN_CLASS(sc)->base.calculate = _elm_genlist_pan_smart_calculate;
2346 ELM_PAN_CLASS(sc)->pos_set = _elm_genlist_pan_smart_pos_set;
2347 ELM_PAN_CLASS(sc)->pos_get = _elm_genlist_pan_smart_pos_get;
2348 ELM_PAN_CLASS(sc)->pos_max_get = _elm_genlist_pan_smart_pos_max_get;
2349 ELM_PAN_CLASS(sc)->pos_min_get = _elm_genlist_pan_smart_pos_min_get;
2350 ELM_PAN_CLASS(sc)->content_size_get =
2351 _elm_genlist_pan_smart_content_size_get;
2355 _item_multi_select_up(Elm_Genlist_Smart_Data *sd)
2357 Elm_Object_Item *prev;
2359 if (!sd->selected) return EINA_FALSE;
2360 if (!sd->multi) return EINA_FALSE;
2362 prev = elm_genlist_item_prev_get(sd->last_selected_item);
2363 if (!prev) return EINA_TRUE;
2365 if (elm_genlist_item_selected_get(prev))
2367 elm_genlist_item_selected_set(sd->last_selected_item, EINA_FALSE);
2368 sd->last_selected_item = prev;
2369 elm_genlist_item_show
2370 (sd->last_selected_item, ELM_GENLIST_ITEM_SCROLLTO_IN);
2374 elm_genlist_item_selected_set(prev, EINA_TRUE);
2375 elm_genlist_item_show(prev, ELM_GENLIST_ITEM_SCROLLTO_IN);
2381 _item_multi_select_down(Elm_Genlist_Smart_Data *sd)
2383 Elm_Object_Item *next;
2385 if (!sd->selected) return EINA_FALSE;
2386 if (!sd->multi) return EINA_FALSE;
2388 next = elm_genlist_item_next_get(sd->last_selected_item);
2389 if (!next) return EINA_TRUE;
2391 if (elm_genlist_item_selected_get(next))
2393 elm_genlist_item_selected_set(sd->last_selected_item, EINA_FALSE);
2394 sd->last_selected_item = next;
2395 elm_genlist_item_show
2396 (sd->last_selected_item, ELM_GENLIST_ITEM_SCROLLTO_IN);
2400 elm_genlist_item_selected_set(next, EINA_TRUE);
2401 elm_genlist_item_show(next, ELM_GENLIST_ITEM_SCROLLTO_IN);
2408 _all_items_deselect(Elm_Genlist_Smart_Data *sd)
2410 if (!sd->selected) return EINA_FALSE;
2412 while (sd->selected)
2413 elm_genlist_item_selected_set(sd->selected->data, EINA_FALSE);
2419 _item_single_select_up(Elm_Genlist_Smart_Data *sd)
2425 prev = ELM_GEN_ITEM_FROM_INLIST(sd->items->last);
2427 prev = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(prev)->prev);
2430 prev = (Elm_Gen_Item *)elm_genlist_item_prev_get
2431 (sd->last_selected_item);
2433 if (!prev) return EINA_FALSE;
2435 _all_items_deselect(sd);
2437 elm_genlist_item_selected_set((Elm_Object_Item *)prev, EINA_TRUE);
2438 elm_genlist_item_show((Elm_Object_Item *)prev, ELM_GENLIST_ITEM_SCROLLTO_IN);
2443 _item_single_select_down(Elm_Genlist_Smart_Data *sd)
2449 next = ELM_GEN_ITEM_FROM_INLIST(sd->items);
2451 next = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(next)->next);
2454 next = (Elm_Gen_Item *)elm_genlist_item_next_get
2455 (sd->last_selected_item);
2457 if (!next) return EINA_FALSE;
2459 _all_items_deselect(sd);
2461 elm_genlist_item_selected_set((Elm_Object_Item *)next, EINA_TRUE);
2462 elm_genlist_item_show
2463 ((Elm_Object_Item *)next, ELM_GENLIST_ITEM_SCROLLTO_IN);
2469 _elm_genlist_smart_event(Evas_Object *obj,
2470 Evas_Object *src __UNUSED__,
2471 Evas_Callback_Type type,
2478 Evas_Coord step_x = 0;
2479 Evas_Coord step_y = 0;
2480 Evas_Coord page_x = 0;
2481 Evas_Coord page_y = 0;
2482 Elm_Object_Item *it;
2483 Evas_Event_Key_Down *ev = event_info;
2484 Evas_Coord pan_max_x = 0, pan_max_y = 0;
2486 ELM_GENLIST_DATA_GET(obj, sd);
2488 if (type != EVAS_CALLBACK_KEY_DOWN) return EINA_FALSE;
2489 if (!sd->items) return EINA_FALSE;
2490 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD) return EINA_FALSE;
2491 if (elm_widget_disabled_get(obj)) return EINA_FALSE;
2493 sd->s_iface->content_pos_get(obj, &x, &y);
2494 sd->s_iface->step_size_get(obj, &step_x, &step_y);
2495 sd->s_iface->page_size_get(obj, &page_x, &page_y);
2496 sd->s_iface->content_viewport_size_get(obj, &v_w, &v_h);
2498 if ((!strcmp(ev->keyname, "Left")) ||
2499 ((!strcmp(ev->keyname, "KP_Left")) && (!ev->string)))
2503 else if ((!strcmp(ev->keyname, "Right")) ||
2504 ((!strcmp(ev->keyname, "KP_Right")) && (!ev->string)))
2508 else if ((!strcmp(ev->keyname, "Up")) ||
2509 ((!strcmp(ev->keyname, "KP_Up")) && (!ev->string)))
2511 if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) &&
2512 (_item_multi_select_up(sd)))
2513 || (_item_single_select_up(sd)))
2515 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2521 else if ((!strcmp(ev->keyname, "Down")) ||
2522 ((!strcmp(ev->keyname, "KP_Down")) && (!ev->string)))
2524 if (((evas_key_modifier_is_set(ev->modifiers, "Shift")) &&
2525 (_item_multi_select_down(sd)))
2526 || (_item_single_select_down(sd)))
2528 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2534 else if ((!strcmp(ev->keyname, "Home")) ||
2535 ((!strcmp(ev->keyname, "KP_Home")) && (!ev->string)))
2537 it = elm_genlist_first_item_get(obj);
2538 elm_genlist_item_bring_in(it, ELM_GENLIST_ITEM_SCROLLTO_IN);
2539 elm_genlist_item_selected_set(it, EINA_TRUE);
2540 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2543 else if ((!strcmp(ev->keyname, "End")) ||
2544 ((!strcmp(ev->keyname, "KP_End")) && (!ev->string)))
2546 it = elm_genlist_last_item_get(obj);
2547 elm_genlist_item_bring_in(it, ELM_GENLIST_ITEM_SCROLLTO_IN);
2548 elm_genlist_item_selected_set(it, EINA_TRUE);
2549 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2552 else if ((!strcmp(ev->keyname, "Prior")) ||
2553 ((!strcmp(ev->keyname, "KP_Prior")) && (!ev->string)))
2556 y -= -(page_y * v_h) / 100;
2560 else if ((!strcmp(ev->keyname, "Next")) ||
2561 ((!strcmp(ev->keyname, "KP_Next")) && (!ev->string)))
2564 y += -(page_y * v_h) / 100;
2568 else if (!strcmp(ev->keyname, "Escape"))
2570 if (!_all_items_deselect(sd)) return EINA_FALSE;
2571 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2574 else if (((!strcmp(ev->keyname, "Return")) ||
2575 (!strcmp(ev->keyname, "KP_Enter")) ||
2576 (!strcmp(ev->keyname, "space")))
2577 && (!sd->multi) && (sd->selected))
2579 it = elm_genlist_selected_item_get(obj);
2580 elm_genlist_item_expanded_set(it, !elm_genlist_item_expanded_get(it));
2581 evas_object_smart_callback_call(WIDGET(it), SIG_ACTIVATED, it);
2583 else return EINA_FALSE;
2585 ev->event_flags |= EVAS_EVENT_FLAG_ON_HOLD;
2586 _elm_genlist_pan_smart_pos_max_get(sd->pan_obj, &pan_max_x, &pan_max_y);
2588 if (x > pan_max_x) x = pan_max_x;
2590 if (y > pan_max_y) y = pan_max_y;
2592 sd->s_iface->content_pos_set(obj, x, y, EINA_TRUE);
2598 _elm_genlist_smart_sub_object_add(Evas_Object *obj,
2601 Elm_Widget_Smart_Class *parent_parent;
2603 parent_parent = (Elm_Widget_Smart_Class *)((Evas_Smart_Class *)
2604 _elm_genlist_parent_sc)->parent;
2606 /* skipping layout's code, which registers size hint changing
2607 * callback on sub objects. this is here because items'
2608 * content_get() routines may change hints on the objects after
2609 * creation, thus issuing TOO MANY sizing_eval()'s here. they are
2610 * not needed at here anyway, so let's skip listening to those
2612 if (!parent_parent->sub_object_add(obj, sobj))
2619 _elm_genlist_smart_sub_object_del(Evas_Object *obj,
2622 ELM_GENLIST_DATA_GET(obj, sd);
2624 /* XXX: hack -- also skipping sizing recalculation on
2625 * sub-object-del. genlist's crazy code paths (like groups and
2626 * such) seem to issue a whole lot of deletions and Evas bitches
2627 * about too many recalculations */
2628 sd->on_sub_del = EINA_TRUE;
2630 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->sub_object_del(obj, sobj))
2633 sd->on_sub_del = EINA_FALSE;
2639 _elm_genlist_smart_on_focus(Evas_Object *obj)
2641 ELM_GENLIST_DATA_GET(obj, sd);
2643 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->on_focus(obj))
2646 if (elm_widget_focus_get(obj) && (sd->items) && (sd->selected) &&
2647 (!sd->last_selected_item))
2648 sd->last_selected_item = eina_list_data_get(sd->selected);
2654 _elm_genlist_smart_focus_next(const Evas_Object *obj,
2655 Elm_Focus_Direction dir,
2658 Evas_Coord x, y, w, h;
2659 Evas_Coord sx, sy, sw, sh;
2661 Eina_List *items = NULL;
2662 Eina_Bool done = EINA_FALSE;
2664 ELM_GENLIST_CHECK(obj) EINA_FALSE;
2665 ELM_GENLIST_DATA_GET(obj, sd);
2667 evas_object_geometry_get(ELM_WIDGET_DATA(sd)->obj, &sx, &sy, &sw, &sh);
2669 EINA_INLIST_FOREACH(sd->blocks, itb)
2677 EINA_LIST_FOREACH(itb->items, l, it)
2681 evas_object_geometry_get(it->base.view, &x, &y, &w, &h);
2683 /* check item which displays more than half of its size */
2684 if (ELM_RECTS_INTERSECT
2685 (x + (w / 2), y + (h / 2), 0, 0, sx, sy, sw, sh))
2686 items = eina_list_append(items, it->base.access_obj);
2688 if (!it->base.access_order) continue;
2692 EINA_LIST_FOREACH(it->base.access_order, subl, subo)
2693 items = eina_list_append(items, subo);
2697 else if (done) break;
2700 return elm_widget_focus_list_next_get
2701 (obj, items, eina_list_data_get, dir, next);
2705 _mirrored_set(Evas_Object *obj,
2708 ELM_GENLIST_DATA_GET(obj, sd);
2710 sd->s_iface->mirrored_set(obj, rtl);
2714 _elm_genlist_smart_theme(Evas_Object *obj)
2718 ELM_GENLIST_DATA_GET(obj, sd);
2720 if (!ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->theme(obj))
2723 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2724 _item_cache_all_free(sd);
2725 _mirrored_set(obj, elm_widget_mirrored_get(obj));
2728 // FIXME: difference from opensource
2729 elm_layout_theme_set(obj, "genlist", "base", elm_widget_style_get(obj));
2732 sd->item_width = sd->item_height = 0;
2733 sd->group_item_width = sd->group_item_height = 0;
2734 sd->minw = sd->minh = sd->realminw = 0;
2735 EINA_INLIST_FOREACH(sd->blocks, itb)
2740 if (itb->realized) _item_block_unrealize(itb);
2741 EINA_LIST_FOREACH(itb->items, l, it)
2742 it->item->mincalcd = EINA_FALSE;
2744 itb->changed = EINA_TRUE;
2746 if (sd->calc_job) ecore_job_del(sd->calc_job);
2747 sd->calc_job = NULL;
2748 elm_layout_sizing_eval(obj);
2749 sd->pan_changed = EINA_TRUE;
2750 evas_object_smart_changed(sd->pan_obj);
2751 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2752 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
2757 /* FIXME: take off later. maybe this show region coords belong in the
2758 * interface (new api functions, set/get)? */
2760 _show_region_hook(void *data,
2763 Evas_Coord x, y, w, h;
2765 ELM_GENLIST_DATA_GET(data, sd);
2767 elm_widget_show_region_get(obj, &x, &y, &w, &h);
2768 //x & y are screen coordinates, Add with pan coordinates
2771 sd->s_iface->content_region_show(obj, x, y, w, h);
2775 _elm_genlist_smart_translate(Evas_Object *obj)
2777 evas_object_smart_callback_call(obj, "language,changed", NULL);
2783 _item_highlight(Elm_Gen_Item *it)
2785 const char *selectraise;
2786 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2788 if (elm_widget_item_disabled_get(it)) return;
2789 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2790 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ) ||
2791 (it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2792 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
2795 if (!sd->highlight || it->highlighted) return;
2796 #if GENLIST_PINCH_ZOOM_SUPPORT
2797 if (sd->pinch_zoom_mode) return;
2800 selectraise = edje_object_data_get(VIEW(it), "selectraise");
2801 if ((selectraise) && (!strcmp(selectraise, "on")))
2803 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
2804 else evas_object_raise(VIEW(it));
2805 if ((it->item->group_item) && (it->item->group_item->realized))
2806 evas_object_raise(it->item->VIEW(group_item));
2808 it->highlighted = EINA_TRUE;
2810 if (it->deco_all_view)
2811 edje_object_signal_emit(it->deco_all_view, "elm,state,selected", "elm");
2812 edje_object_signal_emit(VIEW(it), "elm,state,selected", "elm");
2813 evas_object_smart_callback_call(WIDGET(it), SIG_HIGHLIGHTED, it);
2817 _item_unhighlight(Elm_Gen_Item *it)
2819 if (!it->highlighted) return;
2821 if (!it->item->nostacking)
2823 if ((it->item->order_num_in & 0x1) ^ it->item->stacking_even)
2825 if (it->deco_all_view) evas_object_lower(it->deco_all_view);
2826 else evas_object_lower(VIEW(it));
2830 if (it->deco_all_view) evas_object_raise(it->deco_all_view);
2831 else evas_object_raise(VIEW(it));
2834 it->highlighted = EINA_FALSE;
2836 if (it->deco_all_view)
2837 edje_object_signal_emit(it->deco_all_view, "elm,state,unselected", "elm");
2838 edje_object_signal_emit(VIEW(it), "elm,state,unselected", "elm");
2839 evas_object_smart_callback_call(WIDGET(it), SIG_UNHIGHLIGHTED, it);
2843 _item_unselect(Elm_Gen_Item *it)
2845 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2846 _item_unhighlight(it);
2847 if (!it->selected) return;
2849 it->selected = EINA_FALSE;
2850 sd->selected = eina_list_remove(sd->selected, it);
2851 evas_object_smart_callback_call(WIDGET(it), SIG_UNSELECTED, it);
2855 _item_select(Elm_Gen_Item *it)
2857 Evas_Object *obj = WIDGET(it);
2858 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2859 if (elm_widget_item_disabled_get(it)) return;
2860 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2861 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) ||
2862 (it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
2863 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
2866 #if GENLIST_PINCH_ZOOM_SUPPORT
2867 if (IS_ROOT_PARENT_IT(it) && (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT))
2869 elm_genlist_pinch_zoom_mode_set(obj, ELM_GEN_PINCH_ZOOM_EXPAND);
2870 elm_genlist_item_show((Elm_Object_Item *)it, ELM_GENLIST_ITEM_SCROLLTO_TOP);
2876 // FIXME: difference from upstream
2877 if ((GL_IT(it)->wsd->last_selected_item) &&
2878 (it != (Elm_Gen_Item *) GL_IT(it)->wsd->last_selected_item))
2879 _item_unfocusable_set
2880 ((Elm_Gen_Item *)GL_IT(it)->wsd->last_selected_item, EINA_TRUE);
2883 // Do not check selected because always select mode can be used
2884 _item_highlight(it);
2885 it->selected = EINA_TRUE;
2886 sd->selected = eina_list_append(sd->selected, it);
2887 sd->last_selected_item = (Elm_Object_Item *)it;
2889 if (it->func.func) it->func.func((void *)it->func.data, obj, it);
2890 if (!EINA_MAGIC_CHECK((Elm_Widget_Item *)it, ELM_WIDGET_ITEM_MAGIC))
2892 evas_object_smart_callback_call(WIDGET(it), SIG_SELECTED, it);
2896 _item_select_unselect(Elm_Gen_Item *it, Eina_Bool selected)
2898 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
2899 Evas_Object *obj = ELM_WIDGET_DATA(sd)->obj;
2900 if (elm_widget_item_disabled_get(it)) return;
2902 evas_object_ref(obj);
2905 const Eina_List *l, *ll;
2907 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it2)
2908 if (it2 != it) _item_unselect(it2);
2910 if (selected) _item_select(it);
2911 else _item_unselect(it);
2912 evas_object_unref(obj);
2916 _item_block_position_update(Eina_Inlist *list,
2921 EINA_INLIST_FOREACH(list, tmp)
2923 tmp->position = idx++;
2924 tmp->position_update = EINA_TRUE;
2929 _item_position_update(Eina_List *list,
2935 EINA_LIST_FOREACH(list, l, it)
2937 it->position = idx++;
2938 it->position_update = EINA_TRUE;
2943 _item_block_merge(Item_Block *left,
2949 EINA_LIST_FOREACH(right->items, l, it2)
2951 it2->item->block = left;
2953 left->changed = EINA_TRUE;
2955 left->items = eina_list_merge(left->items, right->items);
2959 _item_block_del(Elm_Gen_Item *it)
2962 Item_Block *itb = it->item->block;
2963 Eina_Bool block_changed = EINA_FALSE;
2965 itb->items = eina_list_remove(itb->items, it);
2967 itb->changed = EINA_TRUE;
2968 if (GL_IT(it)->wsd->calc_job) ecore_job_del(GL_IT(it)->wsd->calc_job);
2969 GL_IT(it)->wsd->calc_job = ecore_job_add(_calc_job, GL_IT(it)->wsd);
2974 il = EINA_INLIST_GET(itb);
2975 itbn = (Item_Block *)(il->next);
2977 it->parent->item->items =
2978 eina_list_remove(it->parent->item->items, it);
2981 _item_block_position_update(il->next, itb->position);
2983 GL_IT(it)->wsd->blocks =
2984 eina_inlist_remove(GL_IT(it)->wsd->blocks, il);
2987 if (itbn) itbn->changed = EINA_TRUE;
2991 if (itb->count < (itb->sd->max_items_per_block / 2))
2996 il = EINA_INLIST_GET(itb);
2997 itbp = (Item_Block *)(il->prev);
2998 itbn = (Item_Block *)(il->next);
3000 /* merge block with previous */
3002 ((itbp->count + itb->count) <
3003 (itb->sd->max_items_per_block +
3004 (itb->sd->max_items_per_block / 2))))
3006 _item_block_merge(itbp, itb);
3007 _item_block_position_update
3008 (EINA_INLIST_GET(itb)->next, itb->position);
3009 GL_IT(it)->wsd->blocks = eina_inlist_remove
3010 (GL_IT(it)->wsd->blocks, EINA_INLIST_GET(itb));
3012 block_changed = EINA_TRUE;
3014 /* merge block with next */
3016 ((itbn->count + itb->count) <
3017 (itb->sd->max_items_per_block +
3018 (itb->sd->max_items_per_block / 2))))
3020 _item_block_merge(itb, itbn);
3021 _item_block_position_update
3022 (EINA_INLIST_GET(itbn)->next, itbn->position);
3023 GL_IT(it)->wsd->blocks =
3024 eina_inlist_remove(GL_IT(it)->wsd->blocks,
3025 EINA_INLIST_GET(itbn));
3027 block_changed = EINA_TRUE;
3034 GL_IT(it)->wsd->pan_changed = EINA_TRUE;
3035 evas_object_smart_changed(GL_IT(it)->wsd->pan_obj);
3036 if (GL_IT(it)->wsd->calc_job) ecore_job_del(GL_IT(it)->wsd->calc_job);
3037 GL_IT(it)->wsd->calc_job = NULL;
3039 #if GENLIST_FX_SUPPORT
3040 it->item->block = NULL;
3045 _decorate_all_item_unrealize(Elm_Gen_Item *it)
3049 if ((!it) || (!it->item->decorate_all_item_realized)) return;
3051 #if GENLIST_FX_SUPPORT
3052 if ((GL_IT(it)->has_proxy_it) && (!GL_IT(it)->wsd->genlist_clearing))
3054 if (!eina_list_data_find(GL_IT(it)->wsd->pending_unrealized_decorate_all_items, it))
3055 GL_IT(it)->wsd->pending_unrealized_decorate_all_items =
3056 eina_list_append(GL_IT(it)->wsd->pending_unrealized_decorate_all_items, it);
3061 edje_object_part_unswallow(it->deco_all_view, VIEW(it));
3062 evas_object_smart_member_add(VIEW(it), GL_IT(it)->wsd->pan_obj);
3063 elm_widget_sub_object_add(WIDGET(it), VIEW(it));
3064 _elm_genlist_item_odd_even_update(it);
3065 _elm_genlist_item_state_update(it, NULL);
3067 edje_object_signal_emit
3068 (it->deco_all_view, "elm,state,decorate,disabled", "elm");
3069 edje_object_signal_emit
3070 (VIEW(it), "elm,state,decorate,disabled", "elm");
3071 if (it->item->wsd->reorder_mode)
3073 edje_object_signal_emit
3074 (VIEW(it), "elm,state,reorder,mode_set", "elm");
3075 edje_object_signal_emit
3076 (it->deco_all_view, "elm,state,reorder,mode_unset", "elm");
3079 edje_object_message_signal_process(VIEW(it));
3080 edje_object_message_signal_process(it->deco_all_view);
3082 evas_object_del(it->deco_all_view);
3083 it->deco_all_view = NULL;
3084 elm_widget_stringlist_free(it->item->deco_all_texts);
3085 it->item->deco_all_texts = NULL;
3086 elm_widget_stringlist_free(it->item->deco_all_contents);
3087 it->item->deco_all_contents = NULL;
3088 elm_widget_stringlist_free(it->item->deco_all_states);
3089 it->item->deco_all_states = NULL;
3090 EINA_LIST_FREE (it->item->deco_all_content_objs, icon)
3091 evas_object_del(icon);
3093 _item_mouse_callbacks_del(it, it->deco_all_view);
3094 _item_mouse_callbacks_add(it, VIEW(it));
3096 it->item->decorate_all_item_realized = EINA_FALSE;
3100 _item_free_common(Elm_Gen_Item *it)
3102 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
3103 elm_widget_item_pre_notify_del(it);
3104 if (it->itc->func.del)
3105 it->itc->func.del((void *)it->base.data, WIDGET(it));
3106 if (it->tooltip.del_cb)
3107 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
3108 if (it->item->block) _item_block_del(it);
3110 it->parent->item->items =
3111 eina_list_remove(it->parent->item->items, it);
3112 if (it->item->queued) sd->queue = eina_list_remove(sd->queue, it);
3113 if (it->group) sd->group_items = eina_list_remove(sd->group_items, it);
3115 // FIXME: relative will be better to be fixed. it is too harsh.
3117 it->item->rel->item->rel_revs =
3118 eina_list_remove(it->item->rel->item->rel_revs, it);
3119 if (it->item->rel_revs)
3122 EINA_LIST_FREE(it->item->rel_revs, tmp) tmp->item->rel = NULL;
3124 _item_sub_items_clear(it);
3126 #if GENLIST_ENTRY_SUPPORT
3127 it->item->unrealize_disabled = EINA_FALSE;
3130 if (it->selected) sd->selected = eina_list_remove(sd->selected, it);
3131 if (sd->show_item == it) sd->show_item = NULL;
3132 if (sd->anchor_item == it)
3135 ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
3136 if (!sd->anchor_item) sd->anchor_item =
3137 ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
3139 if (sd->expanded_item == it) sd->expanded_item = NULL;
3140 if (sd->expanded_next_item == it) sd->expanded_next_item = NULL;
3141 if (sd->state) eina_inlist_sorted_state_free(sd->state);
3143 if (sd->last_selected_item == (Elm_Object_Item *)it)
3144 sd->last_selected_item = NULL;
3148 ecore_timer_del(it->long_timer);
3149 it->long_timer = NULL;
3151 if (it->item->swipe_timer) ecore_timer_del(it->item->swipe_timer);
3153 sd->items = eina_inlist_remove(sd->items, EINA_INLIST_GET(it));
3158 _item_mouse_move_cb(void *data,
3159 Evas *evas __UNUSED__,
3163 EINA_SAFETY_ON_NULL_RETURN(data);
3164 Elm_Gen_Item *it = data;
3165 Elm_Genlist_Smart_Data *sd;
3166 Evas_Event_Mouse_Move *ev = event_info;
3167 Evas_Coord ox, oy, ow, oh, it_scrl_y, y_pos;
3168 Evas_Coord minw = 0, minh = 0, x, y, dx, dy, adx, ady;
3170 sd = GL_IT(it)->wsd;
3172 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
3174 if (!sd->on_hold) _item_unselect(it);
3175 sd->on_hold = EINA_TRUE;
3177 if (sd->multi_touched)
3179 sd->cur_x = ev->cur.canvas.x;
3180 sd->cur_y = ev->cur.canvas.y;
3183 if ((it->dragging) && (it->down))
3185 if (sd->movements == SWIPE_MOVES)
3186 sd->swipe = EINA_TRUE;
3189 sd->history[sd->movements].x = ev->cur.canvas.x;
3190 sd->history[sd->movements].y = ev->cur.canvas.y;
3191 if (abs((sd->history[sd->movements].x -
3192 sd->history[0].x)) > 40)
3193 sd->swipe = EINA_TRUE;
3199 ecore_timer_del(it->long_timer);
3200 it->long_timer = NULL;
3202 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG, it);
3205 if ((!it->down) || (sd->longpressed))
3209 ecore_timer_del(it->long_timer);
3210 it->long_timer = NULL;
3212 if ((sd->reorder_mode) && (sd->reorder_it))
3214 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
3216 if (ev->cur.canvas.y < (oy + (sd->reorder_it->item->h / 2)))
3217 sd->reorder_fast = 1;
3218 else if (ev->cur.canvas.y > (oy + oh - (sd->reorder_it->item->h / 2)))
3219 sd->reorder_fast = -1;
3220 else sd->reorder_fast = 0;
3222 it_scrl_y = ev->cur.canvas.y - sd->reorder_it->dy;
3224 if (!sd->reorder_start_y)
3225 sd->reorder_start_y = it->item->block->y + it->y;
3229 else if (it_scrl_y + sd->reorder_it->item->h > oy + oh)
3230 y_pos = oy + oh - sd->reorder_it->item->h;
3234 if (it->deco_all_view)
3235 _item_position(it, it->deco_all_view, it->item->scrl_x, y_pos);
3236 else if (it->item->deco_it_view)
3238 (it, it->item->deco_it_view, it->item->scrl_x, y_pos);
3240 _item_position(it, VIEW(it), it->item->scrl_x, y_pos);
3242 if (sd->calc_job) ecore_job_del(sd->calc_job);
3243 sd->calc_job = ecore_job_add(_calc_job, sd);
3247 if (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
3248 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
3250 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3251 x = ev->cur.canvas.x - x;
3252 y = ev->cur.canvas.y - y;
3255 if (adx < 0) adx = -dx;
3259 if (ady < 0) ady = -dy;
3263 if ((adx > minw) || (ady > minh))
3265 it->dragging = EINA_TRUE;
3268 ecore_timer_del(it->long_timer);
3269 it->long_timer = NULL;
3274 evas_object_smart_callback_call
3275 (WIDGET(it), SIG_DRAG_START_UP, it);
3279 evas_object_smart_callback_call
3280 (WIDGET(it), SIG_DRAG_START_LEFT, it);
3282 evas_object_smart_callback_call
3283 (WIDGET(it), SIG_DRAG_START_RIGHT, it);
3289 evas_object_smart_callback_call
3290 (WIDGET(it), SIG_DRAG_START_DOWN, it);
3294 evas_object_smart_callback_call
3295 (WIDGET(it), SIG_DRAG_START_LEFT, it);
3297 evas_object_smart_callback_call
3298 (WIDGET(it), SIG_DRAG_START_RIGHT, it);
3305 _long_press_cb(void *data)
3307 Elm_Gen_Item *it = data, *it2;
3308 Elm_Genlist_Smart_Data *sd;
3311 sd = GL_IT(it)->wsd;
3313 it->long_timer = NULL;
3314 if (elm_widget_item_disabled_get(it) || (it->dragging) ||
3315 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
3316 return ECORE_CALLBACK_CANCEL;
3318 GL_IT(it)->wsd->longpressed = EINA_TRUE;
3319 evas_object_smart_callback_call(WIDGET(it), SIG_LONGPRESSED, it);
3320 if ((GL_IT(it)->wsd->reorder_mode) && (!it->group))
3322 GL_IT(it)->wsd->reorder_it = it;
3323 GL_IT(it)->wsd->reorder_start_y = 0;
3324 if (it->deco_all_view)
3325 evas_object_raise(it->deco_all_view);
3327 evas_object_raise(VIEW(it));
3329 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_TRUE);
3330 sd->s_iface->bounce_allow_set
3331 (ELM_WIDGET_DATA(sd)->obj, EINA_FALSE, EINA_FALSE);
3333 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it2)
3335 if (it != it2) _item_unselect(it2);
3338 // FIXME: difference from opensource
3339 if (it->item->items)
3341 EINA_LIST_FOREACH(it->item->items, l, it_tmp)
3343 if (elm_genlist_item_expanded_get((Elm_Object_Item *) it_tmp))
3345 elm_genlist_item_expanded_set((Elm_Object_Item *)it_tmp,
3347 return ECORE_CALLBACK_RENEW;
3352 if (elm_genlist_item_expanded_get((Elm_Object_Item *)it))
3354 elm_genlist_item_expanded_set((Elm_Object_Item *)it, EINA_FALSE);
3355 return ECORE_CALLBACK_RENEW;
3358 if (!GL_IT(it)->wsd->decorate_all_mode)
3359 edje_object_signal_emit
3360 (VIEW(it), "elm,state,reorder,enabled", "elm");
3363 return ECORE_CALLBACK_CANCEL;
3367 _swipe_do(Elm_Gen_Item *it)
3372 if ((it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) ||
3373 elm_widget_item_disabled_get(it)) return;
3375 GL_IT(it)->wsd->swipe = EINA_FALSE;
3376 for (i = 0; i < GL_IT(it)->wsd->movements; i++)
3378 sum += GL_IT(it)->wsd->history[i].x;
3379 if (abs(GL_IT(it)->wsd->history[0].y -
3380 GL_IT(it)->wsd->history[i].y) > 10) return;
3383 sum /= GL_IT(it)->wsd->movements;
3384 if (abs(sum - GL_IT(it)->wsd->history[0].x) <= 10) return;
3385 evas_object_smart_callback_call(WIDGET(it), SIG_SWIPE, it);
3389 _swipe_cancel(void *data)
3391 Elm_Gen_Item *it = data;
3393 if (!it) return ECORE_CALLBACK_CANCEL;
3394 GL_IT(it)->wsd->swipe = EINA_FALSE;
3395 GL_IT(it)->wsd->movements = 0;
3397 return ECORE_CALLBACK_RENEW;
3401 _multi_cancel(void *data)
3403 Elm_Genlist_Smart_Data *sd = data;
3405 if (!sd) return ECORE_CALLBACK_CANCEL;
3406 sd->multi_timeout = EINA_TRUE;
3408 return ECORE_CALLBACK_RENEW;
3412 _multi_touch_gesture_eval(void *data)
3414 Elm_Gen_Item *it = data;
3415 Evas_Coord minw = 0, minh = 0;
3416 Evas_Coord off_x, off_y, off_mx, off_my;
3418 GL_IT(it)->wsd->multi_touched = EINA_FALSE;
3419 if (GL_IT(it)->wsd->multi_timer)
3421 ecore_timer_del(GL_IT(it)->wsd->multi_timer);
3422 GL_IT(it)->wsd->multi_timer = NULL;
3424 if (GL_IT(it)->wsd->multi_timeout)
3426 GL_IT(it)->wsd->multi_timeout = EINA_FALSE;
3430 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
3431 off_x = abs(GL_IT(it)->wsd->cur_x - GL_IT(it)->wsd->prev_x);
3432 off_y = abs(GL_IT(it)->wsd->cur_y - GL_IT(it)->wsd->prev_y);
3433 off_mx = abs(GL_IT(it)->wsd->cur_mx - GL_IT(it)->wsd->prev_mx);
3434 off_my = abs(GL_IT(it)->wsd->cur_my - GL_IT(it)->wsd->prev_my);
3436 if (((off_x > minw) || (off_y > minh)) && ((off_mx > minw)
3437 || (off_my > minh)))
3439 if ((off_x + off_mx) > (off_y + off_my))
3441 if ((GL_IT(it)->wsd->cur_x > GL_IT(it)->wsd->prev_x)
3442 && (GL_IT(it)->wsd->cur_mx > GL_IT(it)->wsd->prev_mx))
3443 evas_object_smart_callback_call
3444 (WIDGET(it), SIG_MULTI_SWIPE_RIGHT, it);
3445 else if ((GL_IT(it)->wsd->cur_x < GL_IT(it)->wsd->prev_x)
3446 && (GL_IT(it)->wsd->cur_mx < GL_IT(it)->wsd->prev_mx))
3447 evas_object_smart_callback_call
3448 (WIDGET(it), SIG_MULTI_SWIPE_LEFT, it);
3449 else if (abs(GL_IT(it)->wsd->cur_x - GL_IT(it)->wsd->cur_mx) >
3450 abs(GL_IT(it)->wsd->prev_x - GL_IT(it)->wsd->prev_mx))
3451 evas_object_smart_callback_call
3452 (WIDGET(it), SIG_MULTI_PINCH_OUT, it);
3454 evas_object_smart_callback_call
3455 (WIDGET(it), SIG_MULTI_PINCH_IN, it);
3459 if ((GL_IT(it)->wsd->cur_y > GL_IT(it)->wsd->prev_y)
3460 && (GL_IT(it)->wsd->cur_my > GL_IT(it)->wsd->prev_my))
3461 evas_object_smart_callback_call
3462 (WIDGET(it), SIG_MULTI_SWIPE_DOWN, it);
3463 else if ((GL_IT(it)->wsd->cur_y < GL_IT(it)->wsd->prev_y)
3464 && (GL_IT(it)->wsd->cur_my < GL_IT(it)->wsd->prev_my))
3465 evas_object_smart_callback_call
3466 (WIDGET(it), SIG_MULTI_SWIPE_UP, it);
3467 else if (abs(GL_IT(it)->wsd->cur_y - GL_IT(it)->wsd->cur_my) >
3468 abs(GL_IT(it)->wsd->prev_y - GL_IT(it)->wsd->prev_my))
3470 evas_object_smart_callback_call
3471 (WIDGET(it), SIG_MULTI_PINCH_OUT, it);
3472 #if GENLIST_PINCH_ZOOM_SUPPORT
3473 if (IS_ROOT_PARENT_IT(it) && (GL_IT(it)->wsd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT))
3475 elm_genlist_pinch_zoom_mode_set(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj, ELM_GEN_PINCH_ZOOM_EXPAND);
3476 elm_genlist_item_show((Elm_Object_Item *)it, ELM_GENLIST_ITEM_SCROLLTO_TOP);
3482 evas_object_smart_callback_call
3483 (WIDGET(it), SIG_MULTI_PINCH_IN, it);
3484 #if GENLIST_PINCH_ZOOM_SUPPORT
3485 elm_genlist_pinch_zoom_mode_set(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj,
3486 ELM_GEN_PINCH_ZOOM_CONTRACT);
3492 GL_IT(it)->wsd->multi_timeout = EINA_FALSE;
3496 _item_multi_down_cb(void *data,
3497 Evas *evas __UNUSED__,
3498 Evas_Object *obj __UNUSED__,
3501 Elm_Gen_Item *it = data;
3502 Evas_Event_Multi_Down *ev = event_info;
3504 if ((GL_IT(it)->wsd->multi_device != 0) || (GL_IT(it)->wsd->multi_touched)
3505 || (GL_IT(it)->wsd->multi_timeout))
3508 GL_IT(it)->wsd->multi_device = ev->device;
3509 GL_IT(it)->wsd->multi_down = EINA_TRUE;
3510 GL_IT(it)->wsd->multi_touched = EINA_TRUE;
3511 GL_IT(it)->wsd->prev_mx = ev->canvas.x;
3512 GL_IT(it)->wsd->prev_my = ev->canvas.y;
3514 if (!GL_IT(it)->wsd->wasselected)
3516 GL_IT(it)->wsd->wasselected = EINA_FALSE;
3520 ecore_timer_del(it->long_timer);
3521 it->long_timer = NULL;
3525 it->dragging = EINA_FALSE;
3526 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG_STOP, it);
3528 if (it->item->swipe_timer)
3530 ecore_timer_del(it->item->swipe_timer);
3531 it->item->swipe_timer = NULL;
3533 GL_IT(it)->wsd->longpressed = EINA_FALSE;
3534 if (GL_IT(it)->wsd->on_hold)
3536 GL_IT(it)->wsd->swipe = EINA_FALSE;
3537 GL_IT(it)->wsd->movements = 0;
3538 GL_IT(it)->wsd->on_hold = EINA_FALSE;
3543 _item_multi_up_cb(void *data,
3544 Evas *evas __UNUSED__,
3545 Evas_Object *obj __UNUSED__,
3548 Elm_Gen_Item *it = data;
3549 Evas_Event_Multi_Up *ev = event_info;
3551 if (GL_IT(it)->wsd->multi_device != ev->device) return;
3552 GL_IT(it)->wsd->multi_device = 0;
3553 GL_IT(it)->wsd->multi_down = EINA_FALSE;
3554 if (GL_IT(it)->wsd->mouse_down) return;
3555 _multi_touch_gesture_eval(data);
3559 _item_multi_move_cb(void *data,
3560 Evas *evas __UNUSED__,
3561 Evas_Object *obj __UNUSED__,
3564 Elm_Gen_Item *it = data;
3565 Evas_Event_Multi_Move *ev = event_info;
3567 if (GL_IT(it)->wsd->multi_device != ev->device) return;
3568 GL_IT(it)->wsd->cur_mx = ev->cur.canvas.x;
3569 GL_IT(it)->wsd->cur_my = ev->cur.canvas.y;
3573 // FIXME: difference from upstream
3575 _item_unfocusable_set(Elm_Gen_Item *it, Eina_Bool unfocus)
3578 Evas_Object *item_obj;
3579 Evas_Object *obj = WIDGET(it);
3583 EINA_LIST_FOREACH(it->content_objs, l, item_obj)
3585 if (unfocus) elm_widget_focused_object_clear(item_obj);
3586 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3588 EINA_LIST_FOREACH(it->item->flip_content_objs, l, item_obj)
3590 if (unfocus) elm_widget_focused_object_clear(item_obj);
3591 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3593 EINA_LIST_FOREACH(it->item->deco_all_content_objs, l, item_obj)
3595 if (unfocus) elm_widget_focused_object_clear(item_obj);
3596 elm_widget_tree_unfocusable_set(item_obj, unfocus);
3598 it->can_focus = !unfocus;
3604 _item_mouse_down_cb(void *data,
3605 Evas *evas __UNUSED__,
3609 Evas_Event_Mouse_Down *ev = event_info;
3610 Elm_Gen_Item *it = data;
3611 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
3614 if (ev->button != 1) return;
3616 _item_unfocusable_set(it, EINA_FALSE);
3618 it->down = EINA_TRUE;
3619 it->dragging = EINA_FALSE;
3620 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3621 it->dx = ev->canvas.x - x;
3622 it->dy = ev->canvas.y - y;
3623 sd->mouse_down = EINA_TRUE;
3624 if (!sd->multi_touched)
3626 sd->prev_x = ev->canvas.x;
3627 sd->prev_y = ev->canvas.y;
3628 sd->multi_timeout = EINA_FALSE;
3629 if (sd->multi_timer) ecore_timer_del(sd->multi_timer);
3630 sd->multi_timer = ecore_timer_add(1, _multi_cancel, sd);
3632 sd->longpressed = EINA_FALSE;
3633 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
3635 sd->on_hold = EINA_TRUE;
3638 else sd->on_hold = EINA_FALSE;
3639 _item_highlight(it);
3640 if (ev->flags & EVAS_BUTTON_DOUBLE_CLICK)
3641 if ((!elm_widget_item_disabled_get(it)) &&
3642 (it->select_mode != ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY))
3644 evas_object_smart_callback_call(WIDGET(it), SIG_CLICKED_DOUBLE, it);
3645 evas_object_smart_callback_call(WIDGET(it), SIG_ACTIVATED, it);
3647 if (it->item->swipe_timer) ecore_timer_del(it->item->swipe_timer);
3648 it->item->swipe_timer = ecore_timer_add(0.4, _swipe_cancel, it);
3649 if (it->long_timer) ecore_timer_del(it->long_timer);
3651 it->long_timer = ecore_timer_add
3652 (sd->longpress_timeout, _long_press_cb, it);
3654 it->long_timer = NULL;
3655 sd->swipe = EINA_FALSE;
3660 _item_block_new(Elm_Genlist_Smart_Data *sd,
3665 itb = calloc(1, sizeof(Item_Block));
3666 if (!itb) return NULL;
3670 sd->blocks = eina_inlist_prepend(sd->blocks, EINA_INLIST_GET(itb));
3671 _item_block_position_update(sd->blocks, 0);
3675 sd->blocks = eina_inlist_append(sd->blocks, EINA_INLIST_GET(itb));
3676 itb->position_update = EINA_TRUE;
3677 if (sd->blocks != EINA_INLIST_GET(itb))
3680 ((Item_Block *)(EINA_INLIST_GET(itb)->prev))->position + 1;
3692 _item_block_add(Elm_Genlist_Smart_Data *sd,
3695 Item_Block *itb = NULL;
3702 itb = calloc(1, sizeof(Item_Block));
3703 if (!itb) return EINA_FALSE;
3705 if (!it->item->rel->item->block)
3708 eina_inlist_append(sd->blocks, EINA_INLIST_GET(itb));
3709 itb->items = eina_list_append(itb->items, it);
3710 itb->position_update = EINA_TRUE;
3711 it->position = eina_list_count(itb->items);
3712 it->position_update = EINA_TRUE;
3714 if (sd->blocks != EINA_INLIST_GET(itb))
3718 (EINA_INLIST_GET(itb)->prev))->position + 1;
3729 tmp = eina_list_data_find_list(itb->items, it->item->rel);
3730 if (it->item->before)
3732 sd->blocks = eina_inlist_prepend_relative
3733 (sd->blocks, EINA_INLIST_GET(itb),
3734 EINA_INLIST_GET(it->item->rel->item->block));
3736 eina_list_prepend_relative_list(itb->items, it, tmp);
3738 /* Update index from where we prepended */
3739 _item_position_update
3740 (eina_list_prev(tmp), it->item->rel->position);
3741 _item_block_position_update
3742 (EINA_INLIST_GET(itb),
3743 it->item->rel->item->block->position);
3747 sd->blocks = eina_inlist_append_relative
3748 (sd->blocks, EINA_INLIST_GET(itb),
3749 EINA_INLIST_GET(it->item->rel->item->block));
3751 eina_list_append_relative_list(itb->items, it, tmp);
3753 /* Update block index from where we appended */
3754 _item_position_update
3755 (eina_list_next(tmp), it->item->rel->position + 1);
3756 _item_block_position_update
3757 (EINA_INLIST_GET(itb),
3758 it->item->rel->item->block->position + 1);
3764 if (it->item->before)
3768 itb = (Item_Block *)(sd->blocks);
3769 if (itb->count >= sd->max_items_per_block)
3771 itb = _item_block_new(sd, EINA_TRUE);
3772 if (!itb) return EINA_FALSE;
3777 itb = _item_block_new(sd, EINA_TRUE);
3778 if (!itb) return EINA_FALSE;
3780 itb->items = eina_list_prepend(itb->items, it);
3782 _item_position_update(itb->items, 0);
3788 itb = (Item_Block *)(sd->blocks->last);
3789 if (itb->count >= sd->max_items_per_block)
3791 itb = _item_block_new(sd, EINA_FALSE);
3792 if (!itb) return EINA_FALSE;
3797 itb = _item_block_new(sd, EINA_FALSE);
3798 if (!itb) return EINA_FALSE;
3800 itb->items = eina_list_append(itb->items, it);
3801 it->position = eina_list_count(itb->items);
3809 if (it->item->rel->item->queued)
3811 /* NOTE: for a strange reason eina_list and eina_inlist
3812 don't have the same property on sorted insertion
3813 order, so the queue is not always ordered like the
3814 item list. This lead to issue where we depend on an
3815 item that is not yet created. As a quick work around,
3816 we reschedule the calc of the item and stop reordering
3817 the list to prevent any nasty issue to show up here.
3819 sd->queue = eina_list_append(sd->queue, it);
3820 sd->requeued = EINA_TRUE;
3821 it->item->queued = EINA_TRUE;
3825 itb = it->item->rel->item->block;
3826 if (!itb) goto newblock;
3827 tmp = eina_list_data_find_list(itb->items, it->item->rel);
3828 if (it->item->before)
3830 itb->items = eina_list_prepend_relative_list(itb->items, it, tmp);
3831 _item_position_update
3832 (eina_list_prev(tmp), it->item->rel->position);
3836 itb->items = eina_list_append_relative_list(itb->items, it, tmp);
3837 _item_position_update
3838 (eina_list_next(tmp), it->item->rel->position + 1);
3843 itb->changed = EINA_TRUE;
3844 it->item->block = itb;
3845 if (itb->sd->calc_job) ecore_job_del(itb->sd->calc_job);
3846 itb->sd->calc_job = ecore_job_add(_calc_job, itb->sd);
3848 if (itb->count > itb->sd->max_items_per_block)
3853 Eina_Bool done = EINA_FALSE;
3855 newc = itb->count / 2;
3857 if (EINA_INLIST_GET(itb)->prev)
3859 Item_Block *itbp = (Item_Block *)(EINA_INLIST_GET(itb)->prev);
3861 if (itbp->count + newc < sd->max_items_per_block / 2)
3863 /* moving items to previous block */
3864 while ((itb->count > newc) && (itb->items))
3866 it2 = eina_list_data_get(itb->items);
3867 itb->items = eina_list_remove_list
3868 (itb->items, itb->items);
3871 itbp->items = eina_list_append(itbp->items, it2);
3872 it2->item->block = itbp;
3880 if (!done && EINA_INLIST_GET(itb)->next)
3882 Item_Block *itbn = (Item_Block *)(EINA_INLIST_GET(itb)->next);
3884 if (itbn->count + newc < sd->max_items_per_block / 2)
3886 /* moving items to next block */
3887 while ((itb->count > newc) && (itb->items))
3891 l = eina_list_last(itb->items);
3892 it2 = eina_list_data_get(l);
3893 itb->items = eina_list_remove_list(itb->items, l);
3896 itbn->items = eina_list_prepend(itbn->items, it2);
3897 it2->item->block = itbn;
3907 /* moving items to new block */
3908 itb2 = calloc(1, sizeof(Item_Block));
3909 if (!itb2) return EINA_FALSE;
3912 eina_inlist_append_relative(sd->blocks, EINA_INLIST_GET(itb2),
3913 EINA_INLIST_GET(itb));
3914 itb2->changed = EINA_TRUE;
3915 while ((itb->count > newc) && (itb->items))
3919 l = eina_list_last(itb->items);
3921 itb->items = eina_list_remove_list(itb->items, l);
3924 itb2->items = eina_list_prepend(itb2->items, it2);
3925 it2->item->block = itb2;
3935 _item_process(Elm_Genlist_Smart_Data *sd,
3938 if (!_item_block_add(sd, it)) return 1;
3940 _item_block_realize(it->item->block);
3946 _item_process_post(Elm_Genlist_Smart_Data *sd,
3950 Eina_Bool show_me = EINA_FALSE;
3952 if (it->item->block->changed)
3954 show_me = _item_block_recalc
3955 (it->item->block, it->item->block->num, qadd);
3956 it->item->block->changed = 0;
3957 if (sd->pan_changed)
3959 if (sd->calc_job) ecore_job_del(sd->calc_job);
3960 sd->calc_job = NULL;
3962 sd->pan_changed = EINA_FALSE;
3965 if (show_me) it->item->block->show_me = EINA_TRUE;
3967 /* when prepending, move the scroller along with the first selected
3968 * item to create the illusion that we're watching the selected
3969 * item this prevents the selected item being scrolled off the
3972 if (sd->selected && it->item->before)
3977 it2 = sd->selected->data;
3978 if (!it2->item->block) return;
3979 sd->s_iface->content_pos_get(ELM_WIDGET_DATA(sd)->obj, NULL, &y);
3980 evas_object_geometry_get(sd->pan_obj, NULL, NULL, NULL, &h);
3981 if ((it->y + it->item->block->y > y + h) ||
3982 (it->y + it->item->block->y + it->item->h < y))
3983 /* offscreen, just update */
3984 sd->s_iface->content_region_show
3985 (ELM_WIDGET_DATA(sd)->obj, it2->x + it2->item->block->x, y,
3986 it2->item->block->w, h);
3988 sd->s_iface->content_region_show
3989 (ELM_WIDGET_DATA(sd)->obj, it->x + it->item->block->x,
3990 y + it->item->h, it->item->block->w, h);
3995 _queue_process(Elm_Genlist_Smart_Data *sd)
4000 t0 = ecore_loop_time_get();
4001 for (n = 0; (sd->queue) && (n < 128); n++)
4005 it = eina_list_data_get(sd->queue);
4006 sd->queue = eina_list_remove_list(sd->queue, sd->queue);
4007 it->item->queued = EINA_FALSE;
4008 if (_item_process(sd, it)) continue;
4009 t = ecore_time_get();
4010 _item_process_post(sd, it, EINA_TRUE);
4011 /* same as eina_inlist_count > 1 */
4012 if (sd->blocks && sd->blocks->next)
4014 if ((t - t0) > (ecore_animator_frametime_get())) break;
4021 _idle_process(void *data,
4024 Elm_Genlist_Smart_Data *sd = data;
4026 if (_queue_process(sd) > 0) *wakeup = EINA_TRUE;
4029 return ECORE_CALLBACK_CANCEL;
4031 #if GENLIST_FX_SUPPORT
4032 if (sd->fx_first_captured)
4033 _elm_genlist_fx_clear(ELM_WIDGET_DATA(sd)->obj);
4035 return ECORE_CALLBACK_RENEW;
4039 _item_idle_enterer(void *data)
4041 Eina_Bool wakeup = EINA_FALSE;
4042 Elm_Genlist_Smart_Data *sd = data;
4043 Eina_Bool ok = _idle_process(data, &wakeup);
4048 if (sd->calc_job) ecore_job_del(sd->calc_job);
4049 sd->calc_job = ecore_job_add(_calc_job, sd);
4051 if (ok == ECORE_CALLBACK_CANCEL) sd->queue_idle_enterer = NULL;
4057 _item_queue(Elm_Genlist_Smart_Data *sd,
4061 if (it->item->queued) return;
4062 it->item->queued = EINA_TRUE;
4063 if (cb && !sd->requeued)
4064 sd->queue = eina_list_sorted_insert(sd->queue, cb, it);
4066 sd->queue = eina_list_append(sd->queue, it);
4067 // FIXME: why does a freeze then thaw here cause some genlist
4068 // elm_genlist_item_append() to be much much slower?
4069 // evas_event_freeze(evas_object_evas_get(sd->obj));
4070 while ((sd->queue) && ((!sd->blocks) || (!sd->blocks->next)))
4072 if (sd->queue_idle_enterer)
4074 ecore_idle_enterer_del(sd->queue_idle_enterer);
4075 sd->queue_idle_enterer = NULL;
4079 while ((sd->queue) && (sd->blocks) &&
4080 (sd->homogeneous) && (sd->mode == ELM_LIST_COMPRESS))
4082 if (sd->queue_idle_enterer)
4084 ecore_idle_enterer_del(sd->queue_idle_enterer);
4085 sd->queue_idle_enterer = NULL;
4090 // evas_event_thaw(evas_object_evas_get(sd->obj));
4091 // evas_event_thaw_eval(evas_object_evas_get(sd->obj));
4092 if (!sd->queue_idle_enterer)
4093 sd->queue_idle_enterer = ecore_idle_enterer_add(_item_idle_enterer, sd);
4096 /* If the application wants to know the relative item, use
4097 * elm_genlist_item_prev_get(it)*/
4099 _item_move_after(Elm_Gen_Item *it,
4100 Elm_Gen_Item *after)
4104 if (it == after) return;
4106 GL_IT(it)->wsd->items =
4107 eina_inlist_remove(GL_IT(it)->wsd->items, EINA_INLIST_GET(it));
4108 if (it->item->block) _item_block_del(it);
4110 GL_IT(it)->wsd->items = eina_inlist_append_relative
4111 (GL_IT(it)->wsd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(after));
4112 it->item->rel = after;
4113 after->item->rel_revs = eina_list_append(after->item->rel_revs, it);
4114 it->item->before = EINA_FALSE;
4115 if (after->item->group_item) it->item->group_item = after->item->group_item;
4116 _item_queue(GL_IT(it)->wsd, it, NULL);
4118 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED_AFTER, it);
4122 _access_activate_cb(void *data __UNUSED__,
4123 Evas_Object *part_obj __UNUSED__,
4124 Elm_Object_Item *item)
4126 _item_select_unselect((Elm_Gen_Item *)item, EINA_TRUE);
4129 /* If the application wants to know the relative item, use
4130 * elm_genlist_item_next_get(it)*/
4132 _item_move_before(Elm_Gen_Item *it,
4133 Elm_Gen_Item *before)
4136 if (!before) return;
4137 if (it == before) return;
4139 GL_IT(it)->wsd->items =
4140 eina_inlist_remove(GL_IT(it)->wsd->items, EINA_INLIST_GET(it));
4141 if (it->item->block) _item_block_del(it);
4142 GL_IT(it)->wsd->items = eina_inlist_prepend_relative
4143 (GL_IT(it)->wsd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(before));
4144 it->item->rel = before;
4145 before->item->rel_revs = eina_list_append(before->item->rel_revs, it);
4146 it->item->before = EINA_TRUE;
4147 if (before->item->group_item)
4148 it->item->group_item = before->item->group_item;
4149 _item_queue(GL_IT(it)->wsd, it, NULL);
4151 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED_BEFORE, it);
4155 _item_mouse_up_cb(void *data,
4156 Evas *evas __UNUSED__,
4157 Evas_Object *obj __UNUSED__,
4160 Evas_Event_Mouse_Up *ev = event_info;
4161 Eina_Bool dragged = EINA_FALSE;
4162 Elm_Genlist_Smart_Data *sd;
4163 Elm_Gen_Item *it = data;
4165 if (ev->button != 1) return;
4166 it->down = EINA_FALSE;
4167 sd = GL_IT(it)->wsd;
4169 sd->mouse_down = EINA_FALSE;
4170 if (sd->multi_touched)
4172 if ((!sd->multi) && (!it->selected) && (it->highlighted))
4173 _item_unhighlight(it);
4174 if (sd->multi_down) return;
4175 _multi_touch_gesture_eval(data);
4180 ecore_timer_del(it->long_timer);
4181 it->long_timer = NULL;
4185 it->dragging = EINA_FALSE;
4186 evas_object_smart_callback_call(WIDGET(it), SIG_DRAG_STOP, it);
4189 if (it->item->swipe_timer)
4191 ecore_timer_del(it->item->swipe_timer);
4192 it->item->swipe_timer = NULL;
4194 if (sd->multi_timer)
4196 ecore_timer_del(sd->multi_timer);
4197 sd->multi_timer = NULL;
4198 sd->multi_timeout = EINA_FALSE;
4200 sd->on_hold = EINA_FALSE;
4201 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
4203 if (sd->swipe) _swipe_do(data);
4204 sd->longpressed = EINA_FALSE;
4207 if ((sd->reorder_mode) && (sd->reorder_it))
4209 Evas_Coord it_scrl_y = ev->canvas.y - sd->reorder_it->dy;
4210 sd->reorder_fast = 0;
4212 if (sd->reorder_rel &&
4213 (sd->reorder_it->parent == sd->reorder_rel->parent))
4215 if (it_scrl_y <= sd->reorder_rel->item->scrl_y)
4216 _item_move_before(sd->reorder_it, sd->reorder_rel);
4218 _item_move_after(sd->reorder_it, sd->reorder_rel);
4219 evas_object_smart_callback_call(WIDGET(it), SIG_MOVED, it);
4223 if (sd->calc_job) ecore_job_del(sd->calc_job);
4224 sd->calc_job = ecore_job_add(_calc_job, sd);
4226 edje_object_signal_emit(VIEW(it), "elm,state,reorder,disabled", "elm");
4227 sd->reorder_it = sd->reorder_rel = NULL;
4228 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
4229 sd->s_iface->bounce_allow_set
4230 (ELM_WIDGET_DATA(sd)->obj, sd->h_bounce, sd->v_bounce);
4234 if (it->want_unrealize && !(it->item->unrealize_disabled))
4236 _item_unrealize(it, EINA_FALSE);
4237 if (it->item->block->want_unrealize)
4238 _item_block_unrealize(it->item->block);
4243 if (!sd->longpressed)
4244 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_ALWAYS) ||
4245 (it->select_mode == ELM_OBJECT_SELECT_MODE_ALWAYS))
4246 _item_select_unselect(it, EINA_TRUE);
4247 else _item_select_unselect(it, !it->selected);
4249 _item_unhighlight(it);
4253 _item_mouse_callbacks_add(Elm_Gen_Item *it,
4256 evas_object_event_callback_add
4257 (view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb, it);
4258 evas_object_event_callback_add
4259 (view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4260 evas_object_event_callback_add
4261 (view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb, it);
4262 evas_object_event_callback_add
4263 (view, EVAS_CALLBACK_MULTI_DOWN, _item_multi_down_cb, it);
4264 evas_object_event_callback_add
4265 (view, EVAS_CALLBACK_MULTI_UP, _item_multi_up_cb, it);
4266 evas_object_event_callback_add
4267 (view, EVAS_CALLBACK_MULTI_MOVE, _item_multi_move_cb, it);
4271 _item_mouse_callbacks_del(Elm_Gen_Item *it,
4274 evas_object_event_callback_del_full
4275 (view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb, it);
4276 evas_object_event_callback_del_full
4277 (view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4278 evas_object_event_callback_del_full
4279 (view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb, it);
4280 evas_object_event_callback_del_full
4281 (view, EVAS_CALLBACK_MULTI_DOWN, _item_multi_down_cb, it);
4282 evas_object_event_callback_del_full
4283 (view, EVAS_CALLBACK_MULTI_UP, _item_multi_up_cb, it);
4284 evas_object_event_callback_del_full
4285 (view, EVAS_CALLBACK_MULTI_MOVE, _item_multi_move_cb, it);
4289 _scroll_hold_timer_cb(void *data)
4291 Elm_Genlist_Smart_Data *sd = data;
4293 if (!data) return ECORE_CALLBACK_CANCEL;
4295 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_FALSE);
4296 sd->scr_hold_timer = NULL;
4298 return ECORE_CALLBACK_CANCEL;
4302 _decorate_item_finished_signal_cb(void *data,
4304 const char *emission __UNUSED__,
4305 const char *source __UNUSED__)
4307 Elm_Gen_Item *it = data;
4310 if (!data || !obj) return;
4311 if ((!it->realized) || (!it->item->deco_it_view)) return;
4313 it->item->nocache_once = EINA_FALSE;
4314 _decorate_item_unrealize(it);
4315 if (it->item->group_item)
4316 evas_object_raise(it->item->VIEW(group_item));
4318 snprintf(buf, sizeof(buf), "elm,state,%s,passive,finished",
4319 GL_IT(it)->wsd->decorate_it_type);
4320 edje_object_signal_callback_del_full
4321 (obj, buf, "elm", _decorate_item_finished_signal_cb, it);
4325 _item_mode_content_unrealize(Elm_Gen_Item *it,
4326 Evas_Object *target,
4329 Eina_List **contents_list)
4331 Eina_List *res = *contents_list;
4333 if (it->itc->func.content_get)
4337 Evas_Object *ic = NULL;
4339 EINA_LIST_FOREACH(*source, l, key)
4341 if (parts && fnmatch(parts, key, FNM_PERIOD))
4344 ic = edje_object_part_swallow_get(target, key);
4347 res = eina_list_remove(res, ic);
4348 edje_object_part_unswallow(target, ic);
4349 evas_object_del(ic);
4358 _item_content_unrealize(Elm_Gen_Item *it,
4359 Evas_Object *target,
4363 Eina_List *res = it->content_objs;
4365 if (it->itc->func.content_get)
4369 Evas_Object *ic = NULL;
4371 EINA_LIST_FOREACH(*source, l, key)
4373 if (parts && fnmatch(parts, key, FNM_PERIOD))
4376 ic = edje_object_part_swallow_get(target, key);
4379 res = eina_list_remove(res, ic);
4380 edje_object_part_unswallow(target, ic);
4381 // FIXME: If parent-child relationship was broken before 'ic'
4382 // is deleted, freeze_pop will not be called. ex) elm_slider
4383 // If layout is used instead of edje, this problme can be
4385 if (0 != elm_widget_scroll_freeze_get(ic))
4386 elm_widget_scroll_freeze_pop(ic);
4387 evas_object_del(ic);
4396 _item_block_recalc(Item_Block *itb,
4400 const Eina_List *l, *ll;
4402 Evas_Coord minw = 0, minh = 0;
4403 Eina_Bool show_me = EINA_FALSE, changed = EINA_FALSE;
4407 EINA_LIST_FOREACH_SAFE(itb->items, l, ll, it)
4409 show_me |= it->item->show_me;
4414 if (!it->item->mincalcd) changed = EINA_TRUE;
4417 _item_realize(it, in, EINA_TRUE);
4418 _item_unrealize(it, EINA_TRUE);
4423 if ((itb->sd->homogeneous) &&
4424 (itb->sd->mode == ELM_LIST_COMPRESS))
4428 it->item->w = it->item->minw =
4429 GL_IT(it)->wsd->group_item_width;
4430 it->item->h = it->item->minh =
4431 GL_IT(it)->wsd->group_item_height;
4435 it->item->w = it->item->minw =
4436 GL_IT(it)->wsd->item_width;
4437 it->item->h = it->item->minh =
4438 GL_IT(it)->wsd->item_height;
4443 _item_realize(it, in, EINA_TRUE);
4444 _item_unrealize(it, EINA_TRUE);
4450 if (!it->item->mincalcd) changed = EINA_TRUE;
4451 _item_realize(it, in, EINA_FALSE);
4453 minh += it->item->minh;
4454 if (minw < it->item->minw) minw = it->item->minw;
4458 #if GENLIST_PINCH_ZOOM_SUPPORT
4459 if (IS_ROOT_PARENT_IT(it))
4460 it->item->pan_scrl_y = itb->y + it->y;
4464 if (changed) itb->sd->pan_changed = changed;
4467 itb->changed = EINA_FALSE;
4468 itb->position_update = EINA_FALSE;
4474 _update_job(void *data)
4476 Eina_Bool position = EINA_FALSE, recalc = EINA_FALSE;
4477 Elm_Genlist_Smart_Data *sd = data;
4482 sd->update_job = NULL;
4485 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4486 EINA_INLIST_FOREACH(sd->blocks, itb)
4488 Evas_Coord itminw, itminh;
4495 _item_block_position(itb, num);
4499 recalc = EINA_FALSE;
4500 EINA_LIST_FOREACH(itb->items, l2, it)
4502 if (it->item->updateme)
4504 itminw = it->item->minw;
4505 itminh = it->item->minh;
4507 it->item->updateme = EINA_FALSE;
4510 _item_unrealize(it, EINA_FALSE);
4511 _item_realize(it, num, EINA_FALSE);
4512 position = EINA_TRUE;
4516 _item_realize(it, num, EINA_TRUE);
4517 _item_unrealize(it, EINA_TRUE);
4519 if ((it->item->minw != itminw) || (it->item->minh != itminh))
4524 itb->updateme = EINA_FALSE;
4527 position = EINA_TRUE;
4528 itb->changed = EINA_TRUE;
4529 _item_block_recalc(itb, num0, EINA_FALSE);
4530 _item_block_position(itb, num0);
4535 if (sd->calc_job) ecore_job_del(sd->calc_job);
4536 sd->calc_job = ecore_job_add(_calc_job, sd);
4538 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4539 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4543 _scroll_animate_start_cb(Evas_Object *obj,
4544 void *data __UNUSED__)
4546 evas_object_smart_callback_call(obj, SIG_SCROLL_ANIM_START, NULL);
4550 _scroll_animate_stop_cb(Evas_Object *obj,
4551 void *data __UNUSED__)
4553 evas_object_smart_callback_call(obj, SIG_SCROLL_ANIM_STOP, NULL);
4557 _scroll_drag_start_cb(Evas_Object *obj,
4558 void *data __UNUSED__)
4560 evas_object_smart_callback_call(obj, SIG_SCROLL_DRAG_START, NULL);
4564 _scroll_drag_stop_cb(Evas_Object *obj,
4565 void *data __UNUSED__)
4567 evas_object_smart_callback_call(obj, SIG_SCROLL_DRAG_STOP, NULL);
4571 _edge_left_cb(Evas_Object *obj,
4572 void *data __UNUSED__)
4574 evas_object_smart_callback_call(obj, SIG_EDGE_LEFT, NULL);
4578 _edge_right_cb(Evas_Object *obj,
4579 void *data __UNUSED__)
4581 evas_object_smart_callback_call(obj, SIG_EDGE_RIGHT, NULL);
4585 _edge_top_cb(Evas_Object *obj,
4586 void *data __UNUSED__)
4588 evas_object_smart_callback_call(obj, SIG_EDGE_TOP, NULL);
4592 _edge_bottom_cb(Evas_Object *obj,
4593 void *data __UNUSED__)
4595 evas_object_smart_callback_call(obj, SIG_EDGE_BOTTOM, NULL);
4599 _vbar_drag_cb(Evas_Object *obj,
4600 void *data __UNUSED__)
4602 evas_object_smart_callback_call(obj, SIG_VBAR_DRAG, NULL);
4606 _vbar_press_cb(Evas_Object *obj,
4607 void *data __UNUSED__)
4609 evas_object_smart_callback_call(obj, SIG_VBAR_PRESS, NULL);
4613 _vbar_unpress_cb(Evas_Object *obj,
4614 void *data __UNUSED__)
4616 evas_object_smart_callback_call(obj, SIG_VBAR_UNPRESS, NULL);
4620 _hbar_drag_cb(Evas_Object *obj,
4621 void *data __UNUSED__)
4623 evas_object_smart_callback_call(obj, SIG_HBAR_DRAG, NULL);
4627 _hbar_press_cb(Evas_Object *obj,
4628 void *data __UNUSED__)
4630 evas_object_smart_callback_call(obj, SIG_HBAR_PRESS, NULL);
4634 _hbar_unpress_cb(Evas_Object *obj,
4635 void *data __UNUSED__)
4637 evas_object_smart_callback_call(obj, SIG_HBAR_UNPRESS, NULL);
4641 _decorate_item_realize(Elm_Gen_Item *it)
4644 if (it->item->deco_it_view) return;
4646 //evas_event_freeze(evas_object_evas_get(obj));
4647 it->item->deco_it_view = edje_object_add(evas_object_evas_get(WIDGET(it)));
4648 edje_object_scale_set
4649 (it->item->deco_it_view, elm_widget_scale_get(WIDGET(it)) *
4650 elm_config_scale_get());
4651 evas_object_smart_member_add
4652 (it->item->deco_it_view, GL_IT(it)->wsd->pan_obj);
4653 elm_widget_sub_object_add(WIDGET(it), it->item->deco_it_view);
4655 strncpy(buf, "item", sizeof(buf));
4656 if (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)
4657 strncat(buf, "_compress", sizeof(buf) - strlen(buf));
4659 if (it->item->order_num_in & 0x1)
4660 strncat(buf, "_odd", sizeof(buf) - strlen(buf));
4661 strncat(buf, "/", sizeof(buf) - strlen(buf));
4662 strncat(buf, it->itc->decorate_item_style, sizeof(buf) - strlen(buf));
4664 elm_widget_theme_object_set
4665 (WIDGET(it), it->item->deco_it_view, "genlist", buf,
4666 elm_widget_style_get(WIDGET(it)));
4667 edje_object_mirrored_set
4668 (it->item->deco_it_view, elm_widget_mirrored_get(WIDGET(it)));
4670 /* signal callback add */
4671 evas_object_event_callback_add
4672 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_DOWN, _item_mouse_down_cb,
4674 evas_object_event_callback_add
4675 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_UP, _item_mouse_up_cb, it);
4676 evas_object_event_callback_add
4677 (it->item->deco_it_view, EVAS_CALLBACK_MOUSE_MOVE, _item_mouse_move_cb,
4680 if (eina_list_count(it->item->deco_it_content_objs) != 0)
4681 ERR_ABORT("If you see this error, please notify us and we"
4684 /* text_get, content_get, state_get */
4686 (it, it->item->deco_it_view, &it->item->deco_it_texts, NULL);
4687 if (!it->item->deco_it_contents)
4688 it->item->deco_it_contents =
4689 elm_widget_stringlist_get
4690 (edje_object_data_get(it->item->deco_it_view, "contents"));
4691 it->item->deco_it_content_objs =
4692 _item_mode_content_realize
4693 (it, it->item->deco_it_view, &it->item->deco_it_contents, NULL,
4694 &it->item->deco_it_content_objs);
4696 (it, it->item->deco_it_view, &it->item->deco_it_states, NULL);
4697 edje_object_part_swallow
4698 (it->item->deco_it_view,
4699 edje_object_data_get(it->item->deco_it_view, "mode_part"), VIEW(it));
4701 it->want_unrealize = EINA_FALSE;
4702 //evas_event_thaw(evas_object_evas_get(obj));
4703 //evas_event_thaw_eval(evas_object_evas_get(obj));
4707 _decorate_item_set(Elm_Gen_Item *it)
4709 Elm_Genlist_Smart_Data *sd;
4714 sd = GL_IT(it)->wsd;
4717 it->item->nocache_once = EINA_TRUE;
4719 if (sd->scr_hold_timer)
4721 ecore_timer_del(sd->scr_hold_timer);
4722 sd->scr_hold_timer = NULL;
4724 sd->s_iface->hold_set(ELM_WIDGET_DATA(sd)->obj, EINA_TRUE);
4725 sd->scr_hold_timer = ecore_timer_add(0.1, _scroll_hold_timer_cb, sd);
4727 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4728 _decorate_item_realize(it);
4729 if (it->item->group_item)
4730 evas_object_raise(it->item->VIEW(group_item));
4732 (it, it->item->deco_it_view, it->item->scrl_x, it->item->scrl_y);
4733 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4734 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
4736 snprintf(buf, sizeof(buf), "elm,state,%s,active", sd->decorate_it_type);
4737 edje_object_signal_emit(it->item->deco_it_view, buf, "elm");
4741 _decorate_item_unset(Elm_Genlist_Smart_Data *sd)
4743 char buf[1024], buf2[1024];
4746 if (!sd->mode_item) return;
4749 it->item->nocache_once = EINA_TRUE;
4751 snprintf(buf, sizeof(buf), "elm,state,%s,passive", sd->decorate_it_type);
4752 snprintf(buf2, sizeof(buf2), "elm,state,%s,passive,finished",
4753 sd->decorate_it_type);
4754 edje_object_signal_emit(it->item->deco_it_view, buf, "elm");
4755 edje_object_signal_callback_add
4756 (it->item->deco_it_view, buf2, "elm", _decorate_item_finished_signal_cb,
4758 sd->mode_item = NULL;
4762 // FIXME: difference from upstream
4764 _mouse_down_scroller(void *data,
4765 Evas *evas __UNUSED__,
4766 Evas_Object *obj __UNUSED__,
4767 void *event_info __UNUSED__)
4769 Widget_Data *wd = elm_widget_data_get(data);
4772 wd->drag_started = EINA_FALSE;
4776 _mouse_up_scroller(void *data,
4777 Evas *evas __UNUSED__,
4778 Evas_Object *obj __UNUSED__,
4779 void *event_info __UNUSED__)
4781 Widget_Data *wd = elm_widget_data_get(data);
4784 wd->drag_started = EINA_FALSE;
4788 _mouse_move_scroller(void *data,
4789 Evas *evas __UNUSED__,
4790 Evas_Object *obj __UNUSED__,
4793 Widget_Data *wd = elm_widget_data_get(data);
4794 Evas_Event_Mouse_Move *ev = event_info;
4795 Evas_Coord minw = 0, minh = 0, dx, dy, adx, ady;
4798 if (wd->drag_started) return;
4800 elm_coords_finger_size_adjust(1, &minw, 1, &minh);
4801 dx = ev->cur.canvas.x - ev->prev.canvas.x;
4802 dy = ev->cur.canvas.y - ev->prev.canvas.y;
4805 if (adx < 0) adx = -dx;
4806 if (ady < 0) ady = -dy;
4807 if (((ady < minh) && (ady > minh / 2)) && (ady > adx))
4811 evas_object_smart_callback_call(data, SIG_DRAG_START_UP, NULL);
4812 wd->drag_started = EINA_TRUE;
4816 evas_object_smart_callback_call(data, SIG_DRAG_START_DOWN, NULL);
4817 wd->drag_started = EINA_TRUE;
4824 _elm_genlist_smart_add(Evas_Object *obj)
4826 Evas_Coord minw, minh;
4827 Elm_Genlist_Pan_Smart_Data *pan_data;
4829 EVAS_SMART_DATA_ALLOC(obj, Elm_Genlist_Smart_Data);
4831 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.add(obj);
4833 priv->hit_rect = evas_object_rectangle_add(evas_object_evas_get(obj));
4834 evas_object_smart_member_add(priv->hit_rect, obj);
4835 elm_widget_sub_object_add(obj, priv->hit_rect);
4837 /* common scroller hit rectangle setup */
4838 evas_object_color_set(priv->hit_rect, 0, 0, 0, 0);
4839 evas_object_show(priv->hit_rect);
4840 evas_object_repeat_events_set(priv->hit_rect, EINA_TRUE);
4842 elm_widget_can_focus_set(obj, EINA_TRUE);
4843 elm_widget_on_show_region_hook_set(obj, _show_region_hook, obj);
4845 elm_layout_theme_set(obj, "genlist", "base", elm_widget_style_get(obj));
4847 /* interface's add() routine issued AFTER the object's smart_add() */
4848 priv->s_iface = evas_object_smart_interface_get
4849 (obj, ELM_SCROLLABLE_IFACE_NAME);
4851 priv->s_iface->objects_set
4852 (obj, ELM_WIDGET_DATA(priv)->resize_obj, priv->hit_rect);
4854 priv->s_iface->bounce_allow_set
4855 (obj, EINA_FALSE, _elm_config->thumbscroll_bounce_enable);
4856 priv->v_bounce = _elm_config->thumbscroll_bounce_enable;
4858 priv->s_iface->animate_start_cb_set(obj, _scroll_animate_start_cb);
4859 priv->s_iface->animate_stop_cb_set(obj, _scroll_animate_stop_cb);
4860 priv->s_iface->drag_start_cb_set(obj, _scroll_drag_start_cb);
4861 priv->s_iface->drag_stop_cb_set(obj, _scroll_drag_stop_cb);
4862 priv->s_iface->edge_left_cb_set(obj, _edge_left_cb);
4863 priv->s_iface->edge_right_cb_set(obj, _edge_right_cb);
4864 priv->s_iface->edge_top_cb_set(obj, _edge_top_cb);
4865 priv->s_iface->edge_bottom_cb_set(obj, _edge_bottom_cb);
4866 priv->s_iface->vbar_drag_cb_set(obj, _vbar_drag_cb);
4867 priv->s_iface->vbar_press_cb_set(obj, _vbar_press_cb);
4868 priv->s_iface->vbar_unpress_cb_set(obj, _vbar_unpress_cb);
4869 priv->s_iface->hbar_drag_cb_set(obj, _hbar_drag_cb);
4870 priv->s_iface->hbar_press_cb_set(obj, _hbar_press_cb);
4871 priv->s_iface->hbar_unpress_cb_set(obj, _hbar_unpress_cb);
4873 priv->mode = ELM_LIST_SCROLL;
4874 priv->max_items_per_block = MAX_ITEMS_PER_BLOCK;
4875 priv->item_cache_max = priv->max_items_per_block * 2;
4876 priv->longpress_timeout = _elm_config->longpress_timeout;
4877 priv->highlight = EINA_TRUE;
4879 #if GENLIST_FX_SUPPORT
4880 priv->fx_mode = EINA_FALSE;
4881 priv->rendered = EINA_FALSE;
4882 priv->fx_first_captured = EINA_FALSE;
4883 priv->fx_playing = EINA_FALSE;
4884 priv->fx_items_deleted = EINA_FALSE;
4885 priv->genlist_clearing = EINA_FALSE;
4888 priv->pan_obj = evas_object_smart_add
4889 (evas_object_evas_get(obj), _elm_genlist_pan_smart_class_new());
4890 pan_data = evas_object_smart_data_get(priv->pan_obj);
4891 pan_data->wsd = priv;
4894 // FIXME: difference from upstream
4895 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_DOWN,
4896 _mouse_down_scroller, obj);
4897 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_UP,
4898 _mouse_up_scroller, obj);
4899 evas_object_event_callback_add(pan_obj, EVAS_CALLBACK_MOUSE_MOVE,
4900 _mouse_move_scroller, obj);
4903 priv->s_iface->extern_pan_set(obj, priv->pan_obj);
4905 edje_object_size_min_calc(ELM_WIDGET_DATA(priv)->resize_obj, &minw, &minh);
4906 evas_object_size_hint_min_set(obj, minw, minh);
4908 _item_cache_all_free(priv);
4909 _mirrored_set(obj, elm_widget_mirrored_get(obj));
4911 elm_layout_sizing_eval(obj);
4915 _elm_genlist_smart_del(Evas_Object *obj)
4917 ELM_GENLIST_DATA_GET(obj, sd);
4919 elm_genlist_clear(obj);
4920 if (sd->calc_job) ecore_job_del(sd->calc_job);
4921 if (sd->update_job) ecore_job_del(sd->update_job);
4922 if (sd->queue_idle_enterer) ecore_idle_enterer_del(sd->queue_idle_enterer);
4923 if (sd->must_recalc_idler) ecore_idler_del(sd->must_recalc_idler);
4924 if (sd->multi_timer) ecore_timer_del(sd->multi_timer);
4925 if (sd->decorate_it_type) eina_stringshare_del(sd->decorate_it_type);
4926 if (sd->scr_hold_timer) ecore_timer_del(sd->scr_hold_timer);
4928 evas_object_del(sd->pan_obj);
4929 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.del(obj);
4933 _elm_genlist_smart_move(Evas_Object *obj,
4937 ELM_GENLIST_DATA_GET(obj, sd);
4939 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.move(obj, x, y);
4941 evas_object_move(sd->hit_rect, x, y);
4945 _elm_genlist_smart_resize(Evas_Object *obj,
4949 ELM_GENLIST_DATA_GET(obj, sd);
4951 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.resize(obj, w, h);
4953 evas_object_resize(sd->hit_rect, w, h);
4957 _elm_genlist_smart_member_add(Evas_Object *obj,
4958 Evas_Object *member)
4960 ELM_GENLIST_DATA_GET(obj, sd);
4962 ELM_WIDGET_CLASS(_elm_genlist_parent_sc)->base.member_add(obj, member);
4965 evas_object_raise(sd->hit_rect);
4969 _access_obj_process(Elm_Genlist_Smart_Data *sd, Eina_Bool is_access)
4972 Eina_Bool done = EINA_FALSE;
4974 EINA_INLIST_FOREACH(sd->blocks, itb)
4982 EINA_LIST_FOREACH(itb->items, l, it)
4984 if (!it->realized) continue;
4985 if (is_access) _access_widget_item_register(it);
4987 _elm_access_widget_item_unregister((Elm_Widget_Item *)it);
4990 else if (done) break;
4995 _elm_genlist_smart_access(Evas_Object *obj, Eina_Bool is_access)
4997 ELM_GENLIST_CHECK(obj);
4998 ELM_GENLIST_DATA_GET(obj, sd);
5001 ELM_WIDGET_CLASS(ELM_WIDGET_DATA(sd)->api)->focus_next =
5002 _elm_genlist_smart_focus_next;
5004 ELM_WIDGET_CLASS(ELM_WIDGET_DATA(sd)->api)->focus_next = NULL;
5005 _access_obj_process(sd, is_access);
5009 _elm_genlist_smart_set_user(Elm_Genlist_Smart_Class *sc)
5011 ELM_WIDGET_CLASS(sc)->base.add = _elm_genlist_smart_add;
5012 ELM_WIDGET_CLASS(sc)->base.del = _elm_genlist_smart_del;
5013 ELM_WIDGET_CLASS(sc)->base.move = _elm_genlist_smart_move;
5014 ELM_WIDGET_CLASS(sc)->base.resize = _elm_genlist_smart_resize;
5015 ELM_WIDGET_CLASS(sc)->base.member_add = _elm_genlist_smart_member_add;
5017 ELM_WIDGET_CLASS(sc)->sub_object_add = _elm_genlist_smart_sub_object_add;
5018 ELM_WIDGET_CLASS(sc)->sub_object_del = _elm_genlist_smart_sub_object_del;
5019 ELM_WIDGET_CLASS(sc)->on_focus = _elm_genlist_smart_on_focus;
5020 ELM_WIDGET_CLASS(sc)->theme = _elm_genlist_smart_theme;
5021 ELM_WIDGET_CLASS(sc)->event = _elm_genlist_smart_event;
5022 ELM_WIDGET_CLASS(sc)->translate = _elm_genlist_smart_translate;
5024 /* not a 'focus chain manager' */
5025 ELM_WIDGET_CLASS(sc)->focus_next = NULL;
5026 ELM_WIDGET_CLASS(sc)->focus_direction = NULL;
5028 ELM_LAYOUT_CLASS(sc)->sizing_eval = _elm_genlist_smart_sizing_eval;
5031 if (_elm_config->access_mode == ELM_ACCESS_MODE_ON)
5032 ELM_WIDGET_CLASS(sc)->focus_next = _elm_genlist_smart_focus_next;
5034 ELM_WIDGET_CLASS(sc)->access = _elm_genlist_smart_access;
5037 EAPI const Elm_Genlist_Smart_Class *
5038 elm_genlist_smart_class_get(void)
5040 static Elm_Genlist_Smart_Class _sc =
5041 ELM_GENLIST_SMART_CLASS_INIT_NAME_VERSION(ELM_GENLIST_SMART_NAME);
5042 static const Elm_Genlist_Smart_Class *class = NULL;
5043 Evas_Smart_Class *esc = (Evas_Smart_Class *)&_sc;
5048 _elm_genlist_smart_set(&_sc);
5049 esc->callbacks = _smart_callbacks;
5056 elm_genlist_add(Evas_Object *parent)
5060 EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL);
5062 obj = elm_widget_add(_elm_genlist_smart_class_new(), parent);
5063 if (!obj) return NULL;
5065 if (!elm_widget_sub_object_add(parent, obj))
5066 ERR("could not add %p as sub object of %p", obj, parent);
5072 static Evas_Object *
5073 _item_content_get_hook(Elm_Gen_Item *it,
5076 Evas_Object *ret = NULL;
5077 if (it->deco_all_view)
5078 ret = edje_object_part_swallow_get(it->deco_all_view, part);
5079 else if (it->decorate_it_set)
5080 ret = edje_object_part_swallow_get(it->item->deco_it_view, part);
5082 ret = edje_object_part_swallow_get(VIEW(it), part);
5087 _item_text_get_hook(Elm_Gen_Item *it,
5090 if (!it->itc->func.text_get) return NULL;
5091 const char *ret = NULL;
5092 if (it->deco_all_view)
5093 ret = edje_object_part_text_get(it->deco_all_view, part);
5094 else if (it->decorate_it_set)
5095 ret = edje_object_part_text_get(it->item->deco_it_view, part);
5097 ret = edje_object_part_text_get(VIEW(it), part);
5102 _item_disable_hook(Elm_Object_Item *item)
5106 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5109 elm_genlist_item_selected_set(item, EINA_FALSE);
5113 if (elm_widget_item_disabled_get(it))
5115 edje_object_signal_emit(VIEW(it), "elm,state,disabled", "elm");
5116 if (it->deco_all_view)
5117 edje_object_signal_emit
5118 (it->deco_all_view, "elm,state,disabled", "elm");
5122 edje_object_signal_emit(VIEW(it), "elm,state,enabled", "elm");
5123 if (it->deco_all_view)
5124 edje_object_signal_emit
5125 (it->deco_all_view, "elm,state,enabled", "elm");
5127 EINA_LIST_FOREACH(it->content_objs, l, obj)
5128 elm_widget_disabled_set(obj, elm_widget_item_disabled_get(it));
5133 _item_free(Elm_Gen_Item *it)
5135 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
5137 #if GENLIST_FX_SUPPORT
5138 if (sd->fx_mode) GL_IT(it)->has_proxy_it = EINA_FALSE;
5139 _elm_genlist_proxy_item_del((Elm_Object_Item *)it);
5140 if ((!sd->fx_mode) || (sd->genlist_clearing))
5143 _item_free_common(it);
5145 _item_unrealize(it, EINA_FALSE);
5146 elm_genlist_item_class_unref((Elm_Genlist_Item_Class *)it->itc);
5149 if (sd->calc_job) ecore_job_del(sd->calc_job);
5150 sd->calc_job = ecore_job_add(_calc_job, sd);
5153 #if GENLIST_FX_SUPPORT
5155 _item_del_pre_fx_process(Elm_Gen_Item *it)
5157 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
5159 sd->fx_items_deleted = EINA_TRUE;
5160 _elm_genlist_fx_capture(ELM_WIDGET_DATA(sd)->obj, 0);
5161 if (!eina_list_data_find(sd->pending_del_items, it))
5162 sd->pending_del_items = eina_list_append(sd->pending_del_items, it);
5164 _item_free_common(it);
5170 _item_del_pre_hook(Elm_Object_Item *item)
5172 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5174 #if GENLIST_FX_SUPPORT
5175 if ((GL_IT(it)->wsd->fx_mode) && (!GL_IT(it)->wsd->genlist_clearing))
5177 _item_del_pre_fx_process(it);
5186 _item_signal_emit_hook(Elm_Object_Item *it,
5187 const char *emission,
5190 edje_object_signal_emit(VIEW(it), emission, source);
5193 static Elm_Gen_Item *
5194 _elm_genlist_item_new(Elm_Genlist_Smart_Data *sd,
5195 const Elm_Genlist_Item_Class *itc,
5197 Elm_Gen_Item *parent,
5198 Elm_Genlist_Item_Type type,
5200 const void *func_data)
5202 Elm_Gen_Item *it, *it2;
5205 if (!itc) return NULL;
5207 it = elm_widget_item_new(ELM_WIDGET_DATA(sd)->obj, Elm_Gen_Item);
5208 if (!it) return NULL;
5211 elm_genlist_item_class_ref((Elm_Genlist_Item_Class *)itc);
5213 it->base.data = data;
5214 it->parent = parent;
5215 it->func.func = func;
5216 it->func.data = func_data;
5218 elm_widget_item_content_get_hook_set(it, _item_content_get_hook);
5219 elm_widget_item_text_get_hook_set(it, _item_text_get_hook);
5220 elm_widget_item_disable_hook_set(it, _item_disable_hook);
5221 elm_widget_item_del_pre_hook_set(it, _item_del_pre_hook);
5222 elm_widget_item_signal_emit_hook_set(it, _item_signal_emit_hook);
5224 #if 0 // FIXME: difference from upstream
5225 it->can_focus = EINA_TRUE;
5227 //it->del_cb = (Ecore_Cb)_item_free;
5228 //it->highlight_cb = (Ecore_Cb)_item_highlight;
5229 //it->unhighlight_cb = (Ecore_Cb)_item_unhighlight;
5230 //it->sel_cb = (Ecore_Cb)_item_select;
5231 //it->unsel_cb = (Ecore_Cb)_item_unselect;
5232 //it->unrealize_cb = (Ecore_Cb)_item_unrealize_cb;
5234 GL_IT(it) = ELM_NEW(Elm_Gen_Item_Type);
5235 GL_IT(it)->wsd = sd;
5236 GL_IT(it)->type = type;
5237 if (type & ELM_GENLIST_ITEM_GROUP) it->group++;
5241 if (it->parent->group)
5242 GL_IT(it)->group_item = parent;
5243 else if (GL_IT(it->parent)->group_item)
5244 GL_IT(it)->group_item = GL_IT(it->parent)->group_item;
5246 for (it2 = it, depth = 0; it2->parent; it2 = it2->parent)
5248 if (!it2->parent->group) depth += 1;
5250 GL_IT(it)->expanded_depth = depth;
5253 #if GENLIST_FX_SUPPORT
5254 it->item->num = sd->item_count;
5257 sd->fx_items_deleted = EINA_FALSE;
5258 _elm_genlist_fx_capture(ELM_WIDGET_DATA(sd)->obj, 0);
5265 _elm_genlist_item_compare(const void *data,
5268 const Elm_Gen_Item *it, *item1;
5270 it = ELM_GEN_ITEM_FROM_INLIST(data);
5271 item1 = ELM_GEN_ITEM_FROM_INLIST(data1);
5272 return GL_IT(it)->wsd->item_compare_cb(it, item1);
5276 _elm_genlist_item_list_compare(const void *data,
5279 const Elm_Gen_Item *it = data;
5280 const Elm_Gen_Item *item1 = data1;
5282 return GL_IT(it)->wsd->item_compare_cb(it, item1);
5286 elm_genlist_items_count(const Evas_Object *obj)
5288 ELM_GENLIST_CHECK(obj) 0;
5289 ELM_GENLIST_DATA_GET(obj, sd);
5291 return sd->item_count;
5294 EAPI Elm_Object_Item *
5295 elm_genlist_item_append(Evas_Object *obj,
5296 const Elm_Genlist_Item_Class *itc,
5298 Elm_Object_Item *parent,
5299 Elm_Genlist_Item_Type type,
5301 const void *func_data)
5305 ELM_GENLIST_CHECK(obj) NULL;
5306 ELM_GENLIST_DATA_GET(obj, sd);
5308 ELM_WIDGET_ITEM_RETURN_IF_ONDEL(((Elm_Widget_Item *)parent),NULL);
5310 it = _elm_genlist_item_new
5311 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5312 if (!it) return NULL;
5317 sd->group_items = eina_list_append(sd->group_items, it);
5318 sd->items = eina_inlist_append(sd->items, EINA_INLIST_GET(it));
5319 it->item->rel = NULL;
5323 Elm_Gen_Item *it2 = NULL;
5324 Eina_List *ll = eina_list_last(it->parent->item->items);
5326 if (ll) it2 = ll->data;
5327 it->parent->item->items =
5328 eina_list_append(it->parent->item->items, it);
5329 if (!it2) it2 = it->parent;
5330 sd->items = eina_inlist_append_relative
5331 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(it2));
5332 it->item->rel = it2;
5333 it2->item->rel_revs = eina_list_append(it2->item->rel_revs, it);
5335 it->item->before = EINA_FALSE;
5336 _item_queue(sd, it, NULL);
5338 return (Elm_Object_Item *)it;
5341 EAPI Elm_Object_Item *
5342 elm_genlist_item_prepend(Evas_Object *obj,
5343 const Elm_Genlist_Item_Class *itc,
5345 Elm_Object_Item *parent,
5346 Elm_Genlist_Item_Type type,
5348 const void *func_data)
5352 ELM_GENLIST_CHECK(obj) NULL;
5353 ELM_GENLIST_DATA_GET(obj, sd);
5354 it = _elm_genlist_item_new
5355 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5356 if (!it) return NULL;
5361 sd->group_items = eina_list_prepend(sd->group_items, it);
5362 sd->items = eina_inlist_prepend(sd->items, EINA_INLIST_GET(it));
5363 it->item->rel = NULL;
5367 Elm_Gen_Item *it2 = NULL;
5368 Eina_List *ll = it->parent->item->items;
5370 if (ll) it2 = ll->data;
5371 it->parent->item->items =
5372 eina_list_prepend(it->parent->item->items, it);
5373 if (!it2) it2 = it->parent;
5374 sd->items = eina_inlist_prepend_relative
5375 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(it2));
5376 it->item->rel = it2;
5377 it2->item->rel_revs = eina_list_append(it2->item->rel_revs, it);
5379 it->item->before = EINA_TRUE;
5380 _item_queue(sd, it, NULL);
5382 return (Elm_Object_Item *)it;
5385 EAPI Elm_Object_Item *
5386 elm_genlist_item_insert_after(Evas_Object *obj,
5387 const Elm_Genlist_Item_Class *itc,
5389 Elm_Object_Item *parent,
5390 Elm_Object_Item *after_it,
5391 Elm_Genlist_Item_Type type,
5393 const void *func_data)
5395 Elm_Gen_Item *after = (Elm_Gen_Item *)after_it;
5398 ELM_GENLIST_CHECK(obj) NULL;
5399 ELM_GENLIST_ITEM_CHECK_OR_RETURN(after_it, NULL);
5400 ELM_GENLIST_DATA_GET(obj, sd);
5402 /* It makes no sense to insert after in an empty list with after !=
5403 * NULL, something really bad is happening in your app. */
5404 EINA_SAFETY_ON_NULL_RETURN_VAL(sd->items, NULL);
5406 it = _elm_genlist_item_new
5407 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5408 if (!it) return NULL;
5412 if ((it->group) && (after->group))
5413 sd->group_items = eina_list_append_relative
5414 (sd->group_items, it, after);
5418 it->parent->item->items =
5419 eina_list_append_relative(it->parent->item->items, it, after);
5421 sd->items = eina_inlist_append_relative
5422 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(after));
5424 it->item->rel = after;
5425 after->item->rel_revs = eina_list_append(after->item->rel_revs, it);
5426 it->item->before = EINA_FALSE;
5427 _item_queue(sd, it, NULL);
5429 return (Elm_Object_Item *)it;
5432 EAPI Elm_Object_Item *
5433 elm_genlist_item_insert_before(Evas_Object *obj,
5434 const Elm_Genlist_Item_Class *itc,
5436 Elm_Object_Item *parent,
5437 Elm_Object_Item *before_it,
5438 Elm_Genlist_Item_Type type,
5440 const void *func_data)
5442 Elm_Gen_Item *before = (Elm_Gen_Item *)before_it;
5445 ELM_GENLIST_CHECK(obj) NULL;
5446 ELM_GENLIST_ITEM_CHECK_OR_RETURN(before_it, NULL);
5447 ELM_GENLIST_DATA_GET(obj, sd);
5449 /* It makes no sense to insert before in an empty list with before
5450 * != NULL, something really bad is happening in your app. */
5451 EINA_SAFETY_ON_NULL_RETURN_VAL(sd->items, NULL);
5453 it = _elm_genlist_item_new
5454 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5455 if (!it) return NULL;
5459 if (it->group && before->group)
5461 eina_list_prepend_relative(sd->group_items, it, before);
5465 it->parent->item->items =
5466 eina_list_prepend_relative(it->parent->item->items, it, before);
5468 sd->items = eina_inlist_prepend_relative
5469 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(before));
5471 it->item->rel = before;
5472 before->item->rel_revs = eina_list_append(before->item->rel_revs, it);
5473 it->item->before = EINA_TRUE;
5474 _item_queue(sd, it, NULL);
5476 return (Elm_Object_Item *)it;
5479 EAPI Elm_Object_Item *
5480 elm_genlist_item_sorted_insert(Evas_Object *obj,
5481 const Elm_Genlist_Item_Class *itc,
5483 Elm_Object_Item *parent,
5484 Elm_Genlist_Item_Type type,
5485 Eina_Compare_Cb comp,
5487 const void *func_data)
5489 Elm_Gen_Item *rel = NULL;
5492 ELM_GENLIST_CHECK(obj) NULL;
5493 ELM_GENLIST_DATA_GET(obj, sd);
5495 it = _elm_genlist_item_new
5496 (sd, itc, data, (Elm_Gen_Item *)parent, type, func, func_data);
5497 if (!it) return NULL;
5499 sd->item_compare_cb = comp;
5506 l = eina_list_search_sorted_near_list
5507 (it->parent->item->items, _elm_genlist_item_list_compare, it,
5511 rel = eina_list_data_get(l);
5515 if (cmp_result >= 0)
5517 it->parent->item->items = eina_list_prepend_relative_list
5518 (it->parent->item->items, it, l);
5519 sd->items = eina_inlist_prepend_relative
5520 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(rel));
5521 it->item->before = EINA_FALSE;
5523 else if (cmp_result < 0)
5525 it->parent->item->items = eina_list_append_relative_list
5526 (it->parent->item->items, it, l);
5527 sd->items = eina_inlist_append_relative
5528 (sd->items, EINA_INLIST_GET(it), EINA_INLIST_GET(rel));
5529 it->item->before = EINA_TRUE;
5536 sd->state = eina_inlist_sorted_state_new();
5537 eina_inlist_sorted_state_init(sd->state, sd->items);
5538 sd->requeued = EINA_FALSE;
5542 sd->group_items = eina_list_append(sd->group_items, it);
5544 sd->items = eina_inlist_sorted_state_insert
5545 (sd->items, EINA_INLIST_GET(it), _elm_genlist_item_compare,
5548 if (EINA_INLIST_GET(it)->next)
5550 rel = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
5551 it->item->before = EINA_TRUE;
5553 else if (EINA_INLIST_GET(it)->prev)
5555 rel = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
5556 it->item->before = EINA_FALSE;
5562 it->item->rel = rel;
5563 rel->item->rel_revs = eina_list_append(rel->item->rel_revs, it);
5566 _item_queue(sd, it, _elm_genlist_item_list_compare);
5568 return (Elm_Object_Item *)it;
5572 _elm_genlist_fx_clear(Evas_Object *obj)
5574 ELM_GENLIST_DATA_GET(obj, sd);
5576 Elm_Gen_FX_Item *fi;
5580 EINA_LIST_FREE(sd->capture_before_items, pi)
5582 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
5583 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
5584 if (pi->proxy) evas_object_del(pi->proxy);
5587 EINA_LIST_FREE(sd->capture_after_items, pi)
5589 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
5590 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
5591 if (pi->proxy) evas_object_del(pi->proxy);
5595 EINA_LIST_FREE(sd->fx_items, fi)
5597 if (fi->trans) elm_transit_del(fi->trans);
5601 EINA_LIST_FREE (sd->pending_unrealized_items, it)
5602 _item_unrealize(it, EINA_FALSE);
5604 EINA_LIST_FREE (sd->pending_unrealized_decorate_all_items, it)
5605 _decorate_all_item_unrealize(it);
5607 EINA_LIST_FREE (sd->pending_del_items, it)
5610 _elm_widget_item_free((Elm_Widget_Item *)it);
5612 if (sd->alpha_bg) evas_object_del(sd->alpha_bg);
5613 sd->alpha_bg = NULL;
5614 if (sd->fx_timer) ecore_timer_del(sd->fx_timer);
5615 sd->fx_timer = NULL;
5617 sd->genlist_clearing = EINA_TRUE;
5618 sd->fx_playing = EINA_FALSE;
5619 sd->sorting = EINA_FALSE;
5620 sd->fx_first_captured = EINA_FALSE;
5621 sd->fx_items_deleted = EINA_FALSE;
5625 elm_genlist_clear(Evas_Object *obj)
5627 ELM_GENLIST_CHECK(obj);
5628 ELM_GENLIST_DATA_GET(obj, sd);
5633 eina_inlist_sorted_state_free(sd->state);
5637 #if GENLIST_FX_SUPPORT
5640 _elm_genlist_fx_clear(obj);
5641 sd->genlist_clearing = EINA_TRUE;
5642 sd->rendered = EINA_FALSE;
5645 #if GENLIST_PINCH_ZOOM_SUPPORT
5646 sd->pinch_zoom_h = 0;
5647 sd->realized_top_item = NULL;
5648 sd->pinch_zoom_mode = ELM_GEN_PINCH_ZOOM_NONE;
5651 //evas_event_freeze(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5653 // Do not use EINA_INLIST_FOREACH or EINA_INLIST_FOREACH_SAFE
5654 // because sd->items can be modified inside elm_widget_item_del()
5657 it = EINA_INLIST_CONTAINER_GET(sd->items->last, Elm_Gen_Item);
5658 it->item->nocache_once = EINA_TRUE;
5659 elm_widget_item_del(it);
5663 _item_cache_all_free(sd);
5665 sd->pan_changed = EINA_TRUE;
5666 if (sd->selected) sd->selected = eina_list_free(sd->selected);
5667 sd->selected = NULL;
5669 sd->anchor_item = NULL;
5670 if (sd->multi_timer)
5672 ecore_timer_del(sd->multi_timer);
5673 sd->multi_timer = NULL;
5677 ecore_job_del(sd->update_job);
5678 sd->update_job = NULL;
5682 ecore_job_del(sd->calc_job);
5683 sd->calc_job = NULL;
5685 if (sd->queue_idle_enterer)
5687 ecore_idle_enterer_del(sd->queue_idle_enterer);
5688 sd->queue_idle_enterer = NULL;
5690 if (sd->must_recalc_idler)
5692 ecore_idler_del(sd->must_recalc_idler);
5693 sd->must_recalc_idler = NULL;
5695 if (sd->queue) sd->queue = eina_list_free(sd->queue);
5696 if (sd->reorder_move_animator)
5698 ecore_animator_del(sd->reorder_move_animator);
5699 sd->reorder_move_animator = NULL;
5701 sd->show_item = NULL;
5702 sd->reorder_old_pan_y = 0;
5709 if (sd->alpha_bg) evas_object_del(sd->alpha_bg);
5710 sd->alpha_bg = NULL;
5714 evas_object_size_hint_min_set(sd->pan_obj, sd->minw, sd->minh);
5715 evas_object_smart_callback_call(sd->pan_obj, "changed", NULL);
5717 elm_layout_sizing_eval(ELM_WIDGET_DATA(sd)->obj);
5718 sd->s_iface->content_region_show(obj, 0, 0, 0, 0);
5720 #if GENLIST_FX_SUPPORT
5721 sd->genlist_clearing = EINA_FALSE;
5723 //evas_event_thaw(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5724 //evas_event_thaw_eval(evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5728 elm_genlist_multi_select_set(Evas_Object *obj,
5731 ELM_GENLIST_CHECK(obj);
5732 ELM_GENLIST_DATA_GET(obj, sd);
5734 sd->multi = !!multi;
5738 elm_genlist_multi_select_get(const Evas_Object *obj)
5740 ELM_GENLIST_CHECK(obj) EINA_FALSE;
5741 ELM_GENLIST_DATA_GET(obj, sd);
5746 EAPI Elm_Object_Item *
5747 elm_genlist_selected_item_get(const Evas_Object *obj)
5749 ELM_GENLIST_CHECK(obj) NULL;
5750 ELM_GENLIST_DATA_GET(obj, sd);
5753 return sd->selected->data;
5759 elm_genlist_selected_items_get(const Evas_Object *obj)
5761 ELM_GENLIST_CHECK(obj) NULL;
5762 ELM_GENLIST_DATA_GET(obj, sd);
5764 return sd->selected;
5768 elm_genlist_realized_items_get(const Evas_Object *obj)
5771 Eina_List *list = NULL;
5772 Eina_Bool done = EINA_FALSE;
5774 ELM_GENLIST_CHECK(obj) NULL;
5775 ELM_GENLIST_DATA_GET(obj, sd);
5777 EINA_INLIST_FOREACH(sd->blocks, itb)
5785 EINA_LIST_FOREACH(itb->items, l, it)
5787 if (it->realized) list = eina_list_append(list, it);
5798 EAPI Elm_Object_Item *
5799 elm_genlist_at_xy_item_get(const Evas_Object *obj,
5804 Evas_Coord ox, oy, ow, oh;
5808 ELM_GENLIST_CHECK(obj) NULL;
5809 ELM_GENLIST_DATA_GET(obj, sd);
5811 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
5813 EINA_INLIST_FOREACH(sd->blocks, itb)
5818 if (!ELM_RECTS_INTERSECT(ox + itb->x - itb->sd->pan_x,
5819 oy + itb->y - itb->sd->pan_y,
5820 itb->w, itb->h, x, y, 1, 1))
5822 EINA_LIST_FOREACH(itb->items, l, it)
5824 Evas_Coord itx, ity;
5826 itx = ox + itb->x + it->x - itb->sd->pan_x;
5827 ity = oy + itb->y + it->y - itb->sd->pan_y;
5828 if (ELM_RECTS_INTERSECT
5829 (itx, ity, it->item->w, it->item->h, x, y, 1, 1))
5833 if (y <= (ity + (it->item->h / 4))) *posret = -1;
5834 else if (y >= (ity + it->item->h - (it->item->h / 4)))
5839 return (Elm_Object_Item *)it;
5841 lasty = ity + it->item->h;
5846 if (y > lasty) *posret = 1;
5853 EAPI Elm_Object_Item *
5854 elm_genlist_first_item_get(const Evas_Object *obj)
5856 Elm_Gen_Item *tit, *it = NULL;
5858 ELM_GENLIST_CHECK(obj) NULL;
5859 ELM_GENLIST_DATA_GET(obj, sd);
5861 EINA_INLIST_REVERSE_FOREACH(sd->items, tit) it = tit;
5863 return (Elm_Object_Item *)it;
5866 EAPI Elm_Object_Item *
5867 elm_genlist_last_item_get(const Evas_Object *obj)
5871 ELM_GENLIST_CHECK(obj) NULL;
5872 ELM_GENLIST_DATA_GET(obj, sd);
5873 if (!sd->items) return NULL;
5875 it = ELM_GEN_ITEM_FROM_INLIST(sd->items->last);
5876 return (Elm_Object_Item *)it;
5879 EAPI Elm_Object_Item *
5880 elm_genlist_item_next_get(const Elm_Object_Item *item)
5884 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
5886 it = (Elm_Gen_Item *)item;
5889 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->next);
5893 return (Elm_Object_Item *)it;
5896 EAPI Elm_Object_Item *
5897 elm_genlist_item_prev_get(const Elm_Object_Item *item)
5901 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
5903 it = (Elm_Gen_Item *)item;
5906 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
5910 return (Elm_Object_Item *)it;
5913 EAPI Elm_Object_Item *
5914 elm_genlist_item_parent_get(const Elm_Object_Item *it)
5916 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, NULL);
5918 return (Elm_Object_Item *)((Elm_Gen_Item *)it)->parent;
5922 elm_genlist_item_subitems_clear(Elm_Object_Item *item)
5924 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5926 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5927 _item_sub_items_clear(it);
5931 elm_genlist_item_selected_set(Elm_Object_Item *item,
5934 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5935 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
5937 if (elm_widget_item_disabled_get(it)) return;
5938 selected = !!selected;
5939 if (it->selected == selected) return;
5941 _item_select_unselect(it, selected);
5945 elm_genlist_item_selected_get(const Elm_Object_Item *it)
5947 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, EINA_FALSE);
5949 return ((Elm_Gen_Item *)it)->selected;
5952 static Elm_Gen_Item *
5953 _elm_genlist_expanded_next_item_get(Elm_Gen_Item *it)
5957 if (it->item->expanded)
5959 it2 = (Elm_Gen_Item *)elm_genlist_item_next_get((Elm_Object_Item *)it);
5963 it2 = (Elm_Gen_Item *)elm_genlist_item_next_get((Elm_Object_Item *)it);
5966 if (it->item->expanded_depth >= it2->item->expanded_depth) break;
5967 it2 = (Elm_Gen_Item *)
5968 elm_genlist_item_next_get((Elm_Object_Item *)it2);
5974 static Evas_Object *
5975 _tray_alpha_bg_create(const Evas_Object *obj)
5977 Evas_Object *bg = NULL;
5978 Evas_Coord ox, oy, ow, oh;
5980 ELM_GENLIST_CHECK(obj) NULL;
5981 ELM_GENLIST_DATA_GET(obj, sd);
5983 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
5984 bg = evas_object_rectangle_add
5985 (evas_object_evas_get(ELM_WIDGET_DATA(sd)->obj));
5986 evas_object_color_set(bg, 0, 0, 0, 0);
5987 evas_object_resize(bg, ow, oh);
5988 evas_object_move(bg, ox, oy);
5994 elm_genlist_item_expanded_set(Elm_Object_Item *item,
5997 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
5999 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6001 expanded = !!expanded;
6002 if (it->item->expanded == expanded) return;
6003 if (it->item->type != ELM_GENLIST_ITEM_TREE) return;
6004 it->item->expanded = expanded;
6005 GL_IT(it)->wsd->expanded_item = it;
6006 GL_IT(it)->wsd->expanded_next_item =
6007 _elm_genlist_expanded_next_item_get(it);
6009 if (it->item->expanded)
6012 edje_object_signal_emit(VIEW(it), "elm,state,expanded", "elm");
6013 evas_object_smart_callback_call(WIDGET(it), SIG_EXPANDED, it);
6014 GL_IT(it)->wsd->auto_scroll_enabled = EINA_TRUE;
6019 edje_object_signal_emit(VIEW(it), "elm,state,contracted", "elm");
6020 evas_object_smart_callback_call(WIDGET(it), SIG_CONTRACTED, it);
6021 GL_IT(it)->wsd->auto_scroll_enabled = EINA_FALSE;
6026 elm_genlist_item_expanded_get(const Elm_Object_Item *it)
6028 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, EINA_FALSE);
6030 return ((Elm_Gen_Item *)it)->item->expanded;
6034 elm_genlist_item_expanded_depth_get(const Elm_Object_Item *it)
6036 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it, 0);
6038 return ((Elm_Gen_Item *)it)->item->expanded_depth;
6042 _elm_genlist_item_coordinates_calc(Elm_Object_Item *item,
6043 Elm_Genlist_Item_Scrollto_Type type,
6050 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6051 Evas_Coord gith = 0;
6053 if (!((GL_IT(it)->wsd->homogeneous) &&
6054 (GL_IT(it)->wsd->mode == ELM_LIST_COMPRESS)))
6056 if ((it->item->queued) || (!it->item->mincalcd))
6058 GL_IT(it)->wsd->show_item = it;
6059 GL_IT(it)->wsd->bring_in = bring_in;
6060 GL_IT(it)->wsd->scroll_to_type = type;
6061 it->item->show_me = EINA_TRUE;
6065 if (GL_IT(it)->wsd->show_item)
6067 GL_IT(it)->wsd->show_item->item->show_me = EINA_FALSE;
6068 GL_IT(it)->wsd->show_item = NULL;
6071 evas_object_geometry_get(GL_IT(it)->wsd->pan_obj, NULL, NULL, w, h);
6074 case ELM_GENLIST_ITEM_SCROLLTO_IN:
6075 if ((it->item->group_item) &&
6076 (GL_IT(it)->wsd->pan_y > (it->y + it->item->block->y)))
6077 gith = it->item->group_item->item->h;
6079 *y = it->y + it->item->block->y - gith;
6082 case ELM_GENLIST_ITEM_SCROLLTO_TOP:
6083 if (it->item->group_item) gith = it->item->group_item->item->h;
6084 *y = it->y + it->item->block->y - gith;
6087 case ELM_GENLIST_ITEM_SCROLLTO_MIDDLE:
6088 *y = it->y + it->item->block->y - (*h / 2) + (it->item->h / 2);
6095 *x = it->x + it->item->block->x;
6096 *w = it->item->block->w;
6102 elm_genlist_item_promote(Elm_Object_Item *item)
6104 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6105 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6107 (it, (Elm_Gen_Item *)elm_genlist_first_item_get(WIDGET(it)));
6111 elm_genlist_item_demote(Elm_Object_Item *item)
6113 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6114 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6115 _item_move_after(it, (Elm_Gen_Item *)elm_genlist_last_item_get(WIDGET(it)));
6119 elm_genlist_item_show(Elm_Object_Item *item,
6120 Elm_Genlist_Item_Scrollto_Type type)
6122 Evas_Coord x, y, w, h;
6123 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6124 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6126 if (_elm_genlist_item_coordinates_calc
6127 (item, type, EINA_FALSE, &x, &y, &w, &h))
6128 GL_IT(it)->wsd->s_iface->content_region_show(WIDGET(item), x, y, w, h);
6132 elm_genlist_item_bring_in(Elm_Object_Item *item,
6133 Elm_Genlist_Item_Scrollto_Type type)
6135 Evas_Coord x, y, w, h;
6136 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6137 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6139 if (_elm_genlist_item_coordinates_calc
6140 (item, type, EINA_TRUE, &x, &y, &w, &h))
6141 GL_IT(it)->wsd->s_iface->region_bring_in(WIDGET(item), x, y, w, h);
6145 elm_genlist_item_all_contents_unset(Elm_Object_Item *item,
6148 Evas_Object *content;
6150 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6151 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6153 EINA_LIST_FREE (it->content_objs, content)
6155 evas_object_smart_member_del(content);
6156 evas_object_hide(content);
6157 if (l) *l = eina_list_append(*l, content);
6162 elm_genlist_item_update(Elm_Object_Item *item)
6164 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6165 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6167 if (!it->item->block) return;
6168 it->item->mincalcd = EINA_FALSE;
6169 it->item->updateme = EINA_TRUE;
6170 it->item->block->updateme = EINA_TRUE;
6171 #if GENLIST_ENTRY_SUPPORT
6172 it->item->unrealize_disabled = EINA_FALSE;
6175 #if GENLIST_FX_SUPPORT
6176 if (GL_IT(it)->wsd->fx_first_captured)
6177 _elm_genlist_fx_clear(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj);
6180 if (GL_IT(it)->wsd->update_job) ecore_job_del(GL_IT(it)->wsd->update_job);
6181 GL_IT(it)->wsd->update_job = ecore_job_add(_update_job, GL_IT(it)->wsd);
6185 elm_genlist_item_fields_update(Elm_Object_Item *item,
6187 Elm_Genlist_Item_Field_Type itf)
6189 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6190 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6192 if (!it->item->block) return;
6194 #if GENLIST_ENTRY_SUPPORT
6195 it->item->unrealize_disabled = EINA_FALSE;
6197 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_TEXT))
6199 _item_text_realize(it, VIEW(it), &it->texts, parts);
6201 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_CONTENT))
6203 it->content_objs = _item_content_unrealize(it, VIEW(it),
6204 &it->contents, parts);
6205 it->content_objs = _item_content_realize(it, VIEW(it),
6206 &it->contents, parts);
6210 it->item->flip_content_objs =
6211 _item_mode_content_unrealize(it, VIEW(it),
6212 &it->item->flip_contents, parts,
6213 &it->item->flip_content_objs);
6214 it->item->flip_content_objs =
6215 _item_mode_content_realize(it, VIEW(it),
6216 &it->item->flip_contents, parts,
6217 &it->item->flip_content_objs);
6219 if (it->item->deco_it_view)
6221 it->item->deco_it_content_objs =
6222 _item_mode_content_unrealize(it, it->item->deco_it_view,
6223 &it->item->deco_it_contents, parts,
6224 &it->item->deco_it_content_objs);
6225 it->item->deco_it_content_objs =
6226 _item_mode_content_realize(it, it->item->deco_it_view,
6227 &it->item->deco_it_contents, parts,
6228 &it->item->deco_it_content_objs);
6230 if (GL_IT(it)->wsd->decorate_all_mode)
6232 it->item->deco_all_content_objs =
6233 _item_mode_content_unrealize
6234 (it, it->deco_all_view, &it->item->deco_all_contents, parts,
6235 &it->item->deco_all_content_objs);
6236 it->item->deco_all_content_objs =
6237 _item_mode_content_realize(it, it->deco_all_view,
6238 &it->item->deco_all_contents, parts,
6239 &it->item->deco_all_content_objs);
6243 if ((!itf) || (itf & ELM_GENLIST_ITEM_FIELD_STATE))
6244 _item_state_realize(it, VIEW(it), &it->states, parts);
6248 elm_genlist_item_item_class_update(Elm_Object_Item *item,
6249 const Elm_Genlist_Item_Class *itc)
6251 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6252 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6254 if (!it->item->block) return;
6255 EINA_SAFETY_ON_NULL_RETURN(itc);
6257 it->item->nocache_once = EINA_TRUE;
6259 elm_widget_stringlist_free(it->texts);
6261 elm_widget_stringlist_free(it->contents);
6262 it->contents = NULL;
6263 elm_widget_stringlist_free(it->states);
6268 elm_widget_stringlist_free(it->item->flip_contents);
6269 it->item->flip_contents = NULL;
6271 if (it->item->deco_it_view)
6273 elm_widget_stringlist_free(it->item->deco_it_texts);
6274 it->item->deco_it_texts = NULL;
6275 elm_widget_stringlist_free(it->item->deco_it_contents);
6276 it->item->deco_it_contents = NULL;
6278 if (GL_IT(it)->wsd->decorate_all_mode)
6280 elm_widget_stringlist_free(it->item->deco_all_texts);
6281 it->item->deco_all_texts = NULL;
6282 elm_widget_stringlist_free(it->item->deco_all_contents);
6283 it->item->deco_all_contents = NULL;
6286 elm_genlist_item_update(item);
6289 EAPI const Elm_Genlist_Item_Class *
6290 elm_genlist_item_item_class_get(const Elm_Object_Item *item)
6292 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
6293 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6297 static Evas_Object *
6298 _elm_genlist_item_label_create(void *data,
6299 Evas_Object *obj __UNUSED__,
6300 Evas_Object *tooltip,
6301 void *it __UNUSED__)
6303 Evas_Object *label = elm_label_add(tooltip);
6308 elm_object_style_set(label, "tooltip");
6309 elm_object_text_set(label, data);
6315 _elm_genlist_item_label_del_cb(void *data,
6316 Evas_Object *obj __UNUSED__,
6317 void *event_info __UNUSED__)
6319 eina_stringshare_del(data);
6323 elm_genlist_item_tooltip_text_set(Elm_Object_Item *it,
6326 ELM_GENLIST_ITEM_CHECK_OR_RETURN(it);
6328 text = eina_stringshare_add(text);
6329 elm_genlist_item_tooltip_content_cb_set
6330 (it, _elm_genlist_item_label_create, text,
6331 _elm_genlist_item_label_del_cb);
6335 elm_genlist_item_tooltip_content_cb_set(Elm_Object_Item *item,
6336 Elm_Tooltip_Item_Content_Cb func,
6338 Evas_Smart_Cb del_cb)
6340 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6342 ELM_GENLIST_ITEM_CHECK_OR_GOTO(item, error);
6344 if ((it->tooltip.content_cb == func) && (it->tooltip.data == data))
6347 if (it->tooltip.del_cb)
6348 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
6350 it->tooltip.content_cb = func;
6351 it->tooltip.data = data;
6352 it->tooltip.del_cb = del_cb;
6356 elm_widget_item_tooltip_content_cb_set
6357 (it, it->tooltip.content_cb, it->tooltip.data, NULL);
6358 elm_widget_item_tooltip_style_set(it, it->tooltip.style);
6359 elm_widget_item_tooltip_window_mode_set(it, it->tooltip.free_size);
6365 if (del_cb) del_cb((void *)data, NULL, NULL);
6369 elm_genlist_item_tooltip_unset(Elm_Object_Item *item)
6371 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6373 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6375 if ((VIEW(it)) && (it->tooltip.content_cb))
6376 elm_widget_item_tooltip_unset(it);
6378 if (it->tooltip.del_cb)
6379 it->tooltip.del_cb((void *)it->tooltip.data, WIDGET(it), it);
6380 it->tooltip.del_cb = NULL;
6381 it->tooltip.content_cb = NULL;
6382 it->tooltip.data = NULL;
6383 it->tooltip.free_size = EINA_FALSE;
6384 if (it->tooltip.style)
6385 elm_genlist_item_tooltip_style_set(item, NULL);
6389 elm_genlist_item_tooltip_style_set(Elm_Object_Item *item,
6392 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6394 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6396 eina_stringshare_replace(&it->tooltip.style, style);
6397 if (VIEW(it)) elm_widget_item_tooltip_style_set(it, style);
6401 elm_genlist_item_tooltip_style_get(const Elm_Object_Item *it)
6403 return elm_object_item_tooltip_style_get(it);
6407 elm_genlist_item_tooltip_window_mode_set(Elm_Object_Item *item,
6410 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6412 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, EINA_FALSE);
6414 it->tooltip.free_size = disable;
6415 if (VIEW(it)) return elm_widget_item_tooltip_window_mode_set(it, disable);
6421 elm_genlist_item_tooltip_window_mode_get(const Elm_Object_Item *it)
6423 return elm_object_tooltip_window_mode_get(VIEW(it));
6427 elm_genlist_item_cursor_set(Elm_Object_Item *item,
6430 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6432 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6433 eina_stringshare_replace(&it->mouse_cursor, cursor);
6434 if (VIEW(it)) elm_widget_item_cursor_set(it, cursor);
6438 elm_genlist_item_cursor_get(const Elm_Object_Item *it)
6440 return elm_widget_item_cursor_get(it);
6444 elm_genlist_item_cursor_unset(Elm_Object_Item *item)
6446 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6448 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6450 if (!it->mouse_cursor) return;
6452 if (VIEW(it)) elm_widget_item_cursor_unset(it);
6454 eina_stringshare_del(it->mouse_cursor);
6455 it->mouse_cursor = NULL;
6459 elm_genlist_item_cursor_style_set(Elm_Object_Item *it,
6462 elm_widget_item_cursor_style_set(it, style);
6466 elm_genlist_item_cursor_style_get(const Elm_Object_Item *it)
6468 return elm_widget_item_cursor_style_get(it);
6472 elm_genlist_item_cursor_engine_only_set(Elm_Object_Item *it,
6473 Eina_Bool engine_only)
6475 elm_widget_item_cursor_engine_only_set(it, engine_only);
6479 elm_genlist_item_cursor_engine_only_get(const Elm_Object_Item *it)
6481 return elm_widget_item_cursor_engine_only_get(it);
6485 elm_genlist_item_index_get(const Elm_Object_Item *item)
6489 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6491 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, -1);
6493 EINA_INLIST_FOREACH(GL_IT(it)->wsd->items, tmp)
6495 if (tmp == it) break;
6502 elm_genlist_mode_set(Evas_Object *obj,
6505 ELM_GENLIST_CHECK(obj);
6506 ELM_GENLIST_DATA_GET(obj, sd);
6508 if (sd->mode == mode) return;
6510 elm_layout_sizing_eval(obj);
6514 elm_genlist_mode_get(const Evas_Object *obj)
6516 ELM_GENLIST_CHECK(obj) ELM_LIST_LAST;
6517 ELM_GENLIST_DATA_GET(obj, sd);
6523 elm_genlist_bounce_set(Evas_Object *obj,
6527 ELM_GENLIST_CHECK(obj);
6528 ELM_GENLIST_DATA_GET(obj, sd);
6530 sd->h_bounce = !!h_bounce;
6531 sd->v_bounce = !!v_bounce;
6532 sd->s_iface->bounce_allow_set(obj, sd->h_bounce, sd->v_bounce);
6536 elm_genlist_bounce_get(const Evas_Object *obj,
6537 Eina_Bool *h_bounce,
6538 Eina_Bool *v_bounce)
6540 ELM_GENLIST_CHECK(obj);
6541 ELM_GENLIST_DATA_GET(obj, sd);
6543 if (h_bounce) *h_bounce = sd->h_bounce;
6544 if (v_bounce) *v_bounce = sd->v_bounce;
6548 elm_genlist_homogeneous_set(Evas_Object *obj,
6549 Eina_Bool homogeneous)
6551 ELM_GENLIST_CHECK(obj);
6552 ELM_GENLIST_DATA_GET(obj, sd);
6554 sd->homogeneous = !!homogeneous;
6558 elm_genlist_homogeneous_get(const Evas_Object *obj)
6560 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6561 ELM_GENLIST_DATA_GET(obj, sd);
6563 return sd->homogeneous;
6567 elm_genlist_block_count_set(Evas_Object *obj,
6570 ELM_GENLIST_CHECK(obj);
6571 ELM_GENLIST_DATA_GET(obj, sd);
6572 EINA_SAFETY_ON_TRUE_RETURN(count < 1);
6574 sd->max_items_per_block = count;
6575 sd->item_cache_max = sd->max_items_per_block * 2;
6576 _item_cache_all_free(sd);
6580 elm_genlist_block_count_get(const Evas_Object *obj)
6582 ELM_GENLIST_CHECK(obj) 0;
6583 ELM_GENLIST_DATA_GET(obj, sd);
6585 return sd->max_items_per_block;
6589 elm_genlist_longpress_timeout_set(Evas_Object *obj,
6592 ELM_GENLIST_CHECK(obj);
6593 ELM_GENLIST_DATA_GET(obj, sd);
6595 sd->longpress_timeout = timeout;
6599 elm_genlist_longpress_timeout_get(const Evas_Object *obj)
6601 ELM_GENLIST_CHECK(obj) 0;
6602 ELM_GENLIST_DATA_GET(obj, sd);
6604 return sd->longpress_timeout;
6608 elm_genlist_scroller_policy_set(Evas_Object *obj,
6609 Elm_Scroller_Policy policy_h,
6610 Elm_Scroller_Policy policy_v)
6612 ELM_GENLIST_CHECK(obj);
6613 ELM_GENLIST_DATA_GET(obj, sd);
6615 if ((policy_h >= ELM_SCROLLER_POLICY_LAST) ||
6616 (policy_v >= ELM_SCROLLER_POLICY_LAST))
6619 sd->s_iface->policy_set(obj, policy_h, policy_v);
6623 elm_genlist_scroller_policy_get(const Evas_Object *obj,
6624 Elm_Scroller_Policy *policy_h,
6625 Elm_Scroller_Policy *policy_v)
6627 Elm_Scroller_Policy s_policy_h, s_policy_v;
6629 ELM_GENLIST_CHECK(obj);
6630 ELM_GENLIST_DATA_GET(obj, sd);
6632 sd->s_iface->policy_get(obj, &s_policy_h, &s_policy_v);
6633 if (policy_h) *policy_h = (Elm_Scroller_Policy)s_policy_h;
6634 if (policy_v) *policy_v = (Elm_Scroller_Policy)s_policy_v;
6638 elm_genlist_realized_items_update(Evas_Object *obj)
6640 Eina_List *list, *l;
6641 Elm_Object_Item *it;
6643 ELM_GENLIST_CHECK(obj);
6645 list = elm_genlist_realized_items_get(obj);
6646 EINA_LIST_FOREACH(list, l, it)
6647 elm_genlist_item_update(it);
6651 elm_genlist_item_decorate_mode_set(Elm_Object_Item *item,
6652 const char *decorate_it_type,
6653 Eina_Bool decorate_it_set)
6655 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6656 Elm_Genlist_Smart_Data *sd;
6658 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6659 sd = GL_IT(it)->wsd;
6661 if (elm_widget_item_disabled_get(it)) return;
6662 if (!decorate_it_type) return;
6663 if (sd->decorate_all_mode) return;
6665 if ((sd->mode_item == it) &&
6666 (!strcmp(decorate_it_type, sd->decorate_it_type)) &&
6669 if (!it->itc->decorate_item_style) return;
6670 it->decorate_it_set = decorate_it_set;
6673 if (((sd->decorate_it_type)
6674 && (strcmp(decorate_it_type, sd->decorate_it_type))) ||
6675 (decorate_it_set) || ((it == sd->mode_item) && (!decorate_it_set)))
6676 _decorate_item_unset(sd);
6678 eina_stringshare_replace(&sd->decorate_it_type, decorate_it_type);
6679 if (decorate_it_set) _decorate_item_set(it);
6683 elm_genlist_item_decorate_mode_get(const Elm_Object_Item *item)
6685 Elm_Gen_Item *i = (Elm_Gen_Item *)item;
6687 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, NULL);
6688 return GL_IT(i)->wsd->decorate_it_type;
6691 EAPI Elm_Object_Item *
6692 elm_genlist_decorated_item_get(const Evas_Object *obj)
6694 ELM_GENLIST_CHECK(obj) NULL;
6695 ELM_GENLIST_DATA_GET(obj, sd);
6697 return (Elm_Object_Item *)sd->mode_item;
6701 elm_genlist_decorate_mode_get(const Evas_Object *obj)
6703 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6704 ELM_GENLIST_DATA_GET(obj, sd);
6706 return sd->decorate_all_mode;
6710 elm_genlist_decorate_mode_set(Evas_Object *obj,
6711 Eina_Bool decorated)
6714 Eina_List *list, *l;
6716 ELM_GENLIST_CHECK(obj);
6717 ELM_GENLIST_DATA_GET(obj, sd);
6719 decorated = !!decorated;
6720 if (sd->decorate_all_mode == decorated) return;
6721 // decorate_all_mode should be set first
6722 // because content_get func. will be called after this
6723 // and user can check whether deocrate_all_mode is enabeld.
6724 sd->decorate_all_mode = decorated;
6726 list = elm_genlist_realized_items_get(obj);
6727 if (!sd->decorate_all_mode)
6729 EINA_LIST_FOREACH(list, l, it)
6731 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6732 _decorate_all_item_unrealize(it);
6734 _item_cache_all_free(sd);
6738 EINA_LIST_FOREACH(list, l, it)
6740 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6742 if (it->itc->decorate_all_item_style)
6743 _decorate_all_item_realize(it, EINA_TRUE);
6747 #if GENLIST_FX_SUPPORT
6748 if (sd->fx_first_captured)
6749 _elm_genlist_fx_clear(ELM_WIDGET_DATA(sd)->obj);
6752 if (sd->calc_job) ecore_job_del(sd->calc_job);
6753 sd->calc_job = ecore_job_add(_calc_job, sd);
6757 elm_genlist_reorder_mode_set(Evas_Object *obj,
6758 Eina_Bool reorder_mode)
6760 #if 1 // FIXME: difference from upstream
6761 Eina_List *list, *l;
6764 ELM_GENLIST_CHECK(obj);
6765 ELM_GENLIST_DATA_GET(obj, sd);
6767 if (sd->reorder_mode == !!reorder_mode) return;
6768 sd->reorder_mode = !!reorder_mode;
6769 #if 1 // FIXME: difference from upstream
6770 list = elm_genlist_realized_items_get(obj);
6771 EINA_LIST_FOREACH(list, l, it)
6773 if (it->item->type != ELM_GENLIST_ITEM_GROUP)
6776 if (it->deco_all_view) view = it->deco_all_view;
6777 else view = VIEW(it);
6779 if (sd->reorder_mode)
6780 edje_object_signal_emit
6781 (view, "elm,state,reorder,mode_set", "elm");
6783 edje_object_signal_emit
6784 (view, "elm,state,reorder,mode_unset", "elm");
6787 eina_list_free(list);
6792 elm_genlist_reorder_mode_get(const Evas_Object *obj)
6794 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6795 ELM_GENLIST_DATA_GET(obj, sd);
6797 return sd->reorder_mode;
6800 EAPI Elm_Genlist_Item_Type
6801 elm_genlist_item_type_get(const Elm_Object_Item *item)
6803 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6805 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, ELM_GENLIST_ITEM_MAX);
6807 return it->item->type;
6810 EAPI Elm_Genlist_Item_Class *
6811 elm_genlist_item_class_new(void)
6813 Elm_Genlist_Item_Class *itc = ELM_NEW(Elm_Genlist_Item_Class);
6814 EINA_SAFETY_ON_NULL_RETURN_VAL(itc, NULL);
6816 itc->version = CLASS_ALLOCATED;
6818 itc->delete_me = EINA_FALSE;
6824 elm_genlist_item_class_free(Elm_Genlist_Item_Class *itc)
6826 if (itc && (itc->version == CLASS_ALLOCATED))
6828 if (!itc->delete_me) itc->delete_me = EINA_TRUE;
6829 if (itc->refcount > 0) elm_genlist_item_class_unref(itc);
6839 elm_genlist_item_class_ref(Elm_Genlist_Item_Class *itc)
6841 if (itc && (itc->version == CLASS_ALLOCATED))
6844 if (itc->refcount == 0) itc->refcount--;
6849 elm_genlist_item_class_unref(Elm_Genlist_Item_Class *itc)
6851 if (itc && (itc->version == CLASS_ALLOCATED))
6853 if (itc->refcount > 0) itc->refcount--;
6854 if (itc->delete_me && (!itc->refcount))
6855 elm_genlist_item_class_free(itc);
6860 elm_genlist_item_flip_set(Elm_Object_Item *item,
6863 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6864 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6865 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
6868 if (it->flipped == flip) return;
6870 it->item->unrealize_disabled = EINA_FALSE;
6874 _item_unrealize(it, EINA_FALSE);
6875 it->flipped = EINA_TRUE;
6876 it->item->nocache = EINA_TRUE;
6880 _item_unrealize(it, EINA_FALSE);
6881 it->flipped = EINA_FALSE;
6882 it->item->nocache = EINA_FALSE;
6884 if (sd->calc_job) ecore_job_del(sd->calc_job);
6885 sd->calc_job = ecore_job_add(_calc_job, sd);
6889 elm_genlist_item_flip_get(const Elm_Object_Item *item)
6891 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6893 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, EINA_FALSE);
6899 elm_genlist_select_mode_set(Evas_Object *obj,
6900 Elm_Object_Select_Mode mode)
6902 ELM_GENLIST_CHECK(obj);
6903 ELM_GENLIST_DATA_GET(obj, sd);
6905 if (mode >= ELM_OBJECT_SELECT_MODE_MAX || (sd->select_mode == mode))
6908 sd->select_mode = mode;
6909 if ((sd->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
6910 (sd->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
6914 EINA_LIST_FOREACH_SAFE(sd->selected, l, ll, it)
6919 EAPI Elm_Object_Select_Mode
6920 elm_genlist_select_mode_get(const Evas_Object *obj)
6922 ELM_GENLIST_CHECK(obj) ELM_OBJECT_SELECT_MODE_MAX;
6923 ELM_GENLIST_DATA_GET(obj, sd);
6925 return sd->select_mode;
6929 elm_genlist_highlight_mode_set(Evas_Object *obj,
6930 Eina_Bool highlight)
6932 ELM_GENLIST_CHECK(obj);
6933 ELM_GENLIST_DATA_GET(obj, sd);
6935 sd->highlight = !!highlight;
6939 elm_genlist_highlight_mode_get(const Evas_Object *obj)
6941 ELM_GENLIST_CHECK(obj) EINA_FALSE;
6942 ELM_GENLIST_DATA_GET(obj, sd);
6944 return sd->highlight;
6948 elm_genlist_item_select_mode_set(Elm_Object_Item *item,
6949 Elm_Object_Select_Mode mode)
6951 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6953 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item);
6955 if (mode >= ELM_OBJECT_SELECT_MODE_MAX)
6957 if (it->select_mode != mode)
6958 it->select_mode = mode;
6960 if ((it->select_mode == ELM_OBJECT_SELECT_MODE_NONE) ||
6961 (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY ))
6964 if (it->select_mode == ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY)
6966 it->item->mincalcd = EINA_FALSE;
6967 it->item->updateme = EINA_TRUE;
6968 if (it->item->block) it->item->block->updateme = EINA_TRUE;
6969 if (GL_IT(it)->wsd->update_job)
6970 ecore_job_del(GL_IT(it)->wsd->update_job);
6971 GL_IT(it)->wsd->update_job =
6972 ecore_job_add(_update_job, GL_IT(it)->wsd);
6974 // reset homogeneous item size
6975 if (GL_IT(it)->wsd->homogeneous)
6978 GL_IT(it)->wsd->group_item_width =
6979 GL_IT(it)->wsd->group_item_height = 0;
6981 GL_IT(it)->wsd->item_width = GL_IT(it)->wsd->item_height = 0;
6986 EAPI Elm_Object_Select_Mode
6987 elm_genlist_item_select_mode_get(const Elm_Object_Item *item)
6989 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
6991 ELM_GENLIST_ITEM_CHECK_OR_RETURN(item, ELM_OBJECT_SELECT_MODE_MAX);
6993 if (!it) return ELM_OBJECT_SELECT_MODE_MAX;
6995 return it->select_mode;
6998 // will be deprecated
7000 elm_genlist_tree_effect_enabled_set(Evas_Object *obj __UNUSED__,
7001 Eina_Bool enabled __UNUSED__)
7003 ELM_GENLIST_CHECK(obj);
7006 // will be deprecated
7008 elm_genlist_tree_effect_enabled_get(const Evas_Object *obj __UNUSED__)
7010 ELM_GENLIST_CHECK(obj) EINA_FALSE;
7015 EAPI Elm_Object_Item *
7016 elm_genlist_nth_item_get(const Evas_Object *obj, unsigned int nth)
7018 Elm_Gen_Item *it = NULL;
7022 ELM_GENLIST_CHECK(obj) NULL;
7023 ELM_GENLIST_DATA_GET(obj, sd);
7025 if (!sd->items) return NULL;
7027 a = eina_inlist_accessor_new(sd->items);
7028 if (!a) return NULL;
7029 if (eina_accessor_data_get(a, nth, &data))
7030 it = ELM_GEN_ITEM_FROM_INLIST(data);
7031 eina_accessor_free(a);
7032 return (Elm_Object_Item *)it;
7035 #if GENLIST_FX_SUPPORT
7037 elm_genlist_fx_mode_set(Evas_Object *obj, Eina_Bool mode)
7039 ELM_GENLIST_CHECK(obj);
7040 ELM_GENLIST_DATA_GET(obj, sd);
7046 elm_genlist_fx_mode_get(const Evas_Object *obj)
7048 ELM_GENLIST_CHECK(obj) EINA_FALSE;
7049 ELM_GENLIST_DATA_GET(obj, sd);
7055 _elm_genlist_proxy_item_del(const Elm_Object_Item *item)
7057 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
7058 if ((!it) || (!it->item)) return;
7060 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
7064 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
7065 if (pi->it == it) pi->it = NULL;
7067 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
7068 if (pi->it == it) pi->it = NULL;
7072 _elm_genlist_proxy_item_new(const Elm_Object_Item *item)
7074 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
7075 if ((!it) || (!it->item)) return EINA_FALSE;
7078 Proxy_Item *pi = NULL;
7079 pi = calloc(1, sizeof(Proxy_Item));
7080 if (!pi) return NULL;
7082 pi->proxy = evas_object_image_filled_add
7083 (evas_object_evas_get(ELM_WIDGET_DATA(GL_IT(it)->wsd)->obj));
7084 if (!pi->proxy) return EINA_FALSE;
7085 evas_object_clip_set(pi->proxy, evas_object_clip_get(GL_IT(it)->wsd->pan_obj));
7086 evas_object_smart_member_add(pi->proxy, GL_IT(it)->wsd->pan_obj);
7087 evas_object_hide(pi->proxy);
7089 if ((GL_IT(it)->wsd->decorate_all_mode) && (it->deco_all_view))
7090 evas_object_image_source_set(pi->proxy, it->deco_all_view);
7092 evas_object_image_source_set(pi->proxy, VIEW(it));
7094 GL_IT(it)->has_proxy_it = EINA_TRUE;
7096 pi->num = it->item->num;
7097 pi->x = it->item->scrl_x;
7098 pi->y = it->item->scrl_y;
7099 pi->w = it->item->w;
7100 pi->h = it->item->h;
7102 evas_object_geometry_get(VIEW(it), NULL, NULL, &w, &h);
7104 if (w <= 0 || h <= 0)
7106 evas_object_size_hint_min_get(VIEW(it), &w, &h);
7107 evas_object_size_hint_min_set(pi->proxy, w, h);
7109 else evas_object_resize(pi->proxy, w, h);
7115 _elm_genlist_fx_capture(Evas_Object *obj, int level)
7117 ELM_GENLIST_DATA_GET(obj, sd);
7121 Eina_Bool done = EINA_FALSE;
7124 Evas_Coord ox, oy, ow, oh;
7128 if ((!sd->rendered) || (sd->fx_playing)) return EINA_FALSE;
7129 if ((!level) && (sd->fx_first_captured)) return EINA_FALSE;
7130 if ((level) && (!sd->fx_first_captured)) return EINA_FALSE;
7132 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7136 sd->fx_first_captured = EINA_TRUE;
7137 EINA_LIST_FREE(sd->capture_before_items, pi)
7139 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
7140 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
7141 if (pi->proxy) evas_object_del(pi->proxy);
7147 EINA_LIST_FREE(sd->capture_after_items, pi)
7149 if ((pi->it) && (GL_IT(pi->it))) GL_IT(pi->it)->has_proxy_it = EINA_FALSE;
7150 if (pi->proxy) evas_object_smart_member_del(pi->proxy);
7151 if (pi->proxy) evas_object_del(pi->proxy);
7155 EINA_INLIST_FOREACH(sd->blocks, itb)
7159 EINA_LIST_FOREACH(itb->items, l, it)
7161 if (it->realized && it->item->scrl_y >= oy)
7163 sd->realized_top_item = it;
7168 if (sd->realized_top_item) break;
7172 #if GENLIST_PINCH_ZOOM_SUPPORT
7173 if (sd->pinch_zoom_mode)
7175 EINA_INLIST_FOREACH(sd->blocks, itb)
7177 EINA_LIST_FOREACH(itb->items, l, it)
7180 if (IS_ROOT_PARENT_IT(it) && it->realized
7181 && (GL_IT(it)->scrl_y + GL_IT(it)->h >= oy && GL_IT(it)->scrl_y <= oy + oh))
7183 pi = _elm_genlist_proxy_item_new((Elm_Object_Item *)it);
7184 if (!level) sd->capture_before_items = eina_list_append(sd->capture_before_items, pi);
7185 else sd->capture_after_items = eina_list_append(sd->capture_after_items, pi);
7189 if ((sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT) && (level)) return EINA_TRUE;
7190 if ((sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_EXPAND) && (!level)) return EINA_TRUE;
7194 EINA_INLIST_FOREACH(sd->blocks, itb)
7199 EINA_LIST_FOREACH(itb->items, l, it)
7201 #if GENLIST_PINCH_ZOOM_SUPPORT
7202 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7206 pi = _elm_genlist_proxy_item_new((Elm_Object_Item *)it);
7209 sd->capture_before_items = eina_list_append(sd->capture_before_items, pi);
7211 sd->capture_after_items = eina_list_append(sd->capture_after_items, pi);
7215 else if (done) break;
7220 static Elm_Gen_FX_Item *
7221 _elm_genlist_fx_item_find(const Elm_Object_Item *item)
7223 Elm_Gen_Item *it = (Elm_Gen_Item *)item;
7224 if (!it) return EINA_FALSE;
7226 Elm_Genlist_Smart_Data *sd = GL_IT(it)->wsd;
7227 if (!sd) return NULL;
7229 Elm_Gen_FX_Item *fi = NULL;
7232 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7234 if (fi->it == it) return fi;
7239 static Elm_Gen_FX_Item *
7240 _elm_genlist_fx_item_new(const Proxy_Item *pi)
7242 if ((!pi) || (!pi->it)) return NULL;
7244 Elm_Gen_FX_Item *fi = NULL;
7245 fi = calloc(1, sizeof(Elm_Gen_FX_Item));
7246 if (!fi) return NULL;
7249 GL_IT(fi->it)->fi = fi;
7250 fi->proxy = pi->proxy;
7252 fi->from.x = fi->to.x = pi->x;
7253 fi->from.y = fi->to.y = pi->y;
7254 fi->from.w = fi->to.w = pi->w;
7255 fi->from.h = fi->to.h = pi->h;
7256 fi->update = EINA_FALSE;
7261 static Elm_Object_Item *
7262 _elm_genlist_fx_item_prev_get(const Elm_Object_Item *item)
7265 it = (Elm_Gen_Item *)item;
7266 if (!it) return NULL;
7267 if (GL_IT(it)->wsd->pinch_zoom_mode) return NULL;
7271 it = ELM_GEN_ITEM_FROM_INLIST(EINA_INLIST_GET(it)->prev);
7275 return (Elm_Object_Item *)it;
7279 _elm_genlist_fx_items_make(Evas_Object *obj)
7281 ELM_GENLIST_CHECK(obj) EINA_FALSE;
7282 ELM_GENLIST_DATA_GET(obj, sd);
7284 Elm_Gen_FX_Item *fi;
7287 Elm_Gen_Item *prev = NULL;
7288 Evas_Coord ox, oy, ow, oh, mv_dist, max_mv_dist = 0;
7290 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7292 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
7294 fi = _elm_genlist_fx_item_new(pi);
7295 if (fi) sd->fx_items = eina_list_append(sd->fx_items, fi);
7298 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
7300 fi = _elm_genlist_fx_item_find((Elm_Object_Item *)pi->it);
7302 if (fi) // pi exists in both before and after capture items
7304 fi->type = ELM_GEN_ITEM_FX_TYPE_SAME;
7305 fi->update = EINA_TRUE;
7311 // find the max distance between before and after capture items
7312 mv_dist = abs(fi->to.y - fi->from.y);
7313 if (max_mv_dist < mv_dist) max_mv_dist = mv_dist;
7315 else // pi only exists in after capture items
7317 fi = _elm_genlist_fx_item_new(pi);
7320 fi->type = ELM_GEN_ITEM_FX_TYPE_ADD;
7321 fi->update = EINA_TRUE;
7322 sd->fx_items = eina_list_append(sd->fx_items, fi);
7327 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7329 // find deleted items
7330 if (!fi->update) // pi only exists in before capture items
7332 fi->type = ELM_GEN_ITEM_FX_TYPE_DEL;
7333 fi->update = EINA_TRUE;
7335 prev = (Elm_Gen_Item *)_elm_genlist_fx_item_prev_get((Elm_Object_Item *)fi->it);
7336 if ((prev) && (GL_IT(prev)->fi))
7338 fi->to.y = GL_IT(prev)->fi->to.y + GL_IT(prev)->fi->to.h;
7341 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_ADD)
7343 prev = (Elm_Gen_Item *)_elm_genlist_fx_item_prev_get((Elm_Object_Item *)fi->it);
7344 if ((prev) && (prev->realized) && (GL_IT(prev)->fi))
7346 fi->from.y = GL_IT(prev)->fi->from.y + GL_IT(prev)->fi->from.h;
7350 if (sd->realized_top_item)
7353 if (fi->num <= sd->realized_top_item->item->num)
7354 fi->from.y -= max_mv_dist;
7356 fi->from.y += max_mv_dist;
7362 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7364 if ((GL_IT(fi->it)->items) && (GL_IT(fi->it)->expanded_depth == 0))
7366 #if GENLIST_PINCH_ZOOM_SUPPORT
7367 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
7369 fi->from.y = oy + GL_IT(fi->it)->pan_scrl_y - sd->pinch_pan_y;
7372 if (fi->type == ELM_GEN_ITEM_FX_TYPE_DEL)
7374 if (sd->realized_top_item)
7376 if (fi->num <= sd->realized_top_item->item->num)
7377 fi->to.y = oy - fi->from.h;
7388 static Elm_Gen_FX_Item *
7389 _fx_cover_item_get(const Elm_Gen_FX_Item *fi)
7391 Elm_Gen_FX_Item *cover_fi;
7393 if (!fi) return NULL;
7395 Elm_Genlist_Smart_Data *sd = GL_IT(fi->it)->wsd;
7396 Evas_Coord ox, oy, ow, oh;
7397 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7399 EINA_LIST_FOREACH(sd->fx_items, l, cover_fi)
7401 if (fi == cover_fi) continue;
7402 if (sd->fx_items_deleted)
7404 if ((cover_fi->from.y >= oy+oh || cover_fi->from.y > fi->to.y) && (cover_fi->from.y - cover_fi->to.y > 0))
7409 if ((cover_fi->to.y > fi->to.y) && (cover_fi->from.y - cover_fi->to.y < 0))
7417 _item_fx_op(Elm_Transit_Effect *data, Elm_Transit *transit __UNUSED__, double progress __UNUSED__)
7419 Elm_Gen_FX_Item *fi = data, *cover_it;
7420 Elm_Genlist_Smart_Data *sd = GL_IT(fi->it)->wsd;
7421 Evas_Coord fi_ox, fi_oy, cover_it_ox, cover_it_oy, ox, oy, ow, oh;
7423 evas_object_show(VIEW(fi->it));
7424 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7425 evas_object_geometry_get(fi->proxy, &fi_ox, &fi_oy, NULL, NULL);
7426 evas_object_move(fi->proxy, ox, fi_oy);
7427 evas_object_show(fi->proxy);
7428 #if GENLIST_PINCH_ZOOM_SUPPORT
7429 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(fi->it))) evas_object_raise(fi->proxy);
7432 if ((!sd->expanded_next_item) || (sd->expanded_next_item == fi->it)) goto raise_event_block;
7433 if (fi->type == ELM_GEN_ITEM_FX_TYPE_SAME) goto raise_event_block;
7435 // find the closest item that cover current item when deleting
7436 cover_it = _fx_cover_item_get(fi);
7439 evas_object_geometry_get(cover_it->proxy, &cover_it_ox, &cover_it_oy, NULL, NULL);
7441 if (sd->fx_items_deleted)
7444 && (fi_oy + fi->to.h >= cover_it_oy + cover_it->to.h ) && (fi->from.y < cover_it->from.y))
7445 evas_object_hide(fi->proxy);
7447 else if (cover_it_oy && (fi_oy >= cover_it_oy))
7448 evas_object_hide(fi->proxy);
7450 evas_object_show(fi->proxy);
7454 evas_object_raise(sd->alpha_bg);
7461 _item_fx_done(Elm_Transit_Effect *data, Elm_Transit *transit __UNUSED__)
7463 Elm_Gen_FX_Item *fx_done_it = data;
7464 Elm_Genlist_Smart_Data *sd = GL_IT(fx_done_it->it)->wsd;
7466 if ((!fx_done_it) || (!fx_done_it->it) || (!sd)) return;
7468 evas_object_image_source_visible_set(fx_done_it->proxy, EINA_TRUE);
7469 evas_object_lower(fx_done_it->proxy);
7471 if ((sd->decorate_all_mode) && (fx_done_it->it->deco_all_view))
7472 evas_object_move(fx_done_it->it->deco_all_view, fx_done_it->to.x, fx_done_it->to.y);
7474 evas_object_move(VIEW(fx_done_it->it), fx_done_it->to.x, fx_done_it->to.y);
7475 GL_IT(fx_done_it->it)->has_proxy_it = EINA_FALSE;
7477 evas_object_clip_unset(fx_done_it->proxy);
7481 _item_fx_del_cb(void *data, Elm_Transit *transit __UNUSED__)
7483 Elm_Gen_FX_Item *fx_done_it = data;
7484 Elm_Gen_Item *it = NULL;
7485 Proxy_Item *pi = NULL;
7487 Elm_Genlist_Smart_Data *sd = GL_IT(fx_done_it->it)->wsd;
7489 if ((!fx_done_it) || (!fx_done_it->it) || (!sd)) return;
7491 sd->fx_items = eina_list_remove(sd->fx_items, fx_done_it);
7492 GL_IT(fx_done_it->it)->fi = NULL;
7495 if (!eina_list_count(sd->fx_items))
7497 EINA_LIST_FREE (sd->pending_unrealized_items, it)
7499 if (GL_IT(it)) GL_IT(it)->has_proxy_it = EINA_FALSE;
7500 #if GENLIST_PINCH_ZOOM_SUPPORT
7501 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7503 _item_unrealize(it, EINA_FALSE);
7505 EINA_LIST_FREE (sd->pending_unrealized_decorate_all_items, it)
7507 if (GL_IT(it)) GL_IT(it)->has_proxy_it = EINA_FALSE;
7508 #if GENLIST_PINCH_ZOOM_SUPPORT
7509 if ((sd->pinch_zoom_mode) && (IS_ROOT_PARENT_IT(it))) continue;
7511 _decorate_all_item_unrealize(it);
7514 EINA_LIST_FREE (sd->pending_del_items, it)
7517 _elm_widget_item_free((Elm_Widget_Item *)it);
7520 EINA_LIST_FOREACH(sd->capture_before_items, l, pi)
7521 evas_object_hide(pi->proxy);
7522 EINA_LIST_FOREACH(sd->capture_after_items, l, pi)
7523 evas_object_hide(pi->proxy);
7525 sd->fx_playing = EINA_FALSE;
7526 sd->sorting = EINA_FALSE;
7527 sd->fx_first_captured = EINA_FALSE;
7528 evas_object_hide(sd->alpha_bg);
7530 sd->realized_top_item = NULL;
7531 sd->pan_changed = EINA_TRUE;
7532 evas_object_smart_changed(sd->pan_obj);
7537 _sorting_effect_animator_cb(void *data)
7539 Elm_Genlist_Smart_Data *sd = data;
7540 Elm_Gen_FX_Item *fi;
7543 Evas_Coord ox, oy, ow, oh;
7544 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7546 sd->fx_timer = NULL;
7547 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7551 fi->changed = EINA_TRUE;
7552 evas_object_resize(fi->proxy, ow, fi->to.h);
7554 fi->trans = elm_transit_add();
7555 elm_transit_object_add(fi->trans, fi->proxy);
7556 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7557 elm_transit_tween_mode_set(fi->trans, ELM_TRANSIT_TWEEN_MODE_DECELERATE);
7559 elm_transit_effect_translation_add(fi->trans, fi->to.x, fi->to.y - 30 * elm_config_scale_get(), fi->to.x, fi->to.y);
7560 elm_transit_effect_color_add(fi->trans,0, 0, 0, 0, 255,255,255,255);
7562 elm_transit_effect_add(fi->trans, _item_fx_op, fi, _item_fx_done);
7563 elm_transit_del_cb_set(fi->trans, _item_fx_del_cb, fi);
7564 elm_transit_duration_set(fi->trans,0.3);
7565 elm_transit_objects_final_state_keep_set(fi->trans, EINA_FALSE);
7566 elm_transit_go(fi->trans);
7568 return ECORE_CALLBACK_RENEW;
7571 return ECORE_CALLBACK_CANCEL;
7575 _elm_genlist_fx_play(Evas_Object *obj)
7577 ELM_GENLIST_CHECK(obj);
7578 ELM_GENLIST_DATA_GET(obj, sd);
7580 Evas_Coord ox, oy, ow, oh, cvx, cvy, cvw, cvh;
7581 Elm_Gen_FX_Item *fi;
7584 if (!sd->fx_mode) return;
7586 EINA_LIST_FREE(sd->fx_items, fi)
7588 if (fi->trans) elm_transit_del(fi->trans);
7591 _item_cache_all_free(sd);
7593 _elm_genlist_fx_items_make(obj);
7594 if (!eina_list_count(sd->fx_items) || (sd->queue))
7596 _elm_genlist_fx_clear(obj);
7600 sd->fx_playing = EINA_TRUE;
7602 if (!sd->alpha_bg) sd->alpha_bg = _tray_alpha_bg_create(obj);
7603 evas_object_show(sd->alpha_bg);
7605 evas_object_geometry_get(sd->pan_obj, &ox, &oy, &ow, &oh);
7606 evas_output_viewport_get(evas_object_evas_get(obj), &cvx, &cvy, &cvw, &cvh);
7610 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7611 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7612 if (sd->fx_timer) ecore_timer_del(sd->fx_timer);
7613 sd->fx_timer = ecore_timer_add(0.05, _sorting_effect_animator_cb, sd);
7617 EINA_LIST_FOREACH(sd->fx_items, l, fi)
7619 if (!fi->proxy) continue;
7621 if ((fi->from.y <= oy) || (fi->from.y + fi->from.h >= oy + oh))
7623 if ((sd->decorate_all_mode) && (fi->it->deco_all_view))
7624 evas_object_move(fi->it->deco_all_view, cvx, fi->to.y);
7626 evas_object_move(VIEW(fi->it), cvx, fi->to.y);
7628 else if ((fi->to.y <= oy) || (fi->to.y + fi->to.h >= oy + oh))
7630 if ((sd->decorate_all_mode) && (fi->it->deco_all_view))
7631 evas_object_move(fi->it->deco_all_view, cvx, fi->from.y);
7633 evas_object_move(VIEW(fi->it), cvx, fi->from.y);
7636 evas_object_resize(fi->proxy, ow, fi->to.h);
7637 evas_object_show(fi->proxy);
7639 fi->trans = elm_transit_add();
7640 elm_transit_object_add(fi->trans, fi->proxy);
7642 evas_object_image_source_visible_set(fi->proxy, EINA_FALSE);
7643 elm_transit_tween_mode_set(fi->trans, ELM_TRANSIT_TWEEN_MODE_DECELERATE);
7645 if (fi->type == ELM_GEN_ITEM_FX_TYPE_SAME)
7647 evas_object_raise(fi->proxy);
7648 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7651 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_ADD)
7653 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7654 elm_transit_effect_color_add(fi->trans, 0, 0, 0, 0, 255, 255, 255, 255);
7656 else if (fi->type == ELM_GEN_ITEM_FX_TYPE_DEL)
7658 elm_transit_effect_translation_add(fi->trans, fi->from.x, fi->from.y, fi->to.x, fi->to.y);
7659 elm_transit_effect_color_add(fi->trans, 255, 255, 255, 255, 0, 0, 0, 0);
7661 elm_transit_effect_add(fi->trans, _item_fx_op, fi, _item_fx_done);
7662 elm_transit_del_cb_set(fi->trans, _item_fx_del_cb, fi);
7664 elm_transit_duration_set(fi->trans, FX_MOVE_TIME);
7665 elm_transit_objects_final_state_keep_set(fi->trans, EINA_FALSE);
7666 elm_transit_go(fi->trans);
7671 #if GENLIST_PINCH_ZOOM_SUPPORT
7673 elm_genlist_pinch_zoom_mode_set(Evas_Object *obj, Elm_Gen_Pinch_Zoom_Mode mode)
7675 ELM_GENLIST_DATA_GET(obj, sd);
7680 Eina_Bool done = EINA_FALSE;
7682 if ((sd->queue) || (!sd->rendered) || (sd->queue_idle_enterer)) return EINA_FALSE;
7684 EINA_INLIST_FOREACH(sd->blocks, itb)
7686 EINA_LIST_FOREACH(itb->items, l, it)
7689 if (IS_ROOT_PARENT_IT(it))
7697 if (!done) return EINA_FALSE;
7699 sd->pinch_zoom_mode = mode;
7701 _item_cache_all_free(sd);
7702 _elm_genlist_fx_capture(obj, 0);
7704 sd->pinch_pan_y = sd->pan_y;
7706 if (sd->pinch_zoom_mode == ELM_GEN_PINCH_ZOOM_CONTRACT)
7707 sd->s_iface->content_region_show(obj, 0,0,0,0);
7709 sd->pan_changed = EINA_TRUE;
7710 evas_object_smart_changed(sd->pan_obj);
7717 eina_list_sort_merge(Eina_List *a, Eina_List *b, Eina_Compare_Cb func)
7719 Eina_List *first, *last;
7721 if (func(a->data, b->data) > 0)
7723 _item_move_after(a->data, b->data);
7724 a = (last = first = a)->next;
7728 b = (last = first = b)->next;
7731 if (func(a->data, b->data) > 0)
7733 _item_move_after(a->data, b->data);
7734 a = (last = last->next = a)->next;
7737 b = (last = last->next = b)->next;
7739 last->next = a ? a : b;
7745 elm_genlist_sort(Evas_Object *obj, Eina_Compare_Cb func)
7747 ELM_GENLIST_CHECK(obj) NULL;
7748 ELM_GENLIST_DATA_GET(obj, sd);
7749 Eina_List *list = NULL;
7750 Elm_Gen_Item *it, *next;
7751 unsigned int limit = 0, i = 0, n = 0;
7752 Eina_List *tail = NULL, *unsort = NULL, *stack[32], *prev = NULL;
7754 sd->sorting = EINA_TRUE;
7756 it = (Elm_Gen_Item*)elm_genlist_first_item_get(obj);
7759 list = eina_list_append(list, it);
7760 next = (Elm_Gen_Item*)elm_genlist_item_next_get((Elm_Object_Item *)it);
7768 limit = eina_list_count(list);
7772 (limit > list->accounting->count))
7773 limit = list->accounting->count;
7775 if (limit != list->accounting->count)
7777 unsort = eina_list_nth_list(list, limit);
7779 unsort->prev->next = NULL;
7784 unsigned int idx, tmp;
7786 Eina_List *a = tail;
7787 Eina_List *b = tail->next;
7797 if (func(a->data, b->data) > 0)
7798 ((stack[i++] = a)->next = b)->next = 0;
7800 ((stack[i++] = b)->next = a)->next = 0;
7803 for (idx = n ^ tmp; idx &= idx - 1; i--)
7804 stack[i - 2] = eina_list_sort_merge(stack[i - 2], stack[i - 1], func);
7808 stack[i - 1] = eina_list_sort_merge(stack[i - 1], stack[i], func);
7812 for (; stack[0]; stack[0] = stack[0]->next)
7814 stack[0]->prev = prev;
7821 tail->next = unsort;
7822 unsort->prev = tail;
7825 list->accounting->last = tail;
7827 if (!sd->fx_mode) sd->sorting = EINA_FALSE;
7828 if (sd->decorate_all_mode) sd->sorting = EINA_FALSE;
7829 sd->s_iface->content_region_show(obj, 0,0,0,0);
7830 sd->pan_changed = EINA_TRUE;
7831 evas_object_smart_changed(sd->pan_obj);