ui.relative_layout: implement Efl.Pack

Now, efl_content_iterate, efl_content_count, efl_pack, efl_pack_unpack,
efl_pack_unpack_all and efl_pack_clear are available for relative_layout.

Reviewed-by: Xavi Artigas <xavierartigas@yahoo.es>
Differential Revision: https://phab.enlightenment.org/D8631
This commit is contained in:
Yeongjong Lee 2019-05-03 09:20:17 +00:00 committed by Marcel Hollerbach
parent aaeff3f7b7
commit 2426656fd6
5 changed files with 158 additions and 61 deletions

View File

@ -27,29 +27,25 @@ _chain_sort_cb(const void *l1, const void *l2)
static void
_on_child_size_changed(void *data, const Efl_Event *event EINA_UNUSED)
{
Efl_Ui_Relative_Layout_Data *pd = data;
Efl_Ui_Relative_Layout *obj = data;
efl_pack_layout_request(pd->obj);
efl_pack_layout_request(obj);
}
static void
_on_child_hints_changed(void *data, const Efl_Event *event EINA_UNUSED)
{
Efl_Ui_Relative_Layout_Data *pd = data;
Efl_Ui_Relative_Layout *obj = data;
efl_pack_layout_request(pd->obj);
efl_pack_layout_request(obj);
}
static void
_on_child_del(void *data, const Efl_Event *event)
{
Efl_Ui_Relative_Layout_Data *pd = data;
Efl_Ui_Relative_Layout *obj = data;
if (eina_hash_del_by_key(pd->children, &event->object))
efl_pack_layout_request(pd->obj);
else
ERR("child(%p(%s)) is not registered", event->object,
efl_class_name_get(event->object));
efl_pack_unpack(obj, event->object);
}
EFL_CALLBACKS_ARRAY_DEFINE(efl_ui_relative_layout_callbacks,
@ -82,7 +78,7 @@ _efl_ui_relative_layout_register(Efl_Ui_Relative_Layout_Data *pd, Eo *child)
efl_key_data_set(child, "_elm_leaveme", pd->obj);
efl_canvas_object_clipper_set(child, pd->clipper);
efl_event_callback_array_add(child, efl_ui_relative_layout_callbacks(), pd);
efl_event_callback_array_add(child, efl_ui_relative_layout_callbacks(), pd->obj);
efl_canvas_group_member_add(pd->obj, child);
efl_canvas_group_change(pd->obj);
@ -366,19 +362,26 @@ _hash_free_cb(void *data)
{
Efl_Ui_Relative_Layout_Child *child = data;
efl_canvas_group_member_remove(child->layout, child->obj);
efl_canvas_object_clipper_set(child->obj, NULL);
efl_key_data_set(child->obj, "_elm_leaveme", NULL);
efl_event_callback_array_del(child->obj, efl_ui_relative_layout_callbacks(),
child->layout);
if (!efl_invalidated_get(child->obj))
_elm_widget_sub_object_redirect_to_top(child->layout, child->obj);
free(child);
}
static Eina_Bool
_hash_free_foreach_cb(const Eina_Hash *hash EINA_UNUSED, const void *key EINA_UNUSED,
void *data, void *fdata EINA_UNUSED)
static void
_hash_clear_cb(void *data)
{
Efl_Ui_Relative_Layout_Child *child = data;
_elm_widget_sub_object_redirect_to_top(child->layout, child->obj);
_hash_free_cb(child);
return EINA_TRUE;
efl_event_callback_array_del(child->obj, efl_ui_relative_layout_callbacks(),
child->layout);
efl_del(child->obj);
}
static Eina_Bool
@ -558,14 +561,9 @@ _efl_ui_relative_layout_efl_object_constructor(Eo *obj, Efl_Ui_Relative_Layout_D
EOLIAN static void
_efl_ui_relative_layout_efl_object_invalidate(Eo *obj, Efl_Ui_Relative_Layout_Data *pd)
{
Eo *child;
efl_invalidate(efl_super(obj, MY_CLASS));
EINA_LIST_FREE(pd->children, child)
{
efl_event_callback_array_del(child, efl_ui_relative_layout_callbacks(), pd);
}
eina_hash_free_buckets(pd->children);
}
EOLIAN static void
@ -578,35 +576,101 @@ _efl_ui_relative_layout_efl_object_destructor(Eo *obj, Efl_Ui_Relative_Layout_Da
efl_destructor(efl_super(obj, MY_CLASS));
}
EOLIAN static void
_efl_ui_relative_layout_unregister(Eo *obj, Efl_Ui_Relative_Layout_Data *pd, Efl_Object *child)
EOLIAN static Eina_Bool
_efl_ui_relative_layout_efl_pack_pack(Eo *obj EINA_UNUSED, Efl_Ui_Relative_Layout_Data *pd, Efl_Gfx_Entity *subobj)
{
_elm_widget_sub_object_redirect_to_top(obj, child);
if (eina_hash_del_by_key(pd->children, &child))
{
efl_canvas_group_member_remove(obj, child);
efl_canvas_object_clipper_set(child, NULL);
efl_key_data_set(child, "_elm_leaveme", NULL);
efl_event_callback_array_del(child, efl_ui_relative_layout_callbacks(), pd);
efl_pack_layout_request(obj);
}
else
{
ERR("child(%p(%s)) is not registered", child, efl_class_name_get(child));
}
EINA_SAFETY_ON_FALSE_RETURN_VAL(subobj, EINA_FALSE);
EINA_SAFETY_ON_TRUE_RETURN_VAL(!!eina_hash_find(pd->children, &subobj), EINA_FALSE);
return !!_efl_ui_relative_layout_register(pd, subobj);
}
EOLIAN static void
_efl_ui_relative_layout_unregister_all(Eo *obj, Efl_Ui_Relative_Layout_Data *pd)
EOLIAN static Eina_Bool
_efl_ui_relative_layout_efl_pack_unpack(Eo *obj, Efl_Ui_Relative_Layout_Data *pd, Efl_Object *child)
{
eina_hash_foreach(pd->children, _hash_free_foreach_cb, NULL);
if (!eina_hash_del_by_key(pd->children, &child))
{
ERR("child(%p(%s)) is not registered", child, efl_class_name_get(child));
return EINA_FALSE;
}
efl_pack_layout_request(obj);
return EINA_TRUE;
}
EOLIAN static Eina_Bool
_efl_ui_relative_layout_efl_pack_unpack_all(Eo *obj, Efl_Ui_Relative_Layout_Data *pd)
{
eina_hash_free_buckets(pd->children);
efl_pack_layout_request(obj);
return EINA_TRUE;
}
EOLIAN static Eina_Bool
_efl_ui_relative_layout_efl_pack_pack_clear(Eo *obj, Efl_Ui_Relative_Layout_Data *pd)
{
eina_hash_free_cb_set(pd->children, _hash_clear_cb);
eina_hash_free_buckets(pd->children);
eina_hash_free_cb_set(pd->children, _hash_free_cb);
efl_pack_layout_request(obj);
return EINA_TRUE;
}
static Eina_Bool
_efl_ui_relative_layout_content_iterator_next(Efl_Ui_Relative_Layout_Content_Iterator *it, void **data)
{
Efl_Ui_Relative_Layout_Child *child;
if (!eina_iterator_next(it->real_iterator, (void **) &child))
return EINA_FALSE;
if (data) *data = child->obj;
return EINA_TRUE;
}
static Eo *
_efl_ui_relative_layout_content_iterator_get_container(Efl_Ui_Relative_Layout_Content_Iterator *it)
{
return it->relative_layout;
}
static void
_efl_ui_relative_layout_content_iterator_free(Efl_Ui_Relative_Layout_Content_Iterator *it)
{
eina_iterator_free(it->real_iterator);
free(it);
}
EOLIAN static Eina_Iterator *
_efl_ui_relative_layout_children_iterate(Eo *obj EINA_UNUSED, Efl_Ui_Relative_Layout_Data *pd)
_efl_ui_relative_layout_efl_container_content_iterate(Eo *obj, Efl_Ui_Relative_Layout_Data *pd)
{
return eina_hash_iterator_data_new(pd->children);
Efl_Ui_Relative_Layout_Content_Iterator *it;
it = calloc(1, sizeof(*it));
if (!it) return NULL;
EINA_MAGIC_SET(&it->iterator, EINA_MAGIC_ITERATOR);
it->relative_layout = obj;
it->real_iterator = eina_hash_iterator_data_new(pd->children);
it->iterator.version = EINA_ITERATOR_VERSION;
it->iterator.next = FUNC_ITERATOR_NEXT(_efl_ui_relative_layout_content_iterator_next);
it->iterator.get_container = FUNC_ITERATOR_GET_CONTAINER(
_efl_ui_relative_layout_content_iterator_get_container);
it->iterator.free = FUNC_ITERATOR_FREE(_efl_ui_relative_layout_content_iterator_free);
return &it->iterator;
}
EOLIAN static int
_efl_ui_relative_layout_efl_container_content_count(Eo *obj EINA_UNUSED, Efl_Ui_Relative_Layout_Data *pd)
{
return eina_hash_population(pd->children);
}
EFL_UI_RELATIVE_LAYOUT_RELATION_SET_GET(left, LEFT);

View File

@ -1,4 +1,4 @@
class @beta Efl.Ui.Relative_Layout extends Efl.Ui.Widget implements Efl.Pack_Layout
class @beta Efl.Ui.Relative_Layout extends Efl.Ui.Widget implements Efl.Pack_Layout, Efl.Pack
{
[[The relative layout class.
@ -53,25 +53,18 @@ class @beta Efl.Ui.Relative_Layout extends Efl.Ui.Widget implements Efl.Pack_Lay
ranging from 0.0 to 1.0.]]
}
}
unregister {
[[Remove all relations of the child.]]
params {
@in child: Efl.Object; [[The child to unregister]]
}
}
unregister_all {
[[Remove all relations from the registered children. ]]
}
children_iterate {
[[Begin iterating over this object's children.]]
return: iterator<Efl.Object> @owned @warn_unused; [[Iterator to object children.]]
}
}
implements {
Efl.Object.constructor;
Efl.Object.invalidate;
Efl.Object.destructor;
Efl.Canvas.Group.group_calculate;
Efl.Pack.pack_clear;
Efl.Pack.unpack_all;
Efl.Pack.unpack;
Efl.Pack.pack;
Efl.Container.content_iterate;
Efl.Container.content_count;
Efl.Gfx.Entity.position { set; }
Efl.Gfx.Entity.size { set; }
Efl.Pack_Layout.layout_update;

View File

@ -21,6 +21,7 @@ typedef struct _Efl_Ui_Relative_Layout_Data Efl_Ui_Relative_Layout_Data;
typedef struct _Efl_Ui_Relative_Layout_Child Efl_Ui_Relative_Layout_Child;
typedef struct _Efl_Ui_Relative_Layout_Calc Efl_Ui_Relative_Layout_Calc;
typedef struct _Efl_Ui_Relative_Layout_Relation Efl_Ui_Relative_Layout_Relation;
typedef struct _Efl_Ui_Relative_Layout_Content_Iterator Efl_Ui_Relative_Layout_Content_Iterator;
struct _Efl_Ui_Relative_Layout_Calc
{
@ -68,6 +69,13 @@ struct _Efl_Ui_Relative_Layout_Child
Efl_Ui_Relative_Layout_Calc calc;
};
struct _Efl_Ui_Relative_Layout_Content_Iterator
{
Eina_Iterator iterator;
Eina_Iterator *real_iterator;
Eo *relative_layout;
};
#define EFL_UI_RELATIVE_LAYOUT_RELATION_SET_GET(direction, DIRECTION) \
EOLIAN static void \
_efl_ui_relative_layout_relation_ ## direction ## _set(Eo *obj, Efl_Ui_Relative_Layout_Data *pd, Eo *child, Eo *target, double relative) \

View File

@ -243,8 +243,7 @@ EFL_START_TEST (efl_ui_relative_layout_layout_update)
{
int i, max_index = (sizeof(hints) / sizeof(Hint));
Eo *btn = efl_add(EFL_UI_BUTTON_CLASS, layout,
efl_ui_relative_layout_relation_left_set(layout, efl_added, NULL, 0.0));
Eo *btn = efl_add(EFL_UI_BUTTON_CLASS, layout, efl_pack(layout, efl_added));
for (i = 0; i < max_index; i++)
{
@ -342,6 +341,38 @@ EFL_START_TEST (efl_ui_relative_layout_relation_set)
}
EFL_END_TEST
EFL_START_TEST (efl_ui_relative_layout_pack)
{
Eo *btn[3], *child;
Eina_Iterator *it;
int i;
for (i = 0; i < 3; i++)
btn[i] = efl_add(EFL_UI_BUTTON_CLASS, layout, efl_pack(layout, efl_added));
ck_assert_int_eq(efl_content_count(layout), 3);
it = efl_content_iterate(layout);
EINA_ITERATOR_FOREACH(it, child)
ck_assert_ptr_eq(layout, efl_canvas_object_render_parent_get(child));
eina_iterator_free(it);
efl_pack_unpack(layout, NULL);
ck_assert_int_eq(efl_content_count(layout), 3);
efl_pack_unpack(layout, btn[0]);
ck_assert_int_eq(efl_content_count(layout), 2);
efl_pack_unpack_all(layout);
ck_assert_int_eq(efl_content_count(layout), 0);
for (i = 0; i < 3; i++)
efl_pack(layout, btn[i]);
ck_assert_int_eq(efl_content_count(layout), 3);
efl_pack_clear(layout);
ck_assert_int_eq(efl_content_count(layout), 0);
for (i = 0; i < 3; i++)
ck_assert(efl_invalidated_get(btn[i]));
}
EFL_END_TEST
void efl_ui_test_relative_layout(TCase *tc)
{
tcase_add_checked_fixture(tc, layout_setup, layout_teardown);
@ -349,4 +380,5 @@ void efl_ui_test_relative_layout(TCase *tc)
tcase_add_test(tc, efl_ui_relative_layout_layout_update);
tcase_add_test(tc, efl_ui_relative_layout_layout_update_chain);
tcase_add_test(tc, efl_ui_relative_layout_relation_set);
tcase_add_test(tc, efl_ui_relative_layout_pack);
}

View File

@ -8,7 +8,7 @@
/* spec-meta-start
{"test-interface":"Efl.Pack",
"test-widgets": ["Efl.Ui.Table"]}
"test-widgets": ["Efl.Ui.Table", "Efl.Ui.Relative_Layout"]}
spec-meta-end */