Skip to content

Game.Simulation.BuildingEfficiencySystem

Assembly: Assembly-CSharp
Namespace: Game.Simulation

Type: public class

Base: GameSystemBase

Summary:
BuildingEfficiencySystem periodically evaluates building efficiencies and maintains the BuildingFlags.LowEfficiency flag on Building components. It schedules a Burst-compiled IJobChunk (LowEfficiencyJob) to scan building entities in chunks, compare per-building efficiency (from the Efficiency buffer) against a threshold provided by the singleton BuildingEfficiencyParameterData, and update the building flag accordingly. When a building's low-efficiency state changes and the entity has effect owners, the system records that effects need updating by adding an EffectsUpdated component (also adding it to installed upgrades). The system is split across frames using an update-frame index (kUpdatesPerDay = 512) and uses an EndFrameBarrier command buffer to make structural changes safely from a job.


Fields

  • private const int kUpdatesPerDay = 512
    The number of update slots per virtual "day". Used with SimulationUtils.GetUpdateFrame to spread building checks over frames.

  • private SimulationSystem m_SimulationSystem
    Cached reference to the SimulationSystem (used to read the current frame index for scheduling work across frames).

  • private EndFrameBarrier m_EndFrameBarrier
    Barrier system used to create an EntityCommandBuffer. The job writes structural changes (adds EffectsUpdated) via the command buffer producer.

  • private EntityQuery m_BuildingQuery
    EntityQuery configured in OnCreate to select entities with an Efficiency buffer, a Building component and a UpdateFrame shared component, excluding Deleted and Temp. This query is used to schedule the LowEfficiencyJob.

  • private TypeHandle __TypeHandle
    Internal container for the Entity/Component/Buffer/SharedComponent type handles used when scheduling the job.

  • private EntityQuery __query_284724292_0
    Internal query used to obtain the BuildingEfficiencyParameterData singleton (the job reads the threshold value).

Properties

  • None (the system exposes no public properties).
    The class does override the update frequency via GetUpdateInterval, but it does not expose public properties.

Constructors

  • public BuildingEfficiencySystem()
    Default constructor. Initialization is performed in OnCreate / OnCreateForCompiler.

Methods

  • public override int GetUpdateInterval(SystemUpdatePhase phase)
    Returns 32. The method controls how often (in system ticks) the system should be considered for updates by the engine.

  • [Preserve] protected override void OnCreate()
    Initializes the system: acquires references to SimulationSystem and EndFrameBarrier, builds m_BuildingQuery (reads Efficiency buffer, Building component, UpdateFrame shared component; excludes Deleted and Temp), and marks the system as requiring update when BuildingEfficiencyParameterData is present. This sets up runtime requirements and ensures the system runs only when appropriate.

  • [Preserve] protected override void OnUpdate()
    Called each system update (subject to GetUpdateInterval). It:

  • Computes an update-frame index with SimulationUtils.GetUpdateFrame(m_SimulationSystem.frameIndex, 512, 16).
  • Constructs and populates a LowEfficiencyJob instance with type handles, the EndFrameBarrier parallel command buffer writer, the singleton BuildingEfficiencyParameterData and the computed update frame index.
  • Schedules the job using ScheduleParallel on m_BuildingQuery.
  • Registers the job dependency with m_EndFrameBarrier so command buffer playback waits for job completion.

  • protected override void OnCreateForCompiler()
    Internal initialization path used by the compilation/runtime to assign queries and type handles; calls __AssignQueries and assigns type handles stored in __TypeHandle.

  • private void __AssignQueries(ref SystemState state)
    Builds the internal query used to get BuildingEfficiencyParameterData as a singleton; used by OnCreateForCompiler().

Nested / Job-related members (important behavior):

  • private struct LowEfficiencyJob : IJobChunk (BurstCompile)
  • Fields: entity/type handles and buffer/component handles (EntityTypeHandle, SharedComponentTypeHandle<UpdateFrame>, BufferTypeHandle<Efficiency>, BufferTypeHandle<EnabledEffect>, BufferTypeHandle<InstalledUpgrade>, ComponentTypeHandle<Building>), EntityCommandBuffer.ParallelWriter, BuildingEfficiencyParameterData m_EfficiencyParameters, and uint m_UpdateFrameIndex.
  • Execute logic:
    • Checks the chunk's UpdateFrame shared component index; only processes chunks whose index equals m_UpdateFrameIndex. This is how checks are distributed across frames.
    • Iterates entities in the chunk and for each:
    • Reads the building's efficiency via the Efficiency buffer (using BuildingUtils.GetEfficiency).
    • Compares that efficiency with m_EfficiencyParameters.m_LowEfficiencyThreshold.
    • Sets or clears the BuildingFlags.LowEfficiency bit on the Building component.
    • If the entity has an EnabledEffect buffer (checked once per chunk) and the low-efficiency state changed, adds EffectsUpdated to the building entity and to each installed upgrade entity (from the InstalledUpgrade buffer) via the EntityCommandBuffer.ParallelWriter.
    • Uses CollectionUtils.TryGet to safely access the InstalledUpgrade buffer for a given index.
  • The job is Burst-compiled and designed to run in parallel across chunks. Structural changes are done via the command buffer to maintain thread safety.

  • private struct TypeHandle

  • Holds typed handles for Entity/SharedComponent/Buffer/Component types used by the job.
  • public void __AssignHandles(ref SystemState state) assigns runtime handles from the given SystemState (EntityTypeHandle, SharedComponentTypeHandle, BufferTypeHandles for Efficiency/EnabledEffect/InstalledUpgrade, and a writable ComponentTypeHandle).

Notes on threading/behavior: - The job is Burst-compiled and scheduled parallel, so any data mutations that require structural changes are performed through the EndFrameBarrier command buffer. - The system only processes a subset of buildings each frame via the UpdateFrame mechanism; this spreads CPU work across frames for large numbers of buildings. - The system depends on a singleton BuildingEfficiencyParameterData to control the low-efficiency threshold. If that data is absent, the system will not run.

Usage Example

Example: change the low-efficiency threshold stored in the singleton BuildingEfficiencyParameterData. Doing this affects how buildings are marked as low-efficiency by BuildingEfficiencySystem.

// Obtain the entity that holds the singleton BuildingEfficiencyParameterData,
// modify the threshold and write it back.
var em = World.DefaultGameObjectInjectionWorld.EntityManager;
var query = em.CreateEntityQuery(typeof(BuildingEfficiencyParameterData));
if (!query.IsEmptyIgnoreFilter)
{
    var parametersEntity = query.GetSingletonEntity();
    var parameters = em.GetComponentData<BuildingEfficiencyParameterData>(parametersEntity);
    parameters.m_LowEfficiencyThreshold = 0.60f; // set new threshold (example)
    em.SetComponentData(parametersEntity, parameters);
}

Additional tip: - If you are observing no changes, ensure that BuildingEfficiencyParameterData exists in the world and that Efficiency buffers on buildings contain valid data. The system only runs when the query requirements are met and processes chunks according to the update-frame index.