eo2: add eo2_parent_set(), eo2_parent_get(), eo2_children_iterator_new()
imported from eo_base_class.c as is in
a7f417e
2013-12-24 23:45:30 +0900 <Carsten Haitzler (Rasterman)>
This commit is contained in:
parent
d4aad6bfc0
commit
c9ccc700fd
|
@ -1391,6 +1391,8 @@ eo2_base_data_del(const char *key);
|
|||
* @see eo_parent_get()
|
||||
*/
|
||||
#define eo_parent_set(parent) EO_BASE_ID(EO_BASE_SUB_ID_PARENT_SET), EO_TYPECHECK(Eo *, parent)
|
||||
EAPI void
|
||||
eo2_parent_set(Eo *parent_id);
|
||||
|
||||
/**
|
||||
* @def eo_parent_get
|
||||
|
@ -1400,6 +1402,8 @@ eo2_base_data_del(const char *key);
|
|||
* @see eo_parent_set()
|
||||
*/
|
||||
#define eo_parent_get(parent) EO_BASE_ID(EO_BASE_SUB_ID_PARENT_GET), EO_TYPECHECK(Eo **, parent)
|
||||
EAPI Eo *
|
||||
eo2_parent_get();
|
||||
|
||||
/**
|
||||
* @def eo_children_iterator_new
|
||||
|
@ -1410,6 +1414,8 @@ eo2_base_data_del(const char *key);
|
|||
* @see eo_parent_set()
|
||||
*/
|
||||
#define eo_children_iterator_new(it) EO_BASE_ID(EO_BASE_SUB_ID_CHILDREN_ITERATOR_NEW), EO_TYPECHECK(Eina_Iterator **, it)
|
||||
EAPI Eina_Iterator *
|
||||
eo2_children_iterator_new();
|
||||
|
||||
/**
|
||||
* @def eo_wref_add
|
||||
|
|
|
@ -650,10 +650,11 @@ eo2_add_internal_start(const char *file, int line, const Eo_Class *klass_id, Eo
|
|||
#endif
|
||||
Eo_Id obj_id = _eo_id_allocate(obj);
|
||||
obj->header.id = obj_id;
|
||||
eo_parent_set((Eo *)obj_id, parent_id);
|
||||
|
||||
_eo_condtor_reset(obj);
|
||||
|
||||
eo2_do((Eo *)obj_id, eo2_parent_set(parent_id));
|
||||
|
||||
return (Eo *)obj_id;
|
||||
}
|
||||
|
||||
|
@ -1655,7 +1656,11 @@ eo_unref(const Eo *obj_id)
|
|||
EAPI void
|
||||
eo_del(const Eo *obj)
|
||||
{
|
||||
eo_do((Eo *) obj, eo_parent_set(NULL));
|
||||
EO_OBJ_POINTER_RETURN(obj, _obj);
|
||||
if (_obj->klass->desc->version == EO2_VERSION)
|
||||
eo2_do((Eo *) obj, eo2_parent_set(NULL));
|
||||
else
|
||||
eo_do((Eo *) obj, eo_parent_set(NULL));
|
||||
eo_unref(obj);
|
||||
}
|
||||
|
||||
|
|
|
@ -14,6 +14,9 @@ typedef struct _Eo_Callback_Description Eo_Callback_Description;
|
|||
|
||||
typedef struct
|
||||
{
|
||||
Eina_List *children;
|
||||
Eo *parent;
|
||||
|
||||
Eina_Inlist *generic_data;
|
||||
Eo ***wrefs;
|
||||
|
||||
|
@ -101,6 +104,165 @@ _data_get(Eo *obj EINA_UNUSED, void *class_data, const char *key)
|
|||
}
|
||||
EAPI EO2_VOID_FUNC_BODYV(eo2_base_data_get, EO2_FUNC_CALL(key), const char *key);
|
||||
|
||||
static void
|
||||
_parent_set(Eo *obj, void *class_data, Eo *parent_id)
|
||||
{
|
||||
Private_Data *pd = (Private_Data *) class_data;
|
||||
|
||||
if (pd->parent == parent_id)
|
||||
return;
|
||||
|
||||
if (eo_composite_is(obj) && pd->parent)
|
||||
{
|
||||
eo_composite_detach(obj, pd->parent);
|
||||
}
|
||||
|
||||
if (pd->parent)
|
||||
{
|
||||
Private_Data *old_parent_pd;
|
||||
|
||||
old_parent_pd = eo_data_scope_get(pd->parent, EO_BASE_CLASS);
|
||||
if (old_parent_pd)
|
||||
{
|
||||
old_parent_pd->children = eina_list_remove(old_parent_pd->children,
|
||||
obj);
|
||||
}
|
||||
else
|
||||
{
|
||||
ERR("CONTACT DEVS!!! SHOULD NEVER HAPPEN!!! Old parent %p for object %p is not a valid Eo object.",
|
||||
pd->parent, obj);
|
||||
}
|
||||
|
||||
eo_xunref(obj, pd->parent);
|
||||
}
|
||||
|
||||
/* Set new parent */
|
||||
if (parent_id)
|
||||
{
|
||||
Private_Data *parent_pd = NULL;
|
||||
parent_pd = eo_data_scope_get(parent_id, EO_BASE_CLASS);
|
||||
|
||||
if (EINA_LIKELY(parent_pd != NULL))
|
||||
{
|
||||
pd->parent = parent_id;
|
||||
parent_pd->children = eina_list_append(parent_pd->children,
|
||||
obj);
|
||||
eo_xref(obj, pd->parent);
|
||||
}
|
||||
else
|
||||
{
|
||||
pd->parent = NULL;
|
||||
ERR("New parent %p for object %p is not a valid Eo object.",
|
||||
parent_id, obj);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
pd->parent = NULL;
|
||||
}
|
||||
}
|
||||
EAPI EO2_VOID_FUNC_BODYV(eo2_parent_set, EO2_FUNC_CALL(parent_id), Eo *parent_id);
|
||||
|
||||
static Eo *
|
||||
_parent_get(Eo *obj EINA_UNUSED, void *class_data)
|
||||
{
|
||||
Private_Data *pd = (Private_Data *) class_data;
|
||||
|
||||
return pd->parent;
|
||||
}
|
||||
EAPI EO2_FUNC_BODY(eo2_parent_get, Eo *, NULL);
|
||||
|
||||
/* Children accessor */
|
||||
typedef struct _Eo_Children_Iterator Eo_Children_Iterator;
|
||||
struct _Eo_Children_Iterator
|
||||
{
|
||||
Eina_Iterator iterator;
|
||||
Eina_List *current;
|
||||
_Eo_Object *obj;
|
||||
Eo *obj_id;
|
||||
};
|
||||
|
||||
static Eina_Bool
|
||||
_eo_children_iterator_next(Eo_Children_Iterator *it, void **data)
|
||||
{
|
||||
if (!it->current) return EINA_FALSE;
|
||||
|
||||
if (data) *data = eina_list_data_get(it->current);
|
||||
it->current = eina_list_next(it->current);
|
||||
|
||||
return EINA_TRUE;
|
||||
}
|
||||
|
||||
static Eo *
|
||||
_eo_children_iterator_container(Eo_Children_Iterator *it)
|
||||
{
|
||||
return it->obj_id;
|
||||
}
|
||||
|
||||
static void
|
||||
_eo_children_iterator_free(Eo_Children_Iterator *it)
|
||||
{
|
||||
_Eo_Class *klass;
|
||||
_Eo_Object *obj;
|
||||
|
||||
klass = (_Eo_Class*) it->obj->klass;
|
||||
obj = it->obj;
|
||||
|
||||
eina_spinlock_take(&klass->iterators.trash_lock);
|
||||
if (klass->iterators.trash_count < 8)
|
||||
{
|
||||
klass->iterators.trash_count++;
|
||||
eina_trash_push(&klass->iterators.trash, it);
|
||||
}
|
||||
else
|
||||
{
|
||||
free(it);
|
||||
}
|
||||
eina_spinlock_release(&klass->iterators.trash_lock);
|
||||
|
||||
_eo_unref(obj);
|
||||
}
|
||||
|
||||
static Eina_Iterator *
|
||||
_children_iterator_new(Eo *obj_id, void *class_data)
|
||||
{
|
||||
Private_Data *pd = class_data;
|
||||
_Eo_Class *klass;
|
||||
Eo_Children_Iterator *it;
|
||||
|
||||
EO_OBJ_POINTER_RETURN_VAL(obj_id, obj, NULL);
|
||||
|
||||
if (!pd->children) return NULL;
|
||||
|
||||
klass = (_Eo_Class *) obj->klass;
|
||||
|
||||
eina_spinlock_take(&klass->iterators.trash_lock);
|
||||
it = eina_trash_pop(&klass->iterators.trash);
|
||||
if (it)
|
||||
{
|
||||
klass->iterators.trash_count--;
|
||||
memset(it, 0, sizeof (Eo_Children_Iterator));
|
||||
}
|
||||
else
|
||||
{
|
||||
it = calloc(1, sizeof (Eo_Children_Iterator));
|
||||
}
|
||||
eina_spinlock_release(&klass->iterators.trash_lock);
|
||||
if (!it) return NULL;
|
||||
|
||||
EINA_MAGIC_SET(&it->iterator, EINA_MAGIC_ITERATOR);
|
||||
it->current = obj->children;
|
||||
it->obj = _eo_ref(obj);
|
||||
it->obj_id = obj_id;
|
||||
|
||||
it->iterator.next = FUNC_ITERATOR_NEXT(_eo_children_iterator_next);
|
||||
it->iterator.get_container = FUNC_ITERATOR_GET_CONTAINER(_eo_children_iterator_container);
|
||||
it->iterator.free = FUNC_ITERATOR_FREE(_eo_children_iterator_free);
|
||||
|
||||
return (Eina_Iterator *)it;
|
||||
}
|
||||
EAPI EO2_FUNC_BODY(eo2_children_iterator_new, Eina_Iterator *, NULL);
|
||||
|
||||
static void
|
||||
_dbg_info_get(Eo *obj EINA_UNUSED, void *class_data EINA_UNUSED, Eo_Dbg_Info *root_node EINA_UNUSED)
|
||||
{ /* No info required in the meantime */
|
||||
|
@ -790,6 +952,9 @@ _class_constructor(Eo_Class *klass EINA_UNUSED)
|
|||
Eo2_Op_Description op_descs [] = {
|
||||
EO2_OP_FUNC(_constructor, eo2_constructor, "Constructor."),
|
||||
EO2_OP_FUNC(_destructor, eo2_destructor, "Destructor."),
|
||||
EO2_OP_FUNC(_parent_set, eo2_parent_set, "Set parent."),
|
||||
EO2_OP_FUNC(_parent_get, eo2_parent_get, "Get parent."),
|
||||
EO2_OP_FUNC(_children_iterator_new, eo2_children_iterator_new, "Get Children Iterator."),
|
||||
EO2_OP_FUNC(_data_set, eo2_base_data_set, "Set data for key."),
|
||||
EO2_OP_FUNC(_data_get, eo2_base_data_get, "Get data for key."),
|
||||
EO2_OP_FUNC(_data_del, eo2_base_data_del, "Del key."),
|
||||
|
|
Loading…
Reference in New Issue