//================================================================================================// // // Constructor from other route element // public TrackCircuitRouteElement(TrackCircuitRouteElement source) { if (null == source) { throw new ArgumentNullException(nameof(source)); } TrackCircuitSection = source.TrackCircuitSection; Direction = source.Direction; OutPin = new EnumArray <TrackDirection, Location>(source.OutPin); if (source.StartAlternativePath != null) { StartAlternativePath = new AlternativePath() { PathIndex = source.StartAlternativePath.PathIndex, TrackCircuitSection = source.StartAlternativePath.TrackCircuitSection, }; } if (source.EndAlternativePath != null) { EndAlternativePath = new AlternativePath() { PathIndex = source.EndAlternativePath.PathIndex, TrackCircuitSection = source.EndAlternativePath.TrackCircuitSection, }; } FacingPoint = source.FacingPoint; UsedAlternativePath = source.UsedAlternativePath; MovingTableApproachPath = source.MovingTableApproachPath; }
/// Constructor (from route path details) public TrackCircuitReversalInfo(TrackCircuitPartialPathRoute lastRoute, int prevReversalIndex, TrackCircuitPartialPathRoute firstRoute, float reverseReversalOffset, int reversalIndex, int reversalSectionIndex) { // preset values Valid = false; LastDivergeIndex = -1; FirstDivergeIndex = -1; LastSignalIndex = -1; FirstSignalIndex = -1; SignalAvailable = false; SignalUsed = false; ReverseReversalOffset = reverseReversalOffset; ReversalIndex = reversalIndex; ReversalSectionIndex = reversalSectionIndex; ReversalActionInserted = false; // search for first common section in last and first int lastIndex = lastRoute.Count - 1; int firstIndex = 0; int lastCommonSection = -1; int firstCommonSection = -1; bool commonFound = false; bool validDivPoint = false; while (!commonFound && lastIndex >= 0) { TrackCircuitRouteElement lastElement = lastRoute[lastIndex]; while (!commonFound && firstIndex <= firstRoute.Count - 1) { TrackCircuitRouteElement firstElement = firstRoute[firstIndex]; if (lastElement.TrackCircuitSection.Index == firstElement.TrackCircuitSection.Index) { commonFound = true; lastCommonSection = lastIndex; firstCommonSection = firstIndex; Valid = (lastElement.Direction != firstElement.Direction); } else { firstIndex++; } } lastIndex--; firstIndex = 0; } // search for last common section going backward along route // do not go back on last route beyond previous reversal point to prevent fall through of reversals if (Valid) { Valid = false; lastIndex = lastCommonSection; firstIndex = firstCommonSection; int endLastIndex = (prevReversalIndex > 0 && prevReversalIndex < lastCommonSection && Simulator.Instance.TimetableMode) ? prevReversalIndex : 0; while (lastIndex >= endLastIndex && firstIndex <= (firstRoute.Count - 1) && lastRoute[lastIndex].TrackCircuitSection.Index == firstRoute[firstIndex].TrackCircuitSection.Index) { LastDivergeIndex = lastIndex; FirstDivergeIndex = firstIndex; DivergeSectorIndex = lastRoute[lastIndex].TrackCircuitSection.Index; lastIndex--; firstIndex++; } // if next route ends within last one, last diverge index can be set to endLastIndex if (firstIndex > firstRoute.Count - 1) { LastDivergeIndex = endLastIndex; DivergeSectorIndex = lastRoute[endLastIndex].TrackCircuitSection.Index; } Valid = LastDivergeIndex >= 0; // it is a reversal validDivPoint = true; if (Simulator.Instance.TimetableMode) { validDivPoint = LastDivergeIndex > 0 && FirstDivergeIndex < (firstRoute.Count - 1); // valid reversal point } if (lastRoute.Count == 1 && FirstDivergeIndex < (firstRoute.Count - 1)) { validDivPoint = true; // valid reversal point in first and only section } } // determine offset if (validDivPoint) { DivergeOffset = 0.0f; for (int iSection = LastDivergeIndex; iSection < lastRoute.Count; iSection++) { TrackCircuitSection thisSection = lastRoute[iSection].TrackCircuitSection; DivergeOffset += thisSection.Length; } // find last signal furthest away from diverging point bool signalFound = false; int startSection = 0; if (!Simulator.Instance.TimetableMode) // In activity mode test starts only after reverse point. { for (int iSection = 0; iSection < firstRoute.Count; iSection++) { if (firstRoute[iSection].TrackCircuitSection.Index == ReversalSectionIndex) { startSection = iSection; break; } } for (int iSection = startSection; iSection <= FirstDivergeIndex && !signalFound; iSection++) { TrackCircuitSection thisSection = firstRoute[iSection].TrackCircuitSection; if (thisSection.EndSignals[firstRoute[iSection].Direction] != null) // signal in required direction { signalFound = true; FirstSignalIndex = iSection; SignalSectorIndex = thisSection.Index; } } } // in timetable mode, search for first signal beyond diverging point else { for (int iSection = FirstDivergeIndex; iSection >= startSection && !signalFound; iSection--) { TrackCircuitSection thisSection = firstRoute[iSection].TrackCircuitSection; if (thisSection.EndSignals[firstRoute[iSection].Direction] != null) // signal in required direction { signalFound = true; FirstSignalIndex = iSection; SignalSectorIndex = thisSection.Index; } } } // signal found if (signalFound) { LastSignalIndex = lastRoute.GetRouteIndex(SignalSectorIndex, LastDivergeIndex); if (LastSignalIndex > 0) { SignalAvailable = true; SignalOffset = 0.0f; for (int iSection = LastSignalIndex; iSection < lastRoute.Count; iSection++) { TrackCircuitSection thisSection = lastRoute[iSection].TrackCircuitSection; SignalOffset += thisSection.Length; } } } } else { FirstDivergeIndex = -1; LastDivergeIndex = -1; } }//constructor