Skip to content

Commit d3e8c3e

Browse files
committed
Improved support for graduated release systems
1 parent 858fa7e commit d3e8c3e

File tree

1 file changed

+52
-19
lines changed
  • Source/Orts.Simulation/Simulation/RollingStocks/SubSystems/Brakes/MSTS

1 file changed

+52
-19
lines changed

Source/Orts.Simulation/Simulation/RollingStocks/SubSystems/Brakes/MSTS/AirSinglePipe.cs

Lines changed: 52 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,8 @@ public class AirSinglePipe : MSTSBrakeSystem
7777
protected float QuickServiceVentRatePSIpS;
7878
protected float AcceleratedApplicationFactor;
7979
protected float AcceleratedApplicationLimitPSIpS = 5.0f;
80-
protected float InitialApplicationThresholdPSI = 1.0f;
80+
protected float InitialApplicationThresholdPSI;
81+
protected float TripleValveSensitivityPSI;
8182
protected float BrakeCylinderSpringPressurePSI;
8283
protected float ServiceMaxCylPressurePSI;
8384
protected float AcceleratedEmergencyReleaseThresholdPSI = 20.0f;
@@ -164,6 +165,7 @@ public override void InitializeFromCopy(BrakeSystem copy)
164165
AcceleratedApplicationFactor = thiscopy.AcceleratedApplicationFactor;
165166
AcceleratedApplicationLimitPSIpS = thiscopy.AcceleratedApplicationLimitPSIpS;
166167
InitialApplicationThresholdPSI = thiscopy.InitialApplicationThresholdPSI;
168+
TripleValveSensitivityPSI = thiscopy.TripleValveSensitivityPSI;
167169
BrakeCylinderSpringPressurePSI = thiscopy.BrakeCylinderSpringPressurePSI;
168170
ServiceMaxCylPressurePSI = thiscopy.ServiceMaxCylPressurePSI;
169171
}
@@ -305,7 +307,7 @@ public override void Parse(string lowercasetoken, STFReader stf)
305307
case "wagon(ortsquickserviceventrate": QuickServiceVentRatePSIpS = stf.ReadFloatBlock(STFReader.UNITS.PressureRateDefaultPSIpS, null); break;
306308
case "wagon(ortsacceleratedapplicationfactor": AcceleratedApplicationFactor = stf.ReadFloatBlock(STFReader.UNITS.None, null); break;
307309
case "wagon(ortsacceleratedapplicationmaxventrate": AcceleratedApplicationLimitPSIpS = stf.ReadFloatBlock(STFReader.UNITS.PressureRateDefaultPSIpS, 5.0f); break;
308-
case "wagon(ortsinitialapplicationthreshold": InitialApplicationThresholdPSI = stf.ReadFloatBlock(STFReader.UNITS.PressureDefaultPSI, 1.0f); break;
310+
case "wagon(ortsinitialapplicationthreshold": InitialApplicationThresholdPSI = stf.ReadFloatBlock(STFReader.UNITS.PressureDefaultPSI, null); break;
309311
case "wagon(ortscylinderspringpressure": BrakeCylinderSpringPressurePSI = stf.ReadFloatBlock(STFReader.UNITS.PressureDefaultPSI, null); break;
310312
case "wagon(ortsmaxservicecylinderpressure": ServiceMaxCylPressurePSI = stf.ReadFloatBlock(STFReader.UNITS.PressureDefaultPSI, null); break;
311313
}
@@ -404,6 +406,22 @@ public override void Initialize()
404406
if ((Car as MSTSWagon).EmergencyReservoirPresent && EmergencyValveActuationRatePSIpS == 0)
405407
EmergencyValveActuationRatePSIpS = 15;
406408

409+
if (InitialApplicationThresholdPSI == 0)
410+
{
411+
if ((Car as MSTSWagon).BrakeValve == MSTSWagon.BrakeValveType.Distributor)
412+
InitialApplicationThresholdPSI = 2.2f; // UIC spec: brakes should release if brake pipe is within 0.15 bar of control res
413+
else
414+
InitialApplicationThresholdPSI = 1.0f;
415+
}
416+
417+
if (TripleValveSensitivityPSI == 0)
418+
{
419+
if ((Car as MSTSWagon).BrakeValve == MSTSWagon.BrakeValveType.Distributor)
420+
TripleValveSensitivityPSI = 1.4f; // UIC spec: brakes should respond to 0.1 bar changes in brake pipe
421+
else
422+
TripleValveSensitivityPSI = 1.0f;
423+
}
424+
407425
if (EmergResVolumeM3 > 0 && EmergAuxVolumeRatio > 0 && BrakePipeVolumeM3 > 0)
408426
{
409427
AuxBrakeLineVolumeRatio = EmergResVolumeM3 / EmergAuxVolumeRatio / BrakePipeVolumeM3;
@@ -440,7 +458,8 @@ public void UpdateTripleValveState(float elapsedClockSeconds)
440458

441459
if (valveType == MSTSWagon.BrakeValveType.Distributor)
442460
{
443-
float targetPressurePSI = (ControlResPressurePSI - BrakeLine1PressurePSI) * AuxCylVolumeRatio;
461+
float applicationPSI = ControlResPressurePSI - BrakeLine1PressurePSI;
462+
float targetPressurePSI = applicationPSI * AuxCylVolumeRatio;
444463
if (!disableGradient && EmergencyValveActuationRatePSIpS > 0 && (prevBrakePipePressurePSI - BrakeLine1PressurePSI) > Math.Max(elapsedClockSeconds, 0.0001f) * EmergencyValveActuationRatePSIpS)
445464
{
446465
if (prevState == ValveState.Release) // If valve transitions from release to emergency, quick service activates
@@ -450,17 +469,24 @@ public void UpdateTripleValveState(float elapsedClockSeconds)
450469
}
451470
TripleValveState = ValveState.Emergency;
452471
}
453-
else if (TripleValveState != ValveState.Emergency &&
454-
targetPressurePSI > AutoCylPressurePSI + (TripleValveState == ValveState.Release ? AuxCylVolumeRatio * InitialApplicationThresholdPSI : (TripleValveState == ValveState.Apply ? 0.0f : 2.2f)))
472+
else if (TripleValveState != ValveState.Emergency && targetPressurePSI > AutoCylPressurePSI + (TripleValveState == ValveState.Apply ? 0.0f : TripleValveSensitivityPSI * AuxCylVolumeRatio))
455473
{
456-
if (prevState == ValveState.Release) // If valve transitions from release to apply, quick service activates
474+
if (prevState == ValveState.Release)
457475
{
458-
QuickServiceActive = true;
459-
UniformChargingActive = false;
476+
if (applicationPSI > InitialApplicationThresholdPSI) // If valve transitions from release to apply, quick service activates
477+
{
478+
QuickServiceActive = true;
479+
UniformChargingActive = false;
480+
481+
TripleValveState = ValveState.Apply;
482+
}
483+
}
484+
else
485+
{
486+
TripleValveState = ValveState.Apply;
460487
}
461-
TripleValveState = ValveState.Apply;
462488
}
463-
else if (targetPressurePSI < AutoCylPressurePSI - (TripleValveState == ValveState.Release ? 0.0f : 2.2f) || targetPressurePSI < 2.2f)
489+
else if (targetPressurePSI < AutoCylPressurePSI - (TripleValveState == ValveState.Release ? 0.0f : TripleValveSensitivityPSI * AuxCylVolumeRatio) || applicationPSI < InitialApplicationThresholdPSI)
464490
{
465491
TripleValveState = ValveState.Release;
466492
}
@@ -480,17 +506,24 @@ public void UpdateTripleValveState(float elapsedClockSeconds)
480506
}
481507
TripleValveState = ValveState.Emergency;
482508
}
483-
else if (TripleValveState != ValveState.Emergency &&
484-
BrakeLine1PressurePSI < AuxResPressurePSI - (TripleValveState == ValveState.Release ? InitialApplicationThresholdPSI : (TripleValveState == ValveState.Apply ? 0.0f : 1.0f)))
509+
else if (TripleValveState != ValveState.Emergency && BrakeLine1PressurePSI < AuxResPressurePSI - (TripleValveState == ValveState.Apply ? 0.0f : TripleValveSensitivityPSI))
485510
{
486-
if (prevState == ValveState.Release) // If valve transitions from release to apply, quick service activates
511+
if (prevState == ValveState.Release)
487512
{
488-
QuickServiceActive = true;
489-
UniformChargingActive = false;
513+
if (BrakeLine1PressurePSI < AuxResPressurePSI - InitialApplicationThresholdPSI) // If valve transitions from release to apply, quick service activates
514+
{
515+
QuickServiceActive = true;
516+
UniformChargingActive = false;
517+
518+
TripleValveState = ValveState.Apply;
519+
}
520+
}
521+
else
522+
{
523+
TripleValveState = ValveState.Apply;
490524
}
491-
TripleValveState = ValveState.Apply;
492525
}
493-
else if (BrakeLine1PressurePSI > AuxResPressurePSI + (TripleValveState == ValveState.Release ? 0.0f : 2.0f))
526+
else if (BrakeLine1PressurePSI > AuxResPressurePSI + (TripleValveState == ValveState.Release ? 0.0f : TripleValveSensitivityPSI * 2))
494527
{
495528
TripleValveState = ValveState.Release;
496529
}
@@ -685,14 +718,14 @@ public override void Update(float elapsedClockSeconds)
685718
}
686719

687720
// Handle brake release: reduce cylinder pressure if all triple valve, EP holding valve and retainers allow so
688-
if (threshold < 2.2f) // Prevent brakes getting stuck with a small amount of air on distributor systems
721+
if (threshold < InitialApplicationThresholdPSI * AuxCylVolumeRatio) // Prevent brakes getting stuck with a small amount of air on distributor systems
689722
threshold = 0;
690723
float minCylPressurePSI = Math.Max(threshold, RetainerPressureThresholdPSI);
691724

692725
if (TripleValveState == ValveState.Release && HoldingValve == ValveState.Release && AutoCylPressurePSI > minCylPressurePSI)
693726
{
694727
float dp = elapsedClockSeconds * ReleaseRatePSIpS;
695-
if (AutoCylPressurePSI < threshold + 1 && threshold > 2.2f)
728+
if (AutoCylPressurePSI < threshold + 1 && threshold > InitialApplicationThresholdPSI * AuxCylVolumeRatio)
696729
dp *= MathHelper.Clamp(AutoCylPressurePSI - threshold, 0.1f, 1.0f); // Reduce release rate if nearing target pressure to prevent toggling between release and lap
697730
if (AutoCylPressurePSI - dp < minCylPressurePSI)
698731
dp = AutoCylPressurePSI - minCylPressurePSI;

0 commit comments

Comments
 (0)