Game.Simulation.WatercraftLaneSelectIterator
Assembly: Game (Assembly-CSharp/Game.dll)
Namespace: Game.Simulation
Type: struct
Base: System.ValueType
Summary:
Iterator/utility used by the watercraft navigation system to evaluate and choose optimal sub-lanes for watercraft. It collects and stores per-sub-lane costs into a temporary buffer, computes costs from lane geometry, lane objects (obstacles, other vehicles), lane reservations and priorities, lane-switch penalties, and supports choosing the best lane for the current and next navigation segments. It also provides helper drawing methods to visualize computed costs. The struct is designed to work with Unity DOTS ECS types: ComponentLookup, BufferLookup, DynamicBuffer and NativeArray.
Fields
-
public ComponentLookup<Owner> m_OwnerData
Component lookup for Owner components of lanes; used to find the buffer of sub-lanes for a slave lane owner. -
public ComponentLookup<Lane> m_LaneData
Component lookup for Lane components (geometry, start/end nodes, length). -
public ComponentLookup<SlaveLane> m_SlaveLaneData
Component lookup for SlaveLane components which contain sub-lane index ranges and flags (allow change, min/max index). -
public ComponentLookup<LaneReservation> m_LaneReservationData
Component lookup for lane reservation metadata (priority, reserved state). -
public ComponentLookup<Moving> m_MovingData
Component lookup for moving flag components used to detect dynamic objects on lanes. -
public ComponentLookup<Watercraft> m_WatercraftData
Component lookup for watercraft-specific component data (e.g., queueing flag). -
public BufferLookup<SubLane> m_Lanes
Buffer lookup that provides the list of sub-lanes (DynamicBuffer) for an owner entity. -
public BufferLookup<LaneObject> m_LaneObjects
Buffer lookup for LaneObject buffers attached to sub-lane entities (obstacles, queued vehicles, etc). -
public Entity m_Entity
The entity for which the iterator is evaluating lanes (typically the watercraft entity). -
public Entity m_Blocker
An entity used as a special blocker when computing costs (e.g., the entity that is considered blocking). -
public int m_Priority
Priority value of the evaluating entity; used to compute additional costs against lane reservations. -
private NativeArray<float> m_Buffer
NativeArray used to store computed costs per sub-lane for the current evaluated navigation segment(s). Provided via SetBuffer. -
private int m_BufferPos
Current write position in m_Buffer. -
private float m_LaneSwitchCost
Current computed multiplier for lane-switch penalty. Adjusted per slave-lane flags. -
private float m_LaneSwitchBaseCost
Base lane switch cost that evolves across calculations (small increment/decrement to break ties). -
private Entity m_PrevLane
Previously selected lane (used to prefer continuity and compute reachable sub-lanes).
Properties
- This struct exposes no public properties. (All state is via public fields and methods.)
Constructors
public WatercraftLaneSelectIterator()
Default value-type constructor (implicit). Typical initialization of lookups and other fields is done by the caller before use (no explicit constructor logic in source).
Methods
-
public void SetBuffer(ref WatercraftLaneSelectBuffer buffer)
Ensures and sets the internal NativeArraybuffer used to store computed sub-lane costs. Call this before computing costs. -
public void CalculateLaneCosts(WatercraftNavigationLane navLaneData, int index)
Calculate costs for all sub-lanes of the given navigation lane (navLaneData) and append them into the internal buffer. This overload is used when there's no "next" lane to consider for switching; it considers lane objects and basic per-sub-lane costs. The index parameter controls whether blocker-aware logic runs (index < 2 uses m_Blocker). -
private float CalculateLaneObjectCost(float laneObjectCost, int index, Entity lane, WatercraftLaneFlags laneFlags)
Helper that computes lane object contribution to cost for a sub-lane by iterating its LaneObject buffer. If a blocker is present and index < 2, it treats that lane object specially. Returns added cost. -
private float CalculateLaneObjectCost(float laneObjectCost, Entity lane, float minCurvePosition, WatercraftLaneFlags laneFlags)
Helper that sums lane object costs only for lane objects whose curve position is after minCurvePosition (useful when evaluating from a particular point on the curve). -
private float CalculateLaneObjectCost(LaneObject laneObject, float laneObjectCost, WatercraftLaneFlags laneFlags)
Evaluates the cost of an individual LaneObject. If the LaneObject entity is not moving:- If it's a queued watercraft and both the object and lane flag indicate queueing, returns laneObjectCost.
- Otherwise returns a high cost proportional to the lane object's curve position (uses lerp between 10M and 9M as a deterrent). If the lane object is moving, returns the base laneObjectCost.
-
public void CalculateLaneCosts(WatercraftNavigationLane navLaneData, WatercraftNavigationLane nextNavLaneData, int index)
The core overload that calculates costs for sub-lanes in navLaneData considering the next navigation lane (nextNavLaneData) — i.e., it factors in lane-switch costs to reach the next lane's sub-lanes and handles GroupTarget / TransformTarget / fixed/reserved flags. Results are appended to the internal buffer. This method:- Sets m_LaneSwitchCost based on allowance of lane changes.
- Computes and merges switch penalties with precomputed costs for nextNavLaneData's sub-lanes stored earlier in the buffer.
- Adds lane object costs and lane reservation priority penalties.
- Advances internal base cost (m_LaneSwitchBaseCost) to break ties.
-
private float GetLaneSwitchCost(int numLanes)
Returns the lane switching penalty for moving numLanes sub-lanes away: (numLanes^3) * m_LaneSwitchCost. -
private float GetLanePriorityCost(int lanePriority)
Returns a penalty for lane reservations based on difference between lanePriority and m_Priority (non-negative). -
public void UpdateOptimalLane(ref WatercraftCurrentLane currentLaneData, WatercraftNavigationLane nextNavLaneData)
Given current lane state for a watercraft and the next navigation lane, evaluate buffer values and pick an optimal sub-lane for the next segment. This method:- Uses m_Buffer entries (computed earlier for nextNavLaneData) to pick best target sub-lane while considering lane-switch cost from the current sub-lane position, lane objects, and reservations.
- Updates currentLaneData.m_ChangeLane and m_ChangeProgress appropriately if a lane change should begin or be completed.
- Tracks m_PrevLane and resets m_LaneSwitchCost to a large value after selection.
-
public void UpdateOptimalLane(ref WatercraftNavigationLane navLaneData)
Finalizes the selection for a navigation lane when previous buffer data exists. Typically called after CalculateLaneCosts for the "next" lane and will pick the best actual sub-lane to use in navLaneData.m_Lane based on earlier computed costs and m_PrevLane. Adjusts base lane switch cost slightly after completion. -
public void DrawLaneCosts(WatercraftCurrentLane currentLaneData, WatercraftNavigationLane nextNavLaneData, ComponentLookup<Curve> curveData, GizmoBatcher gizmoBatcher)
Prepares m_PrevLane based on current lane change progress. (This overload does not draw itself — it sets state used for drawing calls.) -
public void DrawLaneCosts(WatercraftNavigationLane navLaneData, ComponentLookup<Curve> curveData, GizmoBatcher gizmoBatcher)
Iterates the sub-lanes of navLaneData and uses stored buffer values to draw per-sub-lane gizmos (colors represent cost). If nav lane is reserved or fixed, it draws only selection/no-selection coloring. -
private void DrawLane(Entity lane, float2 curvePos, ComponentLookup<Curve> curveData, GizmoBatcher gizmoBatcher, float cost)
Draw helper that converts a numeric cost into a color scale and submits a Bezier curve segment to a GizmoBatcher. Costs >= 100000 are drawn black; otherwise color is interpolated across cyan->yellow->red using sqrt(cost) scaling.
Usage Example
// Example sketch of using the iterator inside a system or job.
// The actual component lookups / initializations are performed by the surrounding system.
WatercraftLaneSelectIterator iter = new WatercraftLaneSelectIterator();
// Setup component & buffer lookups (done by the system)
// iter.m_OwnerData = GetComponentLookup<Owner>(false);
// iter.m_LaneData = GetComponentLookup<Lane>(false);
// iter.m_SlaveLaneData = GetComponentLookup<SlaveLane>(false);
// iter.m_LaneReservationData = GetComponentLookup<LaneReservation>(false);
// iter.m_MovingData = GetComponentLookup<Moving>(false);
// iter.m_WatercraftData = GetComponentLookup<Watercraft>(false);
// iter.m_Lanes = GetBufferLookup<SubLane>(false);
// iter.m_LaneObjects = GetBufferLookup<LaneObject>(false);
// Provide a temporary cost buffer
WatercraftLaneSelectBuffer scratch = /* obtain or allocate a buffer wrapper */;
iter.SetBuffer(ref scratch);
// Configure per-evaluation state
iter.m_Entity = myWatercraftEntity;
iter.m_Blocker = possibleBlockerEntity;
iter.m_Priority = myPriority;
// Compute costs for a pair of navigation lanes (nav and next)
iter.CalculateLaneCosts(navLaneData, nextNavLaneData, index);
// After costs for several segments are calculated, pick best lane
WatercraftCurrentLane current = /* current lane data */;
iter.UpdateOptimalLane(ref current, nextNavLaneData);
// Visualize
iter.DrawLaneCosts(current, nextNavLaneData, curveLookup, gizmoBatcher);
Notes: - This type is tightly coupled to the DOTS ECS layout of the game's road/watercraft lanes. When using or adapting it in a mod, ensure all BufferLookup/ComponentLookup instances are properly created (read-only or writable as necessary). - m_Buffer is a NativeArray and must be properly provided via WatercraftLaneSelectBuffer.Ensure() and released/managed according to your memory management conventions.