code: update flecs & rework vehicle enter/leave states

isolation_bkp/dynres
Dominik Madarász 2021-08-11 10:45:23 +02:00
parent 275cdc65ab
commit 9b829074d4
11 changed files with 23307 additions and 13716 deletions

View File

@ -19,8 +19,7 @@ uint64_t player_spawn(char *name) {
name = zpl_bprintf("player_%d", e); name = zpl_bprintf("player_%d", e);
} }
ecs_set(world_ecs(), e, EcsName, {.alloc_value = name }); ecs_set_name(world_ecs(), e, name);
ecs_add(world_ecs(), e, EcsClient);
ecs_set(world_ecs(), e, ClientInfo, {0}); ecs_set(world_ecs(), e, ClientInfo, {0});
ecs_set(world_ecs(), e, Input, {0}); ecs_set(world_ecs(), e, Input, {0});
ecs_set(world_ecs(), e, Health, {.hp = PLAYER_MAX_HP, .max_hp = PLAYER_MAX_HP}); ecs_set(world_ecs(), e, Health, {.hp = PLAYER_MAX_HP, .max_hp = PLAYER_MAX_HP});

View File

@ -10,14 +10,13 @@ ECS_COMPONENT_DECLARE(ClientInfo);
ECS_COMPONENT_DECLARE(Health); ECS_COMPONENT_DECLARE(Health);
ECS_COMPONENT_DECLARE(Classify); ECS_COMPONENT_DECLARE(Classify);
ECS_COMPONENT_DECLARE(Vehicle); ECS_COMPONENT_DECLARE(Vehicle);
ECS_COMPONENT_DECLARE(IsInVehicle);
ECS_TAG_DECLARE(EcsActor); ECS_TAG_DECLARE(EcsActor);
ECS_TAG_DECLARE(EcsDemoNPC); ECS_TAG_DECLARE(EcsDemoNPC);
ECS_TAG_DECLARE(EcsInVehicle);
ECS_TYPE_DECLARE(Player); ECS_TYPE_DECLARE(Player);
ECS_TYPE_DECLARE(Movement); ECS_TYPE_DECLARE(Movement);
ECS_TYPE_DECLARE(Walking); ECS_TYPE_DECLARE(Walking);
ECS_TYPE_DECLARE(Flying); ECS_TYPE_DECLARE(Flying);
ECS_TYPE_DECLARE(EcsClient);
void ComponentsImport(ecs_world_t *ecs) { void ComponentsImport(ecs_world_t *ecs) {
ECS_MODULE(ecs, Components); ECS_MODULE(ecs, Components);
@ -34,13 +33,13 @@ void ComponentsImport(ecs_world_t *ecs) {
ECS_META_DEFINE(ecs, Classify); ECS_META_DEFINE(ecs, Classify);
ECS_META_DEFINE(ecs, Vehicle); ECS_META_DEFINE(ecs, Vehicle);
ECS_COMPONENT_DEFINE(ecs, IsInVehicle);
ECS_TAG_DEFINE(ecs, Walking); ECS_TAG_DEFINE(ecs, Walking);
ECS_TAG_DEFINE(ecs, Flying); ECS_TAG_DEFINE(ecs, Flying);
ECS_TAG_DEFINE(ecs, EcsClient);
ECS_TAG_DEFINE(ecs, EcsActor); ECS_TAG_DEFINE(ecs, EcsActor);
ECS_TAG_DEFINE(ecs, EcsDemoNPC); ECS_TAG_DEFINE(ecs, EcsDemoNPC);
ECS_TAG_DEFINE(ecs, EcsInVehicle);
ECS_PREFAB(ecs, Base, Position, Velocity, Input, EcsActor); ECS_PREFAB(ecs, Base, Position, Velocity, Input, EcsActor);
ECS_TYPE_DEFINE(ecs, Movement, Walking, Flying); ECS_TYPE_DEFINE(ecs, Movement, Walking, Flying);
@ -55,11 +54,10 @@ void ComponentsImport(ecs_world_t *ecs) {
ECS_SET_COMPONENT(Health); ECS_SET_COMPONENT(Health);
ECS_SET_COMPONENT(Classify); ECS_SET_COMPONENT(Classify);
ECS_SET_COMPONENT(Vehicle); ECS_SET_COMPONENT(Vehicle);
ECS_SET_ENTITY(EcsClient); ECS_SET_COMPONENT(IsInVehicle);
ECS_SET_ENTITY(Walking); ECS_SET_ENTITY(Walking);
ECS_SET_ENTITY(Flying); ECS_SET_ENTITY(Flying);
ECS_SET_ENTITY(EcsActor); ECS_SET_ENTITY(EcsActor);
ECS_SET_ENTITY(EcsDemoNPC); ECS_SET_ENTITY(EcsDemoNPC);
ECS_SET_ENTITY(EcsInVehicle);
ECS_SET_TYPE(Movement); ECS_SET_TYPE(Movement);
} }

View File

@ -41,8 +41,6 @@ ECS_STRUCT(Input, {
uint8_t use; uint8_t use;
uint8_t sprint; uint8_t sprint;
uint8_t is_blocked; uint8_t is_blocked;
ecs_entity_t parent;
}); });
ECS_STRUCT(ClientInfo, { ECS_STRUCT(ClientInfo, {
@ -72,6 +70,10 @@ ECS_STRUCT(Vehicle, {
float wheel_base; float wheel_base;
}); });
typedef struct {
ecs_entity_t veh;
} IsInVehicle;
ECS_COMPONENT_EXTERN(Chunk); ECS_COMPONENT_EXTERN(Chunk);
ECS_COMPONENT_EXTERN(Position); ECS_COMPONENT_EXTERN(Position);
ECS_COMPONENT_EXTERN(Vector2D); ECS_COMPONENT_EXTERN(Vector2D);
@ -82,9 +84,9 @@ ECS_COMPONENT_EXTERN(ClientInfo);
ECS_COMPONENT_EXTERN(Health); ECS_COMPONENT_EXTERN(Health);
ECS_COMPONENT_EXTERN(Classify); ECS_COMPONENT_EXTERN(Classify);
ECS_COMPONENT_EXTERN(Vehicle); ECS_COMPONENT_EXTERN(Vehicle);
ECS_COMPONENT_EXTERN(IsInVehicle);
ECS_TAG_EXTERN(EcsActor); ECS_TAG_EXTERN(EcsActor);
ECS_TAG_EXTERN(EcsDemoNPC); ECS_TAG_EXTERN(EcsDemoNPC);
ECS_TAG_EXTERN(EcsInVehicle);
ECS_TYPE_EXTERN(Player); ECS_TYPE_EXTERN(Player);
ECS_TYPE_EXTERN(Movement); ECS_TYPE_EXTERN(Movement);
ECS_TYPE_EXTERN(Walking); ECS_TYPE_EXTERN(Walking);
@ -102,15 +104,14 @@ typedef struct {
ECS_DECLARE_COMPONENT(Health); ECS_DECLARE_COMPONENT(Health);
ECS_DECLARE_COMPONENT(Classify); ECS_DECLARE_COMPONENT(Classify);
ECS_DECLARE_COMPONENT(Vehicle); ECS_DECLARE_COMPONENT(Vehicle);
ECS_DECLARE_COMPONENT(IsInVehicle);
ECS_DECLARE_ENTITY(EcsActor); ECS_DECLARE_ENTITY(EcsActor);
ECS_DECLARE_ENTITY(EcsDemoNPC); ECS_DECLARE_ENTITY(EcsDemoNPC);
ECS_DECLARE_ENTITY(EcsInVehicle);
ECS_DECLARE_TYPE(Player); ECS_DECLARE_TYPE(Player);
ECS_DECLARE_TYPE(Builder); ECS_DECLARE_TYPE(Builder);
ECS_DECLARE_TYPE(Movement); ECS_DECLARE_TYPE(Movement);
ECS_DECLARE_ENTITY(Walking); ECS_DECLARE_ENTITY(Walking);
ECS_DECLARE_ENTITY(Flying); ECS_DECLARE_ENTITY(Flying);
ECS_DECLARE_ENTITY(EcsClient);
} Components; } Components;
#define ComponentsImportHandles(handles)\ #define ComponentsImportHandles(handles)\
@ -124,6 +125,7 @@ ECS_IMPORT_COMPONENT(handles, ClientInfo);\
ECS_IMPORT_COMPONENT(handles, Health);\ ECS_IMPORT_COMPONENT(handles, Health);\
ECS_IMPORT_COMPONENT(handles, Classify);\ ECS_IMPORT_COMPONENT(handles, Classify);\
ECS_IMPORT_COMPONENT(handles, Vehicle);\ ECS_IMPORT_COMPONENT(handles, Vehicle);\
ECS_IMPORT_COMPONENT(handles, IsInVehicle);\
ECS_IMPORT_TYPE(handles, Player);\ ECS_IMPORT_TYPE(handles, Player);\
ECS_IMPORT_TYPE(handles, Builder);\ ECS_IMPORT_TYPE(handles, Builder);\
ECS_IMPORT_TYPE(handles, Movement);\ ECS_IMPORT_TYPE(handles, Movement);\
@ -131,7 +133,5 @@ ECS_IMPORT_ENTITY(handles, EcsActor);\
ECS_IMPORT_ENTITY(handles, EcsDemoNPC);\ ECS_IMPORT_ENTITY(handles, EcsDemoNPC);\
ECS_IMPORT_ENTITY(handles, Walking);\ ECS_IMPORT_ENTITY(handles, Walking);\
ECS_IMPORT_ENTITY(handles, Flying);\ ECS_IMPORT_ENTITY(handles, Flying);\
ECS_IMPORT_ENTITY(handles, EcsClient);\
ECS_IMPORT_ENTITY(handles, EcsInVehicle);\
void ComponentsImport(ecs_world_t *ecs); void ComponentsImport(ecs_world_t *ecs);

View File

@ -102,10 +102,11 @@ void RegenerateHP(ecs_iter_t *it) {
void SystemsImport(ecs_world_t *ecs) { void SystemsImport(ecs_world_t *ecs) {
ECS_MODULE(ecs, Systems); ECS_MODULE(ecs, Systems);
ECS_SYSTEM(ecs, MovementImpulse, EcsOnLoad, components.Input, components.Velocity); ECS_SYSTEM(ecs, MovementImpulse, EcsOnLoad, components.Input, components.Velocity, !components.IsInVehicle);
//ECS_SYSTEM(ecs, DemoPlaceIceBlock, EcsOnLoad, components.Input, components.Position); //ECS_SYSTEM(ecs, DemoPlaceIceBlock, EcsOnLoad, components.Input, components.Position);
ECS_SYSTEM(ecs, DemoNPCMoveAround, EcsOnLoad, components.Velocity, components.EcsDemoNPC); ECS_SYSTEM(ecs, DemoNPCMoveAround, EcsOnLoad, components.Velocity, components.EcsDemoNPC);
ECS_SYSTEM(ecs, EnterOrLeaveVehicle, EcsOnLoad, components.Input, components.Position); ECS_SYSTEM(ecs, EnterVehicle, EcsOnLoad, components.Input, components.Position, !components.IsInVehicle);
ECS_SYSTEM(ecs, LeaveVehicle, EcsOnLoad, components.Input, components.IsInVehicle);
ECS_SYSTEM(ecs, MoveWalk, EcsOnUpdate, components.Position, components.Velocity); ECS_SYSTEM(ecs, MoveWalk, EcsOnUpdate, components.Position, components.Velocity);
ECS_SYSTEM(ecs, HurtOnHazardBlock, EcsOnUpdate, components.Position, components.Health); ECS_SYSTEM(ecs, HurtOnHazardBlock, EcsOnUpdate, components.Position, components.Health);

View File

@ -19,7 +19,6 @@ void MovementImpulse(ecs_iter_t *it) {
Velocity *v = ecs_column(it, Velocity, 2); Velocity *v = ecs_column(it, Velocity, 2);
for (int i = 0; i < it->count; i++) { for (int i = 0; i < it->count; i++) {
if (world_entity_valid(in[i].parent)) continue;
double speed = PLR_MOVE_SPEED * (in[i].sprint ? PLR_MOVE_SPEED_MULT : 1.0); double speed = PLR_MOVE_SPEED * (in[i].sprint ? PLR_MOVE_SPEED_MULT : 1.0);
if (zpl_abs(v[i].x) < speed && in[i].x) if (zpl_abs(v[i].x) < speed && in[i].x)
v[i].x = in[i].x*speed; v[i].x = in[i].x*speed;

View File

@ -1,7 +1,31 @@
#define VEH_ENTER_RADIUS 45.0f #define VEH_ENTER_RADIUS 45.0f
void EnterOrLeaveVehicle(ecs_iter_t *it) { void LeaveVehicle(ecs_iter_t *it) {
Input *in = ecs_column(it, Input, 1);
IsInVehicle *vehp = ecs_column(it, IsInVehicle, 2);
for (int i = 0; i < it->count; i++) {
if (!in[i].use) continue;
in[i].use = false;
Vehicle *veh = 0;
if ((veh = ecs_get_mut_if(it->world, vehp->veh, Vehicle))) {
for (int k = 0; k < 4; k++) {
if (veh->seats[k] == it->entities[i]) {
veh->seats[k] = 0;
break;
}
}
ecs_remove(it->world, it->entities[i], IsInVehicle);
} else {
ZPL_PANIC("unreachable code");
}
}
}
void EnterVehicle(ecs_iter_t *it) {
Input *in = ecs_column(it, Input, 1); Input *in = ecs_column(it, Input, 1);
Position *p = ecs_column(it, Position, 2); Position *p = ecs_column(it, Position, 2);
@ -9,14 +33,13 @@ void EnterOrLeaveVehicle(ecs_iter_t *it) {
if (!in[i].use) continue; if (!in[i].use) continue;
in[i].use = false; in[i].use = false;
if (!world_entity_valid(in[i].parent)) {
size_t ents_count; size_t ents_count;
int64_t *ents = world_chunk_query_entities(it->entities[i], &ents_count, 2); int64_t *ents = world_chunk_query_entities(it->entities[i], &ents_count, 2);
for (size_t j = 0; j < ents_count; j++) { for (size_t j = 0; j < ents_count; j++) {
Vehicle *veh = 0; Vehicle *veh = 0;
if ((veh = ecs_get_mut_if(world_ecs(), ents[j], Vehicle))) { if ((veh = ecs_get_mut_if(it->world, ents[j], Vehicle))) {
Position const* p2 = ecs_get(world_ecs(), ents[j], Position); Position const* p2 = ecs_get(it->world, ents[j], Position);
float dx = p2->x - p[i].x; float dx = p2->x - p[i].x;
float dy = p2->y - p[i].y; float dy = p2->y - p[i].y;
@ -27,28 +50,15 @@ void EnterOrLeaveVehicle(ecs_iter_t *it) {
// NOTE(zaklaus): We can enter the vehicle, yay! // NOTE(zaklaus): We can enter the vehicle, yay!
veh->seats[k] = it->entities[i]; veh->seats[k] = it->entities[i];
in[i].parent = ents[j]; ecs_set(it->world, it->entities[i], IsInVehicle, {
.veh = ents[j]
});
p[i] = *p2; p[i] = *p2;
break; break;
} }
} }
} }
} }
} else {
Vehicle *veh = 0;
if ((veh = ecs_get_mut_if(world_ecs(), in[i].parent, Vehicle))) {
for (int k = 0; k < 4; k++) {
if (veh->seats[k] == it->entities[i]) {
veh->seats[k] = 0;
break;
}
}
in[i].parent = 0;
} else {
ZPL_PANIC("unreachable code");
}
}
} }
} }
@ -81,15 +91,15 @@ void VehicleHandling(ecs_iter_t *it) {
// NOTE(zaklaus): Update passenger position // NOTE(zaklaus): Update passenger position
{ {
Position *p2 = ecs_get_mut(world_ecs(), pe, Position, NULL); Position *p2 = ecs_get_mut(it->world, pe, Position, NULL);
Velocity *v2 = ecs_get_mut(world_ecs(), pe, Velocity, NULL); Velocity *v2 = ecs_get_mut(it->world, pe, Velocity, NULL);
*p2 = p[i]; *p2 = p[i];
*v2 = v[i]; *v2 = v[i];
} }
// NOTE(zaklaus): Handle driver input // NOTE(zaklaus): Handle driver input
if (j == 0) { if (j == 0) {
Input const* in = ecs_get(world_ecs(), pe, Input); Input const* in = ecs_get(it->world, pe, Input);
car->force += zpl_lerp(0.0f, in->y * VEHICLE_FORCE, VEHICLE_ACCEL); car->force += zpl_lerp(0.0f, in->y * VEHICLE_FORCE, VEHICLE_ACCEL);
car->steer += in->x * -VEHICLE_STEER; car->steer += in->x * -VEHICLE_STEER;

View File

@ -2,16 +2,9 @@ use_cxx11()
file(GLOB SRCS *.h file(GLOB SRCS *.h
flecs.c flecs.c
flecs_json.c
flecs_meta.c flecs_meta.c
flecs_rest.c
flecs_player.c
flecs_rest.c
flecs_systems_civetweb.c
flecs_dash.c
flecs_monitor.c
flecs-os_api-stdcpp.cpp flecs-os_api-stdcpp.cpp
flecs_components_http.c
) )
add_library(flecs-bundle STATIC ${SRCS}) add_library(flecs-bundle STATIC ${SRCS})

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -60,6 +60,35 @@ void ecs_meta_parse_params(
ecs_meta_params_t *token_out, ecs_meta_params_t *token_out,
ecs_meta_parse_ctx_t *ctx); ecs_meta_parse_ctx_t *ctx);
#endif
#ifndef FLECS_META_SERIALIZER_H
#define FLECS_META_SERIALIZER_H
void EcsAddStruct(
ecs_iter_t *it);
void EcsSetPrimitive(
ecs_iter_t *it);
void EcsSetEnum(
ecs_iter_t *it);
void EcsSetBitmask(
ecs_iter_t *it);
void EcsSetStruct(
ecs_iter_t *it);
void EcsSetArray(
ecs_iter_t *it);
void EcsSetVector(
ecs_iter_t *it);
void EcsSetMap(
ecs_iter_t *it);
#endif #endif
static static
@ -67,8 +96,7 @@ ecs_vector_t* serialize_type(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
ecs_vector_t *ops, ecs_vector_t *ops,
int32_t offset, int32_t offset);
FlecsMeta *module);
static static
ecs_size_t ecs_get_primitive_size( ecs_size_t ecs_get_primitive_size(
@ -129,12 +157,10 @@ ecs_vector_t* serialize_primitive(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsPrimitive *type, const EcsPrimitive *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *module)
{ {
(void)world; (void)world;
(void)entity; (void)entity;
(void)module;
ecs_type_op_t *op; ecs_type_op_t *op;
if (!ops) { if (!ops) {
@ -164,13 +190,10 @@ ecs_vector_t* serialize_enum(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsEnum *type, const EcsEnum *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *module)
{ {
(void)type; (void)type;
FlecsMetaImportHandles(*module);
ecs_type_op_t *op; ecs_type_op_t *op;
if (!ops) { if (!ops) {
op = ecs_vector_add(&ops, ecs_type_op_t); op = ecs_vector_add(&ops, ecs_type_op_t);
@ -202,13 +225,10 @@ ecs_vector_t* serialize_bitmask(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsBitmask *type, const EcsBitmask *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *module)
{ {
(void)type; (void)type;
FlecsMetaImportHandles(*module);
ecs_type_op_t *op; ecs_type_op_t *op;
if (!ops) { if (!ops) {
op = ecs_vector_add(&ops, ecs_type_op_t); op = ecs_vector_add(&ops, ecs_type_op_t);
@ -241,11 +261,8 @@ ecs_vector_t* serialize_struct(
ecs_entity_t entity, ecs_entity_t entity,
const EcsStruct *type, const EcsStruct *type,
ecs_vector_t *ops, ecs_vector_t *ops,
int32_t offset, int32_t offset)
FlecsMeta *module)
{ {
FlecsMetaImportHandles(*module);
ecs_type_op_t *op_header = NULL; ecs_type_op_t *op_header = NULL;
if (!ops) { if (!ops) {
op_header = ecs_vector_add(&ops, ecs_type_op_t); op_header = ecs_vector_add(&ops, ecs_type_op_t);
@ -267,7 +284,7 @@ ecs_vector_t* serialize_struct(
for (i = 0; i < count; i ++) { for (i = 0; i < count; i ++) {
/* Add type operations of member to struct ops */ /* Add type operations of member to struct ops */
int32_t prev_count = ecs_vector_count(ops); int32_t prev_count = ecs_vector_count(ops);
ops = serialize_type(world, members[i].type, ops, offset + size, module); ops = serialize_type(world, members[i].type, ops, offset + size);
#ifndef NDEBUG #ifndef NDEBUG
int32_t op_count = ecs_vector_count(ops); int32_t op_count = ecs_vector_count(ops);
@ -281,7 +298,7 @@ ecs_vector_t* serialize_struct(
op->name = members[i].name; op->name = members[i].name;
const EcsMetaType *meta_type = ecs_get(world, members[i].type, EcsMetaType); const EcsMetaType *meta_type = ecs_get(world, members[i].type, EcsMetaType);
ecs_size_t member_size = meta_type->size * op->count; ecs_size_t member_size = meta_type->size * (meta_type->kind == EcsStructType ? 1 : op->count);
int16_t member_alignment = meta_type->alignment; int16_t member_alignment = meta_type->alignment;
ecs_assert(member_size != 0, ECS_INTERNAL_ERROR, op->name); ecs_assert(member_size != 0, ECS_INTERNAL_ERROR, op->name);
@ -367,7 +384,7 @@ ecs_vector_t* serialize_struct(
ecs_assert(op_push->kind == EcsOpPush, ECS_INTERNAL_ERROR, NULL); ecs_assert(op_push->kind == EcsOpPush, ECS_INTERNAL_ERROR, NULL);
op_push->size = size; op_push->size = size;
op_push->alignment = alignment; op_push->alignment = alignment;
op_push->count = 1; op_push->count = count;
return ops; return ops;
} }
@ -377,13 +394,10 @@ ecs_vector_t* serialize_array(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsArray *type, const EcsArray *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *handles)
{ {
(void)entity; (void)entity;
FlecsMetaImportHandles(*handles);
ecs_type_op_t *op_header = NULL; ecs_type_op_t *op_header = NULL;
if (!ops) { if (!ops) {
op_header = ecs_vector_add(&ops, ecs_type_op_t); op_header = ecs_vector_add(&ops, ecs_type_op_t);
@ -428,13 +442,10 @@ ecs_vector_t* serialize_vector(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsVector *type, const EcsVector *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *handles)
{ {
(void)entity; (void)entity;
FlecsMetaImportHandles(*handles);
ecs_type_op_t *op = NULL; ecs_type_op_t *op = NULL;
if (!ops) { if (!ops) {
op = ecs_vector_add(&ops, ecs_type_op_t); op = ecs_vector_add(&ops, ecs_type_op_t);
@ -468,11 +479,8 @@ ecs_vector_t* serialize_map(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
const EcsMap *type, const EcsMap *type,
ecs_vector_t *ops, ecs_vector_t *ops)
FlecsMeta *handles)
{ {
FlecsMetaImportHandles(*handles);
ecs_type_op_t *op = NULL; ecs_type_op_t *op = NULL;
if (!ops) { if (!ops) {
op = ecs_vector_add(&ops, ecs_type_op_t); op = ecs_vector_add(&ops, ecs_type_op_t);
@ -545,11 +553,8 @@ ecs_vector_t* serialize_type(
ecs_world_t *world, ecs_world_t *world,
ecs_entity_t entity, ecs_entity_t entity,
ecs_vector_t *ops, ecs_vector_t *ops,
int32_t offset, int32_t offset)
FlecsMeta *module)
{ {
FlecsMetaImportHandles(*module);
const EcsMetaType *type = ecs_get(world, entity, EcsMetaType); const EcsMetaType *type = ecs_get(world, entity, EcsMetaType);
ecs_assert(type != NULL, ECS_INVALID_PARAMETER, NULL); ecs_assert(type != NULL, ECS_INVALID_PARAMETER, NULL);
@ -557,43 +562,43 @@ ecs_vector_t* serialize_type(
case EcsPrimitiveType: { case EcsPrimitiveType: {
const EcsPrimitive *t = ecs_get(world, entity, EcsPrimitive); const EcsPrimitive *t = ecs_get(world, entity, EcsPrimitive);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_primitive(world, entity, t, ops, module); return serialize_primitive(world, entity, t, ops);
} }
case EcsEnumType: { case EcsEnumType: {
const EcsEnum *t = ecs_get(world, entity, EcsEnum); const EcsEnum *t = ecs_get(world, entity, EcsEnum);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_enum(world, entity, t, ops, module); return serialize_enum(world, entity, t, ops);
} }
case EcsBitmaskType: { case EcsBitmaskType: {
const EcsBitmask *t = ecs_get(world, entity, EcsBitmask); const EcsBitmask *t = ecs_get(world, entity, EcsBitmask);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_bitmask(world, entity, t, ops, module); return serialize_bitmask(world, entity, t, ops);
} }
case EcsStructType: { case EcsStructType: {
const EcsStruct *t = ecs_get(world, entity, EcsStruct); const EcsStruct *t = ecs_get(world, entity, EcsStruct);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_struct(world, entity, t, ops, offset, module); return serialize_struct(world, entity, t, ops, offset);
} }
case EcsArrayType: { case EcsArrayType: {
const EcsArray *t = ecs_get(world, entity, EcsArray); const EcsArray *t = ecs_get(world, entity, EcsArray);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_array(world, entity, t, ops, module); return serialize_array(world, entity, t, ops);
} }
case EcsVectorType: { case EcsVectorType: {
const EcsVector *t = ecs_get(world, entity, EcsVector); const EcsVector *t = ecs_get(world, entity, EcsVector);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_vector(world, entity, t, ops, module); return serialize_vector(world, entity, t, ops);
} }
case EcsMapType: { case EcsMapType: {
const EcsMap *t = ecs_get(world, entity, EcsMap); const EcsMap *t = ecs_get(world, entity, EcsMap);
ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(t != NULL, ECS_INTERNAL_ERROR, NULL);
return serialize_map(world, entity, t, ops, module); return serialize_map(world, entity, t, ops);
} }
default: default:
@ -605,7 +610,6 @@ ecs_vector_t* serialize_type(
void EcsSetPrimitive(ecs_iter_t *it) { void EcsSetPrimitive(ecs_iter_t *it) {
EcsPrimitive *type = ecs_column(it, EcsPrimitive, 1); EcsPrimitive *type = ecs_column(it, EcsPrimitive, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -625,14 +629,13 @@ void EcsSetPrimitive(ecs_iter_t *it) {
ecs_set(world, e, EcsMetaTypeSerializer, { ecs_set(world, e, EcsMetaTypeSerializer, {
serialize_primitive( serialize_primitive(
world, e, &type[i], NULL, &ecs_module(FlecsMeta)) world, e, &type[i], NULL)
}); });
} }
} }
void EcsSetEnum(ecs_iter_t *it) { void EcsSetEnum(ecs_iter_t *it) {
EcsEnum *type = ecs_column(it, EcsEnum, 1); EcsEnum *type = ecs_column(it, EcsEnum, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -641,14 +644,13 @@ void EcsSetEnum(ecs_iter_t *it) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_enum(world, e, &type[i], NULL, &ecs_module(FlecsMeta)) serialize_enum(world, e, &type[i], NULL)
}); });
} }
} }
void EcsSetBitmask(ecs_iter_t *it) { void EcsSetBitmask(ecs_iter_t *it) {
EcsBitmask *type = ecs_column(it, EcsBitmask, 1); EcsBitmask *type = ecs_column(it, EcsBitmask, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -656,14 +658,13 @@ void EcsSetBitmask(ecs_iter_t *it) {
for (i = 0; i < it->count; i ++) { for (i = 0; i < it->count; i ++) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_bitmask(world, e, &type[i], NULL, &ecs_module(FlecsMeta)) serialize_bitmask(world, e, &type[i], NULL)
}); });
} }
} }
void EcsSetStruct(ecs_iter_t *it) { void EcsSetStruct(ecs_iter_t *it) {
EcsStruct *type = ecs_column(it, EcsStruct, 1); EcsStruct *type = ecs_column(it, EcsStruct, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -671,14 +672,13 @@ void EcsSetStruct(ecs_iter_t *it) {
for (i = 0; i < it->count; i ++) { for (i = 0; i < it->count; i ++) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_struct(world, e, &type[i], NULL, 0, &ecs_module(FlecsMeta)) serialize_struct(world, e, &type[i], NULL, 0)
}); });
} }
} }
void EcsSetArray(ecs_iter_t *it) { void EcsSetArray(ecs_iter_t *it) {
EcsArray *type = ecs_column(it, EcsArray, 1); EcsArray *type = ecs_column(it, EcsArray, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -686,14 +686,13 @@ void EcsSetArray(ecs_iter_t *it) {
for (i = 0; i < it->count; i ++) { for (i = 0; i < it->count; i ++) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_array(world, e, &type[i], NULL, &ecs_module(FlecsMeta)) serialize_array(world, e, &type[i], NULL)
}); });
} }
} }
void EcsSetVector(ecs_iter_t *it) { void EcsSetVector(ecs_iter_t *it) {
EcsVector *type = ecs_column(it, EcsVector, 1); EcsVector *type = ecs_column(it, EcsVector, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -701,14 +700,13 @@ void EcsSetVector(ecs_iter_t *it) {
for (i = 0; i < it->count; i ++) { for (i = 0; i < it->count; i ++) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_vector(world, e, &type[i], NULL, &ecs_module(FlecsMeta)) serialize_vector(world, e, &type[i], NULL)
}); });
} }
} }
void EcsSetMap(ecs_iter_t *it) { void EcsSetMap(ecs_iter_t *it) {
EcsMap *type = ecs_column(it, EcsMap, 1); EcsMap *type = ecs_column(it, EcsMap, 1);
ECS_IMPORT_COLUMN(it, FlecsMeta, 2);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -716,7 +714,7 @@ void EcsSetMap(ecs_iter_t *it) {
for (i = 0; i < it->count; i ++) { for (i = 0; i < it->count; i ++) {
ecs_entity_t e = it->entities[i]; ecs_entity_t e = it->entities[i];
ecs_set(it->world, e, EcsMetaTypeSerializer, { ecs_set(it->world, e, EcsMetaTypeSerializer, {
serialize_map(world, e, &type[i], NULL, &ecs_module(FlecsMeta)) serialize_map(world, e, &type[i], NULL)
}); });
} }
} }
@ -935,7 +933,7 @@ void str_ser_primitive(
ecs_strbuf_append(str, "%lld", *(int64_t*)base); ecs_strbuf_append(str, "%lld", *(int64_t*)base);
break; break;
case EcsF32: case EcsF32:
ecs_strbuf_append(str, "%f", *(float*)base); ecs_strbuf_append(str, "%f", (double)*(float*)base);
break; break;
case EcsF64: case EcsF64:
ecs_strbuf_append(str, "%f", *(double*)base); ecs_strbuf_append(str, "%f", *(double*)base);
@ -969,12 +967,13 @@ void str_ser_primitive(
} }
case EcsEntity: { case EcsEntity: {
ecs_entity_t e = *(ecs_entity_t*)base; ecs_entity_t e = *(ecs_entity_t*)base;
const char *name = ecs_get_name(world, e); const char *name;
if (name) { if (e && (name = ecs_get_name(world, e))) {
ecs_strbuf_appendstr(str, name); ecs_strbuf_appendstr(str, name);
} else { } else {
ecs_strbuf_append(str, "%u", e); ecs_strbuf_append(str, "%u", e);
} }
break; break;
} }
} }
@ -1263,7 +1262,6 @@ char* ecs_ptr_to_str(
ecs_entity_t type, ecs_entity_t type,
void* ptr) void* ptr)
{ {
ecs_entity_t ecs_entity(EcsMetaTypeSerializer) = ecs_lookup_fullpath(world, "flecs.meta.MetaTypeSerializer");
const EcsMetaTypeSerializer *ser = ecs_get(world, type, EcsMetaTypeSerializer); const EcsMetaTypeSerializer *ser = ecs_get(world, type, EcsMetaTypeSerializer);
ecs_assert(ser != NULL, ECS_INVALID_PARAMETER, NULL); ecs_assert(ser != NULL, ECS_INVALID_PARAMETER, NULL);
@ -1283,7 +1281,6 @@ char* ecs_entity_to_str(
ecs_entity_t *ids = (ecs_entity_t*)ecs_vector_first(type, ecs_entity_t); ecs_entity_t *ids = (ecs_entity_t*)ecs_vector_first(type, ecs_entity_t);
int32_t count = ecs_vector_count(type); int32_t count = ecs_vector_count(type);
ecs_entity_t ecs_entity(EcsMetaTypeSerializer) = ecs_lookup_fullpath(world, "flecs.meta.MetaTypeSerializer");
ecs_strbuf_t str = ECS_STRBUF_INIT; ecs_strbuf_t str = ECS_STRBUF_INIT;
const char *name = ecs_get_name(world, entity); const char *name = ecs_get_name(world, entity);
@ -1315,35 +1312,6 @@ error:
ecs_strbuf_reset(&str); ecs_strbuf_reset(&str);
return NULL; return NULL;
} }
#ifndef FLECS_META_SERIALIZER_H
#define FLECS_META_SERIALIZER_H
void EcsAddStruct(
ecs_iter_t *it);
void EcsSetPrimitive(
ecs_iter_t *it);
void EcsSetEnum(
ecs_iter_t *it);
void EcsSetBitmask(
ecs_iter_t *it);
void EcsSetStruct(
ecs_iter_t *it);
void EcsSetArray(
ecs_iter_t *it);
void EcsSetVector(
ecs_iter_t *it);
void EcsSetMap(
ecs_iter_t *it);
#endif
#ifndef FLECS_META_TYPE_H #ifndef FLECS_META_TYPE_H
#define FLECS_META_TYPE_H #define FLECS_META_TYPE_H
@ -1366,6 +1334,12 @@ ecs_entity_t ecs_meta_lookup_map(
const char *params_decl, const char *params_decl,
ecs_meta_parse_ctx_t *ctx); ecs_meta_parse_ctx_t *ctx);
ecs_entity_t ecs_meta_lookup_bitmask(
ecs_world_t *world,
ecs_entity_t e,
const char *params_decl,
ecs_meta_parse_ctx_t *ctx);
ecs_entity_t ecs_meta_lookup( ecs_entity_t ecs_meta_lookup(
ecs_world_t *world, ecs_world_t *world,
ecs_meta_type_t *token, ecs_meta_type_t *token,
@ -1375,18 +1349,31 @@ ecs_entity_t ecs_meta_lookup(
#endif #endif
ECS_CTOR(EcsMetaType, ptr, { ECS_COMPONENT_DECLARE(EcsPrimitive);
ECS_COMPONENT_DECLARE(EcsEnum);
ECS_COMPONENT_DECLARE(EcsBitmask);
ECS_COMPONENT_DECLARE(EcsMember);
ECS_COMPONENT_DECLARE(EcsStruct);
ECS_COMPONENT_DECLARE(EcsArray);
ECS_COMPONENT_DECLARE(EcsVector);
ECS_COMPONENT_DECLARE(EcsMap);
ECS_COMPONENT_DECLARE(EcsMetaType);
ECS_COMPONENT_DECLARE(ecs_type_op_kind_t);
ECS_COMPONENT_DECLARE(ecs_type_op_t);
ECS_COMPONENT_DECLARE(EcsMetaTypeSerializer);
static ECS_CTOR(EcsMetaType, ptr, {
ptr->descriptor = NULL; ptr->descriptor = NULL;
ptr->alias = NULL; ptr->alias = NULL;
}) })
ECS_DTOR(EcsMetaType, ptr, { static ECS_DTOR(EcsMetaType, ptr, {
ecs_os_free((char*)ptr->descriptor); ecs_os_free((char*)ptr->descriptor);
ptr->descriptor = NULL; ptr->descriptor = NULL;
ptr->alias = NULL; ptr->alias = NULL;
}) })
ECS_COPY(EcsMetaType, dst, src, { static ECS_COPY(EcsMetaType, dst, src, {
if (dst->descriptor) { if (dst->descriptor) {
ecs_os_free((char*)dst->descriptor); ecs_os_free((char*)dst->descriptor);
dst->descriptor = NULL; dst->descriptor = NULL;
@ -1404,55 +1391,45 @@ ECS_COPY(EcsMetaType, dst, src, {
dst->alias = src->alias; dst->alias = src->alias;
}) })
ECS_MOVE(EcsMetaType, dst, src, { static ECS_CTOR(EcsStruct, ptr, {
dst->kind = src->kind;
dst->size = src->size;
dst->alignment = src->alignment;
dst->alias = src->alias;
src->descriptor = NULL;
src->alias = NULL;
})
ECS_CTOR(EcsStruct, ptr, {
ptr->members = NULL; ptr->members = NULL;
ptr->is_partial = false; ptr->is_partial = false;
}) })
ECS_DTOR(EcsStruct, ptr, { static ECS_DTOR(EcsStruct, ptr, {
ecs_vector_each(ptr->members, EcsMember, m, { ecs_vector_each(ptr->members, EcsMember, m, {
ecs_os_free(m->name); ecs_os_free(m->name);
}); });
ecs_vector_free(ptr->members); ecs_vector_free(ptr->members);
}) })
ECS_CTOR(EcsEnum, ptr, { static ECS_CTOR(EcsEnum, ptr, {
ptr->constants = NULL; ptr->constants = NULL;
}) })
ECS_DTOR(EcsEnum, ptr, { static ECS_DTOR(EcsEnum, ptr, {
ecs_map_each(ptr->constants, char*, key, c_ptr, { ecs_map_each(ptr->constants, char*, key, c_ptr, {
ecs_os_free(*c_ptr); ecs_os_free(*c_ptr);
}) })
ecs_map_free(ptr->constants); ecs_map_free(ptr->constants);
}) })
ECS_CTOR(EcsBitmask, ptr, { static ECS_CTOR(EcsBitmask, ptr, {
ptr->constants = NULL; ptr->constants = NULL;
}) })
ECS_DTOR(EcsBitmask, ptr, { static ECS_DTOR(EcsBitmask, ptr, {
ecs_map_each(ptr->constants, char*, key, c_ptr, { ecs_map_each(ptr->constants, char*, key, c_ptr, {
ecs_os_free(*c_ptr); ecs_os_free(*c_ptr);
}) })
ecs_map_free(ptr->constants); ecs_map_free(ptr->constants);
}) })
ECS_CTOR(EcsMetaTypeSerializer, ptr, { static ECS_CTOR(EcsMetaTypeSerializer, ptr, {
ptr->ops = NULL; ptr->ops = NULL;
}) })
ECS_DTOR(EcsMetaTypeSerializer, ptr, { static ECS_DTOR(EcsMetaTypeSerializer, ptr, {
ecs_vector_free(ptr->ops); ecs_vector_free(ptr->ops);
}) })
@ -1466,9 +1443,6 @@ void ecs_set_primitive(
ecs_assert(e != 0, ECS_INTERNAL_ERROR, NULL); ecs_assert(e != 0, ECS_INTERNAL_ERROR, NULL);
ecs_assert(type != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(type != NULL, ECS_INTERNAL_ERROR, NULL);
ecs_entity_t ecs_entity(EcsPrimitive) = ecs_lookup_fullpath(world, "flecs.meta.Primitive");
ecs_assert(ecs_entity(EcsPrimitive) != 0, ECS_INTERNAL_ERROR, NULL);
const char *descr = type->descriptor; const char *descr = type->descriptor;
if (!strcmp(descr, "bool")) { if (!strcmp(descr, "bool")) {
@ -1513,7 +1487,7 @@ void ecs_set_primitive(
if (!strcmp(descr, "uptr")) { if (!strcmp(descr, "uptr")) {
ecs_set(world, e, EcsPrimitive, {EcsUPtr}); ecs_set(world, e, EcsPrimitive, {EcsUPtr});
} else } else
if (!strcmp(descr, "string")) { if (!strcmp(descr, "string_t")) {
ecs_set(world, e, EcsPrimitive, {EcsString}); ecs_set(world, e, EcsPrimitive, {EcsString});
} else } else
if (!strcmp(descr, "entity")) { if (!strcmp(descr, "entity")) {
@ -1570,9 +1544,7 @@ void ecs_set_bitmask(
ecs_entity_t e, ecs_entity_t e,
EcsMetaType *type) EcsMetaType *type)
{ {
ecs_entity_t comp = ecs_lookup_fullpath(world, "flecs.meta.Bitmask"); ecs_set_constants(world, e, ecs_id(EcsBitmask), true, type);
ecs_assert(comp != 0, ECS_INTERNAL_ERROR, NULL);
ecs_set_constants(world, e, comp, true, type);
} }
static static
@ -1581,9 +1553,7 @@ void ecs_set_enum(
ecs_entity_t e, ecs_entity_t e,
EcsMetaType *type) EcsMetaType *type)
{ {
ecs_entity_t comp = ecs_lookup_fullpath(world, "flecs.meta.Enum"); ecs_set_constants(world, e, ecs_id(EcsEnum), false, type);
ecs_assert(comp != 0, ECS_INTERNAL_ERROR, NULL);
ecs_set_constants(world, e, comp, false, type);
} }
static static
@ -1615,10 +1585,12 @@ void ecs_set_struct(
ecs_assert(type != 0, ECS_INTERNAL_ERROR, NULL); ecs_assert(type != 0, ECS_INTERNAL_ERROR, NULL);
} }
if (!ecs_vector_count(members)) {
ecs_parser_error(name, type->descriptor, 0, "empty struct declaration");
}
is_partial = token.is_partial; is_partial = token.is_partial;
ecs_entity_t ecs_entity(EcsStruct) = ecs_lookup_fullpath(world, "flecs.meta.Struct");
ecs_assert(ecs_entity(EcsStruct) != 0, ECS_INTERNAL_ERROR, NULL);
ecs_set(world, e, EcsStruct, {members, is_partial}); ecs_set(world, e, EcsStruct, {members, is_partial});
} }
@ -1687,7 +1659,7 @@ void ecs_set_map(
static static
void EcsSetType(ecs_iter_t *it) { void EcsSetType(ecs_iter_t *it) {
ECS_COLUMN(it, EcsMetaType, type, 1); EcsMetaType *type = ecs_column(it, EcsMetaType, 1);
ecs_world_t *world = it->world; ecs_world_t *world = it->world;
@ -1754,9 +1726,7 @@ void ecs_new_meta(
ecs_entity_t component, ecs_entity_t component,
EcsMetaType *meta_type) EcsMetaType *meta_type)
{ {
ecs_entity_t ecs_entity(EcsMetaType) = ecs_assert(ecs_id(EcsMetaType) != 0, ECS_MODULE_UNDEFINED, "flecs.meta");
ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_assert(ecs_entity(EcsMetaType) != 0, ECS_MODULE_UNDEFINED, "flecs.meta");
if (meta_type->alias) { if (meta_type->alias) {
EcsMetaType *alias = meta_type->alias; EcsMetaType *alias = meta_type->alias;
@ -1769,13 +1739,13 @@ void ecs_new_meta(
/* Utility macro to insert meta data for type with meta descriptor */ /* Utility macro to insert meta data for type with meta descriptor */
#define ECS_COMPONENT_TYPE(world, type)\ #define ECS_COMPONENT_TYPE(world, type)\
ecs_set_ptr(world, ecs_entity(type), EcsMetaType, &__##type##__) ecs_set_ptr(world, ecs_id(type), EcsMetaType, &__##type##__)
/* Utility macro to insert metadata for primitive type */ /* Utility macro to insert metadata for primitive type */
#define ECS_COMPONENT_PRIMITIVE(world, type, kind)\ #define ECS_COMPONENT_PRIMITIVE(world, type, kind)\
ECS_COMPONENT(world, type);\ ECS_COMPONENT(world, type);\
ecs_set(world, ecs_entity(type), EcsMetaType, {EcsPrimitiveType, 0, 0, NULL, NULL});\ ecs_set(world, ecs_id(type), EcsMetaType, {EcsPrimitiveType, 0, 0, NULL, NULL});\
ecs_set(world, ecs_entity(type), EcsPrimitive, {kind}) ecs_set(world, ecs_id(type), EcsPrimitive, {kind})
void FlecsMetaImport( void FlecsMetaImport(
ecs_world_t *world) ecs_world_t *world)
@ -1784,26 +1754,25 @@ void FlecsMetaImport(
ecs_set_name_prefix(world, "Ecs"); ecs_set_name_prefix(world, "Ecs");
ECS_COMPONENT(world, EcsPrimitive); ECS_COMPONENT_DEFINE(world, EcsPrimitive);
ECS_COMPONENT(world, EcsEnum); ECS_COMPONENT_DEFINE(world, EcsEnum);
ECS_COMPONENT(world, EcsBitmask); ECS_COMPONENT_DEFINE(world, EcsBitmask);
ECS_COMPONENT(world, EcsMember); ECS_COMPONENT_DEFINE(world, EcsMember);
ECS_COMPONENT(world, EcsStruct); ECS_COMPONENT_DEFINE(world, EcsStruct);
ECS_COMPONENT(world, EcsArray); ECS_COMPONENT_DEFINE(world, EcsArray);
ECS_COMPONENT(world, EcsVector); ECS_COMPONENT_DEFINE(world, EcsVector);
ECS_COMPONENT(world, EcsMap); ECS_COMPONENT_DEFINE(world, EcsMap);
ECS_COMPONENT(world, EcsMetaType); ECS_COMPONENT_DEFINE(world, EcsMetaType);
ECS_COMPONENT(world, ecs_type_op_kind_t); ECS_COMPONENT_DEFINE(world, ecs_type_op_kind_t);
ECS_COMPONENT(world, ecs_type_op_t); ECS_COMPONENT_DEFINE(world, ecs_type_op_t);
ECS_COMPONENT(world, EcsMetaTypeSerializer); ECS_COMPONENT_DEFINE(world, EcsMetaTypeSerializer);
ECS_SYSTEM(world, EcsSetType, EcsOnSet, EcsMetaType); ECS_SYSTEM(world, EcsSetType, EcsOnSet, EcsMetaType);
ecs_set_component_actions(world, EcsMetaType, { ecs_set_component_actions(world, EcsMetaType, {
.ctor = ecs_ctor(EcsMetaType), .ctor = ecs_ctor(EcsMetaType),
.dtor = ecs_dtor(EcsMetaType), .dtor = ecs_dtor(EcsMetaType),
.copy = ecs_copy(EcsMetaType), .copy = ecs_copy(EcsMetaType)
.move = ecs_move(EcsMetaType)
}); });
ecs_set_component_actions(world, EcsStruct, { ecs_set_component_actions(world, EcsStruct, {
@ -1826,13 +1795,13 @@ void FlecsMetaImport(
.dtor = ecs_dtor(EcsMetaTypeSerializer) .dtor = ecs_dtor(EcsMetaTypeSerializer)
}); });
ECS_SYSTEM(world, EcsSetPrimitive, EcsOnSet, Primitive, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetPrimitive, EcsOnSet, Primitive);
ECS_SYSTEM(world, EcsSetEnum, EcsOnSet, Enum, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetEnum, EcsOnSet, Enum);
ECS_SYSTEM(world, EcsSetBitmask, EcsOnSet, Bitmask, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetBitmask, EcsOnSet, Bitmask);
ECS_SYSTEM(world, EcsSetStruct, EcsOnSet, Struct, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetStruct, EcsOnSet, Struct);
ECS_SYSTEM(world, EcsSetArray, EcsOnSet, Array, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetArray, EcsOnSet, Array);
ECS_SYSTEM(world, EcsSetVector, EcsOnSet, Vector, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetVector, EcsOnSet, Vector);
ECS_SYSTEM(world, EcsSetMap, EcsOnSet, Map, flecs.meta:flecs.meta); ECS_SYSTEM(world, EcsSetMap, EcsOnSet, Map);
ECS_EXPORT_COMPONENT(EcsPrimitive); ECS_EXPORT_COMPONENT(EcsPrimitive);
ECS_EXPORT_COMPONENT(EcsEnum); ECS_EXPORT_COMPONENT(EcsEnum);
@ -1870,8 +1839,12 @@ void FlecsMetaImport(
* registered with the name _Bool. To make sure meta also knows the type by * registered with the name _Bool. To make sure meta also knows the type by
* its regular name, check and register if necessary */ * its regular name, check and register if necessary */
if (!ecs_lookup(world, "bool")) { if (!ecs_lookup(world, "bool")) {
ecs_entity_t type = ecs_new_component( ecs_entity_t type = ecs_component_init(world, &(ecs_component_desc_t) {
world, 0, "bool", sizeof(bool), ECS_ALIGNOF(bool)); .entity.name = "bool",
.size = sizeof(bool),
.alignment = ECS_ALIGNOF(bool)
});
ecs_set(world, type, EcsMetaType, { ecs_set(world, type, EcsMetaType, {
EcsPrimitiveType, 0, 0, NULL, NULL}); EcsPrimitiveType, 0, 0, NULL, NULL});
ecs_set(world, type, EcsPrimitive, {EcsBool}); ecs_set(world, type, EcsPrimitive, {EcsBool});
@ -1880,12 +1853,11 @@ void FlecsMetaImport(
ecs_set_scope(world, old_scope); ecs_set_scope(world, old_scope);
/* -- Initialize builtin meta components -- */ /* -- Initialize builtin meta components -- */
ecs_set_ptr(world, ecs_set(world, 0,
EcsName, {"ecs_primitive_kind_t", NULL, NULL}), ecs_set_ptr(world, ecs_set_name(world, 0, "ecs_primitive_kind_t"),
EcsMetaType, &__ecs_primitive_kind_t__); EcsMetaType, &__ecs_primitive_kind_t__);
ecs_set(world, ecs_set(world, 0, ecs_set(world, ecs_set_name(world, 0, "ecs_type_kind_t"),
EcsName, {"ecs_type_kind_t", NULL, NULL}),
EcsMetaType, { EcsMetaType, {
EcsEnumType, EcsEnumType,
sizeof(ecs_type_kind_t), sizeof(ecs_type_kind_t),
@ -1909,29 +1881,21 @@ void FlecsMetaImport(
ECS_COMPONENT_TYPE(world, EcsMetaTypeSerializer); ECS_COMPONENT_TYPE(world, EcsMetaTypeSerializer);
/* -- Initialize metadata for public Flecs core components -- */ /* -- Initialize metadata for public Flecs core components -- */
ecs_set(world, ecs_entity(EcsName), EcsMetaType, { ecs_set(world, ecs_id(EcsIdentifier), EcsMetaType, {
.kind = EcsStructType, .kind = EcsStructType,
.size = sizeof(EcsName), .size = sizeof(EcsIdentifier),
.alignment = ECS_ALIGNOF(EcsName), .alignment = ECS_ALIGNOF(EcsIdentifier),
.descriptor = "{ecs_string_t value; ECS_PRIVATE; }", .descriptor = "{ char *value; ECS_PRIVATE }",
.alias = NULL .alias = NULL
}); });
ecs_set(world, ecs_entity(EcsComponent), EcsMetaType, { ecs_set(world, ecs_id(EcsComponent), EcsMetaType, {
.kind = EcsStructType, .kind = EcsStructType,
.size = sizeof(EcsComponent), .size = sizeof(EcsComponent),
.alignment = ECS_ALIGNOF(EcsComponent), .alignment = ECS_ALIGNOF(EcsComponent),
.descriptor = "{int32_t size; int32_t alignment;}", .descriptor = "{int32_t size; int32_t alignment;}",
.alias = NULL .alias = NULL
}); });
ecs_set(world, ecs_entity(EcsSignatureExpr), EcsMetaType, {
.kind = EcsStructType,
.size = sizeof(EcsSignatureExpr),
.alignment = ECS_ALIGNOF(EcsSignatureExpr),
.descriptor = "{const char *expr;}",
.alias = NULL
});
} }
ecs_entity_t ecs_meta_lookup_array( ecs_entity_t ecs_meta_lookup_array(
@ -1955,16 +1919,13 @@ ecs_entity_t ecs_meta_lookup_array(
ecs_meta_error(ctx, params_decl, "invalid array size"); ecs_meta_error(ctx, params_decl, "invalid array size");
} }
ecs_entity_t element_type = ecs_lookup_symbol(world, params.type.type); ecs_entity_t element_type = ecs_lookup_symbol(world, params.type.type, true);
if (!element_type) { if (!element_type) {
ecs_meta_error(ctx, params_decl, "unknown element type '%s'", ecs_meta_error(ctx, params_decl, "unknown element type '%s'",
params.type.type); params.type.type);
} }
if (!e) { if (!e) {
ecs_entity_t ecs_entity(EcsMetaType) = ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_assert(ecs_entity(EcsMetaType) != 0, ECS_INTERNAL_ERROR, NULL);
const EcsMetaType *elem_type = ecs_get(world, element_type, EcsMetaType); const EcsMetaType *elem_type = ecs_get(world, element_type, EcsMetaType);
ecs_assert(elem_type != NULL, ECS_INTERNAL_ERROR, NULL); ecs_assert(elem_type != NULL, ECS_INTERNAL_ERROR, NULL);
@ -1977,9 +1938,6 @@ ecs_entity_t ecs_meta_lookup_array(
}); });
} }
ecs_entity_t ecs_entity(EcsArray) = ecs_lookup_fullpath(world, "flecs.meta.Array");
ecs_assert(ecs_entity(EcsArray) != 0, ECS_INTERNAL_ERROR, NULL);
ecs_assert(params.count <= INT32_MAX, ECS_INVALID_PARAMETER, NULL); ecs_assert(params.count <= INT32_MAX, ECS_INVALID_PARAMETER, NULL);
return ecs_set(world, e, EcsArray, { element_type, (int32_t)params.count }); return ecs_set(world, e, EcsArray, { element_type, (int32_t)params.count });
@ -2007,15 +1965,9 @@ ecs_entity_t ecs_meta_lookup_vector(
world, &params.type, params_decl, 1, &param_ctx); world, &params.type, params_decl, 1, &param_ctx);
if (!e) { if (!e) {
ecs_entity_t ecs_entity(EcsMetaType) = ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_assert(ecs_entity(EcsMetaType) != 0, ECS_INTERNAL_ERROR, NULL);
e = ecs_set(world, 0, EcsMetaType, {EcsVectorType, 0, 0, NULL, NULL}); e = ecs_set(world, 0, EcsMetaType, {EcsVectorType, 0, 0, NULL, NULL});
} }
ecs_entity_t ecs_entity(EcsVector) = ecs_lookup_fullpath(world, "flecs.meta.Vector");
ecs_assert(ecs_entity(EcsVector) != 0, ECS_INTERNAL_ERROR, NULL);
return ecs_set(world, e, EcsVector, { element_type }); return ecs_set(world, e, EcsVector, { element_type });
} }
@ -2044,15 +1996,9 @@ ecs_entity_t ecs_meta_lookup_map(
world, &params.type, params_decl, 1, &param_ctx); world, &params.type, params_decl, 1, &param_ctx);
if (!e) { if (!e) {
ecs_entity_t ecs_entity(EcsMetaType) = ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_assert(ecs_entity(EcsMetaType) != 0, ECS_INTERNAL_ERROR, NULL);
e = ecs_set(world, 0, EcsMetaType, {EcsMapType, 0, 0, NULL, NULL}); e = ecs_set(world, 0, EcsMetaType, {EcsMapType, 0, 0, NULL, NULL});
} }
ecs_entity_t ecs_entity(EcsMap) = ecs_lookup_fullpath(world, "flecs.meta.Map");
ecs_assert(ecs_entity(EcsMap) != 0, ECS_INTERNAL_ERROR, NULL);
return ecs_set(world, e, EcsMap, { key_type, element_type }); return ecs_set(world, e, EcsMap, { key_type, element_type });
} }
@ -2087,9 +2033,6 @@ ecs_entity_t ecs_meta_lookup_bitmask(
#ifndef NDEBUG #ifndef NDEBUG
/* Make sure this is a bitmask type */ /* Make sure this is a bitmask type */
ecs_entity_t ecs_entity(EcsMetaType) = ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_assert(ecs_entity(EcsMetaType) != 0, ECS_INTERNAL_ERROR, NULL);
const EcsMetaType *type_ptr = ecs_get(world, bitmask_type, EcsMetaType); const EcsMetaType *type_ptr = ecs_get(world, bitmask_type, EcsMetaType);
ecs_assert(type_ptr != NULL, ECS_INVALID_PARAMETER, NULL); ecs_assert(type_ptr != NULL, ECS_INVALID_PARAMETER, NULL);
ecs_assert(type_ptr->kind == EcsBitmaskType, ECS_INVALID_PARAMETER, NULL); ecs_assert(type_ptr->kind == EcsBitmaskType, ECS_INVALID_PARAMETER, NULL);
@ -2140,7 +2083,7 @@ ecs_entity_t ecs_meta_lookup(
typename = "ecs_string_t"; typename = "ecs_string_t";
} }
type = ecs_lookup_symbol(world, typename); type = ecs_lookup_symbol(world, typename, true);
if (!type) { if (!type) {
ecs_meta_error(ctx, ptr, "unknown type '%s'", typename); ecs_meta_error(ctx, ptr, "unknown type '%s'", typename);
return 0; return 0;
@ -2151,8 +2094,6 @@ ecs_entity_t ecs_meta_lookup(
/* If count is not 1, insert array type. First lookup EcsMetaType of the /* If count is not 1, insert array type. First lookup EcsMetaType of the
* element type to get the size and alignment. Then create a new * element type to get the size and alignment. Then create a new
* entity for the array type, and assign it to the member type. */ * entity for the array type, and assign it to the member type. */
ecs_entity_t ecs_entity(EcsMetaType) = ecs_lookup_fullpath(world, "flecs.meta.MetaType");
ecs_entity_t ecs_entity(EcsArray) = ecs_lookup_fullpath(world, "flecs.meta.Array");
const EcsMetaType *type_ptr = ecs_get(world, type, EcsMetaType); const EcsMetaType *type_ptr = ecs_get(world, type, EcsMetaType);
ecs_assert(count <= INT32_MAX, ECS_INVALID_PARAMETER, NULL); ecs_assert(count <= INT32_MAX, ECS_INVALID_PARAMETER, NULL);
@ -2197,7 +2138,7 @@ ecs_type_op_t* get_ptr(
} }
ecs_meta_cursor_t ecs_meta_cursor( ecs_meta_cursor_t ecs_meta_cursor(
ecs_world_t *world, const ecs_world_t *world,
ecs_entity_t type, ecs_entity_t type,
void *base) void *base)
{ {
@ -2206,9 +2147,6 @@ ecs_meta_cursor_t ecs_meta_cursor(
ecs_assert(base != NULL, ECS_INVALID_PARAMETER, NULL); ecs_assert(base != NULL, ECS_INVALID_PARAMETER, NULL);
ecs_meta_cursor_t result; ecs_meta_cursor_t result;
ecs_entity_t ecs_entity(EcsMetaTypeSerializer) =
ecs_lookup_fullpath(world, "flecs.meta.MetaTypeSerializer");
ecs_assert(ecs_entity(EcsMetaTypeSerializer) != 0, ECS_INVALID_PARAMETER, NULL);
const EcsMetaTypeSerializer *ser = ecs_get(world, type, EcsMetaTypeSerializer); const EcsMetaTypeSerializer *ser = ecs_get(world, type, EcsMetaTypeSerializer);
ecs_assert(ser != NULL, ECS_INVALID_PARAMETER, NULL); ecs_assert(ser != NULL, ECS_INVALID_PARAMETER, NULL);

View File

@ -51,22 +51,22 @@
#define ECS_ENUM_BOOTSTRAP(name, ...)\ #define ECS_ENUM_BOOTSTRAP(name, ...)\
typedef enum name __VA_ARGS__ name;\ typedef enum name __VA_ARGS__ name;\
ECS_UNUSED \ ECS_UNUSED \
static const char * __##name##__ = #__VA_ARGS__ static const char * __##name##__ = #__VA_ARGS__;
#define ECS_STRUCT_IMPL(name, descriptor, ...)\ #define ECS_STRUCT_IMPL(name, descriptor, ...)\
typedef struct name __VA_ARGS__ name;\ typedef struct name __VA_ARGS__ name;\
ECS_UNUSED \ ECS_UNUSED \
static EcsMetaType __##name##__ = {EcsStructType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL}\ static EcsMetaType __##name##__ = {EcsStructType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL};
#define ECS_ENUM_IMPL(name, descriptor, ...)\ #define ECS_ENUM_IMPL(name, descriptor, ...)\
typedef enum name __VA_ARGS__ name;\ typedef enum name __VA_ARGS__ name;\
ECS_UNUSED \ ECS_UNUSED \
static EcsMetaType __##name##__ = {EcsEnumType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL} static EcsMetaType __##name##__ = {EcsEnumType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL};
#define ECS_BITMASK_IMPL(name, descriptor, ...)\ #define ECS_BITMASK_IMPL(name, descriptor, ...)\
typedef enum name __VA_ARGS__ name;\ typedef enum name __VA_ARGS__ name;\
ECS_UNUSED \ ECS_UNUSED \
static EcsMetaType __##name##__ = {EcsBitmaskType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL} static EcsMetaType __##name##__ = {EcsBitmaskType, sizeof(name), ECS_ALIGNOF(name), descriptor, NULL};
#define ECS_STRUCT_C(T, ...) ECS_STRUCT_IMPL(T, #__VA_ARGS__, __VA_ARGS__) #define ECS_STRUCT_C(T, ...) ECS_STRUCT_IMPL(T, #__VA_ARGS__, __VA_ARGS__)
#define ECS_ENUM_C(T, ...) ECS_ENUM_IMPL(T, #__VA_ARGS__, __VA_ARGS__) #define ECS_ENUM_C(T, ...) ECS_ENUM_IMPL(T, #__VA_ARGS__, __VA_ARGS__)
@ -96,7 +96,7 @@ class __meta__ { };
} }
// Specialized C++ class that stores name and descriptor of type // Specialized C++ class that stores name and descriptor of type
#define ECS_META_CPP(T, kind, descr);\ #define ECS_META_CPP(T, kind, descr)\
namespace flecs {\ namespace flecs {\
template<>\ template<>\
class __meta__ <T> {\ class __meta__ <T> {\
@ -124,17 +124,17 @@ public:\
// Define a struct // Define a struct
#define ECS_STRUCT(T, ...)\ #define ECS_STRUCT(T, ...)\
ECS_STRUCT_IMPL(T, #__VA_ARGS__, __VA_ARGS__);\ ECS_STRUCT_IMPL(T, #__VA_ARGS__, __VA_ARGS__)\
ECS_META_CPP(T, EcsStructType, #__VA_ARGS__) ECS_META_CPP(T, EcsStructType, #__VA_ARGS__)
// Define an enumeration // Define an enumeration
#define ECS_ENUM(T, ...)\ #define ECS_ENUM(T, ...)\
ECS_ENUM_IMPL(T, #__VA_ARGS__, __VA_ARGS__);\ ECS_ENUM_IMPL(T, #__VA_ARGS__, __VA_ARGS__)\
ECS_META_CPP(T, EcsEnumType, #__VA_ARGS__); ECS_META_CPP(T, EcsEnumType, #__VA_ARGS__)
// Define a bitmask // Define a bitmask
#define ECS_BITMASK(T, ...)\ #define ECS_BITMASK(T, ...)\
ECS_BITMASK_IMPL(T, #__VA_ARGS__, __VA_ARGS__);\ ECS_BITMASK_IMPL(T, #__VA_ARGS__, __VA_ARGS__)\
ECS_META_CPP(T, EcsBitmaskType, #__VA_ARGS__) ECS_META_CPP(T, EcsBitmaskType, #__VA_ARGS__)
#else #else
@ -189,8 +189,8 @@ typedef uint8_t ecs_byte_t;
#ifdef __cplusplus #ifdef __cplusplus
namespace flecs { namespace flecs {
using string = ecs_string_t; using string_t = ecs_string_t;
using byte = ecs_byte_t; using byte_t = ecs_byte_t;
// Define a bitmask // Define a bitmask
// In C++ trying to assign multiple flags to a variable of an enum type will // In C++ trying to assign multiple flags to a variable of an enum type will
@ -210,7 +210,7 @@ ECS_ENUM_BOOTSTRAP( ecs_type_kind_t, {
EcsArrayType, EcsArrayType,
EcsVectorType, EcsVectorType,
EcsMapType EcsMapType
}); })
ECS_STRUCT( EcsMetaType, { ECS_STRUCT( EcsMetaType, {
ecs_type_kind_t kind; ecs_type_kind_t kind;
@ -218,7 +218,7 @@ ECS_STRUCT( EcsMetaType, {
int16_t alignment; int16_t alignment;
const char *descriptor; const char *descriptor;
void *alias; void *alias;
}); })
ECS_ENUM( ecs_primitive_kind_t, { ECS_ENUM( ecs_primitive_kind_t, {
EcsBool, EcsBool,
@ -238,40 +238,40 @@ ECS_ENUM( ecs_primitive_kind_t, {
EcsIPtr, EcsIPtr,
EcsString, EcsString,
EcsEntity EcsEntity
}); })
ECS_STRUCT( EcsPrimitive, { ECS_STRUCT( EcsPrimitive, {
ecs_primitive_kind_t kind; ecs_primitive_kind_t kind;
}); })
// Define EcsBitmask for both C and C++. Both representations are equivalent in // Define EcsBitmask for both C and C++. Both representations are equivalent in
// memory, but allow for a nicer type-safe API in C++ // memory, but allow for a nicer type-safe API in C++
#if defined(__cplusplus) && !defined(FLECS_NO_CPP) #if defined(__cplusplus) && !defined(FLECS_NO_CPP)
ECS_STRUCT( EcsBitmask, { ECS_STRUCT( EcsBitmask, {
flecs::map<int32_t, flecs::string> constants; flecs::map<int32_t, flecs::string_t> constants;
}); })
#else #else
ECS_STRUCT( EcsBitmask, { ECS_STRUCT( EcsBitmask, {
ecs_map(int32_t, ecs_string_t) constants; ecs_map(int32_t, ecs_string_t) constants;
}); })
#endif #endif
// Define EcsEnum for both C and C++. Both representations are equivalent in // Define EcsEnum for both C and C++. Both representations are equivalent in
// memory, but allow for a nicer type-safe API in C++ // memory, but allow for a nicer type-safe API in C++
#if defined(__cplusplus) && !defined(FLECS_NO_CPP) #if defined(__cplusplus) && !defined(FLECS_NO_CPP)
ECS_STRUCT( EcsEnum, { ECS_STRUCT( EcsEnum, {
flecs::map<int32_t, flecs::string> constants; flecs::map<int32_t, flecs::string_t> constants;
}); })
#else #else
ECS_STRUCT( EcsEnum, { ECS_STRUCT( EcsEnum, {
ecs_map(int32_t, ecs_string_t) constants; ecs_map(int32_t, ecs_string_t) constants;
}); })
#endif #endif
ECS_STRUCT( EcsMember, { ECS_STRUCT( EcsMember, {
char *name; char *name;
ecs_entity_t type; ecs_entity_t type;
}); })
// Define EcsStruct for both C and C++. Both representations are equivalent in // Define EcsStruct for both C and C++. Both representations are equivalent in
// memory, but allow for a nicer type-safe API in C++ // memory, but allow for a nicer type-safe API in C++
@ -279,27 +279,27 @@ ECS_STRUCT( EcsMember, {
ECS_STRUCT( EcsStruct, { ECS_STRUCT( EcsStruct, {
flecs::vector<EcsMember> members; flecs::vector<EcsMember> members;
bool is_partial; bool is_partial;
}); })
#else #else
ECS_STRUCT( EcsStruct, { ECS_STRUCT( EcsStruct, {
ecs_vector(EcsMember) members; ecs_vector(EcsMember) members;
bool is_partial; bool is_partial;
}); })
#endif #endif
ECS_STRUCT( EcsArray, { ECS_STRUCT( EcsArray, {
ecs_entity_t element_type; ecs_entity_t element_type;
int32_t count; int32_t count;
}); })
ECS_STRUCT( EcsVector, { ECS_STRUCT( EcsVector, {
ecs_entity_t element_type; ecs_entity_t element_type;
}); })
ECS_STRUCT( EcsMap, { ECS_STRUCT( EcsMap, {
ecs_entity_t key_type; ecs_entity_t key_type;
ecs_entity_t element_type; ecs_entity_t element_type;
}); })
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -316,7 +316,7 @@ ECS_ENUM_C( ecs_type_op_kind_t, {
EcsOpArray, EcsOpArray,
EcsOpVector, EcsOpVector,
EcsOpMap EcsOpMap
}); })
typedef ecs_vector_t ecs_type_op_vector_t; typedef ecs_vector_t ecs_type_op_vector_t;
typedef ecs_vector_t ecs_constant_vector_t; typedef ecs_vector_t ecs_constant_vector_t;
@ -326,7 +326,7 @@ ECS_STRUCT_C( ecs_type_op_t, {
ecs_type_op_kind_t kind; ecs_type_op_kind_t kind;
ecs_size_t size; /* Size of value or element type if array or vector */ ecs_size_t size; /* Size of value or element type if array or vector */
int16_t alignment; /* Alignment of value */ int16_t alignment; /* Alignment of value */
int32_t count; /* Number of elements (only used for arrays) */ int32_t count; /* Number of array elements or struct members */
int32_t offset; /* Offset of value */ int32_t offset; /* Offset of value */
const char *name; /* Name of value (only used for struct members) */ const char *name; /* Name of value (only used for struct members) */
@ -343,11 +343,11 @@ ECS_PRIVATE
ecs_ref_t element; ecs_ref_t element;
} map; } map;
} is; } is;
}); })
ECS_STRUCT_C( EcsMetaTypeSerializer, { ECS_STRUCT_C( EcsMetaTypeSerializer, {
ecs_vector(ecs_type_op_t) ops; ecs_vector(ecs_type_op_t) ops;
}); })
#endif #endif
@ -457,14 +457,14 @@ typedef struct ecs_meta_scope_t {
} ecs_meta_scope_t; } ecs_meta_scope_t;
typedef struct ecs_meta_cursor_t { typedef struct ecs_meta_cursor_t {
ecs_world_t *world; const ecs_world_t *world;
ecs_meta_scope_t scope[ECS_META_MAX_SCOPE_DEPTH]; ecs_meta_scope_t scope[ECS_META_MAX_SCOPE_DEPTH];
int32_t depth; int32_t depth;
} ecs_meta_cursor_t; } ecs_meta_cursor_t;
FLECS_META_API FLECS_META_API
ecs_meta_cursor_t ecs_meta_cursor( ecs_meta_cursor_t ecs_meta_cursor(
ecs_world_t *world, const ecs_world_t *world,
ecs_entity_t type, ecs_entity_t type,
void *base); void *base);
@ -554,20 +554,24 @@ typedef struct FlecsMeta {
extern "C" { extern "C" {
#endif #endif
FLECS_META_API ECS_COMPONENT_EXTERN(EcsPrimitive);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsEnum);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsBitmask);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsMember);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsStruct);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsArray);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsVector);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsMap);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsMetaType);
FLECS_META_API ECS_COMPONENT_EXTERN(ecs_type_op_kind_t);
FLECS_META_API ECS_COMPONENT_EXTERN(ecs_type_op_t);
FLECS_META_API ECS_COMPONENT_EXTERN(EcsMetaTypeSerializer);
FLECS_META_API FLECS_META_API
void FlecsMetaImport( void FlecsMetaImport(
ecs_world_t *world); ecs_world_t *world);
#define FlecsMetaImportHandles(handles)\ #define FlecsMetaImportHandles(handles)
ECS_IMPORT_COMPONENT(handles, EcsPrimitive);\
ECS_IMPORT_COMPONENT(handles, EcsEnum);\
ECS_IMPORT_COMPONENT(handles, EcsBitmask);\
ECS_IMPORT_COMPONENT(handles, EcsStruct);\
ECS_IMPORT_COMPONENT(handles, EcsArray);\
ECS_IMPORT_COMPONENT(handles, EcsVector);\
ECS_IMPORT_COMPONENT(handles, EcsMap);\
ECS_IMPORT_COMPONENT(handles, EcsMetaType);\
ECS_IMPORT_COMPONENT(handles, EcsMetaTypeSerializer);
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
//// Macro for inserting metadata in C application //// Macro for inserting metadata in C application
@ -583,6 +587,14 @@ void ecs_new_meta(
ECS_COMPONENT(world, T);\ ECS_COMPONENT(world, T);\
ecs_new_meta(world, ecs_entity(T), &__##T##__); ecs_new_meta(world, ecs_entity(T), &__##T##__);
/** Define a meta component, store in variable outside of the current scope.
* Use this macro in a header when defining a component identifier globally.
* Must be used together with ECS_COMPONENT_DECLARE.
*/
#define ECS_META_DEFINE(world, T)\
ECS_COMPONENT_DEFINE(world, T);\
ecs_new_meta(world, ecs_entity(T), &__##T##__);
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif
@ -620,18 +632,18 @@ public:
}; };
meta(flecs::world& world) { meta(flecs::world& world) {
FlecsMetaImport(world.c_ptr()); FlecsMetaImport(world);
flecs::module<flecs::components::meta>(world, "flecs::components::meta"); world.module<flecs::components::meta>("flecs::components::meta");
flecs::component<Primitive>(world, "EcsPrimitive"); world.component<Primitive>("EcsPrimitive");
flecs::component<Enum>(world, "EcsEnum"); world.component<Enum>("EcsEnum");
flecs::component<Bitmask>(world, "EcsBitmask"); world.component<Bitmask>("EcsBitmask");
flecs::component<Struct>(world, "EcsStruct"); world.component<Struct>("EcsStruct");
flecs::component<Array>(world, "EcsArray"); world.component<Array>("EcsArray");
flecs::component<Vector>(world, "EcsVector"); world.component<Vector>("EcsVector");
flecs::component<Type>(world, "EcsMetaType"); world.component<Type>("EcsMetaType");
flecs::component<TypeSerializer>(world, "EcsMetaTypeSerializer"); world.component<TypeSerializer>("EcsMetaTypeSerializer");
} }
}; };
} }
@ -654,29 +666,27 @@ flecs::entity meta(flecs::world& world) {
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
template <typename T> template <typename T>
std::string pretty_print(flecs::world& world, flecs::entity_t type, T& data) { flecs::string pretty_print(flecs::world& world, flecs::entity_t type, T& data) {
char *str = ecs_ptr_to_str(world.c_ptr(), type, &data); char *str = ecs_ptr_to_str(world.c_ptr(), type, &data);
std::string result = std::string(str); flecs::string result = flecs::string(str);
free(str);
return result; return result;
} }
template <typename T> template <typename T>
std::string pretty_print(flecs::world& world, flecs::entity type, T& data) { flecs::string pretty_print(flecs::world& world, flecs::entity type, T& data) {
return pretty_print(world, type.id(), data); return pretty_print(world, type.id(), data);
} }
template <typename T> template <typename T>
std::string pretty_print(flecs::world& world, T& data) { flecs::string pretty_print(flecs::world& world, T& data) {
entity_t type = _::component_info<T>::id(); entity_t type = _::cpp_type<T>::id();
return flecs::pretty_print(world, type, data); return flecs::pretty_print(world, type, data);
} }
template <> template <>
inline std::string pretty_print<flecs::entity>(flecs::world& world, flecs::entity& entity) { inline flecs::string pretty_print<flecs::entity>(flecs::world& world, flecs::entity& entity) {
char *str = ecs_entity_to_str(world.c_ptr(), entity.id()); char *str = ecs_entity_to_str(world.c_ptr(), entity.id());
std::string result = std::string(str); flecs::string result = flecs::string(str);
free(str);
return result; return result;
} }