20 utl::Logger::log(
"EntityManager: Player with sessionId " + std::to_string(sessionId) +
" already exists",
32 .with<ecs::Velocity>(
"player_velocity_" + std::to_string(sessionId), 0.0f, 0.0f)
33 .with<ecs::Player>(
"player_" + std::to_string(sessionId),
true)
34 .with<ecs::Health>(
"player_health_" + std::to_string(sessionId), 100.0f, 100.0f)
35 .with<ecs::BeamCharge>(
"beam_charge_" + std::to_string(sessionId), 0.0f, 1.0f)
36 .with<ecs::Hitbox>(
"player_hitbox_" + std::to_string(sessionId), 10.0f, 0.0f, 0.0f)
45 utl::Logger::log(
"EntityManager: Created player entity for sessionId " + std::to_string(sessionId) +
46 " at position (" + std::to_string(x) +
", " + std::to_string(y) +
")",
58 metadata->isActive =
false;
64 utl::Logger::log(
"EntityManager: Marked player " + std::to_string(sessionId) +
" for destruction",
93 std::uint32_t aliveCount = 0;
109 utl::Logger::log(
"EntityManager: Player " + std::to_string(sessionId) +
" earned " + std::to_string(points) +
137 .with<ecs::Velocity>(
"enemy_velocity_" + std::to_string(enemyId), -200.0f, 0.0f)
138 .with<ecs::Enemy>(
"enemy_" + std::to_string(enemyId), health, health, 10.0f, 200.0f, 0.0f, 2.0f)
139 .with<ecs::Hitbox>(
"enemy_hitbox_" + std::to_string(enemyId), 30.0f, 0.0f,
146 utl::Logger::log(
"EntityManager: Created basic enemy " + std::to_string(enemyId) +
" at position (" +
147 std::to_string(x) +
", " + std::to_string(y) +
")",
164 .with<ecs::Velocity>(
"enemy_velocity_" + std::to_string(enemyId), -150.0f, 0.0f)
165 .with<ecs::Enemy>(
"enemy_" + std::to_string(enemyId), health, health, 20.0f, 150.0f, 0.0f, 1.5f)
166 .with<ecs::Hitbox>(
"enemy_hitbox_" + std::to_string(enemyId), 35.0f, 0.0f,
173 utl::Logger::log(
"EntityManager: Created advanced enemy " + std::to_string(enemyId) +
" at position (" +
174 std::to_string(x) +
", " + std::to_string(y) +
")",
191 .with<ecs::Velocity>(
"boss_velocity_" + std::to_string(enemyId), -50.0f, 0.0f)
192 .with<ecs::Enemy>(
"boss_" + std::to_string(enemyId), health, health, 50.0f, 50.0f, 0.0f, 0.5f)
193 .with<ecs::Hitbox>(
"boss_hitbox_" + std::to_string(enemyId), 90.0f, 0.0f,
200 utl::Logger::log(
"EntityManager: Created boss " + std::to_string(enemyId) +
" at position (" +
201 std::to_string(x) +
", " + std::to_string(y) +
")",
212 metadata->isActive =
false;
229 float damage = isSupercharged ? 50.0f : 25.0f;
230 int pierce = isSupercharged ? 3 : 1;
231 float hitboxRadius = isSupercharged ? 8.0f : 5.0f;
235 .
with<
ecs::Transform>(
"projectile_transform_" + std::to_string(projectileId), x, y, 0.0f)
236 .with<ecs::Velocity>(
"projectile_velocity_" + std::to_string(projectileId), vx, vy)
237 .with<ecs::Projectile>(
"projectile_" + std::to_string(projectileId), projType, damage, 5.0f, 0.0f,
239 .with<ecs::Hitbox>(
"projectile_hitbox_" + std::to_string(projectileId), hitboxRadius, 0.0f, 0.0f)
245 return projectileEntity;
254 .
with<
ecs::Transform>(
"enemy_projectile_transform_" + std::to_string(projectileId), x, y, 0.0f)
255 .with<ecs::Velocity>(
"enemy_projectile_velocity_" + std::to_string(projectileId), vx, vy)
257 15.0f, 10.0f, 0.0f, 1)
258 .with<ecs::Hitbox>(
"enemy_projectile_hitbox_" + std::to_string(projectileId), 5.0f, 0.0f, 0.0f)
264 return projectileEntity;
272 metadata->isActive =
false;
287 if (metadata.lifetime > 0.0f && metadata.isActive)
289 metadata.currentLife += deltaTime;
290 if (metadata.currentLife >= metadata.lifetime)
321 std::vector<rnp::EntityState> states;
329 if (transform && velocity)
332 state.
id = networkId;
333 state.
type =
static_cast<std::uint16_t
>(netType);
334 state.
subtype =
static_cast<std::uint8_t
>(subtype);
335 state.
x = transform->x;
336 state.
y = transform->y;
337 state.
vx = velocity->
x;
338 state.
vy = velocity->
y;
346 if (health && health->max > 0.0f)
348 float healthPct = (health->current / health->max) * 100.0f;
349 state.
healthPercent =
static_cast<std::uint8_t
>(std::max(0.0f, std::min(100.0f, healthPct)));
355 if (enemy && enemy->max_health > 0.0f)
357 float healthPct = (enemy->health / enemy->max_health) * 100.0f;
358 state.
healthPercent =
static_cast<std::uint8_t
>(std::max(0.0f, std::min(100.0f, healthPct)));
369 state.
stateFlags =
static_cast<std::uint8_t
>(beamCharge->current_charge * 255.0f);
376 states.push_back(state);
383 if (metadata && metadata->isActive)
389 states.back().score =
static_cast<std::uint32_t
>(
getScore(sessionId));
397 if (metadata && metadata->isActive)
418 addEntityState(enemyId, entity, netType, subtype);
425 if (metadata && metadata->isActive)
546 float lifetime, std::uint32_t ownerId)
550 metadata.
type = type;
602 utl::Logger::log(
"EntityManager: Destroyed player entity for sessionId " + std::to_string(networkId),
Centralized entity lifecycle management system for R-Type server.
Configuration constants for the multiplayer game.
This file contains the Logger class.
EntityBuilder & with(Args &&...args)
Class for managing entities and their components.
EntityBuilder createEntity()
bool hasComponent(Entity e)
T * getComponent(Entity e)
void removeComponent(Entity e)
ecs::Entity getPlayer(std::uint32_t sessionId)
Get player entity by session ID.
std::unordered_map< std::uint32_t, EntityMetadata > m_entityMetadata
Entity metadata by network ID.
ecs::Entity getProjectile(std::uint32_t projectileId)
Get projectile entity by network ID.
void addScore(std::uint32_t sessionId, int points)
Add points to a player's score.
std::uint32_t m_nextEnemyId
Next available enemy network ID.
bool hasPlayer(std::uint32_t sessionId) const
Check if player exists.
void cleanupDestroyedEntities()
Process destruction queue and remove destroyed entities.
void markPlayerAsDead(std::uint32_t sessionId)
Mark a player as dead without destroying the entity.
void destroyPlayer(std::uint32_t sessionId)
Destroy a player entity.
ecs::Entity createPlayerProjectile(std::uint32_t playerId, float x, float y, float vx, float vy, bool isSupercharged=false)
Create a player projectile entity.
void updateLifetimes(float deltaTime)
Update lifetime counters for temporary entities.
EntityManager(ecs::Registry ®istry)
Constructor.
std::unordered_map< std::uint32_t, ecs::Entity > m_powerupEntities
Powerup entities by network ID.
std::vector< std::uint32_t > m_destroyQueue
Queue of network IDs pending destruction.
std::uint32_t getNetworkIdForEntity(ecs::Entity entity) const
Get network ID for an entity handle.
rnp::EntityType getNetworkEntityType(ServerEntityType type) const
Convert server entity type to network protocol entity type.
std::unordered_set< std::uint32_t > m_deadPlayers
Set of dead player session IDs.
ecs::Entity createBoss(float x, float y, float health=1000.0f)
Create a boss enemy entity.
void processDestroyQueue()
Process pending entity destructions from queue.
ecs::Entity getPlayerEntity(std::uint32_t sessionId) const
Get player entity by session ID (const version)
int getScore(std::uint32_t sessionId) const
Get player's current score.
ecs::Entity createAdvancedEnemy(float x, float y, float health=100.0f)
Create an advanced enemy entity.
std::unordered_map< ecs::Entity, std::uint32_t > m_entityToNetworkId
Reverse lookup map.
std::unordered_map< std::uint32_t, ecs::Entity > m_projectileEntities
Projectile entities by network ID.
ecs::Entity createPlayer(std::uint32_t sessionId, float x, float y)
Create a new player entity.
std::unordered_map< std::uint32_t, ecs::Entity > m_playerEntities
Player entities by session ID.
EntityMetadata * getEntityMetadata(std::uint32_t networkId)
Get entity metadata by network ID.
void destroyProjectile(std::uint32_t projectileId)
Destroy a projectile entity.
std::vector< rnp::EntityState > getAllEntityStates() const
Get network state for all entities.
ecs::Registry & m_registry
Reference to ECS registry.
void clear()
Clear all entities and reset manager state.
void destroyEnemy(std::uint32_t enemyId)
Destroy an enemy entity.
size_t getTotalEntityCount() const
Get total count of all managed entities.
std::unordered_map< std::uint32_t, ecs::Entity > m_enemyEntities
Enemy entities by network ID.
std::uint32_t getAlivePlayerCount() const
Get count of alive players.
ecs::Entity createBasicEnemy(float x, float y, float health=50.0f)
Create a basic enemy entity.
std::uint32_t m_nextProjectileId
Next available projectile network ID.
ecs::Entity createEnemyProjectile(std::uint32_t enemyId, float x, float y, float vx, float vy)
Create an enemy projectile entity.
void registerEntity(ecs::Entity entity, ServerEntityType type, std::uint32_t networkId, float lifetime=-1.0f, std::uint32_t ownerId=0)
Register a new entity with the manager.
std::unordered_map< std::uint32_t, int > m_playerScores
Player scores by session ID.
void resetScore(std::uint32_t sessionId)
Reset player's score to zero.
void unregisterEntity(std::uint32_t networkId)
Unregister an entity from the manager.
ecs::Entity getEnemy(std::uint32_t enemyId)
Get enemy entity by network ID.
static void log(const std::string &message, const LogLevel &logLevel)
constexpr Entity INVALID_ENTITY
ServerEntityType
Enumeration of entity types managed by the server.
@ ENEMY_ADVANCED
Advanced enemy type (complex behavior)
@ PLAYER
Player-controlled entity.
@ PROJECTILE_PLAYER
Player-fired projectile.
@ ENEMY_BASIC
Basic enemy type (simple behavior)
@ PROJECTILE_ENEMY
Enemy-fired projectile.
@ BOSS
Boss enemy (high health, special patterns)
EntityType
Entity types for world state.
EntitySubtype
Entity subtype enumeration.
@ PROJECTILE_PLAYER_SUPERCHARGED
constexpr float SCREEN_WIDTH
constexpr float SCREEN_HEIGHT
Entity state for WORLD_STATE packet.
std::uint8_t healthPercent