Game.WaterLevelChangeSystem
Assembly: Assembly-CSharp
Namespace: Game.Simulation
Type: class
Base: GameSystemBase
Summary:
WaterLevelChangeSystem processes WaterLevelChange components each simulation tick (on a reduced update interval) and updates their intensity based on prefab-defined WaterLevelChangeData and the current simulation frame. It uses a Burst-compiled IJobChunk (WaterLevelChangeJob) to iterate matching entities in parallel, reads PrefabRef and Duration data, computes elapsed time since start, and applies wave/tsunami-like intensity curves (currently implemented for the Sine change type). The system schedules its work as a job and registers the job handle with an EndFrameBarrier so work completes before end-of-frame operations. It also exposes utilities like computing a minimum delay for wave arrival at a position.
Fields
-
public static readonly int kUpdateInterval
Static constant that controls how often the system runs. Its value is 4, so the system updates every 4 ticks (GetUpdateInterval returns this). -
private SimulationSystem m_SimulationSystem
Reference to the SimulationSystem. Used to read the current simulation frame (m_SimulationSystem.frameIndex) used to compute progression of water level changes. -
private EndFrameBarrier m_EndFrameBarrier
Reference to the EndFrameBarrier system. The system adds its job handle to this barrier to ensure jobs that produce changes complete before other end-of-frame work runs. -
private EntityQuery m_WaterLevelChangeQuery
EntityQuery used to find entities that have a WaterLevelChange component (excluding Deleted). The query is required for update so the system only runs when relevant entities exist. -
private TypeHandle __TypeHandle
Container of ECS type handles used by the job and system (EntityTypeHandle, ComponentTypeHandle, ComponentTypeHandle , ComponentTypeHandle , ComponentLookup ). The TypeHandle provides an __AssignHandles method to initialize these handles from a SystemState. -
private struct WaterLevelChangeJob
(nested)
Burst-compiled IJobChunk implementation that performs the per-chunk work. Contains: EntityTypeHandle m_EntityType
(ReadOnly)ComponentTypeHandle<PrefabRef> m_PrefabRefType
(ReadOnly)ComponentTypeHandle<WaterLevelChange> m_WaterLevelChangeType
(Read/Write)ComponentTypeHandle<Duration> m_DurationType
(ReadOnly)ComponentLookup<WaterLevelChangeData> m_PrefabWaterLevelChangeData
(ReadOnly)uint m_SimulationFrame
(current simulation frame index used in calculations)
The job computes elapsed time, reads WaterLevelChangeData from prefab, and updates WaterLevelChange.m_Intensity. The main logic implements a "Sine" change type behavior, scaling intensities and applying an escalation delay. If other change types are present they are currently not handled (code hints at other types but no implementation).
private struct TypeHandle
(nested)
Struct grouping the various type handles returned by the system. Contains a method __AssignHandles to fetch handles from a given SystemState.
Properties
public static int TsunamiEndDelay { get; }
Computed property returning the Tsunami end delay in frames. It calculates Mathf.RoundToInt((float)WaterSystem.kMapSize / WaterSystem.WaveSpeed). This is used internally to compute wave timings relative to map size and wave speed constants.
Constructors
public WaterLevelChangeSystem()
Default constructor. The system relies on OnCreate to initialize references and queries. Marked with [Preserve] on lifecycle methods to prevent stripping.
Methods
-
public override int GetUpdateInterval(SystemUpdatePhase phase)
Returns the update interval (kUpdateInterval). This tells the framework how often the system should run (every 4 simulation frames by default). -
public static uint GetMinimumDelayAt(WaterLevelChange change, float3 position)
Utility method that computes the minimum delay (in frames) for a water wave generated by a given WaterLevelChange to reach a world position. It computes an origin point on the map edge based on change.m_Direction and projects the position onto a perpendicular vector to estimate radial distance and divides by WaterSystem.WaveSpeed, rounding to nearest frame. Use this to determine arrival times of waves/tsunamis relative to a change event. -
protected override void OnCreate()
System initialization: obtains SimulationSystem and EndFrameBarrier, creates the m_WaterLevelChangeQuery for WaterLevelChange components, and calls RequireForUpdate(m_WaterLevelChangeQuery) so the system only runs when relevant entities exist. -
protected override void OnUpdate()
Main update method that prepares a WaterLevelChangeJob with the required type handles and current simulation frame, schedules it as a parallel chunk job (JobChunkExtensions.ScheduleParallel), sets base.Dependency to the returned handle, and registers the handle with m_EndFrameBarrier via AddJobHandleForProducer to ensure ordering with end-of-frame work. -
private void __AssignQueries(ref SystemState state)
Compiler helper that sets up queries at compile-time; in this build it's effectively a placeholder that instantiates an EntityQueryBuilder and disposes it. Used by OnCreateForCompiler. -
protected override void OnCreateForCompiler()
Compiler helper called during system creation in certain build flows. Calls __AssignQueries and initializes type handles via __TypeHandle.__AssignHandles(ref base.CheckedStateRef). -
private void TypeHandle.__AssignHandles(ref SystemState state)
Initializes the internal type handles (EntityTypeHandle, PrefabRef read-only, WaterLevelChange read/write, Duration read-only, WaterLevelChangeData lookup read-only) using the provided SystemState. Called from OnCreateForCompiler to prepare handles used by jobs. -
private void WaterLevelChangeJob.Execute(in ArchetypeChunk chunk, int unfilteredChunkIndex, bool useEnabledMask, in v128 chunkEnabledMask)
Job execution logic (see nested job fields above). For each entity in the chunk it: - Reads PrefabRef, WaterLevelChange, Duration
- Fetches WaterLevelChangeData from the prefab
- Computes elapsed time since duration.m_StartFrame, subtracting m_EscalationDelay
- If not yet started (elapsed < 0) continues
- If change type is Sine, calculates a time window (num2) and applies different sine-based formulas for early escalation and main wave, capping to zero after end. Finally multiplies computed intensity by 4f.
- Writes back WaterLevelChange.m_Intensity into component array
Note: other change types are present in the data model but currently not implemented in this job (the code has placeholders for other cases).
Usage Example
[Preserve]
protected override void OnCreate()
{
base.OnCreate();
m_SimulationSystem = base.World.GetOrCreateSystemManaged<SimulationSystem>();
m_EndFrameBarrier = base.World.GetOrCreateSystemManaged<EndFrameBarrier>();
m_WaterLevelChangeQuery = GetEntityQuery(ComponentType.ReadWrite<WaterLevelChange>(), ComponentType.Exclude<Deleted>());
RequireForUpdate(m_WaterLevelChangeQuery);
}
Notes and tips: - The system is optimized to run only occasionally (kUpdateInterval) and uses Burst + JobChunk for parallel processing; keep component layouts and chunk sizes in mind for performance. - WaterLevelChangeData (read via prefab lookup) contains configuration like m_MaxIntensity, m_EscalationDelay, and m_ChangeType. Modify those in prefab definitions to adjust behavior. - If adding new change types, extend the WaterLevelChangeJob.Execute logic accordingly and ensure deterministic behavior across frames. - The EndFrameBarrier integration ensures jobs are completed before end-of-frame systems act on the results; remember to register new producer jobs similarly.