From d49c3f106c5a0054f0613d88b152cb72f06923f9 Mon Sep 17 00:00:00 2001 From: Sander Mertens Date: Mon, 21 Mar 2022 09:38:46 -0700 Subject: [PATCH] #680 simplify component lifecycle signatures --- flecs.c | 494 ++++++++---------- flecs.h | 214 ++------ include/flecs.h | 12 +- include/flecs/addons/cpp/impl.hpp | 1 - .../addons/cpp/impl/lifecycle_traits.hpp | 25 - include/flecs/addons/cpp/lifecycle_traits.hpp | 144 ++--- include/flecs/addons/flecs_c.h | 2 + include/flecs/private/api_defines.h | 28 +- include/flecs/private/api_support.h | 2 - src/addons/snapshot.c | 14 +- src/addons/system/system.c | 67 ++- src/bootstrap.c | 84 +-- src/entity.c | 26 +- src/stage.c | 4 +- src/table.c | 240 ++++----- src/world.c | 59 +-- test/api/project.json | 8 +- test/api/src/ComponentLifecycle.c | 424 +++++++++------ test/api/src/Reference.c | 17 +- test/api/src/main.c | 32 +- test/cpp_api/project.json | 3 - test/cpp_api/src/ComponentLifecycle.cpp | 75 +-- test/cpp_api/src/main.cpp | 17 +- 23 files changed, 834 insertions(+), 1158 deletions(-) delete mode 100644 include/flecs/addons/cpp/impl/lifecycle_traits.hpp diff --git a/flecs.c b/flecs.c index 137f168c4d..200c5d71f7 100644 --- a/flecs.c +++ b/flecs.c @@ -2329,6 +2329,9 @@ ecs_flags32_t type_info_flags( if (ti->lifecycle.ctor) { flags |= EcsTableHasCtors; } + if (ti->lifecycle.on_add) { + flags |= EcsTableHasCtors; + } if (ti->lifecycle.dtor) { flags |= EcsTableHasDtors; } @@ -2411,9 +2414,10 @@ void flecs_table_init_data( ecs_entity_t e = ids[i + sw_offset]; ecs_assert(ECS_HAS_ROLE(e, SWITCH), ECS_INTERNAL_ERROR, NULL); e = e & ECS_COMPONENT_MASK; - const EcsType *type_ptr = ecs_get(world, e, EcsType); - ecs_assert(type_ptr != NULL, ECS_INTERNAL_ERROR, NULL); - ecs_table_t *sw_table = type_ptr->normalized; + const EcsType *switch_type = ecs_get(world, e, EcsType); + ecs_assert(switch_type != NULL, + ECS_INVALID_PARAMETER, "not a switch"); + ecs_table_t *sw_table = switch_type->normalized; ecs_type_t sw_type = sw_table->type; ecs_entity_t *sw_array = ecs_vector_first(sw_type, ecs_entity_t); @@ -2481,34 +2485,15 @@ void run_on_remove( /* -- Private functions -- */ static -void ctor_component( - ecs_world_t *world, - ecs_type_info_t *ti, - ecs_column_t *column, - ecs_entity_t *entities, - int32_t row, - int32_t count) -{ - ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); - - /* A new component is constructed */ - ecs_xtor_t ctor = ti->lifecycle.ctor; - if (ctor) { - void *ptr = ecs_vector_get_t( - column->data, ti->size, ti->alignment, row); - ctor(world, entities, ptr, count, ti); - } -} - -static -void on_remove_component( +void on_component_callback( ecs_world_t *world, ecs_table_t *table, - ecs_iter_action_t on_remove, - void *ptr, - ecs_size_t size, + ecs_iter_action_t callback, + ecs_entity_t event, + ecs_column_t *column, ecs_entity_t *entities, ecs_id_t id, + int32_t row, int32_t count, ecs_type_info_t *ti) { @@ -2516,6 +2501,9 @@ void on_remove_component( ecs_iter_t it = { .term_count = 1 }; it.entities = entities; + ecs_size_t size = ti->size; + void *ptr = ecs_vector_get_t(column->data, size, ti->alignment, row); + flecs_iter_init(&it); it.world = world; it.real_world = world; @@ -2524,15 +2512,32 @@ void on_remove_component( it.ptrs[0] = ptr; it.sizes[0] = size; it.ids[0] = id; - it.event = EcsOnRemove; + it.event = event; it.event_id = id; it.ctx = ti->lifecycle.ctx; it.count = count; - on_remove(&it); + callback(&it); } static -void dtor_component( +void ctor_component( + ecs_type_info_t *ti, + ecs_column_t *column, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); + + ecs_xtor_t ctor = ti->lifecycle.ctor; + if (ctor) { + void *ptr = ecs_vector_get_t( + column->data, ti->size, ti->alignment, row); + ctor(ptr, count, ti); + } +} + +static +void add_component( ecs_world_t *world, ecs_table_t *table, ecs_type_info_t *ti, @@ -2540,41 +2545,56 @@ void dtor_component( ecs_entity_t *entities, ecs_id_t id, int32_t row, - int32_t count, - bool is_remove) + int32_t count) { ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); - if (!count) { - return; - } + ctor_component(ti, column, row, count); - ecs_iter_action_t on_remove = 0; - if (is_remove) { - on_remove = ti->lifecycle.on_remove; + ecs_iter_action_t on_add = ti->lifecycle.on_add; + if (on_add) { + on_component_callback(world, table, on_add, EcsOnAdd, column, + entities, id, row, count, ti); } +} + +static +void dtor_component( + ecs_type_info_t *ti, + ecs_column_t *column, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); ecs_xtor_t dtor = ti->lifecycle.dtor; - if (!on_remove && !dtor) { - return; + if (dtor) { + void *ptr = ecs_vector_get_t( + column->data, ti->size, ti->alignment, row); + dtor(ptr, count, ti); } +} - int32_t size = ti->size; - int32_t alignment = ti->alignment; - ecs_entity_t *entity_elem = &entities[row]; - - ecs_assert(column->data != NULL, ECS_INTERNAL_ERROR, NULL); - void *ptr = ecs_vector_get_t(column->data, size, alignment, row); - ecs_assert(ptr != NULL, ECS_INTERNAL_ERROR, NULL); +static +void remove_component( + ecs_world_t *world, + ecs_table_t *table, + ecs_type_info_t *ti, + ecs_column_t *column, + ecs_entity_t *entities, + ecs_id_t id, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); + ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - on_remove_component(world, table, on_remove, ptr, size, - entity_elem, id, count, ti); - } - - if (dtor) { - dtor(world, entity_elem, ptr, count, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, column, + entities, id, row, count, ti); } + + dtor_component(ti, column, row, count); } static @@ -2612,11 +2632,8 @@ void dtor_all_components( ecs_type_info_t *ti = &table->type_info[c]; ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - ecs_size_t size = ti->size; - ecs_size_t align = ti->alignment; - void *ptr = ecs_vector_get_t(column->data, size, align, row); - on_remove_component(world, table, on_remove, ptr, size, - &entities[row], ids[c], count, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, + column, &entities[row], ids[c], row, count, ti); } } @@ -2626,8 +2643,7 @@ void dtor_all_components( for (i = row; i < end; i ++) { for (c = 0; c < ids_count; c++) { ecs_column_t *column = &data->columns[c]; - dtor_component(world, table, &table->type_info[c], column, - entities, ids[c], i, 1, false); + dtor_component(&table->type_info[c], column, i, 1); } /* Update entity index after invoking destructors so that entity can @@ -3083,9 +3099,7 @@ void move_bitset_columns( } static -void grow_column( - ecs_world_t *world, - ecs_entity_t *entities, +void* grow_column( ecs_column_t *column, ecs_type_info_t *ti, int32_t to_add, @@ -3101,6 +3115,7 @@ void grow_column( int32_t src_size = ecs_vector_size(vec); int32_t dst_count = count + to_add; bool can_realloc = dst_size != src_size; + void *result = NULL; ecs_assert(dst_size >= dst_count, ECS_INTERNAL_ERROR, NULL); @@ -3121,12 +3136,12 @@ void grow_column( void *dst_buffer = ecs_vector_first_t(dst_vec, size, alignment); /* Move (and construct) existing elements to new vector */ - move_ctor(world, entities, entities, dst_buffer, src_buffer, count, ti); + move_ctor(dst_buffer, src_buffer, count, ti); if (construct) { /* Construct new element(s) */ - void *elem = ECS_OFFSET(dst_buffer, size * count); - ctor(world, &entities[count], elem, to_add, ti); + result = ECS_OFFSET(dst_buffer, size * count); + ctor(result, to_add, ti); } /* Free old vector */ @@ -3139,13 +3154,13 @@ void grow_column( ecs_vector_set_size_t(&vec, size, alignment, dst_size); } - void *elem = ecs_vector_addn_t(&vec, size, alignment, to_add); + result = ecs_vector_addn_t(&vec, size, alignment, to_add); ecs_xtor_t ctor; if (construct && (ctor = ti->lifecycle.ctor)) { /* If new elements need to be constructed and component has a * constructor, construct */ - ctor(world, &entities[count], elem, to_add, ti); + ctor(result, to_add, ti); } column->data = vec; @@ -3153,6 +3168,8 @@ void grow_column( ecs_assert(ecs_vector_size(column->data) == dst_size, ECS_INTERNAL_ERROR, NULL); + + return result; } static @@ -3202,11 +3219,10 @@ int32_t grow_data( /* Add elements to each column array */ ecs_type_info_t *type_info = table->type_info; - ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); for (i = 0; i < column_count; i ++) { ecs_column_t *column = &columns[i]; ecs_type_info_t *ti = &type_info[i]; - grow_column(world, entities, column, ti, to_add, size, true); + grow_column(column, ti, to_add, size, true); ecs_assert(ecs_vector_size(columns[i].data) == size, ECS_INTERNAL_ERROR, NULL); } @@ -3303,10 +3319,9 @@ int32_t flecs_table_append( int32_t sw_column_count = table->sw_column_count; int32_t bs_column_count = table->bs_column_count; - ecs_sw_column_t *sw_columns = table->storage.sw_columns; - ecs_bs_column_t *bs_columns = table->storage.bs_columns; - ecs_entity_t *entities = ecs_vector_first( - data->entities, ecs_entity_t); + ecs_sw_column_t *sw_columns = data->sw_columns; + ecs_bs_column_t *bs_columns = data->bs_columns; + ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); /* Reobtain size to ensure that the columns have the same size as the * entities and record vectors. This keeps reasoning about when allocations @@ -3318,8 +3333,14 @@ int32_t flecs_table_append( for (i = 0; i < column_count; i ++) { ecs_column_t *column = &columns[i]; ecs_type_info_t *ti = &type_info[i]; - grow_column(world, entities, column, ti, 1, size, construct); - + grow_column(column, ti, 1, size, construct); + + ecs_iter_action_t on_add = ti->lifecycle.on_add; + if (on_add) { + on_component_callback(world, table, on_add, EcsOnAdd, column, + &entities[count], table->storage_ids[i], count, 1, ti); + } + ecs_assert(ecs_vector_size(columns[i].data) == ecs_vector_size(data->entities), ECS_INTERNAL_ERROR, NULL); ecs_assert( ecs_vector_count(columns[i].data) == @@ -3449,24 +3470,18 @@ void flecs_table_delete( } check_table_sanity(table); - return; } - ecs_id_t *ids = ecs_vector_first(table->type, ecs_id_t); + ecs_id_t *ids = table->storage_ids; /* Last element, destruct & remove */ if (index == count) { /* If table has component destructors, invoke */ if (destruct && (table->flags & EcsTableHasDtors)) { for (i = 0; i < column_count; i ++) { - ecs_type_info_t *ti = &type_info[i]; - if (!ti) { - continue; - } - - dtor_component(world, table, ti, &columns[i], - entities, ids[i], index, 1, true); + remove_component(world, table, &type_info[i], &columns[i], + &entity_to_delete, ids[i], index, 1); } } @@ -3487,14 +3502,13 @@ void flecs_table_delete( ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - on_remove_component(world, table, on_remove, dst, - size, &entity_to_delete, ids[i], 1, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, + column, &entity_to_delete, ids[i], index, 1, ti); } ecs_move_t move_dtor = ti->lifecycle.move_dtor; if (move_dtor) { - move_dtor(world, &entity_to_move, - &entity_to_delete, dst, src, 1, ti); + move_dtor(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } @@ -3640,17 +3654,17 @@ void flecs_table_move( ecs_assert(src != NULL, ECS_INTERNAL_ERROR, NULL); if (same_entity) { - ecs_move_t callback = ti->lifecycle.ctor_move_dtor; - if (callback) { + ecs_move_t move = ti->lifecycle.ctor_move_dtor; + if (move) { /* ctor + move + dtor */ - callback(world, &dst_entity, &src_entity, dst, src, 1, ti); + move(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } } else { ecs_copy_t copy = ti->lifecycle.copy_ctor; if (copy) { - copy(world, &dst_entity, &src_entity, dst, src, 1, ti); + copy(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } @@ -3658,13 +3672,14 @@ void flecs_table_move( } else { if (dst_id < src_id) { if (construct) { - ctor_component(world, &dst_type_info[i_new], - &dst_columns[i_new], &dst_entity, dst_index, 1); + add_component(world, dst_table, &dst_type_info[i_new], + &dst_columns[i_new], &dst_entity, dst_id, + dst_index, 1); } } else { - dtor_component(world, src_table, &src_type_info[i_old], + remove_component(world, src_table, &src_type_info[i_old], &src_columns[i_old], &src_entity, src_id, - src_index, 1, true); + src_index, 1); } } @@ -3674,15 +3689,15 @@ void flecs_table_move( if (construct) { for (; (i_new < dst_column_count); i_new ++) { - ctor_component(world, &dst_type_info[i_new], - &dst_columns[i_new], &dst_entity, dst_index, 1); + add_component(world, dst_table, &dst_type_info[i_new], + &dst_columns[i_new], &dst_entity, dst_ids[i_new], dst_index, 1); } } for (; (i_old < src_column_count); i_old ++) { - dtor_component(world, src_table, &src_type_info[i_old], + remove_component(world, src_table, &src_type_info[i_old], &src_columns[i_old], &src_entity, src_ids[i_old], - src_index, 1, true); + src_index, 1); } check_table_sanity(dst_table); @@ -3888,7 +3903,6 @@ void merge_vector( static void merge_column( - ecs_world_t *world, ecs_type_info_t *ti, int32_t size, int32_t alignment, @@ -3896,7 +3910,6 @@ void merge_column( int32_t column_id, ecs_vector_t *src) { - ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); ecs_column_t *column = &data->columns[column_id]; ecs_vector_t *dst = column->data; int32_t dst_count = ecs_vector_count(dst); @@ -3916,7 +3929,7 @@ void merge_column( column->data = dst; /* Construct new values */ - ctor_component(world, ti, column, entities, dst_count, src_count); + ctor_component(ti, column, dst_count, src_count); void *dst_ptr = ecs_vector_first_t(dst, size, alignment); void *src_ptr = ecs_vector_first_t(src, size, alignment); @@ -3926,7 +3939,7 @@ void merge_column( /* Move values into column */ ecs_move_t move = ti->lifecycle.move; if (move) { - move(world, entities, entities, dst_ptr, src_ptr, src_count, ti); + move(dst_ptr, src_ptr, src_count, ti); } else { ecs_os_memcpy(dst_ptr, src_ptr, size * src_count); } @@ -3970,8 +3983,6 @@ void merge_table_data( merge_vector(&dst_data->entities, src_data->entities, ECS_SIZEOF(ecs_entity_t), ECS_ALIGNOF(ecs_entity_t)); src_data->entities = NULL; - ecs_entity_t *entities = ecs_vector_first(dst_data->entities, ecs_entity_t); - ecs_assert(ecs_vector_count(dst_data->entities) == src_count + dst_count, ECS_INTERNAL_ERROR, NULL); @@ -3989,7 +4000,7 @@ void merge_table_data( ecs_assert(size != 0, ECS_INTERNAL_ERROR, NULL); if (dst_id == src_id) { - merge_column(world, dst_ti, size, alignment, dst_data, + merge_column(dst_ti, size, alignment, dst_data, i_new, src_columns[i_old].data); src_columns[i_old].data = NULL; @@ -4006,17 +4017,14 @@ void merge_table_data( src_count + dst_count); /* Construct new values */ - ctor_component(world, dst_ti, column, - entities, 0, src_count + dst_count); + ctor_component(dst_ti, column, 0, src_count + dst_count); i_new ++; } else if (dst_id > src_id) { ecs_column_t *column = &src_columns[i_old]; /* Destruct old values */ - ecs_type_info_t *src_ti = &src_type_info[i_old]; - dtor_component(world, src_table, src_ti, column, - entities, 0, 0, src_count, false); + dtor_component(&src_type_info[i_old], column, 0, src_count); /* Old column does not occur in new table, remove */ ecs_vector_free(column->data); @@ -4043,7 +4051,7 @@ void merge_table_data( src_count + dst_count); /* Construct new values */ - ctor_component(world, ti, column, entities, 0, src_count + dst_count); + ctor_component(ti, column, 0, src_count + dst_count); } /* Destroy remaining columns */ @@ -4051,9 +4059,7 @@ void merge_table_data( ecs_column_t *column = &src_columns[i_old]; /* Destruct old values */ - ecs_type_info_t *ti = &src_type_info[i_old]; - dtor_component(world, src_table, ti, column, entities, 0, - 0, src_count, false); + dtor_component(&src_type_info[i_old], column, 0, src_count); /* Old column does not occur in new table, remove */ ecs_vector_free(column->data); @@ -5047,10 +5053,8 @@ bool override_from_base( ecs_copy_t copy = ti->lifecycle.copy; if (copy) { - ecs_entity_t *entities = ecs_vector_first( - data->entities, ecs_entity_t); for (index = 0; index < count; index ++) { - copy(world, &entities[row], &base, data_ptr, base_ptr, 1, ti); + copy(data_ptr, base_ptr, 1, ti); data_ptr = ECS_OFFSET(data_ptr, data_size); } } else { @@ -5617,13 +5621,9 @@ const ecs_entity_t* new_w_data( ecs_copy_t copy; ecs_move_t move; if (is_move && (move = ti->lifecycle.move)) { - ecs_entity_t *eids = ecs_vector_first( - data->entities, ecs_entity_t); - move(world, eids, eids, ptr, src_ptr, count, ti); + move(ptr, src_ptr, count, ti); } else if (!is_move && (copy = ti->lifecycle.copy)) { - ecs_entity_t *eids = ecs_vector_first( - data->entities, ecs_entity_t); - copy(world, eids, eids, ptr, src_ptr, count, ti); + copy(ptr, src_ptr, count, ti); } else { ecs_os_memcpy(ptr, src_ptr, size * count); } @@ -5759,7 +5759,6 @@ void *get_mutable( return NULL; } - /* -- Private functions -- */ static void flecs_notify_on_add( @@ -7650,14 +7649,14 @@ ecs_entity_t assign_ptr_w_id( if (is_move) { ecs_move_t move = ti->lifecycle.move; if (move) { - move(world, &entity, &entity, dst, ptr, 1, ti); + move(dst, ptr, 1, ti); } else { ecs_os_memcpy(dst, ptr, flecs_utosize(size)); } } else { ecs_copy_t copy = ti->lifecycle.copy; if (copy) { - copy(world, &entity, &entity, dst, ptr, 1, ti); + copy(dst, ptr, 1, ti); } else { ecs_os_memcpy(dst, ptr, flecs_utosize(size)); } @@ -8538,21 +8537,20 @@ void flush_bulk_new( static void free_value( ecs_world_t *world, - ecs_entity_t *entities, ecs_id_t id, void *value, int32_t count) { ecs_entity_t real_id = ecs_get_typeid(world, id); const ecs_type_info_t *ti = flecs_get_type_info(world, real_id); - ecs_xtor_t dtor; + ecs_xtor_t dtor = ti->lifecycle.dtor; - if (ti && (dtor = ti->lifecycle.dtor)) { + if (dtor) { ecs_size_t size = ti->size; void *ptr; int i; for (i = 0, ptr = value; i < count; i ++, ptr = ECS_OFFSET(ptr, size)) { - dtor(world, &entities[i], ptr, 1, ti); + dtor(ptr, 1, ti); } } } @@ -8565,7 +8563,7 @@ void discard_op( if (op->kind != EcsOpBulkNew) { void *value = op->is._1.value; if (value) { - free_value(world, &op->is._1.entity, op->id, op->is._1.value, 1); + free_value(world, op->id, op->is._1.value, 1); ecs_os_free(value); } } else { @@ -9117,14 +9115,14 @@ bool flecs_defer_set( if (value) { ecs_copy_t copy; if (ti && (copy = ti->lifecycle.copy_ctor)) { - copy(world, &entity, &entity, op->is._1.value, value, 1, ti); + copy(op->is._1.value, value, 1, ti); } else { ecs_os_memcpy(op->is._1.value, value, size); } } else { ecs_xtor_t ctor; if (ti && (ctor = ti->lifecycle.ctor)) { - ctor(world, &entity, op->is._1.value, 1, ti); + ctor(op->is._1.value, 1, ti); } } @@ -27275,7 +27273,6 @@ typedef struct ecs_table_leaf_t { static ecs_data_t* duplicate_data( - const ecs_world_t *world, ecs_table_t *table, ecs_data_t *main_data) { @@ -27290,7 +27287,6 @@ ecs_data_t* duplicate_data( /* Copy entities */ result->entities = ecs_vector_copy(main_data->entities, ecs_entity_t); - ecs_entity_t *entities = ecs_vector_first(result->entities, ecs_entity_t); /* Copy record ptrs */ result->record_ptrs = ecs_vector_copy( @@ -27313,12 +27309,11 @@ ecs_data_t* duplicate_data( ecs_xtor_t ctor = ti->lifecycle.ctor; if (ctor) { - ctor((ecs_world_t*)world, entities, dst_ptr, count, ti); + ctor(dst_ptr, count, ti); } void *src_ptr = ecs_vector_first_t(column->data, size, alignment); - copy((ecs_world_t*)world, entities, entities, dst_ptr, - src_ptr, count, ti); + copy(dst_ptr, src_ptr, count, ti); column->data = dst_vec; } else { @@ -27331,7 +27326,6 @@ ecs_data_t* duplicate_data( static void snapshot_table( - const ecs_world_t *world, ecs_snapshot_t *snapshot, ecs_table_t *table) { @@ -27345,7 +27339,7 @@ void snapshot_table( l->table = table; l->type = ecs_vector_copy(table->type, ecs_id_t); - l->data = duplicate_data(world, table, &table->storage); + l->data = duplicate_data(table, &table->storage); } static @@ -27386,13 +27380,13 @@ ecs_snapshot_t* snapshot_create( if (iter) { while (next(iter)) { ecs_table_t *table = iter->table; - snapshot_table(world, result, table); + snapshot_table(result, table); } } else { for (t = 0; t < table_count; t ++) { ecs_table_t *table = flecs_sparse_get( &world->store.tables, ecs_table_t, t); - snapshot_table(world, result, table); + snapshot_table(result, table); } } @@ -27977,42 +27971,51 @@ void* ecs_get_system_binding_ctx( } } -/* System destructor */ +/* System deinitialization */ static -ECS_DTOR(EcsSystem, ptr, { - if (!ecs_is_alive(world, entity)) { - /* This can happen when a set is deferred while a system is being - * cleaned up. The operation will be discarded, but the destructor - * still needs to be invoked for the value */ - continue; - } +void ecs_on_remove(EcsSystem)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsSystem *ptr = ecs_term(it, EcsSystem, 1); - /* Invoke Deactivated action for active systems */ - if (ptr->query && ecs_query_table_count(ptr->query)) { - invoke_status_action(world, entity, ptr, EcsSystemDeactivated); - } + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + EcsSystem *sys = &ptr[i]; + ecs_entity_t entity = it->entities[i]; - /* Invoke Disabled action for enabled systems */ - if (!ecs_has_id(world, entity, EcsDisabled)) { - invoke_status_action(world, entity, ptr, EcsSystemDisabled); - } + if (!ecs_is_alive(world, entity)) { + /* This can happen when a set is deferred while a system is being + * cleaned up. The operation will be discarded, but the destructor + * still needs to be invoked for the value */ + continue; + } - if (ptr->ctx_free) { - ptr->ctx_free(ptr->ctx); - } + /* Invoke Deactivated action for active systems */ + if (sys->query && ecs_query_table_count(sys->query)) { + invoke_status_action(world, entity, sys, EcsSystemDeactivated); + } - if (ptr->status_ctx_free) { - ptr->status_ctx_free(ptr->status_ctx); - } + /* Invoke Disabled action for enabled systems */ + if (!ecs_has_id(world, entity, EcsDisabled)) { + invoke_status_action(world, entity, sys, EcsSystemDisabled); + } - if (ptr->binding_ctx_free) { - ptr->binding_ctx_free(ptr->binding_ctx); - } + if (sys->ctx_free) { + sys->ctx_free(sys->ctx); + } - if (ptr->query) { - ecs_query_fini(ptr->query); + if (sys->status_ctx_free) { + sys->status_ctx_free(sys->status_ctx); + } + + if (sys->binding_ctx_free) { + sys->binding_ctx_free(sys->binding_ctx); + } + + if (sys->query) { + ecs_query_fini(sys->query); + } } -}) +} static void EnableMonitor( @@ -28222,7 +28225,7 @@ void FlecsSystemImport( ecs_set_component_actions_w_id(world, ecs_id(EcsSystem), &(EcsComponentLifecycle) { .ctor = ecs_default_ctor, - .dtor = ecs_dtor(EcsSystem) + .on_remove = ecs_on_remove(EcsSystem) }); ecs_observer_init(world, &(ecs_observer_desc_t) { @@ -34768,99 +34771,80 @@ void flecs_notify_tables( } void ecs_default_ctor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *ti) { - (void)world; (void)entity_ptr; ecs_os_memset(ptr, 0, ti->size * count); } static -void default_copy_ctor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, const void *src_ptr, +void default_copy_ctor(void *dst_ptr, const void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->copy(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->copy(dst_ptr, src_ptr, count, ti); } static -void default_move_ctor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_ctor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); } static -void default_ctor_w_move_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_ctor_w_move_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } static -void default_move_ctor_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_ctor_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move_ctor(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->move_ctor(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } static -void default_move( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); } static -void default_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { - (void)src_entity; - /* When there is no move, destruct the destination component & memcpy the * component to dst. The src component does not have to be destructed when * a component has a trivial move. */ const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->dtor(world, dst_entity, dst_ptr, count, ti); + cl->dtor(dst_ptr, count, ti); ecs_os_memcpy(dst_ptr, src_ptr, flecs_uto(ecs_size_t, ti->size) * count); } static -void default_move_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { /* If a component has a move, the move will take care of memcpying the data * and destroying any data in dst. Because this is not a trivial move, the * src component must also be destructed. */ const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } void ecs_set_component_actions_w_id( @@ -46431,14 +46415,6 @@ uint64_t flecs_string_hash( /* -- Component lifecycle -- */ /* Component lifecycle actions for EcsIdentifier */ -static ECS_CTOR(EcsIdentifier, ptr, { - ptr->value = NULL; - ptr->hash = 0; - ptr->length = 0; - ptr->index_hash = 0; - ptr->index = NULL; -}) - static ECS_DTOR(EcsIdentifier, ptr, { ecs_os_strset(&ptr->value, NULL); }) @@ -46494,7 +46470,8 @@ void ecs_on_set(EcsIdentifier)(ecs_iter_t *it) { } } - for (int i = 0; i < it->count; i ++) { + int i, count = it->count; + for (i = 0; i < count; i ++) { EcsIdentifier *cur = &ptr[i]; uint64_t hash; ecs_size_t len; @@ -46539,51 +46516,28 @@ void ecs_on_set(EcsIdentifier)(ecs_iter_t *it) { } /* Component lifecycle actions for EcsTrigger */ -static ECS_CTOR(EcsTrigger, ptr, { - ptr->trigger = NULL; -}) - -static ECS_DTOR(EcsTrigger, ptr, { - if (ptr->trigger) { - flecs_trigger_fini(world, (ecs_trigger_t*)ptr->trigger); - } -}) - -static ECS_COPY(EcsTrigger, dst, src, { - ecs_abort(ECS_INVALID_OPERATION, "Trigger component cannot be copied"); -}) - -static ECS_MOVE(EcsTrigger, dst, src, { - if (dst->trigger) { - flecs_trigger_fini(world, (ecs_trigger_t*)dst->trigger); +static void ecs_on_remove(EcsTrigger)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsTrigger *ptr = ecs_term(it, EcsTrigger, 1); + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + if (ptr[i].trigger) { + flecs_trigger_fini(world, (ecs_trigger_t*)ptr[i].trigger); + } } - dst->trigger = src->trigger; - src->trigger = NULL; -}) +} /* Component lifecycle actions for EcsObserver */ -static ECS_CTOR(EcsObserver, ptr, { - ptr->observer = NULL; -}) - -static ECS_DTOR(EcsObserver, ptr, { - if (ptr->observer) { - flecs_observer_fini(world, (ecs_observer_t*)ptr->observer); - } -}) - -static ECS_COPY(EcsObserver, dst, src, { - ecs_abort(ECS_INVALID_OPERATION, "Observer component cannot be copied"); -}) - -static ECS_MOVE(EcsObserver, dst, src, { - if (dst->observer) { - flecs_observer_fini(world, (ecs_observer_t*)dst->observer); +static void ecs_on_remove(EcsObserver)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsObserver *ptr = ecs_term(it, EcsObserver, 1); + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + if (ptr[i].observer) { + flecs_observer_fini(world, (ecs_observer_t*)ptr[i].observer); + } } - dst->observer = src->observer; - src->observer = NULL; -}) - +} /* -- Builtin triggers -- */ @@ -47025,7 +46979,7 @@ void flecs_bootstrap( }); ecs_set_component_actions(world, EcsIdentifier, { - .ctor = ecs_ctor(EcsIdentifier), + .ctor = ecs_default_ctor, .dtor = ecs_dtor(EcsIdentifier), .copy = ecs_copy(EcsIdentifier), .move = ecs_move(EcsIdentifier), @@ -47034,17 +46988,13 @@ void flecs_bootstrap( }); ecs_set_component_actions(world, EcsTrigger, { - .ctor = ecs_ctor(EcsTrigger), - .dtor = ecs_dtor(EcsTrigger), - .copy = ecs_copy(EcsTrigger), - .move = ecs_move(EcsTrigger) + .ctor = ecs_default_ctor, + .on_remove = ecs_on_remove(EcsTrigger) }); ecs_set_component_actions(world, EcsObserver, { - .ctor = ecs_ctor(EcsObserver), - .dtor = ecs_dtor(EcsObserver), - .copy = ecs_copy(EcsObserver), - .move = ecs_move(EcsObserver) + .ctor = ecs_default_ctor, + .on_remove = ecs_on_remove(EcsObserver) }); /* Create table for initial components */ diff --git a/flecs.h b/flecs.h index 2f3e4b3b97..48df8c01b5 100644 --- a/flecs.h +++ b/flecs.h @@ -412,24 +412,18 @@ typedef int32_t ecs_size_t; #ifndef FLECS_LEGACY -/* Constructor / destructor convenience macro */ +/* Constructor/Destructor convenience macro */ #define ECS_XTOR_IMPL(type, postfix, var, ...)\ void type##_##postfix(\ - ecs_world_t *world,\ - const ecs_entity_t *entity_ptr,\ void *_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)entity_ptr;\ (void)_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t entity = entity_ptr[i];\ type *var = &((type*)_ptr)[i];\ - (void)entity;\ (void)var;\ __VA_ARGS__\ }\ @@ -438,28 +432,18 @@ typedef int32_t ecs_size_t; /* Copy convenience macro */ #define ECS_COPY_IMPL(type, dst_var, src_var, ...)\ void type##_##copy(\ - ecs_world_t *world,\ - const ecs_entity_t *dst_entities,\ - const ecs_entity_t *src_entities,\ void *_dst_ptr,\ const void *_src_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)dst_entities;\ - (void)src_entities;\ (void)_dst_ptr;\ (void)_src_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t dst_entity = dst_entities[i];\ - ecs_entity_t src_entity = src_entities[i];\ type *dst_var = &((type*)_dst_ptr)[i];\ type *src_var = &((type*)_src_ptr)[i];\ - (void)dst_entity;\ - (void)src_entity;\ (void)dst_var;\ (void)src_var;\ __VA_ARGS__\ @@ -469,28 +453,18 @@ typedef int32_t ecs_size_t; /* Move convenience macro */ #define ECS_MOVE_IMPL(type, dst_var, src_var, ...)\ void type##_##move(\ - ecs_world_t *world,\ - const ecs_entity_t *dst_entities,\ - const ecs_entity_t *src_entities,\ void *_dst_ptr,\ void *_src_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)dst_entities;\ - (void)src_entities;\ (void)_dst_ptr;\ (void)_src_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t dst_entity = dst_entities[i];\ - ecs_entity_t src_entity = src_entities[i];\ type *dst_var = &((type*)_dst_ptr)[i];\ type *src_var = &((type*)_src_ptr)[i];\ - (void)dst_entity;\ - (void)src_entity;\ (void)dst_var;\ (void)src_var;\ __VA_ARGS__\ @@ -2204,17 +2178,12 @@ typedef uint64_t (*ecs_hash_value_action_t)( /** Constructor/destructor callback */ typedef void (*ecs_xtor_t)( - ecs_world_t *world, - const ecs_entity_t *entities, void *ptr, int32_t count, const ecs_type_info_t *type_info); /** Copy is invoked when a component is copied into another component. */ typedef void (*ecs_copy_t)( - ecs_world_t *world, - const ecs_entity_t *dst_entities, - const ecs_entity_t *src_entities, void *dst_ptr, const void *src_ptr, int32_t count, @@ -2222,9 +2191,6 @@ typedef void (*ecs_copy_t)( /** Move is invoked when a component is moved to another component. */ typedef void (*ecs_move_t)( - ecs_world_t *world, - const ecs_entity_t *dst_entities, - const ecs_entity_t *src_entities, void *dst_ptr, void *src_ptr, int32_t count, @@ -2791,8 +2757,6 @@ const char* ecs_identifier_is_var( FLECS_API void ecs_default_ctor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *ctx); @@ -3617,6 +3581,10 @@ typedef struct EcsComponentLifecycle { * not set explicitly it will be derived from other callbacks. */ ecs_move_t move_dtor; + /* Callback that is invoked when an instance of a component is added. This + * callback is invoked before triggers are invoked. */ + ecs_iter_action_t on_add; + /* Callback that is invoked when an instance of the component is set. This * callback is invoked before triggers are invoked, and enable the component * to respond to changes on itself before others can. */ @@ -7525,6 +7493,8 @@ void* ecs_record_get_column( #define ecs_copy(type) type##_copy #define ecs_move(type) type##_move #define ecs_on_set(type) type##_on_set +#define ecs_on_add(type) type##_on_add +#define ecs_on_remove(type) type##_on_remove #define ecs_query_new(world, q_expr)\ ecs_query_init(world, &(ecs_query_desc_t){\ @@ -14005,75 +13975,41 @@ namespace flecs namespace _ { -inline void ecs_ctor_illegal(ecs_world_t* w, const ecs_entity_t*, - void *, int32_t, const ecs_type_info_t* info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot default construct %s, add %s::%s() or use emplace", - path, path, ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_ctor_illegal(void *, int32_t, const ecs_type_info_t*) { + ecs_abort(ECS_INVALID_OPERATION, "invalid constructor"); } -inline void ecs_dtor_illegal(ecs_world_t* w, const ecs_entity_t*, - void *, int32_t, const ecs_type_info_t *info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, "cannnot destruct %s, add ~%s::%s()", - path, path, ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_dtor_illegal(void *, int32_t, const ecs_type_info_t*) { + ecs_abort(ECS_INVALID_OPERATION, "invalid destructor"); } -inline void ecs_copy_illegal(ecs_world_t* w, const ecs_entity_t*, - const ecs_entity_t*, void *, const void *, int32_t, const ecs_type_info_t *info) +inline void ecs_copy_illegal( + void *, const void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot copy assign %s, add %s& %s::operator =(const %s&)", path, - ecs_get_name(w, info->component), path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid copy assignment"); } -inline void ecs_move_illegal(ecs_world_t* w, const ecs_entity_t*, - const ecs_entity_t*, void *, void *, int32_t, const ecs_type_info_t *info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot move assign %s, add %s& %s::operator =(%s&&)", path, - ecs_get_name(w, info->component), path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_move_illegal(void *, void *, int32_t, const ecs_type_info_t *) { + ecs_abort(ECS_INVALID_OPERATION, "invalid move assignment"); } -inline void ecs_copy_ctor_illegal(ecs_world_t* w, - const ecs_entity_t*, const ecs_entity_t*, - void *, const void *, int32_t, const ecs_type_info_t *info) +inline void ecs_copy_ctor_illegal( + void *, const void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot copy construct %s, add %s::%s(const %s&)", - path, path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid copy construct"); } -inline void ecs_move_ctor_illegal(ecs_world_t* w, - const ecs_entity_t*, const ecs_entity_t*, - void *, void *, int32_t, const ecs_type_info_t *info) +inline void ecs_move_ctor_illegal( + void *, void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot move construct %s, add %s::%s(%s&&)", - path, path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid move construct"); } // T() // Can't coexist with T(flecs::entity) or T(flecs::world, flecs::entity) template -void ctor_impl( - ecs_world_t*, const ecs_entity_t*, void *ptr, int32_t count, - const ecs_type_info_t *info) -{ +void ctor_impl(void *ptr, int32_t count, const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); T *arr = static_cast(ptr); @@ -14082,18 +14018,9 @@ void ctor_impl( } } -// T(flecs::world, flecs::entity) -template -void ctor_world_entity_impl( - ecs_world_t* world, const ecs_entity_t* ids, void *ptr, int32_t count, - const ecs_type_info_t *info); - // ~T() template -void dtor_impl( - ecs_world_t*, const ecs_entity_t*, void *ptr, int32_t count, - const ecs_type_info_t *info) -{ +void dtor_impl(void *ptr, int32_t count, const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); T *arr = static_cast(ptr); @@ -14104,9 +14031,8 @@ void dtor_impl( // T& operator=(const T&) template -void copy_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - const void *src_ptr, int32_t count, const ecs_type_info_t *info) +void copy_impl(void *dst_ptr, const void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14119,9 +14045,8 @@ void copy_impl( // T& operator=(T&&) template -void move_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14134,9 +14059,8 @@ void move_impl( // T(T&) template -void copy_ctor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - const void *src_ptr, int32_t count, const ecs_type_info_t *info) +void copy_ctor_impl(void *dst_ptr, const void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14149,9 +14073,8 @@ void copy_ctor_impl( // T(T&&) template -void move_ctor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_ctor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14165,9 +14088,8 @@ void move_ctor_impl( // T(T&&), ~T() // Typically used when moving to a new table, and removing from the old table template -void ctor_move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void ctor_move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14183,9 +14105,8 @@ void ctor_move_dtor_impl( // Typically used when moving a component to a deleted component template ::value > = 0> -void move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14204,9 +14125,8 @@ void move_dtor_impl( // Typically used when moving a component to a deleted component template ::value > = 0> -void move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -14225,29 +14145,11 @@ void move_dtor_impl( } // _ -// Trait to test if type has flecs constructor -template -struct has_flecs_ctor { - static constexpr bool value = - std::is_constructible, - flecs::world&, flecs::entity>::value; -}; - // Trait to test if type is constructible by flecs template struct is_flecs_constructible { static constexpr bool value = - std::is_default_constructible>::value || - std::is_constructible, - flecs::world&, flecs::entity>::value; -}; - -// Trait to test if type has a self constructor (flecs::entity, Args...) -template -struct is_self_constructible { - static constexpr bool value = - std::is_constructible, - flecs::entity, Args...>::value; + std::is_default_constructible>::value; }; namespace _ @@ -14261,8 +14163,7 @@ ecs_xtor_t ctor() { // Not constructible by flecs template ::value && - ! has_flecs_ctor::value > = 0> + ! std::is_default_constructible::value > = 0> ecs_xtor_t ctor() { return ecs_ctor_illegal; } @@ -14270,18 +14171,11 @@ ecs_xtor_t ctor() { // Default constructible template ::value && - std::is_default_constructible::value && - ! has_flecs_ctor::value > = 0> + std::is_default_constructible::value > = 0> ecs_xtor_t ctor() { return ctor_impl; } -// Flecs constructible: T(flecs::world, flecs::entity) -template ::value > = 0> -ecs_xtor_t ctor() { - return ctor_world_entity_impl; -} - // No dtor template ::value > = 0> ecs_xtor_t dtor() { @@ -22600,32 +22494,6 @@ inline units::units(flecs::world& world) { - -namespace flecs -{ - -namespace _ -{ - -template -inline void ctor_world_entity_impl( - ecs_world_t* world, const ecs_entity_t* ids, void *ptr, - int32_t count, const ecs_type_info_t *info) -{ - (void)info; ecs_assert(info->size == ECS_SIZEOF(T), - ECS_INTERNAL_ERROR, NULL); - T *arr = static_cast(ptr); - flecs::world w(world); - for (int i = 0; i < count; i ++) { - flecs::entity e(world, ids[i]); - FLECS_PLACEMENT_NEW(&arr[i], T(w, e)); - } -} - -} // _ -} // flecs - - namespace flecs { diff --git a/include/flecs.h b/include/flecs.h index 17e06791bd..c442a54aea 100644 --- a/include/flecs.h +++ b/include/flecs.h @@ -321,17 +321,12 @@ typedef uint64_t (*ecs_hash_value_action_t)( /** Constructor/destructor callback */ typedef void (*ecs_xtor_t)( - ecs_world_t *world, - const ecs_entity_t *entities, void *ptr, int32_t count, const ecs_type_info_t *type_info); /** Copy is invoked when a component is copied into another component. */ typedef void (*ecs_copy_t)( - ecs_world_t *world, - const ecs_entity_t *dst_entities, - const ecs_entity_t *src_entities, void *dst_ptr, const void *src_ptr, int32_t count, @@ -339,9 +334,6 @@ typedef void (*ecs_copy_t)( /** Move is invoked when a component is moved to another component. */ typedef void (*ecs_move_t)( - ecs_world_t *world, - const ecs_entity_t *dst_entities, - const ecs_entity_t *src_entities, void *dst_ptr, void *src_ptr, int32_t count, @@ -881,6 +873,10 @@ typedef struct EcsComponentLifecycle { * not set explicitly it will be derived from other callbacks. */ ecs_move_t move_dtor; + /* Callback that is invoked when an instance of a component is added. This + * callback is invoked before triggers are invoked. */ + ecs_iter_action_t on_add; + /* Callback that is invoked when an instance of the component is set. This * callback is invoked before triggers are invoked, and enable the component * to respond to changes on itself before others can. */ diff --git a/include/flecs/addons/cpp/impl.hpp b/include/flecs/addons/cpp/impl.hpp index eeebafc473..7b47fbef89 100644 --- a/include/flecs/addons/cpp/impl.hpp +++ b/include/flecs/addons/cpp/impl.hpp @@ -1,4 +1,3 @@ -#include "impl/lifecycle_traits.hpp" #include "impl/iter.hpp" #include "impl/world.hpp" diff --git a/include/flecs/addons/cpp/impl/lifecycle_traits.hpp b/include/flecs/addons/cpp/impl/lifecycle_traits.hpp deleted file mode 100644 index 5a9fabfb85..0000000000 --- a/include/flecs/addons/cpp/impl/lifecycle_traits.hpp +++ /dev/null @@ -1,25 +0,0 @@ - - -namespace flecs -{ - -namespace _ -{ - -template -inline void ctor_world_entity_impl( - ecs_world_t* world, const ecs_entity_t* ids, void *ptr, - int32_t count, const ecs_type_info_t *info) -{ - (void)info; ecs_assert(info->size == ECS_SIZEOF(T), - ECS_INTERNAL_ERROR, NULL); - T *arr = static_cast(ptr); - flecs::world w(world); - for (int i = 0; i < count; i ++) { - flecs::entity e(world, ids[i]); - FLECS_PLACEMENT_NEW(&arr[i], T(w, e)); - } -} - -} // _ -} // flecs diff --git a/include/flecs/addons/cpp/lifecycle_traits.hpp b/include/flecs/addons/cpp/lifecycle_traits.hpp index 37ce44bd35..92d5083ff9 100644 --- a/include/flecs/addons/cpp/lifecycle_traits.hpp +++ b/include/flecs/addons/cpp/lifecycle_traits.hpp @@ -4,75 +4,41 @@ namespace flecs namespace _ { -inline void ecs_ctor_illegal(ecs_world_t* w, const ecs_entity_t*, - void *, int32_t, const ecs_type_info_t* info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot default construct %s, add %s::%s() or use emplace", - path, path, ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_ctor_illegal(void *, int32_t, const ecs_type_info_t*) { + ecs_abort(ECS_INVALID_OPERATION, "invalid constructor"); } -inline void ecs_dtor_illegal(ecs_world_t* w, const ecs_entity_t*, - void *, int32_t, const ecs_type_info_t *info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, "cannnot destruct %s, add ~%s::%s()", - path, path, ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_dtor_illegal(void *, int32_t, const ecs_type_info_t*) { + ecs_abort(ECS_INVALID_OPERATION, "invalid destructor"); } -inline void ecs_copy_illegal(ecs_world_t* w, const ecs_entity_t*, - const ecs_entity_t*, void *, const void *, int32_t, const ecs_type_info_t *info) +inline void ecs_copy_illegal( + void *, const void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot copy assign %s, add %s& %s::operator =(const %s&)", path, - ecs_get_name(w, info->component), path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid copy assignment"); } -inline void ecs_move_illegal(ecs_world_t* w, const ecs_entity_t*, - const ecs_entity_t*, void *, void *, int32_t, const ecs_type_info_t *info) -{ - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot move assign %s, add %s& %s::operator =(%s&&)", path, - ecs_get_name(w, info->component), path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); +inline void ecs_move_illegal(void *, void *, int32_t, const ecs_type_info_t *) { + ecs_abort(ECS_INVALID_OPERATION, "invalid move assignment"); } -inline void ecs_copy_ctor_illegal(ecs_world_t* w, - const ecs_entity_t*, const ecs_entity_t*, - void *, const void *, int32_t, const ecs_type_info_t *info) +inline void ecs_copy_ctor_illegal( + void *, const void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot copy construct %s, add %s::%s(const %s&)", - path, path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid copy construct"); } -inline void ecs_move_ctor_illegal(ecs_world_t* w, - const ecs_entity_t*, const ecs_entity_t*, - void *, void *, int32_t, const ecs_type_info_t *info) +inline void ecs_move_ctor_illegal( + void *, void *, int32_t, const ecs_type_info_t *) { - char *path = ecs_get_path_w_sep(w, 0, info->component, "::", "::"); - ecs_abort(ECS_INVALID_OPERATION, - "cannnot move construct %s, add %s::%s(%s&&)", - path, path, ecs_get_name(w, info->component), ecs_get_name(w, info->component)); - ecs_os_free(path); + ecs_abort(ECS_INVALID_OPERATION, "invalid move construct"); } // T() // Can't coexist with T(flecs::entity) or T(flecs::world, flecs::entity) template -void ctor_impl( - ecs_world_t*, const ecs_entity_t*, void *ptr, int32_t count, - const ecs_type_info_t *info) -{ +void ctor_impl(void *ptr, int32_t count, const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); T *arr = static_cast(ptr); @@ -81,18 +47,9 @@ void ctor_impl( } } -// T(flecs::world, flecs::entity) -template -void ctor_world_entity_impl( - ecs_world_t* world, const ecs_entity_t* ids, void *ptr, int32_t count, - const ecs_type_info_t *info); - // ~T() template -void dtor_impl( - ecs_world_t*, const ecs_entity_t*, void *ptr, int32_t count, - const ecs_type_info_t *info) -{ +void dtor_impl(void *ptr, int32_t count, const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); T *arr = static_cast(ptr); @@ -103,9 +60,8 @@ void dtor_impl( // T& operator=(const T&) template -void copy_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - const void *src_ptr, int32_t count, const ecs_type_info_t *info) +void copy_impl(void *dst_ptr, const void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -118,9 +74,8 @@ void copy_impl( // T& operator=(T&&) template -void move_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -133,9 +88,8 @@ void move_impl( // T(T&) template -void copy_ctor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - const void *src_ptr, int32_t count, const ecs_type_info_t *info) +void copy_ctor_impl(void *dst_ptr, const void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -148,9 +102,8 @@ void copy_ctor_impl( // T(T&&) template -void move_ctor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_ctor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -164,9 +117,8 @@ void move_ctor_impl( // T(T&&), ~T() // Typically used when moving to a new table, and removing from the old table template -void ctor_move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void ctor_move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -182,9 +134,8 @@ void ctor_move_dtor_impl( // Typically used when moving a component to a deleted component template ::value > = 0> -void move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -203,9 +154,8 @@ void move_dtor_impl( // Typically used when moving a component to a deleted component template ::value > = 0> -void move_dtor_impl( - ecs_world_t*, const ecs_entity_t*, const ecs_entity_t*, void *dst_ptr, - void *src_ptr, int32_t count, const ecs_type_info_t *info) +void move_dtor_impl(void *dst_ptr, void *src_ptr, int32_t count, + const ecs_type_info_t *info) { (void)info; ecs_assert(info->size == ECS_SIZEOF(T), ECS_INTERNAL_ERROR, NULL); @@ -224,29 +174,11 @@ void move_dtor_impl( } // _ -// Trait to test if type has flecs constructor -template -struct has_flecs_ctor { - static constexpr bool value = - std::is_constructible, - flecs::world&, flecs::entity>::value; -}; - // Trait to test if type is constructible by flecs template struct is_flecs_constructible { static constexpr bool value = - std::is_default_constructible>::value || - std::is_constructible, - flecs::world&, flecs::entity>::value; -}; - -// Trait to test if type has a self constructor (flecs::entity, Args...) -template -struct is_self_constructible { - static constexpr bool value = - std::is_constructible, - flecs::entity, Args...>::value; + std::is_default_constructible>::value; }; namespace _ @@ -260,8 +192,7 @@ ecs_xtor_t ctor() { // Not constructible by flecs template ::value && - ! has_flecs_ctor::value > = 0> + ! std::is_default_constructible::value > = 0> ecs_xtor_t ctor() { return ecs_ctor_illegal; } @@ -269,18 +200,11 @@ ecs_xtor_t ctor() { // Default constructible template ::value && - std::is_default_constructible::value && - ! has_flecs_ctor::value > = 0> + std::is_default_constructible::value > = 0> ecs_xtor_t ctor() { return ctor_impl; } -// Flecs constructible: T(flecs::world, flecs::entity) -template ::value > = 0> -ecs_xtor_t ctor() { - return ctor_world_entity_impl; -} - // No dtor template ::value > = 0> ecs_xtor_t dtor() { diff --git a/include/flecs/addons/flecs_c.h b/include/flecs/addons/flecs_c.h index a6b408e3f3..8408cdb4ef 100644 --- a/include/flecs/addons/flecs_c.h +++ b/include/flecs/addons/flecs_c.h @@ -402,6 +402,8 @@ #define ecs_copy(type) type##_copy #define ecs_move(type) type##_move #define ecs_on_set(type) type##_on_set +#define ecs_on_add(type) type##_on_add +#define ecs_on_remove(type) type##_on_remove #define ecs_query_new(world, q_expr)\ ecs_query_init(world, &(ecs_query_desc_t){\ diff --git a/include/flecs/private/api_defines.h b/include/flecs/private/api_defines.h index 88dbbe8e1c..ec0f05b0d1 100644 --- a/include/flecs/private/api_defines.h +++ b/include/flecs/private/api_defines.h @@ -255,24 +255,18 @@ typedef int32_t ecs_size_t; #ifndef FLECS_LEGACY -/* Constructor / destructor convenience macro */ +/* Constructor/Destructor convenience macro */ #define ECS_XTOR_IMPL(type, postfix, var, ...)\ void type##_##postfix(\ - ecs_world_t *world,\ - const ecs_entity_t *entity_ptr,\ void *_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)entity_ptr;\ (void)_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t entity = entity_ptr[i];\ type *var = &((type*)_ptr)[i];\ - (void)entity;\ (void)var;\ __VA_ARGS__\ }\ @@ -281,28 +275,18 @@ typedef int32_t ecs_size_t; /* Copy convenience macro */ #define ECS_COPY_IMPL(type, dst_var, src_var, ...)\ void type##_##copy(\ - ecs_world_t *world,\ - const ecs_entity_t *dst_entities,\ - const ecs_entity_t *src_entities,\ void *_dst_ptr,\ const void *_src_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)dst_entities;\ - (void)src_entities;\ (void)_dst_ptr;\ (void)_src_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t dst_entity = dst_entities[i];\ - ecs_entity_t src_entity = src_entities[i];\ type *dst_var = &((type*)_dst_ptr)[i];\ type *src_var = &((type*)_src_ptr)[i];\ - (void)dst_entity;\ - (void)src_entity;\ (void)dst_var;\ (void)src_var;\ __VA_ARGS__\ @@ -312,28 +296,18 @@ typedef int32_t ecs_size_t; /* Move convenience macro */ #define ECS_MOVE_IMPL(type, dst_var, src_var, ...)\ void type##_##move(\ - ecs_world_t *world,\ - const ecs_entity_t *dst_entities,\ - const ecs_entity_t *src_entities,\ void *_dst_ptr,\ void *_src_ptr,\ int32_t _count,\ const ecs_type_info_t *type_info)\ {\ - (void)world;\ - (void)dst_entities;\ - (void)src_entities;\ (void)_dst_ptr;\ (void)_src_ptr;\ (void)_count;\ (void)type_info;\ for (int32_t i = 0; i < _count; i ++) {\ - ecs_entity_t dst_entity = dst_entities[i];\ - ecs_entity_t src_entity = src_entities[i];\ type *dst_var = &((type*)_dst_ptr)[i];\ type *src_var = &((type*)_src_ptr)[i];\ - (void)dst_entity;\ - (void)src_entity;\ (void)dst_var;\ (void)src_var;\ __VA_ARGS__\ diff --git a/include/flecs/private/api_support.h b/include/flecs/private/api_support.h index d71d49b97f..59c38243ad 100644 --- a/include/flecs/private/api_support.h +++ b/include/flecs/private/api_support.h @@ -66,8 +66,6 @@ const char* ecs_identifier_is_var( FLECS_API void ecs_default_ctor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *ctx); diff --git a/src/addons/snapshot.c b/src/addons/snapshot.c index 88a7322437..ddea3b28ad 100644 --- a/src/addons/snapshot.c +++ b/src/addons/snapshot.c @@ -22,7 +22,6 @@ typedef struct ecs_table_leaf_t { static ecs_data_t* duplicate_data( - const ecs_world_t *world, ecs_table_t *table, ecs_data_t *main_data) { @@ -37,7 +36,6 @@ ecs_data_t* duplicate_data( /* Copy entities */ result->entities = ecs_vector_copy(main_data->entities, ecs_entity_t); - ecs_entity_t *entities = ecs_vector_first(result->entities, ecs_entity_t); /* Copy record ptrs */ result->record_ptrs = ecs_vector_copy( @@ -60,12 +58,11 @@ ecs_data_t* duplicate_data( ecs_xtor_t ctor = ti->lifecycle.ctor; if (ctor) { - ctor((ecs_world_t*)world, entities, dst_ptr, count, ti); + ctor(dst_ptr, count, ti); } void *src_ptr = ecs_vector_first_t(column->data, size, alignment); - copy((ecs_world_t*)world, entities, entities, dst_ptr, - src_ptr, count, ti); + copy(dst_ptr, src_ptr, count, ti); column->data = dst_vec; } else { @@ -78,7 +75,6 @@ ecs_data_t* duplicate_data( static void snapshot_table( - const ecs_world_t *world, ecs_snapshot_t *snapshot, ecs_table_t *table) { @@ -92,7 +88,7 @@ void snapshot_table( l->table = table; l->type = ecs_vector_copy(table->type, ecs_id_t); - l->data = duplicate_data(world, table, &table->storage); + l->data = duplicate_data(table, &table->storage); } static @@ -133,13 +129,13 @@ ecs_snapshot_t* snapshot_create( if (iter) { while (next(iter)) { ecs_table_t *table = iter->table; - snapshot_table(world, result, table); + snapshot_table(result, table); } } else { for (t = 0; t < table_count; t ++) { ecs_table_t *table = flecs_sparse_get( &world->store.tables, ecs_table_t, t); - snapshot_table(world, result, table); + snapshot_table(result, table); } } diff --git a/src/addons/system/system.c b/src/addons/system/system.c index fc5e1f4f04..4712e7b841 100644 --- a/src/addons/system/system.c +++ b/src/addons/system/system.c @@ -289,42 +289,51 @@ void* ecs_get_system_binding_ctx( } } -/* System destructor */ +/* System deinitialization */ static -ECS_DTOR(EcsSystem, ptr, { - if (!ecs_is_alive(world, entity)) { - /* This can happen when a set is deferred while a system is being - * cleaned up. The operation will be discarded, but the destructor - * still needs to be invoked for the value */ - continue; - } +void ecs_on_remove(EcsSystem)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsSystem *ptr = ecs_term(it, EcsSystem, 1); + + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + EcsSystem *sys = &ptr[i]; + ecs_entity_t entity = it->entities[i]; + + if (!ecs_is_alive(world, entity)) { + /* This can happen when a set is deferred while a system is being + * cleaned up. The operation will be discarded, but the destructor + * still needs to be invoked for the value */ + continue; + } - /* Invoke Deactivated action for active systems */ - if (ptr->query && ecs_query_table_count(ptr->query)) { - invoke_status_action(world, entity, ptr, EcsSystemDeactivated); - } + /* Invoke Deactivated action for active systems */ + if (sys->query && ecs_query_table_count(sys->query)) { + invoke_status_action(world, entity, sys, EcsSystemDeactivated); + } - /* Invoke Disabled action for enabled systems */ - if (!ecs_has_id(world, entity, EcsDisabled)) { - invoke_status_action(world, entity, ptr, EcsSystemDisabled); - } + /* Invoke Disabled action for enabled systems */ + if (!ecs_has_id(world, entity, EcsDisabled)) { + invoke_status_action(world, entity, sys, EcsSystemDisabled); + } - if (ptr->ctx_free) { - ptr->ctx_free(ptr->ctx); - } + if (sys->ctx_free) { + sys->ctx_free(sys->ctx); + } - if (ptr->status_ctx_free) { - ptr->status_ctx_free(ptr->status_ctx); - } + if (sys->status_ctx_free) { + sys->status_ctx_free(sys->status_ctx); + } - if (ptr->binding_ctx_free) { - ptr->binding_ctx_free(ptr->binding_ctx); - } + if (sys->binding_ctx_free) { + sys->binding_ctx_free(sys->binding_ctx); + } - if (ptr->query) { - ecs_query_fini(ptr->query); + if (sys->query) { + ecs_query_fini(sys->query); + } } -}) +} static void EnableMonitor( @@ -534,7 +543,7 @@ void FlecsSystemImport( ecs_set_component_actions_w_id(world, ecs_id(EcsSystem), &(EcsComponentLifecycle) { .ctor = ecs_default_ctor, - .dtor = ecs_dtor(EcsSystem) + .on_remove = ecs_on_remove(EcsSystem) }); ecs_observer_init(world, &(ecs_observer_desc_t) { diff --git a/src/bootstrap.c b/src/bootstrap.c index e89154ddc4..d8196559c8 100644 --- a/src/bootstrap.c +++ b/src/bootstrap.c @@ -3,14 +3,6 @@ /* -- Component lifecycle -- */ /* Component lifecycle actions for EcsIdentifier */ -static ECS_CTOR(EcsIdentifier, ptr, { - ptr->value = NULL; - ptr->hash = 0; - ptr->length = 0; - ptr->index_hash = 0; - ptr->index = NULL; -}) - static ECS_DTOR(EcsIdentifier, ptr, { ecs_os_strset(&ptr->value, NULL); }) @@ -66,7 +58,8 @@ void ecs_on_set(EcsIdentifier)(ecs_iter_t *it) { } } - for (int i = 0; i < it->count; i ++) { + int i, count = it->count; + for (i = 0; i < count; i ++) { EcsIdentifier *cur = &ptr[i]; uint64_t hash; ecs_size_t len; @@ -111,51 +104,28 @@ void ecs_on_set(EcsIdentifier)(ecs_iter_t *it) { } /* Component lifecycle actions for EcsTrigger */ -static ECS_CTOR(EcsTrigger, ptr, { - ptr->trigger = NULL; -}) - -static ECS_DTOR(EcsTrigger, ptr, { - if (ptr->trigger) { - flecs_trigger_fini(world, (ecs_trigger_t*)ptr->trigger); - } -}) - -static ECS_COPY(EcsTrigger, dst, src, { - ecs_abort(ECS_INVALID_OPERATION, "Trigger component cannot be copied"); -}) - -static ECS_MOVE(EcsTrigger, dst, src, { - if (dst->trigger) { - flecs_trigger_fini(world, (ecs_trigger_t*)dst->trigger); +static void ecs_on_remove(EcsTrigger)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsTrigger *ptr = ecs_term(it, EcsTrigger, 1); + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + if (ptr[i].trigger) { + flecs_trigger_fini(world, (ecs_trigger_t*)ptr[i].trigger); + } } - dst->trigger = src->trigger; - src->trigger = NULL; -}) +} /* Component lifecycle actions for EcsObserver */ -static ECS_CTOR(EcsObserver, ptr, { - ptr->observer = NULL; -}) - -static ECS_DTOR(EcsObserver, ptr, { - if (ptr->observer) { - flecs_observer_fini(world, (ecs_observer_t*)ptr->observer); - } -}) - -static ECS_COPY(EcsObserver, dst, src, { - ecs_abort(ECS_INVALID_OPERATION, "Observer component cannot be copied"); -}) - -static ECS_MOVE(EcsObserver, dst, src, { - if (dst->observer) { - flecs_observer_fini(world, (ecs_observer_t*)dst->observer); +static void ecs_on_remove(EcsObserver)(ecs_iter_t *it) { + ecs_world_t *world = it->world; + EcsObserver *ptr = ecs_term(it, EcsObserver, 1); + int32_t i, count = it->count; + for (i = 0; i < count; i ++) { + if (ptr[i].observer) { + flecs_observer_fini(world, (ecs_observer_t*)ptr[i].observer); + } } - dst->observer = src->observer; - src->observer = NULL; -}) - +} /* -- Builtin triggers -- */ @@ -597,7 +567,7 @@ void flecs_bootstrap( }); ecs_set_component_actions(world, EcsIdentifier, { - .ctor = ecs_ctor(EcsIdentifier), + .ctor = ecs_default_ctor, .dtor = ecs_dtor(EcsIdentifier), .copy = ecs_copy(EcsIdentifier), .move = ecs_move(EcsIdentifier), @@ -606,17 +576,13 @@ void flecs_bootstrap( }); ecs_set_component_actions(world, EcsTrigger, { - .ctor = ecs_ctor(EcsTrigger), - .dtor = ecs_dtor(EcsTrigger), - .copy = ecs_copy(EcsTrigger), - .move = ecs_move(EcsTrigger) + .ctor = ecs_default_ctor, + .on_remove = ecs_on_remove(EcsTrigger) }); ecs_set_component_actions(world, EcsObserver, { - .ctor = ecs_ctor(EcsObserver), - .dtor = ecs_dtor(EcsObserver), - .copy = ecs_copy(EcsObserver), - .move = ecs_move(EcsObserver) + .ctor = ecs_default_ctor, + .on_remove = ecs_on_remove(EcsObserver) }); /* Create table for initial components */ diff --git a/src/entity.c b/src/entity.c index 279e02a15e..885a47931c 100644 --- a/src/entity.c +++ b/src/entity.c @@ -505,10 +505,8 @@ bool override_from_base( ecs_copy_t copy = ti->lifecycle.copy; if (copy) { - ecs_entity_t *entities = ecs_vector_first( - data->entities, ecs_entity_t); for (index = 0; index < count; index ++) { - copy(world, &entities[row], &base, data_ptr, base_ptr, 1, ti); + copy(data_ptr, base_ptr, 1, ti); data_ptr = ECS_OFFSET(data_ptr, data_size); } } else { @@ -1075,13 +1073,9 @@ const ecs_entity_t* new_w_data( ecs_copy_t copy; ecs_move_t move; if (is_move && (move = ti->lifecycle.move)) { - ecs_entity_t *eids = ecs_vector_first( - data->entities, ecs_entity_t); - move(world, eids, eids, ptr, src_ptr, count, ti); + move(ptr, src_ptr, count, ti); } else if (!is_move && (copy = ti->lifecycle.copy)) { - ecs_entity_t *eids = ecs_vector_first( - data->entities, ecs_entity_t); - copy(world, eids, eids, ptr, src_ptr, count, ti); + copy(ptr, src_ptr, count, ti); } else { ecs_os_memcpy(ptr, src_ptr, size * count); } @@ -1217,7 +1211,6 @@ void *get_mutable( return NULL; } - /* -- Private functions -- */ static void flecs_notify_on_add( @@ -3108,14 +3101,14 @@ ecs_entity_t assign_ptr_w_id( if (is_move) { ecs_move_t move = ti->lifecycle.move; if (move) { - move(world, &entity, &entity, dst, ptr, 1, ti); + move(dst, ptr, 1, ti); } else { ecs_os_memcpy(dst, ptr, flecs_utosize(size)); } } else { ecs_copy_t copy = ti->lifecycle.copy; if (copy) { - copy(world, &entity, &entity, dst, ptr, 1, ti); + copy(dst, ptr, 1, ti); } else { ecs_os_memcpy(dst, ptr, flecs_utosize(size)); } @@ -3996,21 +3989,20 @@ void flush_bulk_new( static void free_value( ecs_world_t *world, - ecs_entity_t *entities, ecs_id_t id, void *value, int32_t count) { ecs_entity_t real_id = ecs_get_typeid(world, id); const ecs_type_info_t *ti = flecs_get_type_info(world, real_id); - ecs_xtor_t dtor; + ecs_xtor_t dtor = ti->lifecycle.dtor; - if (ti && (dtor = ti->lifecycle.dtor)) { + if (dtor) { ecs_size_t size = ti->size; void *ptr; int i; for (i = 0, ptr = value; i < count; i ++, ptr = ECS_OFFSET(ptr, size)) { - dtor(world, &entities[i], ptr, 1, ti); + dtor(ptr, 1, ti); } } } @@ -4023,7 +4015,7 @@ void discard_op( if (op->kind != EcsOpBulkNew) { void *value = op->is._1.value; if (value) { - free_value(world, &op->is._1.entity, op->id, op->is._1.value, 1); + free_value(world, op->id, op->is._1.value, 1); ecs_os_free(value); } } else { diff --git a/src/stage.c b/src/stage.c index 4ec98e4bf9..312341a296 100644 --- a/src/stage.c +++ b/src/stage.c @@ -333,14 +333,14 @@ bool flecs_defer_set( if (value) { ecs_copy_t copy; if (ti && (copy = ti->lifecycle.copy_ctor)) { - copy(world, &entity, &entity, op->is._1.value, value, 1, ti); + copy(op->is._1.value, value, 1, ti); } else { ecs_os_memcpy(op->is._1.value, value, size); } } else { ecs_xtor_t ctor; if (ti && (ctor = ti->lifecycle.ctor)) { - ctor(world, &entity, op->is._1.value, 1, ti); + ctor(op->is._1.value, 1, ti); } } diff --git a/src/table.c b/src/table.c index 1c806ad2b8..3adfe36c6f 100644 --- a/src/table.c +++ b/src/table.c @@ -213,6 +213,9 @@ ecs_flags32_t type_info_flags( if (ti->lifecycle.ctor) { flags |= EcsTableHasCtors; } + if (ti->lifecycle.on_add) { + flags |= EcsTableHasCtors; + } if (ti->lifecycle.dtor) { flags |= EcsTableHasDtors; } @@ -295,9 +298,10 @@ void flecs_table_init_data( ecs_entity_t e = ids[i + sw_offset]; ecs_assert(ECS_HAS_ROLE(e, SWITCH), ECS_INTERNAL_ERROR, NULL); e = e & ECS_COMPONENT_MASK; - const EcsType *type_ptr = ecs_get(world, e, EcsType); - ecs_assert(type_ptr != NULL, ECS_INTERNAL_ERROR, NULL); - ecs_table_t *sw_table = type_ptr->normalized; + const EcsType *switch_type = ecs_get(world, e, EcsType); + ecs_assert(switch_type != NULL, + ECS_INVALID_PARAMETER, "not a switch"); + ecs_table_t *sw_table = switch_type->normalized; ecs_type_t sw_type = sw_table->type; ecs_entity_t *sw_array = ecs_vector_first(sw_type, ecs_entity_t); @@ -365,34 +369,15 @@ void run_on_remove( /* -- Private functions -- */ static -void ctor_component( - ecs_world_t *world, - ecs_type_info_t *ti, - ecs_column_t *column, - ecs_entity_t *entities, - int32_t row, - int32_t count) -{ - ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); - - /* A new component is constructed */ - ecs_xtor_t ctor = ti->lifecycle.ctor; - if (ctor) { - void *ptr = ecs_vector_get_t( - column->data, ti->size, ti->alignment, row); - ctor(world, entities, ptr, count, ti); - } -} - -static -void on_remove_component( +void on_component_callback( ecs_world_t *world, ecs_table_t *table, - ecs_iter_action_t on_remove, - void *ptr, - ecs_size_t size, + ecs_iter_action_t callback, + ecs_entity_t event, + ecs_column_t *column, ecs_entity_t *entities, ecs_id_t id, + int32_t row, int32_t count, ecs_type_info_t *ti) { @@ -400,6 +385,9 @@ void on_remove_component( ecs_iter_t it = { .term_count = 1 }; it.entities = entities; + ecs_size_t size = ti->size; + void *ptr = ecs_vector_get_t(column->data, size, ti->alignment, row); + flecs_iter_init(&it); it.world = world; it.real_world = world; @@ -408,15 +396,32 @@ void on_remove_component( it.ptrs[0] = ptr; it.sizes[0] = size; it.ids[0] = id; - it.event = EcsOnRemove; + it.event = event; it.event_id = id; it.ctx = ti->lifecycle.ctx; it.count = count; - on_remove(&it); + callback(&it); } static -void dtor_component( +void ctor_component( + ecs_type_info_t *ti, + ecs_column_t *column, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); + + ecs_xtor_t ctor = ti->lifecycle.ctor; + if (ctor) { + void *ptr = ecs_vector_get_t( + column->data, ti->size, ti->alignment, row); + ctor(ptr, count, ti); + } +} + +static +void add_component( ecs_world_t *world, ecs_table_t *table, ecs_type_info_t *ti, @@ -424,41 +429,56 @@ void dtor_component( ecs_entity_t *entities, ecs_id_t id, int32_t row, - int32_t count, - bool is_remove) + int32_t count) { ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); - if (!count) { - return; - } + ctor_component(ti, column, row, count); - ecs_iter_action_t on_remove = 0; - if (is_remove) { - on_remove = ti->lifecycle.on_remove; + ecs_iter_action_t on_add = ti->lifecycle.on_add; + if (on_add) { + on_component_callback(world, table, on_add, EcsOnAdd, column, + entities, id, row, count, ti); } +} + +static +void dtor_component( + ecs_type_info_t *ti, + ecs_column_t *column, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); ecs_xtor_t dtor = ti->lifecycle.dtor; - if (!on_remove && !dtor) { - return; + if (dtor) { + void *ptr = ecs_vector_get_t( + column->data, ti->size, ti->alignment, row); + dtor(ptr, count, ti); } +} - int32_t size = ti->size; - int32_t alignment = ti->alignment; - ecs_entity_t *entity_elem = &entities[row]; - - ecs_assert(column->data != NULL, ECS_INTERNAL_ERROR, NULL); - void *ptr = ecs_vector_get_t(column->data, size, alignment, row); - ecs_assert(ptr != NULL, ECS_INTERNAL_ERROR, NULL); +static +void remove_component( + ecs_world_t *world, + ecs_table_t *table, + ecs_type_info_t *ti, + ecs_column_t *column, + ecs_entity_t *entities, + ecs_id_t id, + int32_t row, + int32_t count) +{ + ecs_assert(ti != NULL, ECS_INTERNAL_ERROR, NULL); + ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - on_remove_component(world, table, on_remove, ptr, size, - entity_elem, id, count, ti); - } - - if (dtor) { - dtor(world, entity_elem, ptr, count, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, column, + entities, id, row, count, ti); } + + dtor_component(ti, column, row, count); } static @@ -496,11 +516,8 @@ void dtor_all_components( ecs_type_info_t *ti = &table->type_info[c]; ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - ecs_size_t size = ti->size; - ecs_size_t align = ti->alignment; - void *ptr = ecs_vector_get_t(column->data, size, align, row); - on_remove_component(world, table, on_remove, ptr, size, - &entities[row], ids[c], count, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, + column, &entities[row], ids[c], row, count, ti); } } @@ -510,8 +527,7 @@ void dtor_all_components( for (i = row; i < end; i ++) { for (c = 0; c < ids_count; c++) { ecs_column_t *column = &data->columns[c]; - dtor_component(world, table, &table->type_info[c], column, - entities, ids[c], i, 1, false); + dtor_component(&table->type_info[c], column, i, 1); } /* Update entity index after invoking destructors so that entity can @@ -967,9 +983,7 @@ void move_bitset_columns( } static -void grow_column( - ecs_world_t *world, - ecs_entity_t *entities, +void* grow_column( ecs_column_t *column, ecs_type_info_t *ti, int32_t to_add, @@ -985,6 +999,7 @@ void grow_column( int32_t src_size = ecs_vector_size(vec); int32_t dst_count = count + to_add; bool can_realloc = dst_size != src_size; + void *result = NULL; ecs_assert(dst_size >= dst_count, ECS_INTERNAL_ERROR, NULL); @@ -1005,12 +1020,12 @@ void grow_column( void *dst_buffer = ecs_vector_first_t(dst_vec, size, alignment); /* Move (and construct) existing elements to new vector */ - move_ctor(world, entities, entities, dst_buffer, src_buffer, count, ti); + move_ctor(dst_buffer, src_buffer, count, ti); if (construct) { /* Construct new element(s) */ - void *elem = ECS_OFFSET(dst_buffer, size * count); - ctor(world, &entities[count], elem, to_add, ti); + result = ECS_OFFSET(dst_buffer, size * count); + ctor(result, to_add, ti); } /* Free old vector */ @@ -1023,13 +1038,13 @@ void grow_column( ecs_vector_set_size_t(&vec, size, alignment, dst_size); } - void *elem = ecs_vector_addn_t(&vec, size, alignment, to_add); + result = ecs_vector_addn_t(&vec, size, alignment, to_add); ecs_xtor_t ctor; if (construct && (ctor = ti->lifecycle.ctor)) { /* If new elements need to be constructed and component has a * constructor, construct */ - ctor(world, &entities[count], elem, to_add, ti); + ctor(result, to_add, ti); } column->data = vec; @@ -1037,6 +1052,8 @@ void grow_column( ecs_assert(ecs_vector_size(column->data) == dst_size, ECS_INTERNAL_ERROR, NULL); + + return result; } static @@ -1086,11 +1103,10 @@ int32_t grow_data( /* Add elements to each column array */ ecs_type_info_t *type_info = table->type_info; - ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); for (i = 0; i < column_count; i ++) { ecs_column_t *column = &columns[i]; ecs_type_info_t *ti = &type_info[i]; - grow_column(world, entities, column, ti, to_add, size, true); + grow_column(column, ti, to_add, size, true); ecs_assert(ecs_vector_size(columns[i].data) == size, ECS_INTERNAL_ERROR, NULL); } @@ -1187,10 +1203,9 @@ int32_t flecs_table_append( int32_t sw_column_count = table->sw_column_count; int32_t bs_column_count = table->bs_column_count; - ecs_sw_column_t *sw_columns = table->storage.sw_columns; - ecs_bs_column_t *bs_columns = table->storage.bs_columns; - ecs_entity_t *entities = ecs_vector_first( - data->entities, ecs_entity_t); + ecs_sw_column_t *sw_columns = data->sw_columns; + ecs_bs_column_t *bs_columns = data->bs_columns; + ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); /* Reobtain size to ensure that the columns have the same size as the * entities and record vectors. This keeps reasoning about when allocations @@ -1202,8 +1217,14 @@ int32_t flecs_table_append( for (i = 0; i < column_count; i ++) { ecs_column_t *column = &columns[i]; ecs_type_info_t *ti = &type_info[i]; - grow_column(world, entities, column, ti, 1, size, construct); - + grow_column(column, ti, 1, size, construct); + + ecs_iter_action_t on_add = ti->lifecycle.on_add; + if (on_add) { + on_component_callback(world, table, on_add, EcsOnAdd, column, + &entities[count], table->storage_ids[i], count, 1, ti); + } + ecs_assert(ecs_vector_size(columns[i].data) == ecs_vector_size(data->entities), ECS_INTERNAL_ERROR, NULL); ecs_assert( ecs_vector_count(columns[i].data) == @@ -1333,24 +1354,18 @@ void flecs_table_delete( } check_table_sanity(table); - return; } - ecs_id_t *ids = ecs_vector_first(table->type, ecs_id_t); + ecs_id_t *ids = table->storage_ids; /* Last element, destruct & remove */ if (index == count) { /* If table has component destructors, invoke */ if (destruct && (table->flags & EcsTableHasDtors)) { for (i = 0; i < column_count; i ++) { - ecs_type_info_t *ti = &type_info[i]; - if (!ti) { - continue; - } - - dtor_component(world, table, ti, &columns[i], - entities, ids[i], index, 1, true); + remove_component(world, table, &type_info[i], &columns[i], + &entity_to_delete, ids[i], index, 1); } } @@ -1371,14 +1386,13 @@ void flecs_table_delete( ecs_iter_action_t on_remove = ti->lifecycle.on_remove; if (on_remove) { - on_remove_component(world, table, on_remove, dst, - size, &entity_to_delete, ids[i], 1, ti); + on_component_callback(world, table, on_remove, EcsOnRemove, + column, &entity_to_delete, ids[i], index, 1, ti); } ecs_move_t move_dtor = ti->lifecycle.move_dtor; if (move_dtor) { - move_dtor(world, &entity_to_move, - &entity_to_delete, dst, src, 1, ti); + move_dtor(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } @@ -1524,17 +1538,17 @@ void flecs_table_move( ecs_assert(src != NULL, ECS_INTERNAL_ERROR, NULL); if (same_entity) { - ecs_move_t callback = ti->lifecycle.ctor_move_dtor; - if (callback) { + ecs_move_t move = ti->lifecycle.ctor_move_dtor; + if (move) { /* ctor + move + dtor */ - callback(world, &dst_entity, &src_entity, dst, src, 1, ti); + move(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } } else { ecs_copy_t copy = ti->lifecycle.copy_ctor; if (copy) { - copy(world, &dst_entity, &src_entity, dst, src, 1, ti); + copy(dst, src, 1, ti); } else { ecs_os_memcpy(dst, src, size); } @@ -1542,13 +1556,14 @@ void flecs_table_move( } else { if (dst_id < src_id) { if (construct) { - ctor_component(world, &dst_type_info[i_new], - &dst_columns[i_new], &dst_entity, dst_index, 1); + add_component(world, dst_table, &dst_type_info[i_new], + &dst_columns[i_new], &dst_entity, dst_id, + dst_index, 1); } } else { - dtor_component(world, src_table, &src_type_info[i_old], + remove_component(world, src_table, &src_type_info[i_old], &src_columns[i_old], &src_entity, src_id, - src_index, 1, true); + src_index, 1); } } @@ -1558,15 +1573,15 @@ void flecs_table_move( if (construct) { for (; (i_new < dst_column_count); i_new ++) { - ctor_component(world, &dst_type_info[i_new], - &dst_columns[i_new], &dst_entity, dst_index, 1); + add_component(world, dst_table, &dst_type_info[i_new], + &dst_columns[i_new], &dst_entity, dst_ids[i_new], dst_index, 1); } } for (; (i_old < src_column_count); i_old ++) { - dtor_component(world, src_table, &src_type_info[i_old], + remove_component(world, src_table, &src_type_info[i_old], &src_columns[i_old], &src_entity, src_ids[i_old], - src_index, 1, true); + src_index, 1); } check_table_sanity(dst_table); @@ -1772,7 +1787,6 @@ void merge_vector( static void merge_column( - ecs_world_t *world, ecs_type_info_t *ti, int32_t size, int32_t alignment, @@ -1780,7 +1794,6 @@ void merge_column( int32_t column_id, ecs_vector_t *src) { - ecs_entity_t *entities = ecs_vector_first(data->entities, ecs_entity_t); ecs_column_t *column = &data->columns[column_id]; ecs_vector_t *dst = column->data; int32_t dst_count = ecs_vector_count(dst); @@ -1800,7 +1813,7 @@ void merge_column( column->data = dst; /* Construct new values */ - ctor_component(world, ti, column, entities, dst_count, src_count); + ctor_component(ti, column, dst_count, src_count); void *dst_ptr = ecs_vector_first_t(dst, size, alignment); void *src_ptr = ecs_vector_first_t(src, size, alignment); @@ -1810,7 +1823,7 @@ void merge_column( /* Move values into column */ ecs_move_t move = ti->lifecycle.move; if (move) { - move(world, entities, entities, dst_ptr, src_ptr, src_count, ti); + move(dst_ptr, src_ptr, src_count, ti); } else { ecs_os_memcpy(dst_ptr, src_ptr, size * src_count); } @@ -1854,8 +1867,6 @@ void merge_table_data( merge_vector(&dst_data->entities, src_data->entities, ECS_SIZEOF(ecs_entity_t), ECS_ALIGNOF(ecs_entity_t)); src_data->entities = NULL; - ecs_entity_t *entities = ecs_vector_first(dst_data->entities, ecs_entity_t); - ecs_assert(ecs_vector_count(dst_data->entities) == src_count + dst_count, ECS_INTERNAL_ERROR, NULL); @@ -1873,7 +1884,7 @@ void merge_table_data( ecs_assert(size != 0, ECS_INTERNAL_ERROR, NULL); if (dst_id == src_id) { - merge_column(world, dst_ti, size, alignment, dst_data, + merge_column(dst_ti, size, alignment, dst_data, i_new, src_columns[i_old].data); src_columns[i_old].data = NULL; @@ -1890,17 +1901,14 @@ void merge_table_data( src_count + dst_count); /* Construct new values */ - ctor_component(world, dst_ti, column, - entities, 0, src_count + dst_count); + ctor_component(dst_ti, column, 0, src_count + dst_count); i_new ++; } else if (dst_id > src_id) { ecs_column_t *column = &src_columns[i_old]; /* Destruct old values */ - ecs_type_info_t *src_ti = &src_type_info[i_old]; - dtor_component(world, src_table, src_ti, column, - entities, 0, 0, src_count, false); + dtor_component(&src_type_info[i_old], column, 0, src_count); /* Old column does not occur in new table, remove */ ecs_vector_free(column->data); @@ -1927,7 +1935,7 @@ void merge_table_data( src_count + dst_count); /* Construct new values */ - ctor_component(world, ti, column, entities, 0, src_count + dst_count); + ctor_component(ti, column, 0, src_count + dst_count); } /* Destroy remaining columns */ @@ -1935,9 +1943,7 @@ void merge_table_data( ecs_column_t *column = &src_columns[i_old]; /* Destruct old values */ - ecs_type_info_t *ti = &src_type_info[i_old]; - dtor_component(world, src_table, ti, column, entities, 0, - 0, src_count, false); + dtor_component(&src_type_info[i_old], column, 0, src_count); /* Old column does not occur in new table, remove */ ecs_vector_free(column->data); diff --git a/src/world.c b/src/world.c index 24bb571afb..1becbc2eee 100644 --- a/src/world.c +++ b/src/world.c @@ -841,99 +841,80 @@ void flecs_notify_tables( } void ecs_default_ctor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *ti) { - (void)world; (void)entity_ptr; ecs_os_memset(ptr, 0, ti->size * count); } static -void default_copy_ctor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, const void *src_ptr, +void default_copy_ctor(void *dst_ptr, const void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->copy(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->copy(dst_ptr, src_ptr, count, ti); } static -void default_move_ctor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_ctor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); } static -void default_ctor_w_move_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_ctor_w_move_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->ctor(world, dst_entity, dst_ptr, count, ti); - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->ctor(dst_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } static -void default_move_ctor_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_ctor_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move_ctor(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->move_ctor(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } static -void default_move( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); } static -void default_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { - (void)src_entity; - /* When there is no move, destruct the destination component & memcpy the * component to dst. The src component does not have to be destructed when * a component has a trivial move. */ const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->dtor(world, dst_entity, dst_ptr, count, ti); + cl->dtor(dst_ptr, count, ti); ecs_os_memcpy(dst_ptr, src_ptr, flecs_uto(ecs_size_t, ti->size) * count); } static -void default_move_w_dtor( - ecs_world_t *world, const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, +void default_move_w_dtor(void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *ti) { /* If a component has a move, the move will take care of memcpying the data * and destroying any data in dst. Because this is not a trivial move, the * src component must also be destructed. */ const EcsComponentLifecycle *cl = &ti->lifecycle; - cl->move(world, dst_entity, src_entity, dst_ptr, src_ptr, count, ti); - cl->dtor(world, src_entity, src_ptr, count, ti); + cl->move(dst_ptr, src_ptr, count, ti); + cl->dtor(src_ptr, count, ti); } void ecs_set_component_actions_w_id( diff --git a/test/api/project.json b/test/api/project.json index 041754dca6..4c471e958e 100644 --- a/test/api/project.json +++ b/test/api/project.json @@ -706,7 +706,13 @@ "delete_in_dtor_same_type_on_delete", "delete_in_dtor_other_type_on_delete", "delete_self_in_dtor_on_delete", - "on_set_after_set" + "on_set_after_set", + "on_add_after_new", + "on_add_after_add", + "on_add_after_set", + "on_remove_after_remove", + "on_remove_after_clear", + "on_remove_after_delete" ] }, { "id": "Sorting", diff --git a/test/api/src/ComponentLifecycle.c b/test/api/src/ComponentLifecycle.c index 1410b4fcb0..b0739e1346 100644 --- a/test/api/src/ComponentLifecycle.c +++ b/test/api/src/ComponentLifecycle.c @@ -5,19 +5,14 @@ void ComponentLifecycle_setup() { } typedef struct xtor_ctx { - ecs_world_t *world; ecs_entity_t component; - ecs_entity_t entity; size_t size; int32_t count; int32_t invoked; } xtor_ctx; typedef struct copy_ctx { - ecs_world_t *world; ecs_entity_t component; - ecs_entity_t entity; - ecs_entity_t src_entity; size_t size; int32_t count; int32_t invoked; @@ -32,16 +27,12 @@ typedef struct cl_ctx { static void comp_ctor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { cl_ctx *data = info->lifecycle.ctx; - data->ctor.world = world; data->ctor.component = info->component; - data->ctor.entity = entity_ptr[0], data->ctor.size = info->size; data->ctor.count += count; data->ctor.invoked ++; @@ -56,16 +47,12 @@ void comp_ctor( static void comp_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { cl_ctx *data = info->lifecycle.ctx; - data->dtor.world = world; data->dtor.component = info->component; - data->dtor.entity = entity_ptr[0], data->dtor.size = info->size; data->dtor.count += count; data->dtor.invoked ++; @@ -73,19 +60,13 @@ void comp_dtor( static void comp_copy( - ecs_world_t *world, - const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, const void *src_ptr, int32_t count, const ecs_type_info_t *info) { cl_ctx *data = info->lifecycle.ctx; - data->copy.world = world; data->copy.component = info->component; - data->copy.entity = dst_entity[0], - data->copy.src_entity = src_entity[0], data->copy.size = info->size; data->copy.count += count; data->copy.invoked ++; @@ -95,19 +76,13 @@ void comp_copy( static void comp_move( - ecs_world_t *world, - const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, void *dst_ptr, void *src_ptr, int32_t count, const ecs_type_info_t *info) { cl_ctx *data = info->lifecycle.ctx; - data->move.world = world; data->move.component = info->component; - data->move.entity = dst_entity[0], - data->move.src_entity = src_entity[0], data->move.size = info->size; data->move.count = count; data->move.invoked ++; @@ -132,9 +107,7 @@ void ComponentLifecycle_ctor_on_add() { ecs_add(world, e, Position); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 1); @@ -153,11 +126,9 @@ void ComponentLifecycle_ctor_on_new() { .ctx = &ctx }); - ecs_entity_t e = ecs_new(world, Position); + ecs_new(world, Position); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 1); @@ -181,9 +152,7 @@ void ComponentLifecycle_dtor_on_remove() { ecs_remove(world, e, Position); test_assert(ctx.dtor.invoked != 0); - test_assert(ctx.dtor.world == world); test_int(ctx.dtor.component, ecs_id(Position)); - test_int(ctx.dtor.entity, e); test_int(ctx.dtor.size, sizeof(Position)); test_int(ctx.dtor.count, 1); @@ -207,9 +176,7 @@ void ComponentLifecycle_dtor_on_delete() { ecs_delete(world, e); test_assert(ctx.dtor.invoked != 0); - test_assert(ctx.dtor.world == world); test_int(ctx.dtor.component, ecs_id(Position)); - test_int(ctx.dtor.entity, e); test_int(ctx.dtor.size, sizeof(Position)); test_int(ctx.dtor.count, 1); @@ -233,9 +200,7 @@ void ComponentLifecycle_copy_on_set() { ecs_set(world, e, Position, {0, 0}); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, e); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 1); @@ -262,9 +227,7 @@ void ComponentLifecycle_copy_on_override() { ecs_add(world, e, Position); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, e); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 1); @@ -287,12 +250,9 @@ void ComponentLifecycle_copy_on_clone() { test_assert(ctx.copy.invoked != 0); memset(&ctx, 0, sizeof(ctx)); - ecs_entity_t clone = ecs_clone(world, 0, e, true); + ecs_clone(world, 0, e, true); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, clone); - test_int(ctx.copy.src_entity, e); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 1); @@ -344,9 +304,7 @@ void ComponentLifecycle_copy_on_snapshot() { } test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, ids[i - 1]); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 10); @@ -355,9 +313,7 @@ void ComponentLifecycle_copy_on_snapshot() { ecs_snapshot_t *s = ecs_snapshot_take(world); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, ids[0]); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 10); @@ -397,9 +353,7 @@ void ComponentLifecycle_ctor_copy_on_snapshot() { } test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, ids[i - 1]); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 10); @@ -408,16 +362,12 @@ void ComponentLifecycle_ctor_copy_on_snapshot() { ecs_snapshot_t *s = ecs_snapshot_take(world); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, ids[0]); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 10); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, ids[0]); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 10); @@ -474,7 +424,6 @@ void ComponentLifecycle_dtor_on_restore() { ecs_snapshot_restore(world, s); test_assert(ctx.dtor.invoked != 0); - test_assert(ctx.dtor.world == world); test_int(ctx.dtor.component, ecs_id(Position)); test_int(ctx.dtor.size, sizeof(Position)); test_int(ctx.dtor.count, 9); @@ -915,9 +864,7 @@ void ComponentLifecycle_ctor_on_add_pair() { ecs_add_pair(world, e, ecs_id(Pair), ecs_id(Position)); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Pair)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Pair)); test_int(ctx.ctor.count, 1); @@ -943,9 +890,7 @@ void ComponentLifecycle_ctor_on_add_pair_tag() { ecs_add_pair(world, e, Pair, ecs_id(Position)); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 1); @@ -973,9 +918,7 @@ void ComponentLifecycle_ctor_on_move_pair() { ecs_add_pair(world, e, ecs_id(Pair), ecs_id(Position)); test_assert(ctx.ctor.invoked != 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Pair)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Pair)); test_int(ctx.ctor.count, 1); @@ -1001,9 +944,7 @@ void ComponentLifecycle_move_on_realloc() { ecs_add(world, e, Position); test_assert(ctx.ctor.invoked != 0); test_int(ctx.move.invoked, 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 1); @@ -1037,9 +978,7 @@ void ComponentLifecycle_move_on_bulk_new() { ecs_add(world, e, Position); test_assert(ctx.ctor.invoked != 0); test_int(ctx.move.invoked, 0); - test_assert(ctx.ctor.world == world); test_int(ctx.ctor.component, ecs_id(Position)); - test_int(ctx.ctor.entity, e); test_int(ctx.ctor.size, sizeof(Position)); test_int(ctx.ctor.count, 1); @@ -1067,7 +1006,7 @@ void ComponentLifecycle_move_on_delete() { }); ecs_entity_t e1 = ecs_new(world, Position); - ecs_entity_t e2 = ecs_new(world, Position); + ecs_new(world, Position); test_assert(ctx.ctor.invoked != 0); ctx = (cl_ctx){ { 0 } }; @@ -1076,9 +1015,7 @@ void ComponentLifecycle_move_on_delete() { test_int(ctx.ctor.invoked, 0); test_assert(ctx.move.invoked != 0); - test_assert(ctx.move.world == world); test_int(ctx.move.component, ecs_id(Position)); - test_int(ctx.move.entity, e2); test_int(ctx.move.size, sizeof(Position)); test_int(ctx.move.count, 1); @@ -1099,7 +1036,7 @@ void ComponentLifecycle_move_dtor_on_delete() { }); ecs_entity_t e1 = ecs_new(world, Position); - ecs_entity_t e2 = ecs_new(world, Position); + ecs_new(world, Position); ctx = (cl_ctx){ { 0 } }; @@ -1107,15 +1044,12 @@ void ComponentLifecycle_move_dtor_on_delete() { test_assert(ctx.dtor.invoked != 0); test_assert(ctx.move.invoked != 0); - test_assert(ctx.move.world == world); test_int(ctx.dtor.component, ecs_id(Position)); - test_int(ctx.dtor.entity, e1); test_int(ctx.dtor.size, sizeof(Position)); test_int(ctx.dtor.count, 1); test_int(ctx.move.component, ecs_id(Position)); - test_int(ctx.move.entity, e2); test_int(ctx.move.size, sizeof(Position)); test_int(ctx.move.count, 1); @@ -1152,9 +1086,7 @@ void ComponentLifecycle_copy_on_override_pair() { test_assert(ctx.ctor.invoked != 0); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Pair)); - test_int(ctx.copy.entity, instance); test_int(ctx.copy.size, sizeof(Pair)); test_int(ctx.copy.count, 1); @@ -1191,9 +1123,7 @@ void ComponentLifecycle_copy_on_override_pair_tag() { test_assert(ctx.ctor.invoked != 0); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, instance); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 1); @@ -1218,9 +1148,7 @@ void ComponentLifecycle_copy_on_set_pair() { ecs_set_pair(world, e, Pair, ecs_id(Position), {0, 0}); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Pair)); - test_int(ctx.copy.entity, e); test_int(ctx.copy.size, sizeof(Pair)); test_int(ctx.copy.count, 1); @@ -1245,9 +1173,7 @@ void ComponentLifecycle_copy_on_set_pair_tag() { ecs_set_pair_object(world, e, Pair, Position, {0, 0}); test_assert(ctx.copy.invoked != 0); - test_assert(ctx.copy.world == world); test_int(ctx.copy.component, ecs_id(Position)); - test_int(ctx.copy.entity, e); test_int(ctx.copy.size, sizeof(Position)); test_int(ctx.copy.count, 1); @@ -1340,21 +1266,22 @@ void ComponentLifecycle_set_lifecycle_after_trigger() { static int dummy_dtor_invoked = 0; typedef struct Dummy { + ecs_world_t *world; + ecs_entity_t e; int value; } Dummy; static void dummy_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { + Dummy *d = ptr; + int i; for (i = 0; i < count; i ++) { - test_assert(ecs_is_valid(world, entity_ptr[i])); - test_assert(ecs_is_alive(world, entity_ptr[i])); + test_assert(ecs_is_valid(d[i].world, d[i].e)); } dummy_dtor_invoked ++; @@ -1371,6 +1298,7 @@ void ComponentLifecycle_valid_entity_in_dtor_after_delete() { ecs_entity_t e = ecs_new(world, Dummy); test_assert(e != 0); + ecs_set(world, e, Dummy, {world, e, 0}); ecs_delete(world, e); test_assert(!ecs_is_valid(world, e)); @@ -1415,6 +1343,8 @@ void ComponentLifecycle_dtor_on_fini() { ecs_entity_t e = ecs_new(world, Dummy); test_assert(e != 0); + ecs_set(world, e, Dummy, {world, e}); + test_int(dummy_dtor_invoked, 0); ecs_fini(world); @@ -1424,16 +1354,17 @@ void ComponentLifecycle_dtor_on_fini() { static void type_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); - ecs_entity_t e = entity_ptr[0]; + Dummy *d = ptr; + + ecs_world_t *world = d->world; + ecs_entity_t e = d->e; + test_assert(world != NULL); test_assert(e != 0); ecs_type_t type = ecs_get_type(world, e); @@ -1445,10 +1376,14 @@ void type_dtor( } typedef struct { + ecs_world_t *world; ecs_entity_t e; + ecs_entity_t other; } Entity; typedef struct { + ecs_world_t *world; + ecs_entity_t e; char *str; } String; @@ -1457,25 +1392,24 @@ static int other_dtor_valid_entity; static void other_type_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); test_assert(ptr != NULL); - ecs_entity_t e = entity_ptr[0]; + Entity *comp = ptr; + ecs_world_t *world = comp->world; + ecs_entity_t e = comp->e; test_assert(e != 0); + test_assert(world != NULL); test_assert(ecs_is_valid(world, e)); - Entity *comp = ptr; - test_assert(comp->e != 0); + test_assert(comp->other != 0); - if (ecs_is_valid(world, comp->e)) { - ecs_type_t type = ecs_get_type(world, comp->e); + if (ecs_is_valid(world, comp->other)) { + ecs_type_t type = ecs_get_type(world, comp->other); test_assert(type != NULL); test_int(ecs_vector_count(type), 2); other_dtor_valid_entity ++; @@ -1489,33 +1423,31 @@ ECS_COMPONENT_DECLARE(Entity); static void other_comp_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); test_assert(ptr != NULL); Entity *comp = ptr; - ecs_entity_t e = entity_ptr[0]; + ecs_world_t *world = comp->world; + ecs_entity_t e = comp->e; test_assert(e != 0); test_assert(ecs_is_valid(world, e)); - test_assert(comp->e != 0); - - if (ecs_is_valid(world, comp->e)) { - if (ecs_has(world, comp->e, String)) { - const String *str_ptr = ecs_get(world, comp->e, String); + test_assert(comp->other != 0); + + if (ecs_is_valid(world, comp->other)) { + if (ecs_has(world, comp->other, String)) { + const String *str_ptr = ecs_get(world, comp->other, String); test_assert(str_ptr != NULL); test_assert(str_ptr->str != NULL); test_str(str_ptr->str, "Foo"); other_dtor_valid_entity ++; } else { - test_assert(ecs_get(world, comp->e, String) == NULL); + test_assert(ecs_get(world, comp->other, String) == NULL); } } @@ -1524,33 +1456,29 @@ void other_comp_dtor( static void other_delete_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); test_assert(ptr != NULL); Entity *comp = ptr; - ecs_entity_t e = entity_ptr[0]; + ecs_world_t *world = comp->world; + ecs_entity_t e = comp->e; test_assert(e != 0); test_assert(ecs_is_valid(world, e)); - test_assert(ecs_is_alive(world, e)); - test_assert(comp->e != 0); + test_assert(comp->other != 0); - if (ecs_is_valid(world, comp->e)) { - ecs_delete(world, comp->e); + if (ecs_is_valid(world, comp->other)) { + ecs_delete(world, comp->other); other_dtor_valid_entity ++; test_assert(ecs_is_valid(world, e)); - test_assert(entity_ptr[0] == e); test_assert(ecs_get(world, e, Entity) == comp); - test_assert(ecs_is_valid(world, comp->e)); + test_assert(ecs_is_valid(world, comp->other)); } other_dtor_invoked ++; @@ -1558,17 +1486,17 @@ void other_delete_dtor( static void self_delete_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); test_assert(ptr != NULL); - ecs_entity_t e = entity_ptr[0]; + Dummy *d = ptr; + ecs_world_t *world = d->world; + ecs_entity_t e = d->e; + test_assert(world != 0); test_assert(e != 0); if (ecs_is_valid(world, e)) { @@ -1583,18 +1511,16 @@ void self_delete_dtor( static void string_dtor( - ecs_world_t *world, - const ecs_entity_t *entity_ptr, void *ptr, int32_t count, const ecs_type_info_t *info) { test_int(count, 1); - test_assert(entity_ptr != NULL); test_assert(ptr != NULL); String *comp = ptr; - ecs_entity_t e = entity_ptr[0]; + ecs_world_t *world = comp->world; + ecs_entity_t e = comp->e; test_assert(e != 0); test_assert(ecs_is_valid(world, e)); @@ -1615,6 +1541,7 @@ void ComponentLifecycle_valid_type_in_dtor_on_fini() { ecs_entity_t e = ecs_new(world, Dummy); test_assert(e != 0); + ecs_set(world, e, Dummy, {world, e}); ecs_add(world, e, Position); ecs_add(world, e, Velocity); @@ -1638,14 +1565,14 @@ void ComponentLifecycle_valid_other_type_of_entity_in_dtor_on_fini() { ecs_entity_t e1 = ecs_new_id(world); ecs_entity_t e2 = ecs_new(world, Position); - ecs_set(world, e2, Entity, {e1}); + ecs_set(world, e2, Entity, {world, e2, e1}); ecs_add(world, e1, Velocity); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e1, Entity, {world, e1, e2}); test_int(other_dtor_invoked, 0); - ecs_fini(world); + ecs_fini(world); test_int(other_dtor_invoked, 2); test_int(other_dtor_valid_entity, 1); @@ -1668,11 +1595,11 @@ void ComponentLifecycle_valid_same_type_comp_of_entity_in_dtor_on_fini() { ecs_entity_t e1 = ecs_new_id(world); ecs_entity_t e2 = ecs_new_id(world); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1704,11 +1631,11 @@ void ComponentLifecycle_valid_same_type_comp_of_entity_in_dtor_on_delete_parent( ecs_add_pair(world, e1, EcsChildOf, parent); ecs_add_pair(world, e2, EcsChildOf, parent); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1737,11 +1664,11 @@ void ComponentLifecycle_delete_in_dtor_same_type_on_fini() { ecs_entity_t e1 = ecs_new_id(world); ecs_entity_t e2 = ecs_new_id(world); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1770,11 +1697,11 @@ void ComponentLifecycle_delete_in_dtor_other_type_on_fini() { ecs_entity_t e1 = ecs_new(world, Position); ecs_entity_t e2 = ecs_new(world, Velocity); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1793,9 +1720,13 @@ void ComponentLifecycle_delete_self_in_dtor_on_fini() { .dtor = self_delete_dtor }); - ecs_new(world, Dummy); - ecs_new(world, Dummy); - ecs_new(world, Dummy); + ecs_entity_t e1 = ecs_new(world, Dummy); + ecs_entity_t e2 = ecs_new(world, Dummy); + ecs_entity_t e3 = ecs_new(world, Dummy); + + ecs_set(world, e1, Dummy, {world, e1}); + ecs_set(world, e2, Dummy, {world, e2}); + ecs_set(world, e3, Dummy, {world, e3}); test_int(dummy_dtor_invoked, 0); @@ -1826,11 +1757,11 @@ void ComponentLifecycle_delete_in_dtor_same_type_on_delete_parent() { ecs_add_pair(world, e1, EcsChildOf, parent); ecs_add_pair(world, e2, EcsChildOf, parent); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1869,11 +1800,11 @@ void ComponentLifecycle_delete_in_dtor_other_type_on_delete_parent() { ecs_add_pair(world, e1, EcsChildOf, parent); ecs_add_pair(world, e2, EcsChildOf, parent); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1903,6 +1834,10 @@ void ComponentLifecycle_delete_self_in_dtor_on_delete_parent() { ecs_entity_t e2 = ecs_new(world, Dummy); ecs_entity_t e3 = ecs_new(world, Dummy); + ecs_set(world, e1, Dummy, {world, e1}); + ecs_set(world, e2, Dummy, {world, e2}); + ecs_set(world, e3, Dummy, {world, e3}); + ecs_add_pair(world, e1, EcsChildOf, parent); ecs_add_pair(world, e2, EcsChildOf, parent); ecs_add_pair(world, e3, EcsChildOf, parent); @@ -1938,13 +1873,13 @@ void ComponentLifecycle_delete_in_dtor_same_type_on_delete() { ecs_entity_t e2 = ecs_new_id(world); ecs_entity_t e3 = ecs_new_id(world); - ecs_set(world, e1, Entity, {e2}); - ecs_set(world, e2, Entity, {e3}); - ecs_set(world, e3, Entity, {e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); + ecs_set(world, e2, Entity, {world, e2, e3}); + ecs_set(world, e3, Entity, {world, e3, e1}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e3, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); + ecs_set(world, e3, String, {world, e3, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -1981,11 +1916,11 @@ void ComponentLifecycle_delete_in_dtor_other_type_on_delete() { ecs_entity_t e1 = ecs_new(world, Position); ecs_entity_t e2 = ecs_new(world, Velocity); - ecs_set(world, e2, Entity, {e1}); - ecs_set(world, e1, Entity, {e2}); + ecs_set(world, e2, Entity, {world, e2, e1}); + ecs_set(world, e1, Entity, {world, e1, e2}); - ecs_set(world, e1, String, {ecs_os_strdup("Foo")}); - ecs_set(world, e2, String, {ecs_os_strdup("Foo")}); + ecs_set(world, e1, String, {world, e1, ecs_os_strdup("Foo")}); + ecs_set(world, e2, String, {world, e2, ecs_os_strdup("Foo")}); test_int(other_dtor_invoked, 0); @@ -2011,6 +1946,10 @@ void ComponentLifecycle_delete_self_in_dtor_on_delete() { ecs_entity_t e2 = ecs_new(world, Dummy); ecs_entity_t e3 = ecs_new(world, Dummy); + ecs_set(world, e1, Dummy, {world, e1}); + ecs_set(world, e2, Dummy, {world, e2}); + ecs_set(world, e3, Dummy, {world, e3}); + test_int(dummy_dtor_invoked, 0); ecs_delete(world, e1); @@ -2066,3 +2005,164 @@ void ComponentLifecycle_on_set_after_set() { ecs_fini(world); } + +static int on_add_position = 0; + +static void ecs_on_add(Position)(ecs_iter_t *it) { + test_assert(it->count >= 1); + test_assert(it->event == EcsOnAdd); + + Position *p = ecs_term(it, Position, 1); + for (int i = 0; i < it->count; i ++) { + on_add_position ++; + test_int(p[i].x, 0); + test_int(p[i].y, 0); + } +} + +void ComponentLifecycle_on_add_after_new() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .ctor = ecs_default_ctor, + .on_add = ecs_on_add(Position) + }); + + ecs_new(world, Position); + test_int(on_add_position, 1); + ecs_new(world, Position); + test_int(on_add_position, 2); + ecs_new(world, Position); + test_int(on_add_position, 3); + + ecs_fini(world); +} + +void ComponentLifecycle_on_add_after_add() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .ctor = ecs_default_ctor, + .on_add = ecs_on_add(Position) + }); + + ecs_entity_t e1 = ecs_new_id(world); + ecs_entity_t e2 = ecs_new_id(world); + ecs_entity_t e3 = ecs_new_id(world); + + ecs_add(world, e1, Position); + test_int(on_add_position, 1); + ecs_add(world, e2, Position); + test_int(on_add_position, 2); + ecs_add(world, e3, Position); + test_int(on_add_position, 3); + + ecs_fini(world); +} + +void ComponentLifecycle_on_add_after_set() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .ctor = ecs_default_ctor, + .on_add = ecs_on_add(Position) + }); + + ecs_set(world, 0, Position, {10, 20}); + test_int(on_add_position, 1); + ecs_set(world, 0, Position, {10, 20}); + test_int(on_add_position, 2); + ecs_set(world, 0, Position, {10, 20}); + test_int(on_add_position, 3); + + ecs_fini(world); +} + +static int on_remove_position = 0; + +static void ecs_on_remove(Position)(ecs_iter_t *it) { + test_assert(it->count >= 1); + test_assert(it->event == EcsOnRemove); + + Position *p = ecs_term(it, Position, 1); + for (int i = 0; i < it->count; i ++) { + on_remove_position ++; + test_int(p[i].x, 10); + test_int(p[i].y, 20); + } +} + +void ComponentLifecycle_on_remove_after_remove() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .on_remove = ecs_on_remove(Position) + }); + + ecs_entity_t e1 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e2 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e3 = ecs_set(world, 0, Position, {10, 20}); + + ecs_remove(world, e1, Position); + test_int(on_remove_position, 1); + ecs_remove(world, e2, Position); + test_int(on_remove_position, 2); + ecs_remove(world, e3, Position); + test_int(on_remove_position, 3); + + ecs_fini(world); +} + +void ComponentLifecycle_on_remove_after_clear() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .on_remove = ecs_on_remove(Position) + }); + + ecs_entity_t e1 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e2 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e3 = ecs_set(world, 0, Position, {10, 20}); + + ecs_clear(world, e1); + test_int(on_remove_position, 1); + ecs_clear(world, e2); + test_int(on_remove_position, 2); + ecs_clear(world, e3); + test_int(on_remove_position, 3); + + ecs_fini(world); +} + +void ComponentLifecycle_on_remove_after_delete() { + ecs_world_t *world = ecs_init(); + + ECS_COMPONENT(world, Position); + + ecs_set_component_actions(world, Position, { + .on_remove = ecs_on_remove(Position) + }); + + ecs_entity_t e1 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e2 = ecs_set(world, 0, Position, {10, 20}); + ecs_entity_t e3 = ecs_set(world, 0, Position, {10, 20}); + + ecs_delete(world, e1); + test_int(on_remove_position, 1); + ecs_delete(world, e2); + test_int(on_remove_position, 2); + ecs_delete(world, e3); + test_int(on_remove_position, 3); + + ecs_fini(world); +} diff --git a/test/api/src/Reference.c b/test/api/src/Reference.c index 4068ebad48..334fca3ca7 100644 --- a/test/api/src/Reference.c +++ b/test/api/src/Reference.c @@ -219,18 +219,9 @@ void Reference_get_nonexisting() { ecs_fini(world); } -static -void comp_move( - ecs_world_t *world, - const ecs_entity_t *dst_entity, - const ecs_entity_t *src_entity, - void *dst_ptr, - void *src_ptr, - int32_t count, - const ecs_type_info_t *ti) -{ - memcpy(dst_ptr, src_ptr, ti->size * count); -} +static ECS_MOVE(Position, dst, src, { + ecs_os_memcpy_t(dst, src, Position); +}) void Reference_get_ref_after_realloc_w_lifecycle() { ecs_world_t *world = ecs_init(); @@ -238,7 +229,7 @@ void Reference_get_ref_after_realloc_w_lifecycle() { ECS_COMPONENT(world, Position); ecs_set(world, ecs_id(Position), EcsComponentLifecycle, { - .move = comp_move + .move = ecs_move(Position) }); ECS_ENTITY(world, e, Position); diff --git a/test/api/src/main.c b/test/api/src/main.c index 4296c90331..c3225d8d1b 100644 --- a/test/api/src/main.c +++ b/test/api/src/main.c @@ -661,6 +661,12 @@ void ComponentLifecycle_delete_in_dtor_same_type_on_delete(void); void ComponentLifecycle_delete_in_dtor_other_type_on_delete(void); void ComponentLifecycle_delete_self_in_dtor_on_delete(void); void ComponentLifecycle_on_set_after_set(void); +void ComponentLifecycle_on_add_after_new(void); +void ComponentLifecycle_on_add_after_add(void); +void ComponentLifecycle_on_add_after_set(void); +void ComponentLifecycle_on_remove_after_remove(void); +void ComponentLifecycle_on_remove_after_clear(void); +void ComponentLifecycle_on_remove_after_delete(void); // Testsuite 'Sorting' void Sorting_sort_by_component(void); @@ -4150,6 +4156,30 @@ bake_test_case ComponentLifecycle_testcases[] = { { "on_set_after_set", ComponentLifecycle_on_set_after_set + }, + { + "on_add_after_new", + ComponentLifecycle_on_add_after_new + }, + { + "on_add_after_add", + ComponentLifecycle_on_add_after_add + }, + { + "on_add_after_set", + ComponentLifecycle_on_add_after_set + }, + { + "on_remove_after_remove", + ComponentLifecycle_on_remove_after_remove + }, + { + "on_remove_after_clear", + ComponentLifecycle_on_remove_after_clear + }, + { + "on_remove_after_delete", + ComponentLifecycle_on_remove_after_delete } }; @@ -8188,7 +8218,7 @@ static bake_test_suite suites[] = { "ComponentLifecycle", ComponentLifecycle_setup, NULL, - 50, + 56, ComponentLifecycle_testcases }, { diff --git a/test/cpp_api/project.json b/test/cpp_api/project.json index 3720ffaffc..82d5643fb5 100644 --- a/test/cpp_api/project.json +++ b/test/cpp_api/project.json @@ -731,10 +731,7 @@ "no_copy", "no_move", "no_dtor", - "flecs_ctor", - "flecs_ctor_w_default_ctor", "default_ctor_w_value_ctor", - "flecs_ctor_w_value_ctor", "no_default_ctor_move_ctor_on_set", "emplace_w_ctor", "emplace_no_default_ctor", diff --git a/test/cpp_api/src/ComponentLifecycle.cpp b/test/cpp_api/src/ComponentLifecycle.cpp index a350917bb2..8a15d2b6d4 100644 --- a/test/cpp_api/src/ComponentLifecycle.cpp +++ b/test/cpp_api/src/ComponentLifecycle.cpp @@ -350,8 +350,7 @@ void ComponentLifecycle_implicit_after_query() { test_int(Pod::move_invoked, 0); } -template ::value, void>::type* = nullptr> +template static void try_add(flecs::world& ecs) { flecs::entity e = ecs.entity().add(); @@ -364,20 +363,6 @@ static void try_add(flecs::world& ecs) { test_assert(!e.has()); } -template ::value, void>::type* = nullptr> -static void try_add(flecs::world& ecs) { - flecs::entity e = ecs.entity().add(); - test_assert(e.has()); - - const T *ptr = e.get(); - test_int(ptr->x_, 89); - test_int(ptr->e_, e); - - e.remove(); - test_assert(!e.has()); -} - template static void try_add_relation(flecs::world& ecs) { flecs::entity obj = ecs.entity(); @@ -406,25 +391,12 @@ static void try_add_w_object(flecs::world& ecs) { test_assert(!e.has()); } -template ::value, void>::type* = nullptr> -static void try_set(flecs::world& ecs) { - flecs::entity e = ecs.entity().set({10}); - - const T *ptr = e.get(); - test_int(ptr->x_, 10); -} - -template ::value, void>::type* = nullptr> +template static void try_set(flecs::world& ecs) { flecs::entity e = ecs.entity().set({10}); const T *ptr = e.get(); test_int(ptr->x_, 10); - test_int(ptr->e_, 0); - - e.remove(); } template @@ -435,25 +407,12 @@ static void try_emplace(flecs::world& ecs) { test_int(ptr->x_, 10); } -template ::value, void>::type* = nullptr> -static void try_set_default(flecs::world& ecs) { - flecs::entity e = ecs.entity().set(T()); - - const T *ptr = e.get(); - test_int(ptr->x_, 99); - - e.remove(); -} - -template ::value, void>::type* = nullptr> +template static void try_set_default(flecs::world& ecs) { flecs::entity e = ecs.entity().set(T()); const T *ptr = e.get(); test_int(ptr->x_, 99); - test_int(ptr->e_, 0); e.remove(); } @@ -604,24 +563,6 @@ void ComponentLifecycle_no_dtor() { ecs.component(); } -void ComponentLifecycle_flecs_ctor() { - flecs::world ecs; - - ecs.component(); - - try_add(ecs); -} - -void ComponentLifecycle_flecs_ctor_w_default_ctor() { - flecs::world ecs; - - ecs.component(); - - try_add(ecs); - - try_set_default(ecs); -} - void ComponentLifecycle_default_ctor_w_value_ctor() { flecs::world ecs; @@ -634,16 +575,6 @@ void ComponentLifecycle_default_ctor_w_value_ctor() { try_set_default(ecs); } -void ComponentLifecycle_flecs_ctor_w_value_ctor() { - flecs::world ecs; - - ecs.component(); - - try_add(ecs); - - try_set(ecs); -} - void ComponentLifecycle_no_default_ctor_move_ctor_on_set() { flecs::world ecs; diff --git a/test/cpp_api/src/main.cpp b/test/cpp_api/src/main.cpp index a0ccc33b03..94f46604b0 100644 --- a/test/cpp_api/src/main.cpp +++ b/test/cpp_api/src/main.cpp @@ -691,10 +691,7 @@ void ComponentLifecycle_no_move_assign(void); void ComponentLifecycle_no_copy(void); void ComponentLifecycle_no_move(void); void ComponentLifecycle_no_dtor(void); -void ComponentLifecycle_flecs_ctor(void); -void ComponentLifecycle_flecs_ctor_w_default_ctor(void); void ComponentLifecycle_default_ctor_w_value_ctor(void); -void ComponentLifecycle_flecs_ctor_w_value_ctor(void); void ComponentLifecycle_no_default_ctor_move_ctor_on_set(void); void ComponentLifecycle_emplace_w_ctor(void); void ComponentLifecycle_emplace_no_default_ctor(void); @@ -3535,22 +3532,10 @@ bake_test_case ComponentLifecycle_testcases[] = { "no_dtor", ComponentLifecycle_no_dtor }, - { - "flecs_ctor", - ComponentLifecycle_flecs_ctor - }, - { - "flecs_ctor_w_default_ctor", - ComponentLifecycle_flecs_ctor_w_default_ctor - }, { "default_ctor_w_value_ctor", ComponentLifecycle_default_ctor_w_value_ctor }, - { - "flecs_ctor_w_value_ctor", - ComponentLifecycle_flecs_ctor_w_value_ctor - }, { "no_default_ctor_move_ctor_on_set", ComponentLifecycle_no_default_ctor_move_ctor_on_set @@ -4408,7 +4393,7 @@ static bake_test_suite suites[] = { "ComponentLifecycle", NULL, NULL, - 43, + 40, ComponentLifecycle_testcases }, {