cedric pushed a commit to branch master. http://git.enlightenment.org/core/efl.git/commit/?id=3bbaf71b68060078bc229c9c2949202e849e986e
commit 3bbaf71b68060078bc229c9c2949202e849e986e Author: Cedric BAIL <cedric.b...@free.fr> Date: Fri Mar 15 16:56:33 2019 -0700 elementary: destroy fileselector children when they are not itemized yet. As we now do everything asynchronously, we do have model representing child of the main model that don't provide enough information to be displayed yet. This are not tracked by a genlist item, nor are they a child of the fileselector. To properly handle their lifecycle, it is necessary to unref them manually explicitely. Reviewed-by: Marcel Hollerbach <m...@marcel-hollerbach.de> Differential Revision: https://phab.enlightenment.org/D8375 --- src/lib/elementary/elc_fileselector.c | 26 +++++++++++--------------- src/lib/elementary/elm_widget_fileselector.h | 1 + 2 files changed, 12 insertions(+), 15 deletions(-) diff --git a/src/lib/elementary/elc_fileselector.c b/src/lib/elementary/elc_fileselector.c index 7be8f0dc09..f1fb69620d 100644 --- a/src/lib/elementary/elc_fileselector.c +++ b/src/lib/elementary/elc_fileselector.c @@ -99,6 +99,7 @@ EFL_CALLBACKS_ARRAY_DEFINE(monitoring_callbacks, { EFL_MODEL_EVENT_CHILD_ADDED, _resource_created }, { EFL_MODEL_EVENT_CHILD_REMOVED, _resource_deleted }); +static void _properties_changed(void *data, const Efl_Event *ev); static void _focus_chain_update(Eo *obj, Elm_Fileselector_Data *pd) @@ -200,6 +201,12 @@ _elm_fileselector_replace_model(Elm_Fileselector *fs, Elm_Fileselector_Data *sd, static void _elm_fileselector_smart_del_do(Elm_Fileselector *fs, Elm_Fileselector_Data *sd) { + Eo *child; + EINA_LIST_FREE(sd->children, child) + { + efl_event_callback_del(child, EFL_MODEL_EVENT_PROPERTIES_CHANGED, _properties_changed, sd); + efl_unref(child); + } _elm_fileselector_replace_model(fs, sd, NULL, NULL); efl_replace(&sd->prev_model, NULL); free(ecore_idler_del(sd->populate_idler)); @@ -809,13 +816,6 @@ _fetch_int64_value(Efl_Model *child, const char *name, int64_t *i) return r; } -static void _invalidate(void *data, const Efl_Event *ev); -static void _properties_changed(void *data, const Efl_Event *ev); - -EFL_CALLBACKS_ARRAY_DEFINE(child_model_callbacks, - { EFL_MODEL_EVENT_PROPERTIES_CHANGED, _properties_changed }, - { EFL_EVENT_INVALIDATE, _invalidate }); - static void _process_model(Elm_Fileselector_Data *sd, Efl_Model *child) { @@ -852,7 +852,8 @@ _process_model(Elm_Fileselector_Data *sd, Efl_Model *child) // SETUP listener to retry fetching all data when ready if (err == EAGAIN) { - efl_event_callback_array_add(efl_ref(child), child_model_callbacks(), sd); + efl_event_callback_add(efl_ref(child), EFL_MODEL_EVENT_PROPERTIES_CHANGED, _properties_changed, sd); + sd->children = eina_list_append(sd->children, child); } goto cleanup; } @@ -928,19 +929,14 @@ _process_model(Elm_Fileselector_Data *sd, Efl_Model *child) free(parent_path); } -static void -_invalidate(void *data EINA_UNUSED, const Efl_Event *ev) -{ - efl_unref(ev->object); -} - static void _properties_changed(void *data, const Efl_Event *ev) { Elm_Fileselector_Data *sd = data; Efl_Model *child = ev->object; - efl_event_callback_array_del(child, child_model_callbacks(), sd); + sd->children = eina_list_remove(sd->children, child); + efl_event_callback_del(child, EFL_MODEL_EVENT_PROPERTIES_CHANGED, _properties_changed, sd); _process_model(sd, child); efl_unref(child); } diff --git a/src/lib/elementary/elm_widget_fileselector.h b/src/lib/elementary/elm_widget_fileselector.h index 1ebf33c0ca..d8c37f3dd8 100644 --- a/src/lib/elementary/elm_widget_fileselector.h +++ b/src/lib/elementary/elm_widget_fileselector.h @@ -54,6 +54,7 @@ struct _Elm_Fileselector_Data const char *path; Efl_Model *model; Efl_Model *prev_model; + Eina_List *children; Ecore_Idler *populate_idler; Ecore_Idler *path_entry_idler; --