mirror of
https://github.com/michaelrausch/Party-Parrots-At-Sea.git
synced 2026-05-09 06:18:44 +00:00
Plugged Canvas map to canvas view controller to display map
- rebase on the latest develop status - optimised the scaling factor the map to fit the canvas view - a new image containing map image is displayed under race canvas #story[928]
This commit is contained in:
@@ -15,8 +15,10 @@ public class App extends Application {
|
|||||||
public void start(Stage primaryStage) throws Exception {
|
public void start(Stage primaryStage) throws Exception {
|
||||||
Parent root = FXMLLoader.load(getClass().getResource("/views/MainView.fxml"));
|
Parent root = FXMLLoader.load(getClass().getResource("/views/MainView.fxml"));
|
||||||
primaryStage.setTitle("RaceVision");
|
primaryStage.setTitle("RaceVision");
|
||||||
primaryStage.setScene(new Scene(root));
|
primaryStage.setScene(new Scene(root, 1530, 960));
|
||||||
primaryStage.setMaximized(true);
|
primaryStage.setMaxWidth(1530);
|
||||||
|
primaryStage.setMaxHeight(960);
|
||||||
|
// primaryStage.setMaximized(true);
|
||||||
|
|
||||||
primaryStage.show();
|
primaryStage.show();
|
||||||
primaryStage.setOnCloseRequest(e -> {
|
primaryStage.setOnCloseRequest(e -> {
|
||||||
@@ -64,6 +66,7 @@ public class App extends Application {
|
|||||||
else{
|
else{
|
||||||
// sr = new StreamReceiver("localhost", 4949, "RaceStream");
|
// sr = new StreamReceiver("localhost", 4949, "RaceStream");
|
||||||
sr = new StreamReceiver("livedata.americascup.com", 4941, "RaceStream");
|
sr = new StreamReceiver("livedata.americascup.com", 4941, "RaceStream");
|
||||||
|
// sr = new StreamReceiver("csse-s302staff.canterbury.ac.nz", 4941, "RaceStream");
|
||||||
}
|
}
|
||||||
|
|
||||||
sr.start();
|
sr.start();
|
||||||
|
|||||||
@@ -12,12 +12,15 @@ import javafx.geometry.Point2D;
|
|||||||
import javafx.scene.Group;
|
import javafx.scene.Group;
|
||||||
import javafx.scene.canvas.Canvas;
|
import javafx.scene.canvas.Canvas;
|
||||||
import javafx.scene.canvas.GraphicsContext;
|
import javafx.scene.canvas.GraphicsContext;
|
||||||
|
import javafx.scene.image.ImageView;
|
||||||
import javafx.scene.layout.AnchorPane;
|
import javafx.scene.layout.AnchorPane;
|
||||||
import javafx.scene.paint.Color;
|
import javafx.scene.paint.Color;
|
||||||
import javafx.scene.text.Font;
|
import javafx.scene.text.Font;
|
||||||
import seng302.models.BoatGroup;
|
import seng302.models.BoatGroup;
|
||||||
import seng302.models.Colors;
|
import seng302.models.Colors;
|
||||||
import seng302.models.Yacht;
|
import seng302.models.Yacht;
|
||||||
|
import seng302.models.map.Boundary;
|
||||||
|
import seng302.models.map.CanvasMap;
|
||||||
import seng302.models.mark.GateMark;
|
import seng302.models.mark.GateMark;
|
||||||
import seng302.models.mark.Mark;
|
import seng302.models.mark.Mark;
|
||||||
import seng302.models.mark.MarkGroup;
|
import seng302.models.mark.MarkGroup;
|
||||||
@@ -28,6 +31,8 @@ import seng302.models.stream.XMLParser;
|
|||||||
import seng302.models.stream.XMLParser.RaceXMLObject.Limit;
|
import seng302.models.stream.XMLParser.RaceXMLObject.Limit;
|
||||||
import seng302.models.stream.XMLParser.RaceXMLObject.Participant;
|
import seng302.models.stream.XMLParser.RaceXMLObject.Participant;
|
||||||
import seng302.models.stream.packets.BoatPositionPacket;
|
import seng302.models.stream.packets.BoatPositionPacket;
|
||||||
|
import seng302.server.simulator.GeoUtility;
|
||||||
|
import seng302.server.simulator.mark.Position;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Created by ptg19 on 15/03/17.
|
* Created by ptg19 on 15/03/17.
|
||||||
@@ -42,15 +47,18 @@ public class CanvasController {
|
|||||||
private ResizableCanvas canvas;
|
private ResizableCanvas canvas;
|
||||||
private Group group;
|
private Group group;
|
||||||
private GraphicsContext gc;
|
private GraphicsContext gc;
|
||||||
|
private ImageView mapImage;
|
||||||
|
|
||||||
private final int MARK_SIZE = 10;
|
private final int MARK_SIZE = 10;
|
||||||
private final int BUFFER_SIZE = 50;
|
private final int BUFFER_SIZE = 50;
|
||||||
|
private final int PANEL_WIDTH = 1260; // it should be 1280 but, minors 40 to cancel the bias.
|
||||||
|
private final int PANEL_HEIGHT = 960;
|
||||||
private final int CANVAS_WIDTH = 720;
|
private final int CANVAS_WIDTH = 720;
|
||||||
private final int CANVAS_HEIGHT = 720;
|
private final int CANVAS_HEIGHT = 720;
|
||||||
private final int LHS_BUFFER = BUFFER_SIZE;
|
private final int LHS_BUFFER = BUFFER_SIZE;
|
||||||
private final int RHS_BUFFER = BUFFER_SIZE + MARK_SIZE / 2;
|
private final int RHS_BUFFER = BUFFER_SIZE;
|
||||||
private final int TOP_BUFFER = BUFFER_SIZE;
|
private final int TOP_BUFFER = BUFFER_SIZE;
|
||||||
private final int BOT_BUFFER = TOP_BUFFER + MARK_SIZE / 2;
|
private final int BOT_BUFFER = TOP_BUFFER;
|
||||||
private boolean horizontalInversion = false;
|
private boolean horizontalInversion = false;
|
||||||
|
|
||||||
private double distanceScaleFactor;
|
private double distanceScaleFactor;
|
||||||
@@ -61,6 +69,8 @@ public class CanvasController {
|
|||||||
private Mark maxLonPoint;
|
private Mark maxLonPoint;
|
||||||
private double referencePointX;
|
private double referencePointX;
|
||||||
private double referencePointY;
|
private double referencePointY;
|
||||||
|
private double metersPerPixelX;
|
||||||
|
private double metersPerPixelY;
|
||||||
|
|
||||||
private List<MarkGroup> markGroups = new ArrayList<>();
|
private List<MarkGroup> markGroups = new ArrayList<>();
|
||||||
private List<BoatGroup> boatGroups = new ArrayList<>();
|
private List<BoatGroup> boatGroups = new ArrayList<>();
|
||||||
@@ -87,6 +97,12 @@ public class CanvasController {
|
|||||||
canvas = new ResizableCanvas();
|
canvas = new ResizableCanvas();
|
||||||
group = new Group();
|
group = new Group();
|
||||||
|
|
||||||
|
// create image view for map, bind panel size to image
|
||||||
|
mapImage = new ImageView();
|
||||||
|
canvasPane.getChildren().add(mapImage);
|
||||||
|
mapImage.fitWidthProperty().bind(canvasPane.widthProperty());
|
||||||
|
mapImage.fitHeightProperty().bind(canvasPane.heightProperty());
|
||||||
|
|
||||||
canvasPane.getChildren().add(canvas);
|
canvasPane.getChildren().add(canvas);
|
||||||
canvasPane.getChildren().add(group);
|
canvasPane.getChildren().add(group);
|
||||||
// Bind canvas size to stack pane size.
|
// Bind canvas size to stack pane size.
|
||||||
@@ -97,11 +113,13 @@ public class CanvasController {
|
|||||||
public void initializeCanvas (){
|
public void initializeCanvas (){
|
||||||
|
|
||||||
gc = canvas.getGraphicsContext2D();
|
gc = canvas.getGraphicsContext2D();
|
||||||
gc.save();
|
// gc.save();
|
||||||
gc.setFill(Color.SKYBLUE);
|
// gc.setFill(Color.SKYBLUE);
|
||||||
gc.fillRect(0,0, CANVAS_WIDTH, CANVAS_HEIGHT);
|
// gc.fillRect(0,0, CANVAS_WIDTH, CANVAS_HEIGHT);
|
||||||
gc.restore();
|
// gc.restore();
|
||||||
|
gc.setGlobalAlpha(0.5);
|
||||||
fitMarksToCanvas();
|
fitMarksToCanvas();
|
||||||
|
drawGoogleMap();
|
||||||
|
|
||||||
|
|
||||||
// TODO: 1/05/17 wmu16 - Change this call to now draw the marks as from the xml
|
// TODO: 1/05/17 wmu16 - Change this call to now draw the marks as from the xml
|
||||||
@@ -137,6 +155,30 @@ public class CanvasController {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* First find the top right and bottom left points' geo locations, then retrieve
|
||||||
|
* map from google to display on image view. - Haoming 22/5/2017
|
||||||
|
*/
|
||||||
|
private void drawGoogleMap() {
|
||||||
|
findMetersPerPixel();
|
||||||
|
Point2D topLeftPoint = findScaledXY(maxLatPoint.getLatitude(), minLonPoint.getLongitude());
|
||||||
|
// distance from top left extreme to panel origin (top left corner)
|
||||||
|
double distanceFromTopLeftToOrigin = Math.sqrt(Math.pow(topLeftPoint.getX() * metersPerPixelX, 2) + Math.pow(topLeftPoint.getY() * metersPerPixelY, 2));
|
||||||
|
// angle from top left extreme to panel origin
|
||||||
|
double bearingFromTopLeftToOrigin = Math.toDegrees(Math.atan2(-topLeftPoint.getX(), topLeftPoint.getY()));
|
||||||
|
// the top left extreme
|
||||||
|
Position topLeftPos = new Position(maxLatPoint.getLatitude(), minLonPoint.getLongitude());
|
||||||
|
Position originPos = GeoUtility.getGeoCoordinate(topLeftPos, bearingFromTopLeftToOrigin, distanceFromTopLeftToOrigin);
|
||||||
|
|
||||||
|
// distance from origin corner to bottom right corner of the panel
|
||||||
|
double distanceFromOriginToBottomRight = Math.sqrt(Math.pow(PANEL_HEIGHT* metersPerPixelY, 2) + Math.pow(PANEL_WIDTH * metersPerPixelX, 2));
|
||||||
|
double bearingFromOriginToBottomRight = Math.toDegrees(Math.atan2(PANEL_WIDTH, -PANEL_HEIGHT));
|
||||||
|
Position bottomRightPos = GeoUtility.getGeoCoordinate(originPos, bearingFromOriginToBottomRight, distanceFromOriginToBottomRight);
|
||||||
|
|
||||||
|
Boundary boundary = new Boundary(originPos.getLat(), bottomRightPos.getLng(), bottomRightPos.getLat(), originPos.getLng());
|
||||||
|
CanvasMap canvasMap = new CanvasMap(boundary);
|
||||||
|
mapImage.setImage(canvasMap.getMapImage());
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds border marks to the canvas, taken from the XML file
|
* Adds border marks to the canvas, taken from the XML file
|
||||||
@@ -174,8 +216,8 @@ public class CanvasController {
|
|||||||
borderPoint2.getX(), borderPoint2.getY());
|
borderPoint2.getX(), borderPoint2.getY());
|
||||||
xBoundaryPoints[courseLimits.size()-1] = borderPoint1.getX();
|
xBoundaryPoints[courseLimits.size()-1] = borderPoint1.getX();
|
||||||
yBoundaryPoints[courseLimits.size()-1] = borderPoint1.getY();
|
yBoundaryPoints[courseLimits.size()-1] = borderPoint1.getY();
|
||||||
gc.setFill(Color.LIGHTBLUE);
|
// gc.setFill(Color.LIGHTBLUE);
|
||||||
gc.fillPolygon(xBoundaryPoints,yBoundaryPoints,yBoundaryPoints.length);
|
// gc.fillPolygon(xBoundaryPoints,yBoundaryPoints,yBoundaryPoints.length);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateGroups(){
|
private void updateGroups(){
|
||||||
@@ -201,11 +243,13 @@ public class CanvasController {
|
|||||||
|
|
||||||
private void checkForCourseChanges() {
|
private void checkForCourseChanges() {
|
||||||
if (StreamParser.isNewRaceXmlReceived()){
|
if (StreamParser.isNewRaceXmlReceived()){
|
||||||
gc.setFill(Color.SKYBLUE);
|
// gc.setFill(Color.SKYBLUE);
|
||||||
gc.fillRect(0,0, CANVAS_WIDTH, CANVAS_HEIGHT);
|
// gc.fillRect(0,0, CANVAS_WIDTH, CANVAS_HEIGHT);
|
||||||
gc.restore();
|
// gc.restore();
|
||||||
|
gc.clearRect(0, 0, CANVAS_WIDTH, CANVAS_HEIGHT);
|
||||||
|
drawGoogleMap();
|
||||||
addRaceBorder();
|
addRaceBorder();
|
||||||
canvas.toBack();
|
// canvas.toBack();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -465,6 +509,27 @@ public class CanvasController {
|
|||||||
return new Point2D(xAxisLocation, yAxisLocation);
|
return new Point2D(xAxisLocation, yAxisLocation);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find the number of meters per pixel.
|
||||||
|
*/
|
||||||
|
private void findMetersPerPixel () {
|
||||||
|
Point2D p1, p2;
|
||||||
|
Mark m1, m2;
|
||||||
|
double theta, distance, dx, dy, dHorizontal, dVertical;
|
||||||
|
m1 = new SingleMark("m1", maxLatPoint.getLatitude(), minLonPoint.getLongitude(), 1);
|
||||||
|
m2 = new SingleMark("m2", minLatPoint.getLatitude(), maxLonPoint.getLongitude(), 2);
|
||||||
|
p1 = findScaledXY(m1);
|
||||||
|
p2 = findScaledXY(m2);
|
||||||
|
theta = Mark.calculateHeadingRad(m1, m2);
|
||||||
|
distance = Mark.calculateDistance(m1, m2);
|
||||||
|
dHorizontal = Math.abs(Math.sin(theta) * distance);
|
||||||
|
dVertical = Math.abs(Math.cos(theta) * distance);
|
||||||
|
dx = Math.abs(p1.getX() - p2.getX());
|
||||||
|
dy = Math.abs(p1.getY() - p2.getY());
|
||||||
|
metersPerPixelX = dHorizontal / dx;
|
||||||
|
metersPerPixelY = dVertical / dy;
|
||||||
|
}
|
||||||
|
|
||||||
List<BoatGroup> getBoatGroups() {
|
List<BoatGroup> getBoatGroups() {
|
||||||
return boatGroups;
|
return boatGroups;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user