Elvas Tower: Locomotive Dynamic Braking Forces - Elvas Tower

Jump to content

Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

Locomotive Dynamic Braking Forces Rate Topic: -----

#1 User is offline   steamer_ctn 

  • Open Rails Developer
  • Group: Status: Elite Member
  • Posts: 1,888
  • Joined: 24-June 11
  • Gender:Male
  • Country:

Posted 01 July 2019 - 02:56 AM

I have been trying to reverse engineer some of the code for the couplers and speed calculations in OR in order to understand the logic and how it impacts on the performance of a locomotive (and train).

In particular, I am trying to understand a couple of code sections in Train.cs:

The first one is in ComputeCouplerForces:

Cars[i].TotalForceN -= (Cars[i].FrictionForceN + Cars[i].BrakeForceN + Cars[i].CurveForceN + Cars[i].WindForceN + Cars[i].TunnelForceN +
                        	((Cars[i] is MSTSLocomotive && (Cars[i] as MSTSLocomotive).DynamicBrakeForceN > 0) ? Math.Abs(Cars[i].MotiveForceN) : 0));

The second line of this code appears to be checking to see if the dynamic brake is in operation (fair enough). As I understand the code if the dynamic brake is on, it is adding the MotiveForce of the locomotive as one of the "resistive" forces applied to the locomotive. Unless there is a reason created by some code logic somewhere else, shouldn't the DynamicBrakeForceN be used in the formula instead of the MotiveForce?



The second code block is further down in UpdateCarSpeeds. It is also used for locomotives -

f += car.TotalForceN - (car.FrictionForceN + car.CurveForceN + car.WindForceN + car.TunnelForceN);
                    	if ((car as MSTSLocomotive).DynamicBrakeForceN > 0)
                    	{
                        	f -= Math.Abs(car.MotiveForceN);
                    	}


This code uses the MotiveForce as well. In addition, there is no allowance for the normal braking force (BrakeForceN) of the locomotive (which is included in the above code block, and the following formula for "normal wagons").
My gut feel is that these formulas need to be adjusted slightly by changing MotiveForce to DynamicBrakeForce, and including the BrakeForceN as well.

However before applying any changes, I was hoping that somebody, especially a developer who may have worked on this section of code, might give me some insight in order to confirm or challenge my thinking.

Thanks

#2 User is offline   Csantucci 

  • Member, Board of Directors
  • Group: Status: Elite Member
  • Posts: 6,996
  • Joined: 31-December 11
  • Gender:Male
  • Country:

Posted 01 July 2019 - 06:08 AM

I haven't worked on such section of code, or, better said, I tried to but I found it quite mysterious.
Re including BrakeForceN I think you're right: I don't see why BrakeForceN is not used for locomotives, but is used for wagons.
Re DynamicBrakeForce and MotiveForceN, they are linked by following code in Locomotive.cs
            if (DynamicBrakePercent > 0 && DynamicBrakeForceCurves != null)
            {
                float f = DynamicBrakeForceCurves.Get(.01f * DynamicBrakePercent, AbsSpeedMpS);
                if (f > 0 && PowerOn)
                {
                    MotiveForceN -= (SpeedMpS > 0 ? 1 : SpeedMpS < 0 ? -1 : Direction == Direction.Reverse ? -1 : 1) * f * (1 - PowerReduction);
                    DynamicBrakeForceN = f * (1 - PowerReduction);
                }
                else
                {
                    DynamicBrakeForceN = 0f;
                }
            }

so their absolute value is the same if DynamicBrakeForceN is > 0 and if MotiveForceN enters this block of code with value 0. Is this always the case?

#3 User is offline   dajones 

  • Open Rails Developer
  • Group: Status: Contributing Member
  • Posts: 413
  • Joined: 27-February 08
  • Gender:Male
  • Location:Durango, CO
  • Country:

Posted 01 July 2019 - 02:58 PM

It looks like this code could use either DynamicBrakeForceN or MotiveForceN. This code appears to be relative new and was probably added as a bug fix. Before that MotiveForceN was added to TotalForceN without regard to the direction of travel and that probably caused the dynamic brakes to not work when going backwards.

The second block of code is used to calculate when a car that isn't moving should start moving. So, it should be comparing the total motive force to the total static force. The force variables named in the code are not being included as static forces. So brake force is used for locomotives but not for cars. I don't remember why. I also don't know why friction forces are not used. If the static force is under estimated here, then the car/train might oscillate between moving and stopped. It the static force is over estimated then the train might not start when it should.

Doug

#4 User is offline   steamer_ctn 

  • Open Rails Developer
  • Group: Status: Elite Member
  • Posts: 1,888
  • Joined: 24-June 11
  • Gender:Male
  • Country:

Posted 01 July 2019 - 11:41 PM

View PostCsantucci, on 01 July 2019 - 06:08 AM, said:

I haven't worked on such section of code, or, better said, I tried to but I found it quite mysterious.
I agree with that. The reason why the code does certain functions is not very well described.

Thanks for the feedback and finding the code snippet.


View PostCsantucci, on 01 July 2019 - 06:08 AM, said:

so their absolute value is the same if DynamicBrakeForceN is > 0 and if MotiveForceN enters this block of code with value 0. Is this always the case?

I assume that when dynamic braking is applied that the locomotive is not producing any MotiveForce (ie it will be 0), however I think that it is then confusing to be modifying the MotiveForce to insert the DynamicBrakeForce.


This may also introduce some issues in the code, if a test exists to check when MotiveForce is equal to zero, if it is then artificially changed to accommodate DynamicForce.

View Postdajones, on 01 July 2019 - 02:58 PM, said:

It looks like this code could use either DynamicBrakeForceN or MotiveForceN. This code appears to be relative new and was probably added as a bug fix. Before that MotiveForceN was added to TotalForceN without regard to the direction of travel and that probably caused the dynamic brakes to not work when going backwards.
Thanks for the feedback.

It certainly appears to be a convoluted process to modify MotiveForce to accommodate the DynamicBrakeForce. Given that the DynamicBrakeForce is a retarding force similar to normal BrakeForce, any thoughts on why couldn't it have been treated in the same manner, and if necessary an ABS value used to eliminate any directionality issues in DynamicBrakeForce (do you think that this was the issue trying to be fixed)? Having DynamicBrakeForce appear in these formulas would certainly make it easier to understand the code rather then mixing the meaning of parameters.

Would it be as simple as using the DynamicBrakeForce value calculated in the code block posted by Carlo, and removing relevant alterations to MotiveForceN?

View Postdajones, on 01 July 2019 - 02:58 PM, said:

So brake force is used for locomotives but not for cars. I don't remember why. I also don't know why friction forces are not used. If the static force is under estimated here, then the car/train might oscillate between moving and stopped. It the static force is over estimated then the train might not start when it should.

Thanks also for the feedback on this, as it helps to clarify some of the code operation.

The full code block below shows that BrakeForceN is used sometimes in both locomotive and cars, and other times just in the cars.
            	TrainCar car = Cars[i];
            	if (car.SpeedMpS != 0 || car.TotalForceN <= (car.FrictionForceN + car.BrakeForceN + car.CurveForceN + car.WindForceN + car.TunnelForceN + 
                	((car is MSTSLocomotive && (car as MSTSLocomotive).DynamicBrakeForceN > 0) ? Math.Abs(car.MotiveForceN) : 0)))
                	continue;
            	int j = i;
            	float f = 0;
            	float m = 0;
            	for (;;)
            	{
                	if (car is MSTSLocomotive)
                	{
                    	f += car.TotalForceN - (car.FrictionForceN + car.CurveForceN + car.WindForceN + car.TunnelForceN);
                    	if ((car as MSTSLocomotive).DynamicBrakeForceN > 0)
                    	{
                        	f -= Math.Abs(car.MotiveForceN);
                    	}
                	}
                	else
                    	f += car.TotalForceN - (car.FrictionForceN + car.BrakeForceN + car.CurveForceN + car.WindForceN + car.TunnelForceN);
                	m += car.MassKG;
                	if (j == Cars.Count - 1 || car.CouplerSlackM < car.GetMaximumCouplerSlack2M())
                    	break;
                	j++;
                	car = Cars[j];
            	}


If there are anymore thoughts/insights, then it would be appreciated.

Thanks

#5 User is offline   steamer_ctn 

  • Open Rails Developer
  • Group: Status: Elite Member
  • Posts: 1,888
  • Joined: 24-June 11
  • Gender:Male
  • Country:

Posted 02 July 2019 - 12:14 AM

ADDENDUM:

Thinking a bit more about the code block for starting the cars, I am wondering whether it even needs to consider the DynamicBrakeForce information? The code is only used to start a car, and in this scenario DynamicBrakeForce will always either be off (as throttle is opened to start train), or alternatively there will be minimal or no DynamicBrakeForce as the train will not be moving and regenerating any power?

Thoughts?

#6 User is offline   longiron 

  • Open Rails Developer
  • Group: Status: Elite Member
  • Posts: 3,179
  • Joined: 25-July 08
  • Gender:Male
  • Location:Manasquan, NJ
  • Simulator:Open Rails, MSTS editors
  • Country:

Posted 02 July 2019 - 04:17 AM

I believe you are 100% correct. You may want to include the parameter for consistency's sake and for future coders - even though its value will be zero force and not impact anything.

#7 User is offline   dajones 

  • Open Rails Developer
  • Group: Status: Contributing Member
  • Posts: 413
  • Joined: 27-February 08
  • Gender:Male
  • Location:Durango, CO
  • Country:

Posted 02 July 2019 - 05:21 AM

It looks like the dynamic brake force was originally included in MotiveForceN and the DynamicBrakeForceN variable was added later so that it could be used to trigger sounds. The dynamic brake force should probably be removed from MotiveForceN now that there is a separate variable for it. That would simplify the code where it is used.

There should be no need to include DynamicBrakeForceN in the starting logic. The same is probably true for CurveForceN. Both should be zero if there is no movement.

Doug

#8 User is offline   Csantucci 

  • Member, Board of Directors
  • Group: Status: Elite Member
  • Posts: 6,996
  • Joined: 31-December 11
  • Gender:Male
  • Country:

Posted 02 July 2019 - 05:57 AM

DynamicBrakeForceN is needed in starting logic, when the train is on a slope IMHO.

#9 User is offline   steamer_ctn 

  • Open Rails Developer
  • Group: Status: Elite Member
  • Posts: 1,888
  • Joined: 24-June 11
  • Gender:Male
  • Country:

Posted 02 July 2019 - 09:04 PM

Thanks for all your replies.

I agree with the thoughts, and will have a look at what is involved in tidying up the code as appropriate.

Page 1 of 1
  • You cannot start a new topic
  • You cannot reply to this topic

1 User(s) are reading this topic
0 members, 1 guests, 0 anonymous users