Skip to content

Game.Net.NodeAlignSystem

Assembly: Assembly-CSharp.dll
Namespace: Game.Net

Type: class NodeAlignSystem

Base: GameSystemBase

Summary:
NodeAlignSystem is an ECS system responsible for aligning network node positions and rotations based on their connected edges/curves. It runs a Burst-compiled IJobChunk (UpdateNodeRotationsJob) over nodes that have been updated, iterates connected edges, samples curve tangents and positions, and computes a preferred node position and rotation. The system: - Nudges node positions toward the average of connected curve endpoints (unless the node is marked Standalone). - Computes candidate directions (angles) from connected curve tangents, finds the largest angular gap, and orients the node to lie in that gap (so networks visually align nicely). - Handles special cases such as outside connections (snapping to primary axes) and near-colinear edges (pairwise segment intersection logic). - Uses ComponentLookup and BufferLookup to read Edge, Curve, PrefabRef, NetData, OutsideConnection, Temp, Hidden and the ConnectedEdge buffer for adjacency info. - Schedules the work in parallel via ScheduleParallel and uses Burst for performance.


Fields

  • private EntityQuery m_NodeQuery
    m_NodeQuery is the EntityQuery used to select nodes to process (nodes with Node + Updated components). The system requires this query for update so the job only runs when relevant nodes are marked updated.

  • private TypeHandle __TypeHandle
    Holds precomputed type/handle information used by the job: EntityTypeHandle, ComponentTypeHandles (Standalone, PrefabRef, Node), ComponentLookup handles (Edge, Curve, OutsideConnection, Temp, Hidden, PrefabRef, NetData) and BufferLookup. This struct is initialized for the current SystemState and used to create the job's handles.

  • private struct UpdateNodeRotationsJob (nested)
    Burst-compiled IJobChunk that performs the per-node processing. Key points:

  • Reads entity, Standalone, PrefabRef and other component data and writes Node components.
  • Uses an EdgeIterator over the ConnectedEdge buffer to iterate edges attached to each node.
  • Builds two temporary NativeLists per chunk: angleBuffer (candidate rotation angles normalized to [0,1)) and lineBuffer (Line2.Segment describing offset+direction for pairwise intersection tests).
  • For each connected edge whose net layers are compatible, it accumulates position offsets (to adjust node position) and computes tangent directions (to determine possible node orientations).
  • If not Standalone, it averages positions to nudge node position toward connected curves.
  • If multiple tangents exist, it sorts angles, finds the largest angular gap and orients the node to the midpoint of that gap; handles 2-way special-case.
  • For outside connections (no edges), snaps rotation to the closest world axis.
  • Uses math utilities (MathUtils, Line2, Curve data) heavily.

  • private struct LineComparer : IComparer<Line2.Segment> (nested)
    Comparer used to sort lineBuffer segments. It orders segments using a compact integer selection expression based on segment.ab comparison. Used in the intersection/averaging step prior to computing averaged node position from segment intersections.

  • private struct TypeHandle (nested)
    Contains the per-system ComponentTypeHandle/Lookup/BufferLookup members and exposes __AssignHandles(ref SystemState) to populate them from the current SystemState. This is used in OnCreateForCompiler to prime handles before job scheduling.

Properties

  • (none public)
    This system defines no public properties. All required handles and query references are private and managed by the system.

Constructors

  • public NodeAlignSystem()
    Default preserved constructor. No custom initialization beyond base. System initialization that requires ECS handles/queries is done in OnCreate / OnCreateForCompiler.

Methods

  • protected override void OnCreate() : System.Void
    Initializes the system's EntityQuery (m_NodeQuery) to select entities with Node and Updated components, and calls RequireForUpdate(m_NodeQuery) so the system only runs when such entities exist. Marked with [Preserve] in the original to avoid stripping.

  • protected override void OnUpdate() : System.Void
    Builds and schedules the Burst-compiled UpdateNodeRotationsJob with ScheduleParallel using handles taken from __TypeHandle (via InternalCompilerInterface.Get* wrappers) and the m_NodeQuery. The scheduled JobHandle is assigned to base.Dependency for proper chaining.

  • protected override void OnCreateForCompiler() : System.Void
    Called for compiler-time initialization in generated systems. It calls __AssignQueries and __TypeHandle.__AssignHandles to prepare the TypeHandle and query structures for job creation.

  • private void __AssignQueries(ref SystemState state) : System.Void
    Internal helper used during system initialization. In this implementation it simply constructs and disposes a temporary EntityQueryBuilder — present as a placeholder for query assignment in generated code.

  • UpdateNodeRotationsJob.Execute(in ArchetypeChunk chunk, int unfilteredChunkIndex, bool useEnabledMask, in v128 chunkEnabledMask) : System.Void
    Chunk-execution entry point for the job. Extracts NativeArrays for Entity, Node, PrefabRef and iterates entities in the chunk calling AlignNode for each. Allocates temporary NativeLists per chunk and disposes them when done.

  • UpdateNodeRotationsJob.AlignNode(Entity entity, bool isStandalone, NativeList<float> angleBuffer, NativeList<Line2.Segment> lineBuffer, PrefabRef prefabRef, ref Node node) : System.Void
    Core per-node logic that reads connected edges via EdgeIterator, accumulates offsets and tangents, fills angleBuffer and lineBuffer, and finally computes node.m_Position and node.m_Rotation based on the collected data. Handles special cases for standalone nodes and outside connections.

  • LineComparer.Compare(Line2.Segment x, Line2.Segment y) : int
    Implements ordering used when sorting segment list (lineBuffer) before performing pairwise intersection/averaging computations.

  • TypeHandle.__AssignHandles(ref SystemState state) : System.Void
    Populates the TypeHandle fields with the proper handles (EntityTypeHandle, ComponentTypeHandle, ComponentLookup, BufferLookup) using the SystemState API. Called on system initialization so jobs can read/write the correct component types.

Notes on correctness and usage: - The job uses NativeList and temporary allocations per chunk — keep in mind the memory and CPU cost if many nodes/edges are processed each frame. However, the job is Burst-compiled and scheduled in parallel. - The alignment logic depends on PrefabRef/NetData layer compatibility to include/exclude certain connected edges. - The system expects various ECS components/types (Node, Edge, Curve, ConnectedEdge buffer, PrefabRef, NetData, Standalone, Updated, OutsideConnection, Temp, Hidden) provided by the game's ECS model.

Usage Example

[Preserve]
protected override void OnCreate()
{
    base.OnCreate();
    // NodeAlignSystem initializes its query and requires it for updates:
    // m_NodeQuery = GetEntityQuery(ComponentType.ReadOnly<Node>(), ComponentType.ReadOnly<Updated>());
    // RequireForUpdate(m_NodeQuery);
}

This demonstrates how the system primes its runtime query in OnCreate; the actual alignment occurs in OnUpdate via the Burst-scheduled UpdateNodeRotationsJob.