elementary: converting Efl.Ui.List to the new Efl.Model API.

This commit is contained in:
Cedric BAIL 2018-02-06 16:28:51 -08:00
parent cb7550eb1c
commit bf2e65a38d
6 changed files with 138 additions and 154 deletions

View File

@ -195,32 +195,6 @@ _on_item_mouse_up(void *data, Evas *evas EINA_UNUSED, Evas_Object *o EINA_UNUSED
_efl_ui_view_list_item_select_set(item, EINA_TRUE);
}
static void
_count_then(void * data, Efl_Event const* event EINA_UNUSED)
{
Efl_Ui_View_List_Data *pd = data;
EINA_SAFETY_ON_NULL_RETURN(pd);
pd->count_future = NULL;
_layout(pd);
}
static void
_count_error(void * data, Efl_Event const* event EINA_UNUSED)
{
Efl_Ui_View_List_Data *pd = data;
EINA_SAFETY_ON_NULL_RETURN(pd);
pd->count_future = NULL;
}
static void
_children_slice_error(void * data EINA_UNUSED, Efl_Event const* event EINA_UNUSED)
{
Efl_Ui_View_List_Data *pd = data;
EINA_SAFETY_ON_NULL_RETURN(pd);
pd->slice_future = NULL;
}
EOLIAN static void
_efl_ui_view_list_select_mode_set(Eo *obj EINA_UNUSED, Efl_Ui_View_List_Data *pd, Elm_Object_Select_Mode mode)
{
@ -735,8 +709,7 @@ _efl_ui_view_list_efl_object_constructor(Eo *obj, Efl_Ui_View_List_Data *pd)
pd->style = eina_stringshare_add(elm_widget_style_get(obj));
pd->factory = NULL;
pd->align.h = 0;
pd->align.v = 0;
pd->orient = EFL_ORIENT_DOWN;
pd->min.w = 0;
pd->min.h = 0;
@ -776,29 +749,20 @@ _efl_ui_view_list_efl_ui_view_model_set(Eo *obj EINA_UNUSED, Efl_Ui_View_List_Da
if (pd->model == model)
return;
if (pd->count_future)
{
efl_future_cancel(pd->count_future);
pd->count_future = NULL;
}
if (pd->model)
{
if (pd->relayout)
efl_ui_view_list_relayout_model_set(pd->relayout, NULL);
efl_ui_view_list_segarray_flush(pd->segarray);
efl_unref(pd->model);
pd->model = NULL;
}
efl_replace(&pd->model, model);
if (model)
{
pd->model = model;
efl_ref(pd->model);
if (pd->relayout)
efl_ui_view_list_relayout_model_set(pd->relayout, model);
pd->count_future = efl_model_children_count_get(pd->model);
efl_future_then(pd->count_future, &_count_then, &_count_error, NULL, pd);
}
evas_object_smart_changed(pd->obj);
@ -908,11 +872,7 @@ _efl_ui_view_list_item_select_set(Efl_Ui_View_List_LayoutItem *item, Eina_Bool s
static void
_efl_ui_view_list_relayout_set(Eo *obj EINA_UNUSED, Efl_Ui_View_List_Data *pd EINA_UNUSED, Efl_Ui_View_List_Relayout *object)
{
if(pd->relayout)
efl_unref(pd->relayout);
pd->relayout = object;
efl_ref(pd->relayout);
efl_replace(&pd->relayout, object);
}
static Efl_Ui_View_List_Relayout *
@ -930,17 +890,22 @@ _layout(Efl_Ui_View_List_Data *pd)
efl_ui_view_list_relayout_layout_do(pd->relayout, pd->obj, pd->segarray_first, pd->segarray);
}
static void
_children_slice_then(void * data, Efl_Event const* event)
static Eina_Value
_children_slice_then(void * data, const Eina_Value v, const Eina_Future *dead_future EINA_UNUSED)
{
Efl_Ui_View_List_Data *pd = data;
Eina_Accessor *acc = (Eina_Accessor*)((Efl_Future_Event_Success*)event->info)->value;
efl_ui_view_list_segarray_insert_accessor(pd->segarray, pd->outstanding_slice.slice_start, acc);
if (eina_value_type_get(&v) == EINA_VALUE_TYPE_ERROR)
goto on_error;
pd->segarray_first = pd->outstanding_slice.slice_start;
pd->outstanding_slice.slice_start = pd->outstanding_slice.slice_count = 0;
pd->slice_future = NULL;
efl_ui_view_list_segarray_insert_value(pd->segarray, pd->slice.start, v);
pd->segarray_first = pd->slice.start;
pd->slice.start = pd->slice.count = 0;
pd->slice.future = NULL;
on_error:
return v;
}
/* EFL UI LIST MODEL INTERFACE */
@ -1039,21 +1004,24 @@ _efl_ui_view_list_efl_ui_view_list_model_unrealize(Eo *obj, Efl_Ui_View_List_Dat
}
EOLIAN static void
_efl_ui_view_list_efl_ui_view_list_model_load_range_set(Eo* obj EINA_UNUSED, Efl_Ui_View_List_Data* pd, int first, int count)
_efl_ui_view_list_efl_ui_view_list_model_load_range_set(Eo* obj, Efl_Ui_View_List_Data* pd, int first, int count)
{
if(!pd->slice_future)
{
pd->slice_future = efl_model_children_slice_get(pd->model, first, count);
pd->outstanding_slice.slice_start = first;
pd->outstanding_slice.slice_count = count;
efl_future_then(pd->slice_future, &_children_slice_then, &_children_slice_error, NULL, pd);
}
Eina_Future *f;
if (pd->slice.future) return ;
pd->slice.start = first;
pd->slice.count = count;
f = efl_model_children_slice_get(pd->model, first, count);
f = eina_future_then(f, _children_slice_then, pd);
pd->slice.future = efl_future_Eina_FutureXXX_then(obj, f);
}
EOLIAN static int
_efl_ui_view_list_efl_ui_view_list_model_model_size_get(const Eo *obj EINA_UNUSED, Efl_Ui_View_List_Data *pd)
{
return pd->item_count;
return efl_model_children_count_get(pd->model);
}
ELM_WIDGET_KEY_DOWN_DEFAULT_IMPLEMENT(efl_ui_view_list, Efl_Ui_View_List_Data)

View File

@ -13,31 +13,35 @@
typedef struct _Efl_Ui_View_List_Precise_Layouter_Data
{
Eina_Bool initialized;
Eina_Bool recalc;
Eina_Bool resize;
Eina_Size2D min;
Efl_Model* model;
Efl_Ui_View_List_Model *modeler;
Efl_Future *count_future;
Ecore_Job *calc_job;
Efl_Ui_View_List_SegArray *segarray;
Eina_Size2D min;
unsigned int calc_progress;
int first;
int count_total;
unsigned int calc_progress;
Eina_Bool initialized : 1;
Eina_Bool recalc : 1;
Eina_Bool resize : 1;
} Efl_Ui_View_List_Precise_Layouter_Data;
typedef struct _Efl_Ui_View_List_Precise_Layouter_Node_Data
{
Eina_Size2D min;
Eina_Size2D size;
Eina_Bool realized;
Eina_Bool realized;
} Efl_Ui_View_List_Precise_Layouter_Node_Data;
typedef struct _Efl_Ui_View_List_Precise_Layouter_Callback_Data
{
Efl_Ui_View_List_Precise_Layouter_Data* pd;
Efl_Ui_View_List_LayoutItem* item;
Efl_Ui_View_List_Precise_Layouter_Data *pd;
Efl_Ui_View_List_LayoutItem *item;
} Efl_Ui_View_List_Precise_Layouter_Callback_Data;
#include "efl_ui_view_list_precise_layouter.eo.h"
@ -175,29 +179,6 @@ _item_min_calc(Efl_Ui_View_List_Precise_Layouter_Data *pd, Efl_Ui_View_List_Layo
_item_size_calc(pd, item);
}
static void
_count_then(void * data, Efl_Event const* event)
{
Efl_Ui_View_List_Precise_Layouter_Data *pd = data;
EINA_SAFETY_ON_NULL_RETURN(pd);
pd->count_future = NULL;
pd->count_total = *(int*)((Efl_Future_Event_Success*)event->info)->value;
if (pd->modeler && (pd->count_total != efl_ui_view_list_segarray_count(pd->segarray)))
{
pd->recalc = EINA_TRUE;
efl_ui_view_list_model_load_range_set(pd->modeler, 0, 0); // load all
}
}
static void
_count_error(void * data, Efl_Event const* event EINA_UNUSED)
{
Efl_Ui_View_List_Precise_Layouter_Data *pd = data;
EINA_SAFETY_ON_NULL_RETURN(pd);
pd->count_future = NULL;
}
static void
_on_item_size_hint_change(void *data, Evas *e EINA_UNUSED,
Evas_Object *obj, void *event_info EINA_UNUSED)
@ -225,15 +206,46 @@ _on_modeler_resize(void *data, Evas *e EINA_UNUSED,
pd->resize = EINA_TRUE;
}
typedef struct _Request Request;
struct _Request
{
Efl_Ui_View_List_Precise_Layouter_Data *pd;
unsigned int index;
};
static Eina_Value
_children_get(void *data, const Eina_Value v, const Eina_Future *dead_future EINA_UNUSED)
{
Request *r = data;
if (eina_value_type_get(&v) == EINA_VALUE_TYPE_ERROR)
goto on_error;
efl_ui_view_list_segarray_insert_value(r->pd->segarray, r->index, v);
r->pd->recalc = EINA_TRUE;
evas_object_smart_changed(r->pd->modeler);
on_error:
free(r);
return v;
}
static void
_child_added_cb(void *data, const Efl_Event *event)
{
Efl_Model_Children_Event* evt = event->info;
Efl_Ui_View_List_Precise_Layouter_Data *pd = data;
Eina_Future *f;
Request *r;
efl_ui_view_list_segarray_insert(pd->segarray, evt->index, evt->child);
pd->recalc = EINA_TRUE;
evas_object_smart_changed(pd->modeler);
r = calloc(1, sizeof (Request));
if (!r) return ;
r->index = evt->index;
r->pd = pd;
f = efl_model_children_slice_get(pd->model, evt->index, 1);
f = eina_future_then(f, _children_get, r);
}
static void
@ -518,7 +530,6 @@ _efl_ui_view_list_precise_layouter_efl_object_constructor(Eo *obj EINA_UNUSED, E
{
obj = efl_constructor(efl_super(obj, MY_CLASS));
pd->initialized = EINA_FALSE;
pd->count_future = NULL;
return obj;
}
@ -552,29 +563,21 @@ _efl_ui_view_list_precise_layouter_efl_ui_view_list_relayout_elements_get(const
EOLIAN static void
_efl_ui_view_list_precise_layouter_efl_ui_view_list_relayout_model_set(Eo *obj EINA_UNUSED, Efl_Ui_View_List_Precise_Layouter_Data *pd, Efl_Model *model)
{
if (pd->model == model)
return;
_finalize(obj, pd);
efl_replace(&pd->model, model);
pd->count_total = 0;
if (pd->count_future)
{
efl_future_cancel(pd->count_future);
pd->count_future = NULL;
}
if (pd->model)
{
_finalize(obj, pd);
efl_unref(pd->model);
pd->model = NULL;
}
if (model)
{
pd->model = model;
efl_ref(pd->model);
pd->count_future = efl_model_children_count_get(pd->model);
efl_future_then(pd->count_future, &_count_then, &_count_error, NULL, pd);
pd->count_total = efl_model_children_count_get(pd->model);
if (pd->modeler && (pd->count_total != efl_ui_view_list_segarray_count(pd->segarray)))
{
pd->recalc = EINA_TRUE;
efl_ui_view_list_model_load_range_set(pd->modeler, 0, pd->count_total); // load all
}
}
}

View File

@ -27,39 +27,31 @@ struct _Efl_Ui_View_List_Data
Efl_Ui_View_List_Pan *pan_obj;
Efl_Model *model;
struct {
double h, v;
Eina_Bool scalable: 1;
} pad;
Eina_Stringshare *style;
struct {
double h, v;
} align;
Eina_Future *future;
struct {
double x, y;
} weight;
int start;
int count;
} slice;
Efl_Ui_Layout_Factory *factory;
Eina_List *selected_items;
Efl_Ui_Focus_Manager *manager;
Efl_Ui_View_List_Relayout *relayout;
Efl_Orient orient;
int segarray_first;
Efl_Ui_View_List_SegArray *segarray;
Efl_Ui_Layout_Factory *factory;
Eina_List *selected_items;
Eina_Stringshare *style;
Elm_Object_Select_Mode select_mode;
Elm_List_Mode mode;
Efl_Ui_Focus_Manager *manager;
Eina_Rect gmt;
Eina_Size2D min;
int item_count;
Efl_Future *slice_future;
Efl_Future *count_future;
Efl_Ui_View_List_Relayout *relayout;
struct {
int slice_start;
int slice_count;
} outstanding_slice;
Eina_Bool homogeneous : 1;
Eina_Bool recalc : 1;

View File

@ -215,28 +215,49 @@ _efl_ui_view_list_segarray_insert(Eo *obj EINA_UNUSED, Efl_Ui_View_List_SegArray
_efl_ui_view_list_segarray_insert_at_node(pd, index, item, NULL);
}
EOLIAN static void
_efl_ui_view_list_segarray_insert_accessor(Eo *obj EINA_UNUSED, Efl_Ui_View_List_SegArray_Data* pd, int first, Eina_Accessor* accessor)
static void
efl_ui_view_list_segarray_insert_object(Efl_Ui_View_List_SegArray_Data *segarray, unsigned int index, Efl_Model *children)
{
int i;
Efl_Model* children;
Efl_Ui_View_List_SegArray_Node *node;
EINA_ACCESSOR_FOREACH(accessor, i, children)
node = (void*)eina_rbtree_inline_lookup(EINA_RBTREE_GET(segarray->root),
&index, sizeof(index), &_insert_lookup_cb, NULL);
if (!node)
{
Efl_Ui_View_List_SegArray_Node *node;
int idx = first + i;
node = _alloc_node(segarray, index);
}
node = (void*)eina_rbtree_inline_lookup(EINA_RBTREE_GET(pd->root),
&idx, sizeof(idx), &_insert_lookup_cb, NULL);
if (!node)
assert(node->length < node->max);
node->pointers[node->length] = _create_item(children, node, index);
node->length++;
segarray->count++;
}
EOLIAN static void
_efl_ui_view_list_segarray_insert_value(Eo *obj EINA_UNUSED, Efl_Ui_View_List_SegArray_Data *segarray, int first, Eina_Value v)
{
Efl_Model *children;
unsigned int i, len;
if (eina_value_type_get(&v) == EINA_VALUE_TYPE_OBJECT)
{
children = eina_value_object_get(&v);
efl_ui_view_list_segarray_insert_object(segarray, first, children);
}
else if (eina_value_type_get(&v) == EINA_VALUE_TYPE_ARRAY)
{
Eina_Value vo = EINA_VALUE_EMPTY;
EINA_VALUE_ARRAY_FOREACH(&v, len, i, children)
{
node = _alloc_node(pd, idx);
}
unsigned int idx = first + i;
assert(node->length < node->max);
node->pointers[node->length] = _create_item(children, node, idx);
node->length++;
pd->count++;
efl_ui_view_list_segarray_insert_object(segarray, idx, children);
}
}
else
{
printf("Unknow type !\n");
}
}

View File

@ -20,11 +20,11 @@ class Efl.Ui.View_List_SegArray (Efl.Object)
acc: accessor<ptr(Efl.Ui.View.List.SegArray.Node)>;
}
}
insert_accessor {
insert_value {
[[ Insert a accessor in segarray tree ]]
params {
@in first: int;
@in acc: accessor<Efl.Model>;
@in v: any_value;
}
}
count {

View File

@ -428,7 +428,7 @@ _elm_view_list_model_set(Eo *obj EINA_UNUSED, Elm_View_List_Data *priv, Efl_Mode
}
static Efl_Model *
_elm_view_list_model_get(Eo *obj EINA_UNUSED, Elm_View_List_Data *priv)
_elm_view_list_model_get(const Eo *obj EINA_UNUSED, Elm_View_List_Data *priv)
{
return priv->connect.model;
}