using Unity.Burst; using Unity.Collections; using Unity.Entities; using Unity.NetCode; using EE2Clone.Components; using EE2Clone.Core; namespace EE2Clone.Systems { /// /// Server-side: sums population-providing buildings per player and updates PopulationMax. /// [BurstCompile] [WorldSystemFilter(WorldSystemFilterFlags.ServerSimulation)] public partial struct PopulationSystem : ISystem { [BurstCompile] public void OnUpdate(ref SystemState state) { // Build a map of playerId → total pop capacity from buildings var popCapMap = new NativeHashMap(GameConstants.MaxPlayers, Allocator.Temp); foreach (var (pop, owner) in SystemAPI.Query, RefRO>() .WithAll() .WithNone()) { int playerId = owner.ValueRO.PlayerId; if (popCapMap.TryGetValue(playerId, out int current)) popCapMap[playerId] = current + pop.ValueRO.Amount; else popCapMap[playerId] = GameConstants.StartingPopulationCap + pop.ValueRO.Amount; } // Count current population per player (units) var popCurrentMap = new NativeHashMap(GameConstants.MaxPlayers, Allocator.Temp); foreach (var owner in SystemAPI.Query>().WithAll()) { int playerId = owner.ValueRO.PlayerId; if (popCurrentMap.TryGetValue(playerId, out int current)) popCurrentMap[playerId] = current + 1; else popCurrentMap[playerId] = 1; } // Update PlayerStateComponent foreach (var playerState in SystemAPI.Query>()) { int pid = playerState.ValueRO.PlayerId; if (popCapMap.TryGetValue(pid, out int cap)) playerState.ValueRW.PopulationMax = System.Math.Min(cap, GameConstants.MaxPopulationCap); else playerState.ValueRW.PopulationMax = GameConstants.StartingPopulationCap; if (popCurrentMap.TryGetValue(pid, out int current)) playerState.ValueRW.PopulationCurrent = current; else playerState.ValueRW.PopulationCurrent = 0; } popCapMap.Dispose(); popCurrentMap.Dispose(); } } }