diff options
| author | kasull <qsullian@gmail.com> | 2026-03-11 00:24:47 -0400 |
|---|---|---|
| committer | kasull <qsullian@gmail.com> | 2026-03-11 00:24:47 -0400 |
| commit | ae6718ec0fb21077b767e189aca26b0fed488775 (patch) | |
| tree | a4216103d8a9a77edbc470dc4ab094e77ac30261 /src/game/world/map.cpp | |
| parent | bc1ea16c5be92e3bc810b0a30e01fbc9a7f191a9 (diff) | |
editor object placement and context menus
replace the editor menubar dropdown flow with a reusable context menu
component
merge sprite/entity placement into a single object tool
persist entities, and add undo
support for created sprites and entities
Diffstat (limited to 'src/game/world/map.cpp')
| -rw-r--r-- | src/game/world/map.cpp | 56 |
1 files changed, 56 insertions, 0 deletions
diff --git a/src/game/world/map.cpp b/src/game/world/map.cpp index ba6bb00..a44f191 100644 --- a/src/game/world/map.cpp +++ b/src/game/world/map.cpp @@ -303,6 +303,40 @@ STAT map_sprites_from_section( WORLD_MAP* m, GAME_DATA* g, CFG_SECTION* sprites, return parsec > 0 ? STAT_OK : STAT_ERR; } +STAT map_entities_from_section( WORLD_MAP* m, GAME_DATA*, CFG_SECTION* entities, U32 entityc ) { + if( !entityc ) { + dlog( "map_entities_from_section() : no entities in %s\n", m->name ); + return STAT_OK; + } + + U32 parsec = 0; + char entitysec[256] = { 0 }; + for( U32 i = 0; i < entityc; ++i ) { + MAP_ENTITY entity{}; + + sprintf( entitysec, "%d", i ); + CFG_SECTION* s = cfg_section( entities, entitysec ); + if( !s ) { + dlog( "map_entities_from_section() : missing entity %d in %s\n", i, m->name ); + continue; + } + + CFG_INT* classid = cfg_int( s, "classid" ); + CFG_VEC3* pos = cfg_vec3( s, "pos" ); + if( !classid || !pos ) { + dlog( "map_entities_from_section() : invalid entity %d in %s\n", i, m->name ); + continue; + } + + entity.classid = (U32)classid->value; + entity.pos = pos->value; + m->entities.push( entity ); + ++parsec; + } + + return parsec > 0 ? STAT_OK : STAT_ERR; +} + STAT map_skybox_from_section( CFG_SECTION* s, GAME_DATA* g, WORLD_MAP* m ) { CFG_SECTION* props = cfg_section( s, "props" ); if( !props ) @@ -496,6 +530,13 @@ WORLD_MAP* map_from_file( GAME_DATA* game, const char* path ) { if( !OK( map_sprites_from_section( m, game, sprites, spritec->value ) ) ) { delete m; return 0; } } + CFG_INT* entityc = cfg_int( s, "entitycount" ); + if( entityc ) { + CFG_SECTION* entities = cfg_section( s, "entities" ); + if( !entities ) { dlog( errstr, path, "entities" ); delete m; return 0; } + if( !OK( map_entities_from_section( m, game, entities, entityc->value ) ) ) { delete m; return 0; } + } + CFG_VEC3* startpos = cfg_vec3( s, "startpos" ); if( !startpos ) { dlog( errstr, path, "startpos" ); @@ -537,6 +578,7 @@ void map_serialize_info( CFG_SECTION* s, WORLD_MAP* map ) { cfg_int( "polycount", s, map->polygons.size ); cfg_int( "propcount", s, map->props.size ); cfg_int( "spritecount", s, map->sprites.size ); + cfg_int( "entitycount", s, map->entities.size ); cfg_vec3( "startpos", s, map->startpos ); cfg_float( "startang", s, map->startang ); } @@ -597,6 +639,19 @@ void map_serialize_sprites( CFG_SECTION* s, WORLD_MAP* map ) { } ); } +void map_serialize_entities( CFG_SECTION* s, WORLD_MAP* map ) { + CFG_SECTION* entities = cfg_section_new( "entities", s ); + char name[64]; + + U32 i = 0; + map->entities.each( fn( MAP_ENTITY* e ) { + sprintf( name, "%d", i++ ); + CFG_SECTION* entitysec = cfg_section_new( name, entities ); + cfg_int( "classid", entitysec, e->classid ); + cfg_vec3( "pos", entitysec, e->pos ); + } ); +} + void map_serialize_props( CFG_SECTION* s, WORLD_MAP* map ) { CFG_SECTION* props = cfg_section_new( "props", s ); char name[64]; @@ -623,6 +678,7 @@ CFG_SECTION* map_serialize( WORLD_MAP* map ) { map_serialize_walls( s, map ); map_serialize_polygons( s, map ); map_serialize_sprites( s, map ); + map_serialize_entities( s, map ); return s; } |
