group2 0.1.0
CSE 125 Group 2
Loading...
Searching...
No Matches
ServerGame Class Reference

Top-level server game loop. More...

#include <ServerGame.hpp>

Collaboration diagram for ServerGame:
[legend]

Classes

struct  ShotIntentKey
struct  ShotIntentKeyHash

Public Member Functions

bool init (const char *addr, Uint16 port, int tickRateHz=128, int snapshotHz=32, const TransportConfig &transport={})
 Bind to the given address and port, spawn test entities.
void run ()
 Block on the game loop until shutdown() is called.
void shutdown ()
 Signal the loop to stop and release all resources.

Private Member Functions

void eventHandler (Event event)
 Apply a single event to the ECS registry.
void tick (float dt, Uint64 nextTick)
 Advance one physics tick: drain events, run ECS systems, broadcast state.
void initNewPlayerEntity (ClientId clientId)
 Create a new player entity and map it to the given client ID.
void deletePlayerEntity (ClientId clientId)
 Remove player entity from ECS.
void initAnimation ()
 Initialise the server-side animation subsystem (skeleton, clips, hitboxes).
void attachServerAnimator (entt::entity player)
 Create and store a server-side animator for the given player entity.
void detachServerAnimator (entt::entity player)
 Remove the server-side animator for the given entity.
void updateAnimationAndHitboxes (float dt)
 Update all server-side animators and recompute hitbox capsules.
void updateLagCompTargets ()
 Phase 6: write LagCompTarget onto each connected player's entity from their connection's last-reported RTT.
void openGroundTruthLog ()
 Open the ground-truth CSV from env var if set.
void writeGroundTruthLogIfDue ()
 Write one row per replicated player entity if the current tickCount aligns with truthHzDivider_.
void closeGroundTruthLog () noexcept
 Flush + close the CSV if open. Safe to call from dtor.

Private Attributes

physics::MapCollisionData mapCollision_
 Map collision data — owns vectors backing activeWorld().
Server server
 Owns the TCP socket and network I/O.
Registry registry
 ECS entity/component store.
MatchController matchController
 Manages match flow and state.
std::unordered_map< ClientId, entt::entity > clientEntities
 Maps client IDs to ECS entities.
std::vector< NetKillEventpendingKillEvents
 Accumulates kill events waiting for network broadcast.
bool running = false
 Loop continues while true.
int tickRateHz = 128
 Physics ticks per second.
int tickCount = 0
 Total ticks since start, used for periodic logging.
int snapshotEveryNTicks = 4
 Send a registry snapshot every Nth tick.
CharacterRig serverRig_
 Shared skeleton (loaded from same FBX as client).
AnimationLibrary serverAnimLibrary_
 Animation clips for server-side sampling.
HitboxRig hitboxRig_
 Shared hitbox capsule definitions.
float rigScale_ = 1.0f
 Rig model-space → game-unit scale factor.
float rigMeshMinY_ = 0.0f
 Minimum Y of bind-pose mesh (for vertical offset).
bool animationLoaded_ = false
 True if rig+clips loaded successfully.
std::unordered_map< entt::entity, std::unique_ptr< CharacterAnimator > > serverAnimators_
 Per-entity server animators (not ECS components to avoid pulling animation headers into the component registry).
std::FILE * truthCsv_ = nullptr
int truthHzDivider_ = 4
std::unordered_map< ShotIntentKey, ShotIntentPayload, ShotIntentKeyHashpendingShotIntents_

Static Private Attributes

static constexpr std::size_t k_pendingShotIntentsMax = 256

Detailed Description

Top-level server game loop.

Owns the ECS registry and the network Server. Each tick it drains incoming messages, runs all ECS systems, and broadcasts state.

Member Function Documentation

◆ attachServerAnimator()

void ServerGame::attachServerAnimator ( entt::entity player)
private

Create and store a server-side animator for the given player entity.

Here is the caller graph for this function:

◆ closeGroundTruthLog()

void ServerGame::closeGroundTruthLog ( )
privatenoexcept

Flush + close the CSV if open. Safe to call from dtor.

Here is the caller graph for this function:

◆ deletePlayerEntity()

void ServerGame::deletePlayerEntity ( ClientId clientId)
private

Remove player entity from ECS.

Parameters
clientIdNetwork client identifier for the player.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ detachServerAnimator()

void ServerGame::detachServerAnimator ( entt::entity player)
private

Remove the server-side animator for the given entity.

Here is the caller graph for this function:

◆ eventHandler()

void ServerGame::eventHandler ( Event event)
private

Apply a single event to the ECS registry.

Parameters
eventThe event to process.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ init()

bool ServerGame::init ( const char * addr,
Uint16 port,
int tickRateHz = 128,
int snapshotHz = 32,
const TransportConfig & transport = {} )

Bind to the given address and port, spawn test entities.

Parameters
addrHostname or IP to bind to (e.g. "127.0.0.1").
portTCP port to listen on.
tickRateHzPhysics tick rate in Hz (default 128).
snapshotHzRegistry snapshot send rate in Hz (default 32). Must be ≤ tickRateHz; clamped if not. Phase 4 decouples snapshot rate from tick rate so the server can keep deterministic 128 Hz physics while only paying the serialization+broadcast cost a fraction as often.
transportPhase 3d: UDP sidecar feature toggles.
Returns
True on success, false on network or initialisation failure.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ initAnimation()

void ServerGame::initAnimation ( )
private

Initialise the server-side animation subsystem (skeleton, clips, hitboxes).

Called once during init() after map loading.

Here is the call graph for this function:
Here is the caller graph for this function:

◆ initNewPlayerEntity()

void ServerGame::initNewPlayerEntity ( ClientId clientId)
private

Create a new player entity and map it to the given client ID.

Parameters
clientIdNetwork client identifier for the new player.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ openGroundTruthLog()

void ServerGame::openGroundTruthLog ( )
private

Open the ground-truth CSV from env var if set.

No-op when the env var is missing; load tests stay fast by default.

Here is the caller graph for this function:

◆ run()

void ServerGame::run ( )

Block on the game loop until shutdown() is called.

Loop structure (each iteration = one tick at tickRateHz):

  1. server.poll() — accept new connections, read incoming packets, enqueue events (Connected / Disconnected / Input).
  2. tick(dt, nextTick) — process events and run all ECS systems.
  3. Sleep — hybrid sleep+spin-wait to maintain tick cadence.
See also
tick for the per-tick ECS system execution order.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ shutdown()

void ServerGame::shutdown ( )

Signal the loop to stop and release all resources.

Here is the call graph for this function:
Here is the caller graph for this function:

◆ tick()

void ServerGame::tick ( float dt,
Uint64 nextTick )
private

Advance one physics tick: drain events, run ECS systems, broadcast state.

Execution order each tick:

  1. Event drain — dequeue Connected/Disconnected/Input events from the network server until the queue is empty or the tick deadline is exceeded.
  2. Animation + hitboxesupdateAnimationAndHitboxes(dt) samples skeleton poses and recomputes bone-capsule hitboxes for all players.
  3. Weapon systemrunWeapon() processes fire inputs, performs hitscan raycasts against hitbox capsules, applies damage, generates particle/kill events.
  4. MovementrunMovement() applies acceleration, friction, gravity, and special movement modes (wallrun, slide, grapple).
  5. CollisionrunCollision() performs swept-AABB resolution against the world geometry (planes, boxes, brushes).
  6. ExplosionsrunExplosion() processes pending projectile detonations with radius damage.
  7. Player statusrunPlayerStatus() handles respawn timers, death state transitions, and health regeneration.
  8. Weapon spawnersrunWeaponSpawners() ticks pickup cooldowns and spawns weapon entities.
  9. Match controllermatchController.update() manages match phase transitions (warmup → countdown → in-progress → finished).

Broadcast — send updated registry snapshot, particle events, and kill events to all connected clients.

Parameters
dtFixed delta time in seconds (1 / tickRateHz).
nextTickPerformance counter deadline for the current tick.
See also
Game::iterate for the client-side frame loop.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ updateAnimationAndHitboxes()

void ServerGame::updateAnimationAndHitboxes ( float dt)
private

Update all server-side animators and recompute hitbox capsules.

Called once per tick before weapon/damage systems.

Here is the call graph for this function:
Here is the caller graph for this function:

◆ updateLagCompTargets()

void ServerGame::updateLagCompTargets ( )
private

Phase 6: write LagCompTarget onto each connected player's entity from their connection's last-reported RTT.

Translates Connection::lastReportedRttMs (ms) into a targetServerTick = max(0, currentServerTick - rewindTicks), where rewindTicks = clamp(rttMs * tickRateHz / 2000, 0, k_maxLagCompTicks). Players with no client connection (e.g. AI bots in a future expansion) keep their previous target, which on the next pushHitboxHistory will become a valid rewind anchor — but for now, only entities bound through clientEntities get a target.

Called once per tick between pushHitboxHistory and runWeapon.

Here is the caller graph for this function:

◆ writeGroundTruthLogIfDue()

void ServerGame::writeGroundTruthLogIfDue ( )
private

Write one row per replicated player entity if the current tickCount aligns with truthHzDivider_.

Called at the end of each tick after the per-tick physics + broadcast settles.

Here is the caller graph for this function:

Member Data Documentation

◆ animationLoaded_

bool ServerGame::animationLoaded_ = false
private

True if rig+clips loaded successfully.

◆ clientEntities

std::unordered_map<ClientId, entt::entity> ServerGame::clientEntities
private

Maps client IDs to ECS entities.

◆ hitboxRig_

HitboxRig ServerGame::hitboxRig_
private

Shared hitbox capsule definitions.

◆ k_pendingShotIntentsMax

std::size_t ServerGame::k_pendingShotIntentsMax = 256
staticconstexprprivate

◆ mapCollision_

physics::MapCollisionData ServerGame::mapCollision_
private

Map collision data — owns vectors backing activeWorld().

◆ matchController

MatchController ServerGame::matchController
private

Manages match flow and state.

◆ pendingKillEvents

std::vector<NetKillEvent> ServerGame::pendingKillEvents
private

Accumulates kill events waiting for network broadcast.

◆ pendingShotIntents_

std::unordered_map<ShotIntentKey, ShotIntentPayload, ShotIntentKeyHash> ServerGame::pendingShotIntents_
private

◆ registry

Registry ServerGame::registry
private

ECS entity/component store.

◆ rigMeshMinY_

float ServerGame::rigMeshMinY_ = 0.0f
private

Minimum Y of bind-pose mesh (for vertical offset).

◆ rigScale_

float ServerGame::rigScale_ = 1.0f
private

Rig model-space → game-unit scale factor.

◆ running

bool ServerGame::running = false
private

Loop continues while true.

◆ server

Server ServerGame::server
private

Owns the TCP socket and network I/O.

◆ serverAnimators_

std::unordered_map<entt::entity, std::unique_ptr<CharacterAnimator> > ServerGame::serverAnimators_
private

Per-entity server animators (not ECS components to avoid pulling animation headers into the component registry).

◆ serverAnimLibrary_

AnimationLibrary ServerGame::serverAnimLibrary_
private

Animation clips for server-side sampling.

◆ serverRig_

CharacterRig ServerGame::serverRig_
private

Shared skeleton (loaded from same FBX as client).

◆ snapshotEveryNTicks

int ServerGame::snapshotEveryNTicks = 4
private

Send a registry snapshot every Nth tick.

Computed in init() as max(1, tickRateHz / snapshotHz) so the snapshot rate is roughly tickRateHz / snapshotEveryNTicks Hz. With the default 128 / 32 = 4 the server snapshots every 4th tick — 4× less serialization + broadcast work than pre-Phase-4.

◆ tickCount

int ServerGame::tickCount = 0
private

Total ticks since start, used for periodic logging.

◆ tickRateHz

int ServerGame::tickRateHz = 128
private

Physics ticks per second.

◆ truthCsv_

std::FILE* ServerGame::truthCsv_ = nullptr
private

◆ truthHzDivider_

int ServerGame::truthHzDivider_ = 4
private

The documentation for this class was generated from the following files: