/*public VehiclePosition GetCurrentPosition() { * LinkedListNode<VehiclePosition> firstNode = CurrentPosition; * if (firstNode == null) * return null; * return firstNode.Value; * }*/ internal void UpdatePosition(ref Vehicle vehicleData, ref PathUnit.Position curPos, ref PathUnit.Position nextPos, bool skipCheck = false) { if (!skipCheck && !CheckValidity(ref vehicleData)) { return; } LastPositionUpdate = Singleton <SimulationManager> .instance.m_currentFrameIndex; SegmentEnd end = TrafficPriority.GetPrioritySegment(GetTransitNodeId(ref curPos, ref nextPos), curPos.m_segment); if (CurrentSegmentEnd != end) { if (CurrentSegmentEnd != null) { Unlink(); } WaitTime = 0; if (end != null) { Link(end); JunctionTransitState = VehicleJunctionTransitState.Enter; } else { JunctionTransitState = VehicleJunctionTransitState.None; } } }
private void Link(SegmentEnd end) { ushort oldFirstRegVehicleId = end.FirstRegisteredVehicleId; if (oldFirstRegVehicleId != 0) { VehicleStateManager._GetVehicleState(oldFirstRegVehicleId).PreviousVehicleIdOnSegment = VehicleId; NextVehicleIdOnSegment = oldFirstRegVehicleId; } end.FirstRegisteredVehicleId = VehicleId; CurrentSegmentEnd = end; }
public static void AddPrioritySegment(ushort nodeId, ushort segmentId, SegmentEnd.PriorityType type) { if (nodeId <= 0 || segmentId <= 0) return; Log.Info("adding PrioritySegment @ node " + nodeId + ", seg. " + segmentId + ", type " + type); var prioritySegment = PrioritySegments[segmentId]; if (prioritySegment != null) { // do not replace with IsPrioritySegment! prioritySegment.Segment = segmentId; Log._Debug("Priority segment already exists. Node1=" + prioritySegment.Node1 + " Node2=" + prioritySegment.Node2); if (prioritySegment.Node1 == nodeId || prioritySegment.Node1 == 0) { Log._Debug("Updating Node1"); prioritySegment.Node1 = nodeId; PrioritySegments[segmentId].Instance1 = new SegmentEnd(nodeId, segmentId, type); return; } if (prioritySegment.Node2 != 0) { // overwrite Node2 Log.Warning("Overwriting priority segment for node " + nodeId + ", seg. " + segmentId + ", type " + type); prioritySegment.Node2 = nodeId; prioritySegment.Instance2 = new SegmentEnd(nodeId, segmentId, type); rebuildPriorityNodes(); } else { // add Node2 Log._Debug("Adding as Node2"); prioritySegment.Node2 = nodeId; prioritySegment.Instance2 = new SegmentEnd(nodeId, segmentId, type); } } else { // add Node1 Log._Debug("Adding as Node1"); prioritySegment = new TrafficSegment(); prioritySegment.Segment = segmentId; prioritySegment.Node1 = nodeId; prioritySegment.Instance1 = new SegmentEnd(nodeId, segmentId, type); PrioritySegments[segmentId] = prioritySegment; } priorityNodes.Add(nodeId); }
internal void Recalculate() { #if DEBUGGEO Log._Debug($"NodeGeometry: Recalculate @ {NodeId}"); #endif Cleanup(); Flags.applyNodeTrafficLightFlag(NodeId); // check if node is valid if (!IsValid()) { for (int i = 0; i < 8; ++i) { SegmentEndGeometries[i] = null; } TrafficLightSimulation.RemoveNodeFromSimulation(NodeId, false, true); Flags.setNodeTrafficLight(NodeId, false); } else { NetManager netManager = Singleton <NetManager> .instance; bool hasTrafficLight = (netManager.m_nodes.m_buffer[NodeId].m_flags & NetNode.Flags.TrafficLights) != NetNode.Flags.None; var nodeSim = TrafficLightSimulation.GetNodeSimulation(NodeId); if (nodeSim == null) { byte numSegmentsWithSigns = 0; for (var s = 0; s < 8; s++) { var segmentId = netManager.m_nodes.m_buffer[NodeId].GetSegment(s); if (segmentId <= 0) { continue; } #if DEBUGx Log._Debug($"NodeGeometry.Recalculate: Housekeeping segment {segmentId}"); #endif SegmentEnd prioritySegment = TrafficPriority.GetPrioritySegment(NodeId, segmentId); if (prioritySegment == null) { continue; } // if node is a traffic light, it must not have priority signs if (hasTrafficLight && prioritySegment.Type != SegmentEnd.PriorityType.None) { Log.Warning($"Housekeeping: Node {NodeId}, Segment {segmentId} is a priority sign but node has a traffic light!"); prioritySegment.Type = SegmentEnd.PriorityType.None; } // if a priority sign is set, everything is ok if (prioritySegment.Type != SegmentEnd.PriorityType.None) { ++numSegmentsWithSigns; } } if (numSegmentsWithSigns > 0) { // add priority segments for newly created segments numSegmentsWithSigns += TrafficPriority.AddPriorityNode(NodeId); } } // calculate node properties byte incomingSegments = 0; byte outgoingSegments = 0; for (int i = 0; i < 8; ++i) { if (SegmentEndGeometries[i] == null) { continue; } #if DEBUGGEO Log._Debug($"NodeGeometry.Recalculate: Iterating over segment end {SegmentEndGeometries[i].SegmentId} @ node {NodeId}"); #endif bool startNode = SegmentEndGeometries[i].StartNode; if (SegmentEndGeometries[i].GetSegmentGeometry().IsIncoming(startNode)) { ++incomingSegments; } if (SegmentEndGeometries[i].GetSegmentGeometry().IsOutgoing(startNode)) { ++outgoingSegments; } } IsSimpleJunction = incomingSegments == 1 || outgoingSegments == 1; #if DEBUGGEO Log._Debug($"NodeGeometry.Recalculate: Node {NodeId} has {incomingSegments} incoming and {outgoingSegments} outgoing segments."); #endif } NotifyObservers(); }