Arrow is now displayed on screen more vividly, the arrow can be customised to a different colour scheme if needed. #story[882]
This commit is contained in:
@@ -17,7 +17,7 @@ public class RaceStatus extends AC35Data {
|
|||||||
private int windSpeed;
|
private int windSpeed;
|
||||||
private int raceType;
|
private int raceType;
|
||||||
private ArrayList<BoatStatus> boatStatuses;
|
private ArrayList<BoatStatus> boatStatuses;
|
||||||
private static final double windDirectionScalar = 360.0 / 32768.0; // 0x8000 / 360
|
private static final double windDirectionScalar = 360.0 / 49152; // 0xC000 / 360
|
||||||
|
|
||||||
public RaceStatus(long currentTime, int raceID, int raceStatus, long expectedStartTime, int windDirection, int windSpeed, int raceType, ArrayList<BoatStatus> boatStatuses){
|
public RaceStatus(long currentTime, int raceID, int raceStatus, long expectedStartTime, int windDirection, int windSpeed, int raceType, ArrayList<BoatStatus> boatStatuses){
|
||||||
super(MessageType.RACESTATUS);
|
super(MessageType.RACESTATUS);
|
||||||
|
|||||||
@@ -54,6 +54,12 @@
|
|||||||
<version>1.0-SNAPSHOT</version>
|
<version>1.0-SNAPSHOT</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>eu.hansolo</groupId>
|
||||||
|
<artifactId>Medusa</artifactId>
|
||||||
|
<version>7.9</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,16 +1,27 @@
|
|||||||
package seng302.Controllers;
|
package seng302.Controllers;
|
||||||
|
|
||||||
|
|
||||||
|
import eu.hansolo.medusa.Fonts;
|
||||||
|
import eu.hansolo.medusa.Gauge;
|
||||||
|
import eu.hansolo.medusa.GaugeBuilder;
|
||||||
|
import eu.hansolo.medusa.skins.GaugeSkin;
|
||||||
|
import eu.hansolo.medusa.skins.GaugeSkinBase;
|
||||||
import javafx.collections.ObservableList;
|
import javafx.collections.ObservableList;
|
||||||
import javafx.fxml.FXML;
|
import javafx.fxml.FXML;
|
||||||
|
import javafx.geometry.Pos;
|
||||||
import javafx.scene.control.*;
|
import javafx.scene.control.*;
|
||||||
import javafx.scene.layout.GridPane;
|
import javafx.scene.layout.GridPane;
|
||||||
|
import javafx.scene.layout.Pane;
|
||||||
|
import javafx.scene.layout.StackPane;
|
||||||
|
import javafx.scene.paint.Color;
|
||||||
|
import javafx.scene.paint.Paint;
|
||||||
import seng302.Mock.StreamedRace;
|
import seng302.Mock.StreamedRace;
|
||||||
import seng302.Model.*;
|
import seng302.Model.*;
|
||||||
import seng302.VisualiserInput;
|
import seng302.VisualiserInput;
|
||||||
|
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Locale;
|
||||||
import java.util.ResourceBundle;
|
import java.util.ResourceBundle;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -24,7 +35,9 @@ public class RaceController extends Controller {
|
|||||||
|
|
||||||
private ResizableRaceCanvas raceMap;
|
private ResizableRaceCanvas raceMap;
|
||||||
private ResizableRaceMap raceBoundaries;
|
private ResizableRaceMap raceBoundaries;
|
||||||
|
private Gauge arrow;
|
||||||
@FXML SplitPane race;
|
@FXML SplitPane race;
|
||||||
|
@FXML StackPane arrowPane;
|
||||||
@FXML CheckBox showFPS;
|
@FXML CheckBox showFPS;
|
||||||
@FXML CheckBox showBoatPath;
|
@FXML CheckBox showBoatPath;
|
||||||
@FXML CheckBox showAnnotations;
|
@FXML CheckBox showAnnotations;
|
||||||
@@ -94,6 +107,8 @@ public class RaceController extends Controller {
|
|||||||
StreamedRace newRace = new StreamedRace(visualiserInput, this);
|
StreamedRace newRace = new StreamedRace(visualiserInput, this);
|
||||||
//newRace.initialiseBoats();
|
//newRace.initialiseBoats();
|
||||||
|
|
||||||
|
makeArrow();
|
||||||
|
|
||||||
raceMap = new ResizableRaceCanvas(visualiserInput.getCourse());
|
raceMap = new ResizableRaceCanvas(visualiserInput.getCourse());
|
||||||
raceMap.setMouseTransparent(true);
|
raceMap.setMouseTransparent(true);
|
||||||
raceMap.widthProperty().bind(canvasBase.widthProperty());
|
raceMap.widthProperty().bind(canvasBase.widthProperty());
|
||||||
@@ -101,6 +116,7 @@ public class RaceController extends Controller {
|
|||||||
//raceMap.setBoats(newRace.getStartingBoats());
|
//raceMap.setBoats(newRace.getStartingBoats());
|
||||||
raceMap.draw();
|
raceMap.draw();
|
||||||
raceMap.setVisible(true);
|
raceMap.setVisible(true);
|
||||||
|
raceMap.setArrow(this.arrow);
|
||||||
|
|
||||||
canvasBase.getChildren().add(0, raceMap);
|
canvasBase.getChildren().add(0, raceMap);
|
||||||
|
|
||||||
@@ -110,6 +126,7 @@ public class RaceController extends Controller {
|
|||||||
raceBoundaries.heightProperty().bind(canvasBase.heightProperty());
|
raceBoundaries.heightProperty().bind(canvasBase.heightProperty());
|
||||||
raceBoundaries.draw();
|
raceBoundaries.draw();
|
||||||
raceBoundaries.setVisible(true);
|
raceBoundaries.setVisible(true);
|
||||||
|
|
||||||
canvasBase.getChildren().add(0, raceBoundaries);
|
canvasBase.getChildren().add(0, raceBoundaries);
|
||||||
|
|
||||||
race.setVisible(true);
|
race.setVisible(true);
|
||||||
@@ -211,4 +228,44 @@ public class RaceController extends Controller {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void makeArrow() {
|
||||||
|
arrow = GaugeBuilder.create()
|
||||||
|
.minValue(0)
|
||||||
|
.maxValue(359)
|
||||||
|
.startAngle(180)
|
||||||
|
.angleRange(360)
|
||||||
|
.autoScale(false)
|
||||||
|
.customTickLabelsEnabled(true)
|
||||||
|
.customTickLabels("N", "", "", "", "", "", "", "", "",
|
||||||
|
"E", "", "", "", "", "", "", "", "",
|
||||||
|
"S", "", "", "", "", "", "", "", "",
|
||||||
|
"W", "", "", "", "", "", "", "", "")
|
||||||
|
.customTickLabelFontSize(72)
|
||||||
|
.needleBehavior(Gauge.NeedleBehavior.OPTIMIZED)
|
||||||
|
.borderPaint(Color.web("#1f1e23"))
|
||||||
|
.backgroundPaint(Color.web("#1f1e23"))
|
||||||
|
.needleColor(Color.web("#dad9db"))
|
||||||
|
.tickMarkColor(Color.web("#9f9fa1"))
|
||||||
|
.tickLabelColor(Color.web("#dad9db"))
|
||||||
|
.valueColor(Color.web("#dad9db"))
|
||||||
|
.title("Wind direction")
|
||||||
|
.titleColor(Color.web("#dad9db"))
|
||||||
|
.knobType(Gauge.KnobType.FLAT)
|
||||||
|
.knobColor(Gauge.BRIGHT_COLOR)
|
||||||
|
.prefSize(125, 125)
|
||||||
|
.maxWidth(125)
|
||||||
|
.maxHeight(125)
|
||||||
|
.build();
|
||||||
|
|
||||||
|
Label value = new Label("0°");
|
||||||
|
value.setFont(Fonts.latoBold(72));
|
||||||
|
value.setAlignment(Pos.CENTER);
|
||||||
|
|
||||||
|
arrow.valueProperty().addListener(o -> {
|
||||||
|
value.setText(String.format("%f°", arrow.getValue()));
|
||||||
|
});
|
||||||
|
arrow.setValue(0);
|
||||||
|
arrowPane.getChildren().add(arrow);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,9 @@
|
|||||||
package seng302.Model;
|
package seng302.Model;
|
||||||
|
|
||||||
|
|
||||||
|
import eu.hansolo.medusa.Gauge;
|
||||||
|
import eu.hansolo.medusa.GaugeBuilder;
|
||||||
|
import javafx.scene.layout.Pane;
|
||||||
import javafx.scene.paint.Color;
|
import javafx.scene.paint.Color;
|
||||||
import javafx.scene.paint.Paint;
|
import javafx.scene.paint.Paint;
|
||||||
import javafx.scene.transform.Rotate;
|
import javafx.scene.transform.Rotate;
|
||||||
@@ -31,6 +34,7 @@ public class ResizableRaceCanvas extends ResizableCanvas {
|
|||||||
private final List<Marker> markers;
|
private final List<Marker> markers;
|
||||||
double[] xpoints = {}, ypoints = {};
|
double[] xpoints = {}, ypoints = {};
|
||||||
private final RaceDataSource raceData;
|
private final RaceDataSource raceData;
|
||||||
|
private Gauge arrow;
|
||||||
|
|
||||||
public ResizableRaceCanvas(RaceDataSource raceData) {
|
public ResizableRaceCanvas(RaceDataSource raceData) {
|
||||||
super();
|
super();
|
||||||
@@ -146,6 +150,13 @@ public class ResizableRaceCanvas extends ResizableCanvas {
|
|||||||
gc.restore();
|
gc.restore();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void displayFancyArrow(GraphCoordinate coordinate, double angle) {
|
||||||
|
angle = angle % 360;
|
||||||
|
if (arrow != null && arrow.getValue() != angle) {
|
||||||
|
this.arrow.setValue(angle);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Rotates things on the canvas Note: this must be called in between gc.save() and gc.restore() else they will rotate everything
|
* Rotates things on the canvas Note: this must be called in between gc.save() and gc.restore() else they will rotate everything
|
||||||
*
|
*
|
||||||
@@ -240,9 +251,9 @@ public class ResizableRaceCanvas extends ResizableCanvas {
|
|||||||
|
|
||||||
//display wind direction arrow - specify origin point and angle - angle now set to random angle
|
//display wind direction arrow - specify origin point and angle - angle now set to random angle
|
||||||
if (raceData instanceof StreamedCourse) {
|
if (raceData instanceof StreamedCourse) {
|
||||||
displayArrow(new GraphCoordinate((int) getWidth() - 40, 40), ((StreamedCourse) raceData).getWindDirection());
|
displayFancyArrow(new GraphCoordinate((int) getWidth() - 40, 40), ((StreamedCourse) raceData).getWindDirection());
|
||||||
} else {
|
} else {
|
||||||
displayArrow(new GraphCoordinate((int) getWidth() - 40, 40), 150);
|
displayFancyArrow(new GraphCoordinate((int) getWidth() - 40, 40), 150);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -349,4 +360,8 @@ public class ResizableRaceCanvas extends ResizableCanvas {
|
|||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void setArrow(Gauge arrow) {
|
||||||
|
this.arrow = arrow;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -219,7 +219,7 @@ public class VisualiserInput implements Runnable {
|
|||||||
|
|
||||||
//If no heartbeat has been received in more the heartbeat period
|
//If no heartbeat has been received in more the heartbeat period
|
||||||
//then the connection will need to be restarted.
|
//then the connection will need to be restarted.
|
||||||
System.out.println("time since last heartbeat: " + timeSinceHeartbeat());//TEMP REMOVE
|
//System.out.println("time since last heartbeat: " + timeSinceHeartbeat());//TEMP REMOVE
|
||||||
long heartBeatPeriod = 10 * 1000;
|
long heartBeatPeriod = 10 * 1000;
|
||||||
if (timeSinceHeartbeat() > heartBeatPeriod) {
|
if (timeSinceHeartbeat() > heartBeatPeriod) {
|
||||||
System.out.println("Connection has stopped, trying to reconnect.");
|
System.out.println("Connection has stopped, trying to reconnect.");
|
||||||
@@ -285,7 +285,7 @@ public class VisualiserInput implements Runnable {
|
|||||||
for (BoatStatus boatStatus: this.raceStatus.getBoatStatuses()) {
|
for (BoatStatus boatStatus: this.raceStatus.getBoatStatuses()) {
|
||||||
this.boatStatusMap.put(boatStatus.getSourceID(), boatStatus);
|
this.boatStatusMap.put(boatStatus.getSourceID(), boatStatus);
|
||||||
}
|
}
|
||||||
setCourseWindDirection(raceStatus.getScaledWindDirection() + 180);
|
setCourseWindDirection(raceStatus.getScaledWindDirection());
|
||||||
}
|
}
|
||||||
//DisplayTextMessage.
|
//DisplayTextMessage.
|
||||||
/*else if (message instanceof DisplayTextMessage) {
|
/*else if (message instanceof DisplayTextMessage) {
|
||||||
|
|||||||
@@ -1,12 +1,14 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
|
||||||
|
<?import java.lang.*?>
|
||||||
|
<?import javafx.geometry.*?>
|
||||||
|
<?import javafx.scene.text.*?>
|
||||||
<?import javafx.geometry.Insets?>
|
<?import javafx.geometry.Insets?>
|
||||||
<?import javafx.scene.control.*?>
|
<?import javafx.scene.control.*?>
|
||||||
<?import javafx.scene.layout.*?>
|
<?import javafx.scene.layout.*?>
|
||||||
<?import javafx.scene.text.Font?>
|
<?import javafx.scene.text.Font?>
|
||||||
<SplitPane xmlns:fx="http://javafx.com/fxml/1" fx:id="race" dividerPositions="0.7" visible="false" AnchorPane.bottomAnchor="0.0"
|
|
||||||
AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0"
|
<SplitPane fx:id="race" dividerPositions="0.7" visible="false" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="seng302.Controllers.RaceController">
|
||||||
xmlns="http://javafx.com/javafx/8" fx:controller="seng302.Controllers.RaceController">
|
|
||||||
<items>
|
<items>
|
||||||
<GridPane fx:id="canvasBase">
|
<GridPane fx:id="canvasBase">
|
||||||
<columnConstraints>
|
<columnConstraints>
|
||||||
@@ -24,28 +26,13 @@
|
|||||||
<content>
|
<content>
|
||||||
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="240.0" prefWidth="200.0">
|
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="240.0" prefWidth="200.0">
|
||||||
<children>
|
<children>
|
||||||
<CheckBox fx:id="showBoatPath" mnemonicParsing="false" selected="true"
|
<CheckBox fx:id="showBoatPath" mnemonicParsing="false" selected="true" text="Show Boat Paths" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="104.0" />
|
||||||
text="Show Boat Paths" AnchorPane.leftAnchor="0.0"
|
<CheckBox fx:id="showAnnotations" layoutX="-2.0" layoutY="14.0" mnemonicParsing="false" selected="true" text="Show Annotations" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="0.0" />
|
||||||
AnchorPane.topAnchor="104.0"/>
|
<CheckBox fx:id="showName" layoutY="39.0" mnemonicParsing="false" selected="true" text="Show Boat Name" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="26.0" />
|
||||||
<CheckBox fx:id="showAnnotations" layoutX="-2.0" layoutY="14.0"
|
<CheckBox fx:id="showAbbrev" layoutY="61.0" mnemonicParsing="false" selected="true" text="Show Boat Abbreviation" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="52.0" />
|
||||||
mnemonicParsing="false" selected="true"
|
<CheckBox fx:id="showSpeed" layoutY="90.0" mnemonicParsing="false" selected="true" text="Show Boat Speed" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="78.0" />
|
||||||
text="Show Annotations" AnchorPane.leftAnchor="0.0"
|
<Button fx:id="saveAnno" layoutX="11.0" layoutY="106.0" maxWidth="154.0" mnemonicParsing="false" prefWidth="154.0" text="Save Annotation" AnchorPane.topAnchor="130.0" />
|
||||||
AnchorPane.topAnchor="0.0"/>
|
<Button fx:id="showSetAnno" layoutX="11.0" layoutY="139.0" mnemonicParsing="false" text="Show Set Annotation" AnchorPane.topAnchor="160.0" />
|
||||||
<CheckBox fx:id="showName" layoutY="39.0" mnemonicParsing="false"
|
|
||||||
selected="true" text="Show Boat Name"
|
|
||||||
AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="26.0"/>
|
|
||||||
<CheckBox fx:id="showAbbrev" layoutY="61.0" mnemonicParsing="false"
|
|
||||||
selected="true" text="Show Boat Abbreviation"
|
|
||||||
AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="52.0"/>
|
|
||||||
<CheckBox fx:id="showSpeed" layoutY="90.0" mnemonicParsing="false"
|
|
||||||
selected="true" text="Show Boat Speed"
|
|
||||||
AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="78.0"/>
|
|
||||||
<Button fx:id="saveAnno" layoutX="11.0" layoutY="106.0" maxWidth="154.0"
|
|
||||||
mnemonicParsing="false" prefWidth="154.0" text="Save Annotation"
|
|
||||||
AnchorPane.topAnchor="130.0"/>
|
|
||||||
<Button fx:id="showSetAnno" layoutX="11.0" layoutY="139.0"
|
|
||||||
mnemonicParsing="false" text="Show Set Annotation"
|
|
||||||
AnchorPane.topAnchor="160.0"/>
|
|
||||||
</children>
|
</children>
|
||||||
</AnchorPane>
|
</AnchorPane>
|
||||||
</content>
|
</content>
|
||||||
@@ -54,9 +41,7 @@
|
|||||||
<content>
|
<content>
|
||||||
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
|
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
|
||||||
<children>
|
<children>
|
||||||
<CheckBox fx:id="showFPS" layoutX="-14.0" layoutY="13.0"
|
<CheckBox fx:id="showFPS" layoutX="-14.0" layoutY="13.0" mnemonicParsing="false" selected="true" text="Show FPS" AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="0.0" />
|
||||||
mnemonicParsing="false" selected="true" text="Show FPS"
|
|
||||||
AnchorPane.leftAnchor="0.0" AnchorPane.topAnchor="0.0"/>
|
|
||||||
</children>
|
</children>
|
||||||
</AnchorPane>
|
</AnchorPane>
|
||||||
</content>
|
</content>
|
||||||
@@ -65,15 +50,12 @@
|
|||||||
</Accordion>
|
</Accordion>
|
||||||
</children>
|
</children>
|
||||||
</Pane>
|
</Pane>
|
||||||
<Label fx:id="timer" layoutX="45.0" layoutY="146.0" maxHeight="20.0" text="0:0"
|
<Label fx:id="timer" layoutX="45.0" layoutY="146.0" maxHeight="20.0" text="0:0" AnchorPane.bottomAnchor="0.0" AnchorPane.rightAnchor="0.0" GridPane.halignment="RIGHT" GridPane.valignment="BOTTOM">
|
||||||
AnchorPane.bottomAnchor="0.0" AnchorPane.rightAnchor="0.0" GridPane.halignment="RIGHT"
|
|
||||||
GridPane.valignment="BOTTOM">
|
|
||||||
<font>
|
<font>
|
||||||
<Font name="System Bold" size="15.0" />
|
<Font name="System Bold" size="15.0" />
|
||||||
</font>
|
</font>
|
||||||
</Label>
|
</Label>
|
||||||
<Label fx:id="FPS" text="FPS: 0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0"
|
<Label fx:id="FPS" text="FPS: 0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" GridPane.halignment="LEFT" GridPane.valignment="BOTTOM">
|
||||||
GridPane.halignment="LEFT" GridPane.valignment="BOTTOM">
|
|
||||||
<font>
|
<font>
|
||||||
<Font name="System Bold" size="15.0" />
|
<Font name="System Bold" size="15.0" />
|
||||||
</font>
|
</font>
|
||||||
@@ -86,14 +68,16 @@
|
|||||||
<Font name="System Bold" size="15.0" />
|
<Font name="System Bold" size="15.0" />
|
||||||
</font>
|
</font>
|
||||||
</Label>
|
</Label>
|
||||||
|
<StackPane fx:id="arrowPane" alignment="TOP_RIGHT" prefHeight="150.0" prefWidth="150.0" snapToPixel="false" GridPane.halignment="RIGHT" GridPane.valignment="TOP">
|
||||||
|
<GridPane.margin>
|
||||||
|
<Insets bottom="5.0" left="5.0" right="5.0" top="5.0" />
|
||||||
|
</GridPane.margin>
|
||||||
|
</StackPane>
|
||||||
</children>
|
</children>
|
||||||
</GridPane>
|
</GridPane>
|
||||||
<AnchorPane layoutX="450.0" minHeight="0.0" minWidth="0.0" prefHeight="160.0" prefWidth="200.0"
|
<AnchorPane layoutX="450.0" minHeight="0.0" minWidth="0.0" prefHeight="160.0" prefWidth="200.0" GridPane.columnIndex="1">
|
||||||
GridPane.columnIndex="1">
|
|
||||||
<children>
|
<children>
|
||||||
<TableView fx:id="boatInfoTable" layoutX="-2.0" prefHeight="600.0" prefWidth="264.0"
|
<TableView fx:id="boatInfoTable" layoutX="-2.0" prefHeight="600.0" prefWidth="264.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="-2.0" AnchorPane.rightAnchor="-62.0" AnchorPane.topAnchor="0.0">
|
||||||
AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="-2.0" AnchorPane.rightAnchor="-62.0"
|
|
||||||
AnchorPane.topAnchor="0.0">
|
|
||||||
<columns>
|
<columns>
|
||||||
<TableColumn fx:id="boatPlacingColumn" prefWidth="50.0" text="Place" />
|
<TableColumn fx:id="boatPlacingColumn" prefWidth="50.0" text="Place" />
|
||||||
<TableColumn fx:id="boatTeamColumn" prefWidth="100.0" text="Team" />
|
<TableColumn fx:id="boatTeamColumn" prefWidth="100.0" text="Team" />
|
||||||
|
|||||||
Reference in New Issue
Block a user