ATC Dimetronic: Implement double signal codes
This commit is contained in:
parent
77869e9c1e
commit
5477d7389c
3 changed files with 70 additions and 28 deletions
|
@ -51,15 +51,15 @@ namespace OpenbveFcmbTrainPlugin
|
|||
/// <summary>The current state of the track.</summary>
|
||||
private TrackStates TrackState;
|
||||
|
||||
/// <summary>The current position of the train.</summary>
|
||||
private double TrainLocation;
|
||||
|
||||
/// <summary>The length of the train.</summary>
|
||||
private readonly double TrainLength;
|
||||
|
||||
/// <summary>The maximum speed in YARD mode.</summary>
|
||||
private readonly Speed YardMaximumSpeed;
|
||||
|
||||
/// <summary>The speed limit for each signal aspect.</summary>
|
||||
private readonly Speed[] AspectLimit = { new Speed(0), new Speed(25 / 3.6), new Speed(25 / 3.6), new Speed(25 / 3.6), new Speed(25 / 3.6), new Speed(45 / 3.6), new Speed(45 / 3.6), new Speed(45 / 3.6), new Speed(45 / 3.6), new Speed(70 / 3.6), new Speed(70 / 3.6), new Speed(70 / 3.6), new Speed(70 / 3.6) };
|
||||
|
||||
/// <summary>The target speed limit for each signal aspect.</summary>
|
||||
private readonly Speed[] AspectTargetLimit = { new Speed(0), new Speed(0), new Speed(0), new Speed(25 / 3.6), new Speed(25 / 3.6), new Speed(0), new Speed(0), new Speed(45 / 3.6), new Speed(45 / 3.6), new Speed(0), new Speed(0), new Speed(70 / 3.6), new Speed(70 / 3.6) };
|
||||
|
||||
/// <summary>Whether ATO is available or not on the train.</summary>
|
||||
private readonly bool AtoAvailable;
|
||||
|
||||
|
@ -113,17 +113,21 @@ namespace OpenbveFcmbTrainPlugin
|
|||
internal int Aspect;
|
||||
internal Speed Limit;
|
||||
internal Speed Target;
|
||||
internal Speed EntryTarget;
|
||||
|
||||
internal SignalCode(int aspect, string data)
|
||||
{
|
||||
Aspect = aspect;
|
||||
Limit = new Speed(0);
|
||||
Target = new Speed(0);
|
||||
EntryTarget = new Speed(0);
|
||||
if (data.Contains("/"))
|
||||
{
|
||||
int separator = data.IndexOf('/');
|
||||
string a = data.Substring(0, separator);
|
||||
string b = data.Substring(separator + 1);
|
||||
string[] speeds = data.Split('/');
|
||||
if (speeds.Length > 1)
|
||||
{
|
||||
string a = speeds[0];
|
||||
string b = speeds[1];
|
||||
if (double.TryParse(a, NumberStyles.Float, CultureInfo.InvariantCulture, out double an) && double.TryParse(b, NumberStyles.Float, CultureInfo.InvariantCulture, out double bn))
|
||||
{
|
||||
if (an >= bn && an >= 0)
|
||||
|
@ -134,6 +138,14 @@ namespace OpenbveFcmbTrainPlugin
|
|||
{
|
||||
Target = new Speed(bn / 3.6);
|
||||
}
|
||||
if (speeds.Length > 2)
|
||||
{
|
||||
if (double.TryParse(speeds[2], NumberStyles.Float, CultureInfo.InvariantCulture, out double cn))
|
||||
{
|
||||
EntryTarget = new Speed(cn / 3.6);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -145,6 +157,12 @@ namespace OpenbveFcmbTrainPlugin
|
|||
/// <summary>The aspect of the current signal in the route.</summary>
|
||||
private int CurrentSignalAspect;
|
||||
|
||||
/// <summary>The start position of the current signal.</summary>
|
||||
private double CurrentSignalStartLocation;
|
||||
|
||||
/// <summary>The end position of the current signal.</summary>
|
||||
private double CurrentSignalEndLocation;
|
||||
|
||||
/// <summary>The ideal power notch for the AI.</summary>
|
||||
private int AiPowerNotch;
|
||||
|
||||
|
@ -155,8 +173,9 @@ namespace OpenbveFcmbTrainPlugin
|
|||
/// <param name="yardMaxSpeed">The maximum speed in YARD mode, in km/h.</param>
|
||||
/// <param name="signalCodes">The list of signal codes recognised by the device.</param>
|
||||
/// <param name="atoAvailable">Whether ATO is available or not.</param>
|
||||
internal AtcDimetronic(Speed yardMaxSpeed, List<SignalCode> signalCodes, bool atoAvailable)
|
||||
internal AtcDimetronic(double trainLength, Speed yardMaxSpeed, List<SignalCode> signalCodes, bool atoAvailable)
|
||||
{
|
||||
TrainLength = trainLength;
|
||||
YardMaximumSpeed = yardMaxSpeed;
|
||||
SignalCodes = signalCodes;
|
||||
AtoAvailable = atoAvailable;
|
||||
|
@ -175,6 +194,10 @@ namespace OpenbveFcmbTrainPlugin
|
|||
DeviceState = DeviceStates.NoMode;
|
||||
}
|
||||
|
||||
// Update train location
|
||||
// TODO: implement runback/rollfoward protection
|
||||
TrainLocation = train.State.Location;
|
||||
|
||||
double speed = train.State.Speed.KilometersPerHour;
|
||||
bool stopped = speed < 0.05;
|
||||
|
||||
|
@ -252,13 +275,13 @@ namespace OpenbveFcmbTrainPlugin
|
|||
case DeviceStates.ATP:
|
||||
train.ContinuousProtection = true;
|
||||
train.VigilanceOverride = false;
|
||||
CurrentSpeedCode = GetSpeedCodeFromAspect(SignalCodes, CurrentSignalAspect);
|
||||
CurrentSpeedCode = GetSpeedCodeFromAspect();
|
||||
break;
|
||||
// ATC device is in ATO driving mode
|
||||
case DeviceStates.ATO:
|
||||
train.ContinuousProtection = true;
|
||||
train.VigilanceOverride = true;
|
||||
CurrentSpeedCode = GetSpeedCodeFromAspect(SignalCodes, CurrentSignalAspect);
|
||||
CurrentSpeedCode = GetSpeedCodeFromAspect();
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -376,6 +399,8 @@ namespace OpenbveFcmbTrainPlugin
|
|||
internal override void SetSignal(SignalData[] signal)
|
||||
{
|
||||
CurrentSignalAspect = signal[0].Aspect;
|
||||
CurrentSignalStartLocation = signal[0].Distance + TrainLocation;
|
||||
CurrentSignalEndLocation = signal.Length > 1 ? signal[1].Distance + TrainLocation : double.MaxValue;
|
||||
}
|
||||
|
||||
/// <summary>Is called when a beacon is passed.</summary>
|
||||
|
@ -511,15 +536,18 @@ namespace OpenbveFcmbTrainPlugin
|
|||
}
|
||||
|
||||
/// <summary>Generates the corresponding speed code from a signal aspect.</summary>
|
||||
/// <param name="signalCodes">The list of signal codes.</param>
|
||||
/// <param name="aspect">The current signal aspect.</param>
|
||||
private SpeedCode GetSpeedCodeFromAspect(List<SignalCode> signalCodes, int aspect)
|
||||
private SpeedCode GetSpeedCodeFromAspect()
|
||||
{
|
||||
foreach (SignalCode signal in signalCodes)
|
||||
foreach (SignalCode signal in SignalCodes)
|
||||
{
|
||||
if (signal.Aspect == aspect)
|
||||
if (signal.Aspect == CurrentSignalAspect)
|
||||
{
|
||||
return new SpeedCode(signal.Limit, signal.Target);
|
||||
if (TrainLocation - TrainLength < CurrentSignalStartLocation && signal.EntryTarget.MetersPerSecond > 0)
|
||||
{
|
||||
// The train has not fully entered the signal section, use the entry target speed
|
||||
return new SpeedCode(signal.Limit, signal.EntryTarget, CurrentSignalEndLocation);
|
||||
}
|
||||
return new SpeedCode(signal.Limit, signal.Target, CurrentSignalEndLocation);
|
||||
}
|
||||
}
|
||||
return new SpeedCode(new Speed(0), new Speed(0));
|
||||
|
|
|
@ -11,6 +11,8 @@ namespace OpenbveFcmbTrainPlugin
|
|||
/// <summary>Represents a collection of plugin settings.</summary>
|
||||
internal class SettingsCollection
|
||||
{
|
||||
internal double TrainLength;
|
||||
|
||||
internal bool DoorSelectionDeviceEnabled;
|
||||
internal bool DoorClosingSoundDeviceEnabled;
|
||||
internal bool DoorTractionCutDeviceEnabled;
|
||||
|
@ -75,6 +77,19 @@ namespace OpenbveFcmbTrainPlugin
|
|||
}
|
||||
switch (Section)
|
||||
{
|
||||
case "train":
|
||||
switch (Key)
|
||||
{
|
||||
case "length":
|
||||
{
|
||||
if (double.TryParse(Value, NumberStyles.Float, CultureInfo.InvariantCulture, out double a))
|
||||
{
|
||||
PluginSettings.TrainLength = a;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case "doorselection":
|
||||
switch (Key)
|
||||
{
|
||||
|
@ -211,8 +226,7 @@ namespace OpenbveFcmbTrainPlugin
|
|||
PluginSettings.AtcDimetronicAtoAvailable = string.Compare(Value, "false", StringComparison.OrdinalIgnoreCase) != 0;
|
||||
break;
|
||||
default:
|
||||
int aspect;
|
||||
if (int.TryParse(Key, NumberStyles.Integer, CultureInfo.InvariantCulture, out aspect))
|
||||
if (int.TryParse(Key, NumberStyles.Integer, CultureInfo.InvariantCulture, out int aspect))
|
||||
{
|
||||
AtcDimetronic.SignalCode signalCode = new AtcDimetronic.SignalCode(aspect, Value);
|
||||
if (signalCode != null)
|
||||
|
|
|
@ -98,7 +98,7 @@ namespace OpenbveFcmbTrainPlugin
|
|||
}
|
||||
if (settings.AtcDimetronicDeviceEnabled)
|
||||
{
|
||||
Devices.Add(new AtcDimetronic(settings.AtcDimetronicYardSpeedLimit, settings.AtcDimetronicSignalCodes, settings.AtcDimetronicAtoAvailable));
|
||||
Devices.Add(new AtcDimetronic(settings.TrainLength, settings.AtcDimetronicYardSpeedLimit, settings.AtcDimetronicSignalCodes, settings.AtcDimetronicAtoAvailable));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue