diff --git a/code/apps/client/CMakeLists.txt b/code/apps/client/CMakeLists.txt index ffa6701..1d58b46 100644 --- a/code/apps/client/CMakeLists.txt +++ b/code/apps/client/CMakeLists.txt @@ -6,7 +6,6 @@ add_library(client-common STATIC source/game.c source/main.c source/camera.c - source/entity_view.c source/world_view.c source/utils/options.c diff --git a/code/apps/client/header/world_view.h b/code/apps/client/header/world_view.h index 611ff0a..d5ade23 100644 --- a/code/apps/client/header/world_view.h +++ b/code/apps/client/header/world_view.h @@ -7,6 +7,13 @@ typedef struct { uint64_t owner_id; entity_view_tbl entities; librg_world *tracker; + + uint32_t size; + uint32_t width; + uint32_t height; + uint16_t block_size; + uint16_t chunk_size; + uint16_t world_size; } world_view; world_view world_view_create(void); diff --git a/code/apps/client/source/platform_raylib.c b/code/apps/client/source/platform_raylib.c index e48190f..a33e103 100644 --- a/code/apps/client/source/platform_raylib.c +++ b/code/apps/client/source/platform_raylib.c @@ -39,7 +39,6 @@ void platform_render() { BeginDrawing(); ClearBackground(BLACK); BeginMode2D(render_camera); - DrawRectangleV((Vector2){0,0}, (Vector2){40,40}, RED); entity_view_map(&game_world_view_get_active()->entities, DEBUG_draw_entities); EndMode2D(); display_conn_status(); @@ -59,5 +58,13 @@ void display_conn_status() { } void DEBUG_draw_entities(uint64_t key, entity_view data) { - DrawCircle(data.x, data.y, 15.0f, RAYWHITE); + world_view *view = game_world_view_get_active(); + + switch (data.kind) { + case EKIND_PLAYER: { + DrawCircle(data.x-8.0f, data.y-8.0f, 16.0f, RED); + }break; + + default:break; + } } \ No newline at end of file diff --git a/code/apps/client/source/world_view.c b/code/apps/client/source/world_view.c index 4af26f3..14ffb5d 100644 --- a/code/apps/client/source/world_view.c +++ b/code/apps/client/source/world_view.c @@ -1,17 +1,6 @@ #include "world_view.h" #include "librg.h" -int32_t tracker_read_create(librg_world *w, librg_event *e) { - int64_t owner_id = librg_event_owner_get(w, e); - int64_t entity_id = librg_event_entity_get(w, e); - zpl_printf("[INFO] An entity %d was created for owner: %d\n", (int)entity_id, (int)owner_id); - world_view *view = (world_view*)librg_world_userdata_get(w); - - // TODO(zaklaus): receive real data - entity_view_update_or_create(&view->entities, entity_id, (entity_view){0}); - return 0; -} - int32_t tracker_read_remove(librg_world *w, librg_event *e) { int64_t owner_id = librg_event_owner_get(w, e); int64_t entity_id = librg_event_entity_get(w, e); @@ -26,8 +15,23 @@ int32_t tracker_read_update(librg_world *w, librg_event *e) { int64_t entity_id = librg_event_entity_get(w, e); size_t actual_length = librg_event_size_get(w, e); char *buffer = librg_event_buffer_get(w, e); + world_view *view = (world_view*)librg_world_userdata_get(w); - // TODO(zaklaus): update real data + entity_view data = entity_view_unpack_struct(buffer, actual_length); + entity_view_update_or_create(&view->entities, entity_id, data); + return 0; +} + +int32_t tracker_read_create(librg_world *w, librg_event *e) { + int64_t owner_id = librg_event_owner_get(w, e); + int64_t entity_id = librg_event_entity_get(w, e); + zpl_printf("[INFO] An entity %d was created for owner: %d\n", (int)entity_id, (int)owner_id); + size_t actual_length = librg_event_size_get(w, e); + char *buffer = librg_event_buffer_get(w, e); + world_view *view = (world_view*)librg_world_userdata_get(w); + + entity_view data = entity_view_unpack_struct(buffer, actual_length); + entity_view_update_or_create(&view->entities, entity_id, data); return 0; } @@ -40,6 +44,14 @@ world_view world_view_create(void) { void world_view_init(world_view *view, uint64_t ent_id, uint16_t block_size, uint16_t chunk_size, uint16_t world_size) { view->owner_id = ent_id; + view->chunk_size = chunk_size; + view->world_size = world_size; + + view->width = chunk_size * world_size; + view->height = chunk_size * world_size; + view->block_size = block_size; + view->size = view->width * view->height; + librg_config_chunksize_set(view->tracker, block_size * chunk_size, block_size * chunk_size, 1); librg_config_chunkamount_set(view->tracker, world_size, world_size, 1); librg_config_chunkoffset_set(view->tracker, LIBRG_OFFSET_MID, LIBRG_OFFSET_MID, 0); diff --git a/code/apps/client/source/entity_view.c b/code/common/entity_view.c similarity index 88% rename from code/apps/client/source/entity_view.c rename to code/common/entity_view.c index 64ef183..3fce6f9 100644 --- a/code/apps/client/source/entity_view.c +++ b/code/common/entity_view.c @@ -4,22 +4,24 @@ ZPL_TABLE_DEFINE(entity_view_tbl, entity_view_tbl_, entity_view); pkt_desc pkt_entity_view_desc[] = { + { PKT_UINT(entity_view, kind) }, { PKT_REAL(entity_view, x) }, { PKT_REAL(entity_view, y) }, { PKT_END }, }; -void entity_view_pack_struct(void *data, size_t len, entity_view view) { +size_t entity_view_pack_struct(void *data, size_t len, entity_view view) { cw_pack_context pc = {0}; cw_pack_context_init(&pc, data, len, 0); pkt_pack_struct(&pc, pkt_entity_view_desc, PKT_STRUCT_PTR(&view)); + return pc.current - pc.start; } entity_view entity_view_unpack_struct(void *data, size_t len) { cw_unpack_context uc = {0}; cw_unpack_context_init(&uc, data, len, 0); - entity_view view; + entity_view view = {0}; pkt_unpack_struct(&uc, pkt_entity_view_desc, PKT_STRUCT_PTR(&view)); return view; } diff --git a/code/apps/client/header/entity_view.h b/code/common/entity_view.h similarity index 79% rename from code/apps/client/header/entity_view.h rename to code/common/entity_view.h index 36f8038..ed44f27 100644 --- a/code/apps/client/header/entity_view.h +++ b/code/common/entity_view.h @@ -6,7 +6,14 @@ #include "packet_utils.h" +typedef enum { + EKIND_PLAYER, + EKIND_CHUNK, + FORCE_EKIND_UINT16 = UINT16_MAX +} entity_kind; + typedef struct entity_view { + entity_kind kind; double x; double y; } entity_view; @@ -24,5 +31,5 @@ void entity_view_destroy(entity_view_tbl *map, uint64_t ent_id); entity_view *entity_view_get(entity_view_tbl *map, uint64_t ent_id); void entity_view_map(entity_view_tbl *map, void (*map_proc)(uint64_t key, entity_view value)); -void entity_view_pack_struct(void *data, size_t len, entity_view view); +size_t entity_view_pack_struct(void *data, size_t len, entity_view view); entity_view entity_view_unpack_struct(void *data, size_t len); diff --git a/code/common/packet.c b/code/common/packet.c index a2c5869..f4d462c 100644 --- a/code/common/packet.c +++ b/code/common/packet.c @@ -66,9 +66,15 @@ int32_t pkt_unpack_struct(cw_unpack_context *uc, pkt_desc *desc, void *raw_blob, if (uc->item.type != field->type) return -1; // unexpected field if (blob + field->offset + field->size > blob + blob_size) return -1; // field does not fit switch (field->type) { - case CWP_ITEM_NEGATIVE_INTEGER: - case CWP_ITEM_DOUBLE: - case CWP_ITEM_FLOAT: + case CWP_ITEM_DOUBLE: { + zpl_memcopy(blob + field->offset, (uint8_t*)&uc->item.as.long_real, field->size); + }break; + case CWP_ITEM_FLOAT: { + zpl_memcopy(blob + field->offset, (uint8_t*)&uc->item.as.real, field->size); + } break; + case CWP_ITEM_NEGATIVE_INTEGER: { + zpl_memcopy(blob + field->offset, (uint8_t*)&uc->item.as.i64, field->size); + }break; case CWP_ITEM_POSITIVE_INTEGER: { zpl_memcopy(blob + field->offset, (uint8_t*)&uc->item.as.u64, field->size); }break; diff --git a/code/common/packets/pkt_00_init.c b/code/common/packets/pkt_00_init.c index a874a10..c364345 100644 --- a/code/common/packets/pkt_00_init.c +++ b/code/common/packets/pkt_00_init.c @@ -31,7 +31,7 @@ int32_t pkt_00_init_handler(pkt_header *header) { PKT_IF(pkt_msg_decode(header, pkt_00_init_desc, pkt_pack_desc_args(pkt_00_init_desc), PKT_STRUCT_PTR(&table))); uint64_t peer_id = (uint64_t)header->udata; - uint64_t ent_id = player_spawn(zpl_bprintf("client_%d", peer_id)); + uint64_t ent_id = player_spawn(NULL); ecs_set(world_ecs(), ent_id, ClientInfo, {.peer = ent_id, .view_id = header->view_id }); pkt_01_welcome_send(peer_id, header->view_id, ent_id, world_block_size(), world_chunk_size(), world_world_size()); return 0; diff --git a/code/common/player.c b/code/common/player.c index a306c19..2eb1126 100644 --- a/code/common/player.c +++ b/code/common/player.c @@ -7,6 +7,7 @@ #include "modules/general.h" #include "modules/controllers.h" #include "modules/net.h" +#include "zpl.h" uint64_t player_spawn(char *name) { ECS_IMPORT(world_ecs(), General); @@ -14,6 +15,10 @@ uint64_t player_spawn(char *name) { ECS_IMPORT(world_ecs(), Net); ecs_entity_t e = ecs_new(world_ecs(), 0); + + if (!name) { + name = zpl_bprintf("player_%d", e); + } ecs_add(world_ecs(), e, EcsClient); ecs_set(world_ecs(), e, ClientInfo, {0}); diff --git a/code/common/world/world.c b/code/common/world/world.c index 6579516..aba6a66 100644 --- a/code/common/world/world.c +++ b/code/common/world/world.c @@ -34,9 +34,20 @@ entity_view world_build_entity_view(int64_t e) { ECS_IMPORT(world_ecs(), General); entity_view view = {0}; - Position *pos = ecs_get(world_ecs(), e, Position); - view.x = pos->x; - view.y = pos->y; + // TODO(zaklaus): branch out based on ECS tags + const Position *pos = ecs_get(world_ecs(), e, Position); + if (pos) { + view.kind = EKIND_PLAYER; + view.x = pos->x; + view.y = pos->y; + } + + const Chunk *chpos = ecs_get(world_ecs(), e, Chunk); + if (chpos) { + view.kind = EKIND_CHUNK; + view.x = chpos->x; + view.y = chpos->y; + } return view; } @@ -47,9 +58,7 @@ int32_t tracker_write_create(librg_world *w, librg_event *e) { size_t actual_length = librg_event_size_get(w, e); char *buffer = librg_event_buffer_get(w, e); - entity_view_pack_struct(buffer, actual_length, world_build_entity_view(entity_id)); - - return 0; + return entity_view_pack_struct(buffer, actual_length, world_build_entity_view(entity_id)); } int32_t tracker_write_remove(librg_world *w, librg_event *e) { @@ -61,9 +70,7 @@ int32_t tracker_write_update(librg_world *w, librg_event *e) { size_t actual_length = librg_event_size_get(w, e); char *buffer = librg_event_buffer_get(w, e); - entity_view_pack_struct(buffer, actual_length, world_build_entity_view(entity_id)); - - return 0; + return entity_view_pack_struct(buffer, actual_length, world_build_entity_view(entity_id)); } void world_setup_pkt_handlers(world_pkt_reader_proc *reader_proc, world_pkt_writer_proc *writer_proc) { @@ -140,6 +147,8 @@ int32_t world_destroy(void) { return WORLD_ERROR_NONE; } +#define WORLD_LIBRG_BUFSIZ 8192 + static void world_tracker_update(void) { if (world.tracker_update > zpl_time_rel_ms()) return; world.tracker_update = zpl_time_rel_ms() + WORLD_TRACKER_UPDATE_MS; @@ -148,13 +157,13 @@ static void world_tracker_update(void) { ecs_query_t *query = ecs_query_new(world.ecs, "Net.ClientInfo"); ecs_iter_t it = ecs_query_iter(query); - char buffer[8096] = {0}; + static char buffer[WORLD_LIBRG_BUFSIZ] = {0}; while (ecs_query_next(&it)) { ClientInfo *p = ecs_column(&it, ClientInfo, 1); for (int i = 0; i < it.count; i++) { - size_t datalen = 8096; + size_t datalen = WORLD_LIBRG_BUFSIZ; int32_t result = librg_world_write(world_tracker(), p[i].peer, buffer, &datalen, NULL); if (result > 0) { diff --git a/code/common/world/world.h b/code/common/world/world.h index 74b7ac4..7667910 100644 --- a/code/common/world/world.h +++ b/code/common/world/world.h @@ -30,4 +30,4 @@ librg_world * world_tracker(void); uint16_t world_block_size(void); uint16_t world_chunk_size(void); -uint16_t world_world_size(void); \ No newline at end of file +uint16_t world_world_size(void); diff --git a/code/modules/source/general.c b/code/modules/source/general.c index 1327915..fab4bf3 100644 --- a/code/modules/source/general.c +++ b/code/modules/source/general.c @@ -4,10 +4,9 @@ void GeneralImport(ecs_world_t *ecs) { ECS_MODULE(ecs, General); ecs_set_name_prefix(ecs, "General"); - ECS_COMPONENT(ecs, Position); - ECS_IMPORT(ecs, FlecsMeta); + ECS_META(ecs, Position); ECS_META(ecs, Chunk); ECS_META(ecs, Vector2D); ECS_META(ecs, Drawable);