107 lines
2.9 KiB
Java
107 lines
2.9 KiB
Java
package de.srsoftware.web4rail.threads;
|
|
|
|
import org.slf4j.Logger;
|
|
import org.slf4j.LoggerFactory;
|
|
|
|
import de.srsoftware.web4rail.Application;
|
|
import de.srsoftware.web4rail.BaseClass;
|
|
import de.srsoftware.web4rail.Route;
|
|
import de.srsoftware.web4rail.moving.Train;
|
|
|
|
public class BrakeProcess extends BaseClass implements Runnable{
|
|
|
|
private static final Logger LOG = LoggerFactory.getLogger(BrakeProcess.class);
|
|
|
|
public static int defaultTimeStep = 500;
|
|
private Train train;
|
|
private int targetSpeed = Train.defaultEndSpeed;
|
|
boolean ended = false;
|
|
long distance = 0;
|
|
private int startSpeed;
|
|
private int lastSpeed;
|
|
private long lastTime;
|
|
|
|
private Integer timeStep;
|
|
|
|
private Route route;
|
|
|
|
private String brakeId;
|
|
|
|
public BrakeProcess(Train train) {
|
|
this.train = train;
|
|
this.brakeId = train.brakeId();
|
|
this.route = train.route();
|
|
new Thread(this, Application.threadName(this)).start();
|
|
}
|
|
|
|
private long calcDistance(Integer ts) {
|
|
long dist = 0;
|
|
int s = startSpeed;
|
|
while (s > Train.defaultEndSpeed) {
|
|
dist += s*ts;
|
|
s -= Train.defaultSpeedStep;
|
|
}
|
|
LOG.debug("Estimated distamce with {} ms timestep: {}",ts,dist);
|
|
return dist;
|
|
}
|
|
|
|
public BrakeProcess end() {
|
|
LOG.debug("{}.end()",this);
|
|
ended = true;
|
|
return this;
|
|
}
|
|
|
|
@Override
|
|
public void run() {
|
|
timeStep = train.route().brakeTime(train.brakeId());
|
|
LOG.debug("{}.run() with timestep = {} ms",this,timeStep);
|
|
if (timeStep == null) timeStep = defaultTimeStep;
|
|
startSpeed = train.speed;
|
|
lastTime = timestamp();
|
|
while (!train.hasNextPreparedRoute()) {
|
|
sleep(timeStep);
|
|
lastSpeed = train.speed;
|
|
updateDistance();
|
|
if (lastSpeed > targetSpeed) lastSpeed -= Train.defaultSpeedStep;
|
|
if (ended) break;
|
|
if (lastSpeed <= targetSpeed && (ended = true)) lastSpeed = targetSpeed;
|
|
train.setSpeed(lastSpeed);
|
|
}
|
|
}
|
|
|
|
private void updateDistance() {
|
|
long newTime = timestamp();
|
|
distance += (newTime-lastTime)*lastSpeed;
|
|
lastTime = newTime;
|
|
LOG.debug("measured distance: {} units",distance);
|
|
}
|
|
|
|
@Override
|
|
public String toString() {
|
|
return getClass().getSimpleName()+"("+train+")";
|
|
}
|
|
|
|
public void updateTime() {
|
|
updateDistance();
|
|
LOG.debug("updateTime(): start speed was {} {}.",startSpeed,BaseClass.speedUnit);
|
|
Integer newTimeStep = timeStep;
|
|
long calculated;
|
|
int step = 32*newTimeStep;
|
|
for (int i=0; i<20; i++) {
|
|
step = step/2;
|
|
if (step<1) step = 1;
|
|
calculated = calcDistance(newTimeStep);
|
|
LOG.debug("Calculated distance for step = {} ms: {}",newTimeStep,calculated);
|
|
LOG.debug("Update step: {}",step);
|
|
newTimeStep = newTimeStep + (calculated > distance ? -step : step);
|
|
}
|
|
|
|
if (!newTimeStep.equals(timeStep)) {
|
|
route.brakeTime(brakeId,newTimeStep);
|
|
calculated = calcDistance(newTimeStep);
|
|
LOG.debug("Corrected brake timestep from {} to {} ms for {} @ {}.",timeStep,newTimeStep,train,route);
|
|
LOG.debug("Differemce from estimated distance: {} ({}%)",distance-calculated,100*(distance-calculated)/(float)distance);
|
|
}
|
|
}
|
|
}
|