Browse Source

working on train movements

lookup-tables
Stephan Richter 5 years ago
parent
commit
cd022ce4a3
  1. 2
      resources/css/style.css
  2. 48
      resources/js/plan.js
  3. 10
      src/main/java/de/srsoftware/web4rail/Application.java
  4. 16
      src/main/java/de/srsoftware/web4rail/Plan.java
  5. 66
      src/main/java/de/srsoftware/web4rail/Route.java
  6. 49
      src/main/java/de/srsoftware/web4rail/moving/Train.java
  7. 23
      src/main/java/de/srsoftware/web4rail/tiles/Block.java
  8. 8
      src/main/java/de/srsoftware/web4rail/tiles/Tile.java

2
resources/css/style.css

@ -174,7 +174,7 @@ svg.left rect, @@ -174,7 +174,7 @@ svg.left rect,
svg.right rect,
svg.straight .left,
svg.straight .right{
fill: white !important;
fill: #ddd !important;
}
.occupied .block{

48
resources/js/plan.js

@ -1,10 +1,10 @@ @@ -1,10 +1,10 @@
const ADD = 'add';
const MOVE = 'move';
const SQUARE = 30;
const BODY = '#plan';
const BODY = 'body';
const DIV = 'DIV';
const SVG = 'svg';
const PLAN = 'plan';
const PLAN = '#plan';
const POST = 'POST';
var selected = null;
var mode = null;
@ -23,23 +23,6 @@ function addTile(x,y){ @@ -23,23 +23,6 @@ function addTile(x,y){
return request({action:mode,tile:selected.id,x:x,y:y});
}
function bodyClick(ev){
//console.log('bodyClick:',ev);
var x = Math.floor(ev.clientX/SQUARE);
var y = Math.floor(ev.clientY/SQUARE);
switch (mode){
case undefined:
case null:
return clickTile(x,y);
case ADD:
return addTile(x,y);
case MOVE:
return moveTile(x,y);
}
console.log('unknown action "'+mode+'" @ ('+ev.clientX+','+ev.clientY+')');
}
function clickTile(x,y){
console.log("clickTile:",x,y);
if ($('#tile-'+x+'-'+y).length > 0) request({action:'click',x:x,y:y});
@ -113,10 +96,27 @@ function openRoute(id){ @@ -113,10 +96,27 @@ function openRoute(id){
function place(data){
var tag = $(data);
$('#'+tag.attr('id')).remove();
$(BODY).append(tag);
$(PLAN).append(tag);
return false;
}
function planClick(ev){
//console.log('bodyClick:',ev);
var x = Math.floor(ev.clientX/SQUARE);
var y = Math.floor(ev.clientY/SQUARE);
switch (mode){
case undefined:
case null:
return clickTile(x,y);
case ADD:
return addTile(x,y);
case MOVE:
return moveTile(x,y);
}
console.log('unknown action "'+mode+'" @ ('+ev.clientX+','+ev.clientY+')');
}
function remove(id){
$('#'+id).remove();
return false;
@ -124,14 +124,15 @@ function remove(id){ @@ -124,14 +124,15 @@ function remove(id){
function request(data){
$.ajax({
url : PLAN,
url : 'plan',
method : POST,
data : data,
success: function(resp){
closeWindows();
if (resp.startsWith('<svg')){
$('#plan').append($(resp));
$(PLAN).append($(resp));
} else if (resp.startsWith('<')) {
console.log("appending to body: "+resp.substring(0,10));
$(BODY).append($(resp));
} else {
addMessage(resp);
@ -163,11 +164,10 @@ function stream(ev){ @@ -163,11 +164,10 @@ function stream(ev){
window.onload = function () {
var isDragging = false;
console.log($(BODY).each(function(){console.log(this)}));
$('.menu > div').click(closeMenu);
$('.menu .addtile .list svg').click(enableAdding);
$('.menu .move .list div').click(enableMove);
$('.menu .actions .list > div').click(runAction);
$(BODY).click(bodyClick);
$(PLAN).click(planClick);
(new EventSource("stream")).onmessage = stream;
}

10
src/main/java/de/srsoftware/web4rail/Application.java

@ -53,10 +53,16 @@ public class Application { @@ -53,10 +53,16 @@ public class Application {
plan = new Plan();
}
Locomotive BR110 = new Locomotive("BR110");
Locomotive BR130 = new Locomotive("BR130");
Vector<Block> blocks = new Vector<>(plan.blocks());
Random rand = new Random();
Block block = blocks.get(rand.nextInt(blocks.size()));
if (block != null) block.train(new Train(BR110));
Block block1 = blocks.get(rand.nextInt(blocks.size()));
if (block1 != null) block1.train(new Train(BR110));
Block block2 = null;
do {
block2 = blocks.get(rand.nextInt(blocks.size()));
} while (block2 == block1);
if (block2 != null) block2.train(new Train(BR130));
Desktop.getDesktop().browse(URI.create("http://localhost:"+config.getInt(PORT)+"/plan"));
}

16
src/main/java/de/srsoftware/web4rail/Plan.java

@ -66,7 +66,17 @@ import de.srsoftware.web4rail.tiles.TurnoutRW; @@ -66,7 +66,17 @@ import de.srsoftware.web4rail.tiles.TurnoutRW;
public class Plan {
public enum Direction{
NORTH, SOUTH, EAST, WEST
NORTH, SOUTH, EAST, WEST;
Direction inverse() {
switch (this) {
case NORTH: return SOUTH;
case SOUTH: return NORTH;
case EAST: return WEST;
case WEST: return EAST;
}
return null;
}
}
private class Heartbeat extends Thread {
@ -148,7 +158,7 @@ public class Plan { @@ -148,7 +158,7 @@ public class Plan {
private String analyze() {
Vector<Route> routes = new Vector<Route>();
for (Block block : blocks) {
for (Connector con : block.startPoints()) routes.addAll(follow(new Route().start(block),con));
for (Connector con : block.startPoints()) routes.addAll(follow(new Route().start(block,con.from.inverse()),con));
}
this.routes.clear();
for (HashMap<Integer, Tile> column: tiles.values()) {
@ -279,7 +289,7 @@ public class Plan { @@ -279,7 +289,7 @@ public class Plan {
JSONObject pos = (JSONObject) entry;
Tile tile = result.get(pos.getInt("x"),pos.getInt("y"),false);
if (route.path().isEmpty()) {
route.start((Block) tile);
route.start((Block) tile,null);
} else {
route.add(tile, null);
}

66
src/main/java/de/srsoftware/web4rail/Route.java

@ -45,6 +45,8 @@ public class Route { @@ -45,6 +45,8 @@ public class Route {
private String id;
public Train train;
private Block startBlock = null,endBlock;
public Direction startDirection;
private Direction endDirection;
/**
* Route wurde von Zug betreten
@ -56,7 +58,10 @@ public class Route { @@ -56,7 +58,10 @@ public class Route {
public Tile add(Tile tile, Direction direrction) {
if (tile instanceof Shadow) tile = ((Shadow)tile).overlay();
if (tile instanceof Block) endBlock = (Block) tile;
if (tile instanceof Block) {
endBlock = (Block) tile;
endDirection = direrction;
}
path.add(tile);
if (tile instanceof Contact) contacts.add((Contact) tile);
if (tile instanceof Signal) {
@ -67,6 +72,15 @@ public class Route { @@ -67,6 +72,15 @@ public class Route {
return tile;
}
private void addAction(Object trigger, Action action) {
Vector<Action> actions = triggers.get(trigger);
if (actions == null) {
actions = new Vector<Action>();
triggers.put(trigger, actions);
}
actions.add(action);
}
void addSignal(Signal signal) {
signals.add(signal);
}
@ -78,7 +92,9 @@ public class Route { @@ -78,7 +92,9 @@ public class Route {
protected Route clone() {
Route clone = new Route();
clone.startBlock = startBlock;
clone.startDirection = startDirection;
clone.endBlock = endBlock;
clone.endDirection = endDirection;
clone.contacts = new Vector<Contact>(contacts);
clone.signals = new Vector<Signal>(signals);
clone.turnouts = new HashMap<>(turnouts);
@ -99,23 +115,6 @@ public class Route { @@ -99,23 +115,6 @@ public class Route {
addAction(lastContact, new FinishRoute(this));
}
}
private void addAction(Object trigger, Action action) {
// TODO Auto-generated method stub
Vector<Action> actions = triggers.get(trigger);
if (actions == null) {
actions = new Vector<Action>();
triggers.put(trigger, actions);
}
actions.add(action);
}
public void finish() throws IOException {
startBlock.train(null);
endBlock.train(train);
unlock();
}
/**
* Kontakt der Route aktivieren
@ -134,6 +133,13 @@ public class Route { @@ -134,6 +133,13 @@ public class Route {
}
}
public void finish() throws IOException {
startBlock.train(null);
endBlock.train(train.heading(endDirection.inverse()));
train.route = null;
unlock();
}
public String id() {
if (id == null) {
StringBuilder sb = new StringBuilder();
@ -152,8 +158,11 @@ public class Route { @@ -152,8 +158,11 @@ public class Route {
return id;
}
public boolean inUse() {
return false;
public boolean free() {
for (int i=1; i<path.size(); i++) {
if (!path.get(i).free()) return false;
}
return true;
}
@ -213,24 +222,31 @@ public class Route { @@ -213,24 +222,31 @@ public class Route {
public Window properties() {
Window win = new Window("route-properties",t("Properties of {}",this));
new Tag("h4").content(t("Origin and destination")).addTo(win);
Tag list = new Tag("ul");
Plan.addLink(startBlock, t("Origin: {} to {}",startBlock.name,startDirection), list);
Plan.addLink(endBlock, t("Destination: {} from {}",endBlock.name,endDirection), list);
list.addTo(win);
if (!signals.isEmpty()) {
new Tag("h4").content(t("Signals")).addTo(win);
Tag list = new Tag("ul");
list = new Tag("ul");
for (Signal s : signals) Plan.addLink(s,s.toString(),list);
list.addTo(win);
}
if (!contacts.isEmpty()) {
new Tag("h4").content(t("Contacts")).addTo(win);
Tag list = new Tag("ul");
list = new Tag("ul");
for (Contact c : contacts) Plan.addLink(c,c.toString(),list);
list.addTo(win);
}
if (!turnouts.isEmpty()) {
new Tag("h4").content(t("Turnouts")).addTo(win);
Tag list = new Tag("ul");
list = new Tag("ul");
for (Entry<Turnout, State> entry : turnouts.entrySet()) {
Turnout turnout = entry.getKey();
Plan.addLink(turnout, turnout+": "+entry.getValue(), list);
@ -257,12 +273,14 @@ public class Route { @@ -257,12 +273,14 @@ public class Route {
return form;
}
public Route start(Block block) {
public Route start(Block block,Direction from) {
// add those fields to clone, too!
contacts = new Vector<Contact>();
signals = new Vector<Signal>();
path = new Vector<Tile>();
turnouts = new HashMap<>();
startBlock = block;
startDirection = from;
path.add(block);
return this;
}

49
src/main/java/de/srsoftware/web4rail/moving/Train.java

@ -11,11 +11,11 @@ import org.slf4j.LoggerFactory; @@ -11,11 +11,11 @@ import org.slf4j.LoggerFactory;
import de.keawe.tools.translations.Translation;
import de.srsoftware.tools.Tag;
import de.srsoftware.web4rail.Application;
import de.srsoftware.web4rail.Plan.Direction;
import de.srsoftware.web4rail.Route;
import de.srsoftware.web4rail.Window;
import de.srsoftware.web4rail.tiles.Block;
import de.srsoftware.web4rail.tiles.Signal;
import de.srsoftware.web4rail.tiles.Tile;
public class Train {
private static final Logger LOG = LoggerFactory.getLogger(Train.class);
@ -23,8 +23,9 @@ public class Train { @@ -23,8 +23,9 @@ public class Train {
private Vector<Car> cars = new Vector<Car>();
private String name = null;
private Block block = null;
private Route route;
public Route route;
public int speed = 0;
private Direction direction;
public Train(Locomotive loco) {
add(loco);
@ -49,12 +50,33 @@ public class Train { @@ -49,12 +50,33 @@ public class Train {
}
public String name() {
return name != null ? name : locos.firstElement().name();
String result = (name != null ? name : locos.firstElement().name());
if (direction == null) return result;
switch (direction) {
case NORTH:
case WEST:
return '←'+result;
case SOUTH:
case EAST:
return result+'→';
}
return result;
}
public Tag props() {
Window window = new Window("train-properties",t("Properties of {}",getClass().getSimpleName()));
Tag list = new Tag("ul");
Tag locos = new Tag("li").content(t("Locomotives:"));
Tag l2 = new Tag("ul");
for (Locomotive loco : this.locos) new Tag("li").content(loco.name()).addTo(l2);
l2.addTo(locos).addTo(list);
new Tag("li").content(t("Current location: {}",block)).addTo(list);
new Tag("li").content(t("Direction: heading {}",direction)).addTo(list);
new Tag("li").clazz("link").attr("onclick","train("+block.x+","+block.y+",'start')").content(t("start")).addTo(list).addTo(window);
return window;
}
@ -64,19 +86,23 @@ public class Train { @@ -64,19 +86,23 @@ public class Train {
}
public String start() throws IOException {
if (block == null) return t("{] not in a block",this);
if (block == null) return t("{} not in a block",this);
HashSet<Route> routes = block.routes();
Vector<Route> availableRoutes = new Vector<Route>();
for (Route route : routes) {
Vector<Tile> path = route.path();
if (path.firstElement() != block) continue;
if (route.inUse()) continue;
if (route.path().firstElement() != block) continue; // route does not start with current location of loco
if (direction != null && route.startDirection != direction) continue;
if (!route.free()) {
LOG.debug("{} is not free!",route);
continue;
}
availableRoutes.add(route);
}
Random rand = new Random();
if (route != null) route.unlock().setSignals(Signal.STOP);
Random rand = new Random();
if (availableRoutes.isEmpty()) return t("No free routes from {}",block);
int sel = rand.nextInt(availableRoutes.size());
route = availableRoutes.get(sel).lock(this).setSignals(null);
this.route = availableRoutes.get(sel).lock(this).setSignals(null);
setSpeed(100);
return t("started {}",this);
}
@ -89,4 +115,9 @@ public class Train { @@ -89,4 +115,9 @@ public class Train {
public String toString() {
return name();
}
public Train heading(Direction dir) {
direction = dir;
return this;
}
}

23
src/main/java/de/srsoftware/web4rail/tiles/Block.java

@ -28,8 +28,11 @@ public abstract class Block extends StretchableTile{ @@ -28,8 +28,11 @@ public abstract class Block extends StretchableTile{
super.configure(config);
if (config.has(NAME)) name = config.getString(NAME);
}
public abstract List<Connector> startPoints();
@Override
public boolean free() {
return train == null && super.free();
}
@Override
public Tag propForm() {
@ -54,6 +57,8 @@ public abstract class Block extends StretchableTile{ @@ -54,6 +57,8 @@ public abstract class Block extends StretchableTile{
return window;
}
public abstract List<Connector> startPoints();
@Override
public Tag tag(Map<String, Object> replacements) throws IOException {
if (replacements == null) replacements = new HashMap<String, Object>();
@ -68,13 +73,6 @@ public abstract class Block extends StretchableTile{ @@ -68,13 +73,6 @@ public abstract class Block extends StretchableTile{
return getClass().getSimpleName()+"("+name+") @ ("+x+","+y+")";
}
@Override
public Tile update(HashMap<String, String> params) {
super.update(params);
if (params.containsKey(NAME)) name=params.get(NAME);
return this;
}
public void train(Train train) throws IOException {
this.train = train;
if (train != null) train.block(this);
@ -93,4 +91,11 @@ public abstract class Block extends StretchableTile{ @@ -93,4 +91,11 @@ public abstract class Block extends StretchableTile{
plan.stream("dropclass tile-"+x+"-"+y+" locked");
} else plan.stream("dropclass tile-"+x+"-"+y+" locked occupied");
}
@Override
public Tile update(HashMap<String, String> params) {
super.update(params);
if (params.containsKey(NAME)) name=params.get(NAME);
return this;
}
}

8
src/main/java/de/srsoftware/web4rail/tiles/Tile.java

@ -62,6 +62,10 @@ public abstract class Tile { @@ -62,6 +62,10 @@ public abstract class Tile {
public void configure(JSONObject config) {}
public boolean free() {
return route == null;
}
public int height() {
return 1;
}
@ -210,4 +214,8 @@ public abstract class Tile { @@ -210,4 +214,8 @@ public abstract class Tile {
LOG.debug("{}.update({})",getClass().getSimpleName(),params);
return this;
}
public Route route() {
return route;
}
}

Loading…
Cancel
Save