diff --git a/src/lib/elementary/elm_view_form.c b/src/lib/elementary/elm_view_form.c index 3055339659..4969310f9b 100644 --- a/src/lib/elementary/elm_view_form.c +++ b/src/lib/elementary/elm_view_form.c @@ -25,264 +25,52 @@ typedef struct _Elm_View_Form_Promise Elm_View_Form_Promise; /** * @brief Local-use callbacks */ -typedef void (*Elm_View_Form_Event_Cb)(Elm_View_Form_Widget *, Elm_View_Form_Data *, Evas_Object *); -typedef void (*Elm_View_Form_Widget_Object_Set_Cb)(Evas_Object *, const Eina_Value *, const char *); - -struct _Elm_View_Form_Widget -{ - Eina_Stringshare *widget_propname; - Evas_Object *widget_obj; - Elm_View_Form_Event_Cb widget_obj_value_update_cb; - Elm_View_Form_Widget_Object_Set_Cb widget_obj_set_cb; -}; - struct _Elm_View_Form_Data { - Eo *model_obj; - Eina_List *widgets; + Eo *model; + Eina_List *links; // List of linked object }; -struct _Elm_View_Form_Promise -{ - Elm_View_Form_Data *priv; - Eina_Stringshare *property_name; -}; - - static void -_efl_promise_then_widget(void* data, Efl_Event const* event) +_link_dying(void* data, Efl_Event const* event) { - Elm_View_Form_Widget *w = data; - Efl_Future_Event_Success* info = event->info; - Eina_Value *value = info->value; - w->widget_obj_set_cb(w->widget_obj, value, w->widget_propname); -} - -static void -_efl_promise_error_widget(void *data EINA_UNUSED, Efl_Event const* event EINA_UNUSED) -{ -} - -static void -_efl_model_promise_then_cb(void* data, Efl_Event const* event) -{ - Elm_View_Form_Promise *p = data; - Eina_Value *value = ((Efl_Future_Event_Success*)event->info)->value; - Elm_View_Form_Data *priv = p->priv; - Elm_View_Form_Widget *w = NULL; - Eina_List *l = NULL; - - EINA_SAFETY_ON_NULL_RETURN(p); - - EINA_LIST_FOREACH(priv->widgets, l, w) - { - if (!strcmp(w->widget_propname, p->property_name)) - { - w->widget_obj_set_cb(w->widget_obj, value, w->widget_propname); - } - } - - eina_stringshare_del(p->property_name); - free(p); -} - -static void -_efl_model_promise_error_cb(void* data, Efl_Event const* event EINA_UNUSED) -{ - Elm_View_Form_Promise *p = data; - EINA_SAFETY_ON_NULL_RETURN(p); - - eina_stringshare_del(p->property_name); - free(p); -} - -static void -_efl_model_properties_change_cb(void *data, const Efl_Event *event) -{ - const Efl_Model_Property_Event *evt = event->info; - const char *prop; - unsigned int i; Elm_View_Form_Data *priv = data; - Elm_View_Form_Promise *p = NULL; - Eina_Array_Iterator it; - EINA_SAFETY_ON_NULL_RETURN(priv); - EINA_SAFETY_ON_NULL_RETURN(evt); - - if (!evt->changed_properties) - return; - - //update all widgets with this property - EINA_ARRAY_ITER_NEXT(evt->changed_properties, i, prop, it) - { - p = calloc(1, sizeof(Elm_View_Form_Promise)); - p->property_name = eina_stringshare_add(prop); - p->priv = priv; - efl_future_then(efl_model_property_get(priv->model_obj, prop), - &_efl_model_promise_then_cb, - &_efl_model_promise_error_cb, NULL, p); - } + priv->links = eina_list_remove(priv->links, event->object); } -static void -_update_model_properties(Elm_View_Form_Data *priv) -{ - Eina_List *l; - Elm_View_Form_Widget *w; - //update all widgets property - if (priv->model_obj == NULL) - return; - - EINA_LIST_FOREACH(priv->widgets, l, w) - { - efl_future_then(efl_model_property_get(priv->model_obj, w->widget_propname), - &_efl_promise_then_widget, &_efl_promise_error_widget, NULL, w); - } -} - -/** - * @brief Set widget. - * Works, so far, for widget(s): Entry, Label - */ -static void -_elm_evas_object_text_set_cb(Evas_Object *widget, const Eina_Value *value, const char *propname EINA_UNUSED) -{ - const char *c_text = NULL; - char *text = NULL; - - EINA_SAFETY_ON_NULL_RETURN(value); - EINA_SAFETY_ON_NULL_RETURN(widget); - - text = eina_value_to_string(value); - EINA_SAFETY_ON_NULL_RETURN(text); - - c_text = elm_object_text_get(widget); - EINA_SAFETY_ON_NULL_RETURN(c_text); - - if (strcmp(text, c_text) != 0) - { - elm_object_text_set(widget, text); - } - free(text); -} - -static void -_elm_evas_object_thumb_set_cb(Evas_Object *thumb, const Eina_Value *value, const char *propname EINA_UNUSED) -{ - char *filename = NULL; - - EINA_SAFETY_ON_NULL_RETURN(value); - filename = eina_value_to_string(value); - EINA_SAFETY_ON_NULL_RETURN(filename); - if (strlen(filename) < PATH_MAX) - { - elm_thumb_file_set(thumb, filename, NULL); - elm_thumb_reload(thumb); - } - free(filename); -} - -/** - * @brief Evas object callback implementation. - * Updates Widget's value if not the same object - * and the widget itself. - */ -static void -_elm_evas_object_text_changed_cb(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED) -{ - Eina_Value value; - Eina_List *l; - Elm_View_Form_Data *priv = (Elm_View_Form_Data *)data; - Elm_View_Form_Widget *w = NULL; - - EINA_LIST_FOREACH(priv->widgets, l, w) - { - if (w->widget_obj == obj) - break; - } - - EINA_SAFETY_ON_NULL_RETURN(w); - eina_value_setup(&value, EINA_VALUE_TYPE_STRING); - eina_value_set(&value, elm_object_text_get(obj)); - efl_model_property_set(priv->model_obj, w->widget_propname, &value); - eina_value_flush(&value); -} /** * @brief Add new widget object. * Adds new widget object on the list * and perform initial setup. */ static Eina_Bool -_elm_view_widget_add(Elm_View_Form_Data *priv, const char *propname, Evas_Object *widget_obj) +_elm_view_widget_add(Elm_View_Form_Data *priv, const char *property, Evas_Object *link) { - Efl_Future *future = NULL; - Elm_View_Form_Widget *w = calloc(1, sizeof(Elm_View_Form_Widget)); - EINA_SAFETY_ON_NULL_RETURN_VAL(w, EINA_FALSE); + if (!efl_isa(link, EFL_UI_MODEL_CONNECT_INTERFACE)) return EINA_FALSE; + if (!property) property = "default"; - w->widget_propname = eina_stringshare_add(propname); - w->widget_obj = widget_obj; - priv->widgets = eina_list_append(priv->widgets, w); + efl_ui_view_model_set(link, priv->model); + efl_ui_model_connect(link, "default", property); + efl_event_callback_add(link, EFL_EVENT_DEL, _link_dying, priv); - if(efl_isa(widget_obj, ELM_ENTRY_CLASS)) - { - w->widget_obj_set_cb = _elm_evas_object_text_set_cb; - evas_object_event_callback_add(w->widget_obj, EVAS_CALLBACK_KEY_DOWN, _elm_evas_object_text_changed_cb, priv); - } - else if(efl_isa(widget_obj, ELM_LABEL_CLASS)) - { - w->widget_obj_set_cb = _elm_evas_object_text_set_cb; - } - else if(efl_isa(widget_obj, ELM_THUMB_CLASS)) - { - w->widget_obj_set_cb = _elm_evas_object_thumb_set_cb; - } - else - { - // Widget yet not supported - EINA_SAFETY_ON_NULL_RETURN_VAL(NULL, EINA_FALSE); - } + priv->links = eina_list_append(priv->links, link); - if (priv->model_obj != NULL) - { - future = efl_model_property_get(priv->model_obj, w->widget_propname); - efl_future_then(future, &_efl_promise_then_widget, - &_efl_promise_error_widget, NULL, priv); - } return EINA_TRUE; } /** * Helper functions - End */ - -/** - * @brief constructor - */ -static Efl_Object* -_elm_view_form_efl_object_constructor(Eo *obj EINA_UNUSED, Elm_View_Form_Data *_pd) -{ - Elm_View_Form_Data *priv = (Elm_View_Form_Data *)_pd; - priv->model_obj = NULL; - - efl_constructor(efl_super(obj, MY_CLASS)); - - return obj; -} - /** * @brief destructor */ static void _elm_view_form_efl_object_destructor(Eo *obj, Elm_View_Form_Data *priv) { - Elm_View_Form_Widget *w = NULL; - EINA_LIST_FREE(priv->widgets, w) - { - eina_stringshare_del(w->widget_propname); - free(w); - w = NULL; - } - priv->widgets = NULL; + priv->links = eina_list_free(priv->links); + efl_unref(priv->model); + priv->model = NULL; efl_destructor(efl_super(obj, MY_CLASS)); } @@ -291,32 +79,21 @@ _elm_view_form_efl_object_destructor(Eo *obj, Elm_View_Form_Data *priv) static void _elm_view_form_model_set(Eo *obj EINA_UNUSED, Elm_View_Form_Data *priv, Eo *model) { - if (priv->model_obj != NULL) - { - efl_event_callback_del(priv->model_obj, EFL_MODEL_EVENT_PROPERTIES_CHANGED, _efl_model_properties_change_cb, priv); - efl_unref(priv->model_obj); - } + Efl_Object *link; + Eina_List *l; - priv->model_obj = model; + efl_replace(&priv->model, model); - if (priv->model_obj != NULL) - { - efl_ref(priv->model_obj); - efl_event_callback_add(priv->model_obj, EFL_MODEL_EVENT_PROPERTIES_CHANGED, _efl_model_properties_change_cb, priv); - _update_model_properties(priv); - } + EINA_LIST_FOREACH(priv->links, l, link) + efl_ui_view_model_set(link, priv->model); } static void _elm_view_form_widget_add(Eo *obj EINA_UNUSED, Elm_View_Form_Data *priv, const char *propname, Evas_Object *evas) { - Eina_Bool status; - EINA_SAFETY_ON_NULL_RETURN(evas); - EINA_SAFETY_ON_NULL_RETURN(propname); - status = _elm_view_widget_add(priv, propname, evas); - EINA_SAFETY_ON_FALSE_RETURN(status); + _elm_view_widget_add(priv, propname, evas); } #include "elm_view_form.eo.c" diff --git a/src/lib/elementary/elm_view_form.eo b/src/lib/elementary/elm_view_form.eo index 1045653613..bdc4183fd7 100644 --- a/src/lib/elementary/elm_view_form.eo +++ b/src/lib/elementary/elm_view_form.eo @@ -24,7 +24,6 @@ class Elm.View.Form (Efl.Object) } implements { Efl.Object.destructor; - Efl.Object.constructor; } constructors { .model_set;