diff --git a/src/main/java/seng302/model/Yacht.java b/src/main/java/seng302/model/Yacht.java index 1c9e7ec6..34bbb4f0 100644 --- a/src/main/java/seng302/model/Yacht.java +++ b/src/main/java/seng302/model/Yacht.java @@ -10,6 +10,8 @@ import javafx.beans.property.ReadOnlyDoubleWrapper; import javafx.beans.property.ReadOnlyLongProperty; import javafx.beans.property.ReadOnlyLongWrapper; import javafx.scene.paint.Color; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import seng302.gameServer.GameState; import seng302.model.mark.CompoundMark; import seng302.model.mark.Mark; @@ -28,8 +30,11 @@ public class Yacht { void notifyLocation(Yacht yacht, double lat, double lon, double heading, double velocity); } + private Logger logger = LoggerFactory.getLogger(Yacht.class); + private static final Double ROUNDING_DISTANCE = 50d; // TODO: 3/08/17 wmu16 - Look into this value further + //BOTH AFAIK private String boatType; private Integer sourceId; @@ -39,7 +44,7 @@ public class Yacht { private String country; private Long estimateTimeAtFinish; - private Integer currentMarkSeqID = 1; + private Integer currentMarkSeqID = 0; private Long markRoundTime; private Double distanceToNextMark; private Long timeTillNext; @@ -119,6 +124,7 @@ public class Yacht { } //UPDATE BOAT LOCATION + lastLocation = location; location = GeoUtility.getGeoCoordinate(location, heading, velocity * secondsElapsed); //CHECK FOR MARK ROUNDING @@ -167,11 +173,22 @@ public class Yacht { * 'mark passing algorithm' */ private void checkForMarkRounding() { - if (!GameState.getMarkOrder().isLastMark(currentMarkSeqID) && currentMarkSeqID != 0) { + CompoundMark currentMark = GameState.getMarkOrder().getCurrentMark(currentMarkSeqID); + + if (GameState.getMarkOrder().isLastMark(currentMarkSeqID) || currentMarkSeqID == 0) { + if (GeoUtility.checkCrossedLine(currentMark.getSubMark(1), + currentMark.getSubMark(2), lastLocation, location)) { + System.out.println( + "(" + currentMarkSeqID + ") Passed gate: " + currentMark.getMarks().get(0) + .getName() + + " ID(" + currentMark.getId() + ")"); + currentMarkSeqID++; + } + } else { + //ALL OTHER MARKS distanceToNextMark = calcDistanceToNextMark(); // System.out.println("distanceToNextMark = " + distanceToNextMark); CompoundMark nextMark = GameState.getMarkOrder().getNextMark(currentMarkSeqID); - CompoundMark currentMark = GameState.getMarkOrder().getCurrentMark(currentMarkSeqID); CompoundMark prevMark = GameState.getMarkOrder().getPreviousMark(currentMarkSeqID); //1 TEST FOR ENTERING THE ROUDNING DISTANCE @@ -188,7 +205,6 @@ public class Yacht { if (GeoUtility.isPointInTriangle(lastLocation, location, nextMark.getMarks().get(0), thisCurrentMark)) { hasPassedFirstLine = true; - System.out.println("Passed first line!"); } //3 TEST FOR CROSSING PREV - CURRENT LINE SECOND @@ -198,7 +214,10 @@ public class Yacht { currentMarkSeqID++; hasPassedFirstLine = false; hasEnteredRoundingZone = false; - System.out.println("SUCCESFUL ROUDNING!"); + System.out.println( + "(" + currentMarkSeqID + ") Passed mark: " + currentMark.getMarks() + .get(0).getName() + + " ID(" + currentMark.getId() + ")"); break; } } @@ -206,6 +225,7 @@ public class Yacht { } } + public void adjustHeading(Double amount) { Double newVal = heading + amount; lastHeading = heading; diff --git a/src/main/java/seng302/utilities/GeoUtility.java b/src/main/java/seng302/utilities/GeoUtility.java index 9aa61b9d..81acebe6 100644 --- a/src/main/java/seng302/utilities/GeoUtility.java +++ b/src/main/java/seng302/utilities/GeoUtility.java @@ -1,7 +1,10 @@ package seng302.utilities; import javafx.geometry.Point2D; +import seng302.gameServer.GameState; import seng302.model.GeoPoint; +import seng302.model.mark.CompoundMark; +import seng302.model.mark.Mark; public class GeoUtility { @@ -126,6 +129,35 @@ public class GeoUtility { } + /** + * Checks if a point passes across a line, either direction + * See the wiki Mark Rounding algorithm for more info + * + * @param mark1 One mark of the line + * @param mark2 The second mark of the line + * @param lastLocation The last location of the point crossing this line + * @param location The current location of the point crossing this line + * @return True if crossed since last location --> current location, false otherwise + */ + public static Boolean checkCrossedLine(GeoPoint mark1, GeoPoint mark2, GeoPoint lastLocation, + GeoPoint location) { + //START GATE OR FINISH GATE + Double alpha = GeoUtility.getBearing(mark1, lastLocation); + Double beta = GeoUtility.getBearing(mark1, mark2); + Double theta = GeoUtility.getBearing(mark1, location); + alpha = (alpha > 180) ? 360 - alpha : alpha; + beta = (beta > 180) ? 360 - beta : beta; + theta = (theta > 180) ? 360 - theta : theta; + + if (alpha < beta && theta > beta) { + if (!GeoUtility.isPointInTriangle(mark1, lastLocation, location, mark2)) { + return true; + } + } + return false; + } + + /** * Given a point and a vector (angle and vector length) Will create a new point, that vector * away from the origin point diff --git a/src/main/java/seng302/visualiser/GameClient.java b/src/main/java/seng302/visualiser/GameClient.java index 915eef37..b00a6cda 100644 --- a/src/main/java/seng302/visualiser/GameClient.java +++ b/src/main/java/seng302/visualiser/GameClient.java @@ -174,7 +174,6 @@ public class GameClient { break; case BOAT_XML: - System.out.println("GOT SUM BOATS YAY :)"); allBoatsMap = XMLParser.parseBoats( StreamParser.extractXmlMessage(packet) ); diff --git a/src/main/java/seng302/visualiser/controllers/RaceViewController.java b/src/main/java/seng302/visualiser/controllers/RaceViewController.java index a6df4f61..2a166081 100644 --- a/src/main/java/seng302/visualiser/controllers/RaceViewController.java +++ b/src/main/java/seng302/visualiser/controllers/RaceViewController.java @@ -312,7 +312,7 @@ public class RaceViewController extends Thread implements ImportantAnnotationDel updateRaceTime(); updateWindDirection(); updateOrder(); - updateSparkLine(); +// updateSparkLine(); } }, 0, 1000); } diff --git a/src/test/java/seng302/utilities/GeoUtilityTest.java b/src/test/java/seng302/utilities/GeoUtilityTest.java index 8382bb8c..4bd1e128 100644 --- a/src/test/java/seng302/utilities/GeoUtilityTest.java +++ b/src/test/java/seng302/utilities/GeoUtilityTest.java @@ -9,9 +9,11 @@ import javafx.geometry.Point2D; import org.junit.Before; import org.junit.Test; import seng302.model.GeoPoint; +import seng302.model.mark.CompoundMark; import seng302.utilities.GeoUtility; /** + * http://www.geoplaner.com/ For plotting geo points for visualisation * To test methods in GeoUtility. * Use this site to calculate distances * https://rechneronline.de/geo-coordinates/#distance @@ -150,4 +152,22 @@ public class GeoUtilityTest { assertFalse(GeoUtility.isPointInTriangle(v1, v2, v3, p2)); } + + + @Test + public void testCheckCrossedGate() { + GeoPoint mark1 = new GeoPoint(37.40937, -122.62233); + GeoPoint mark2 = new GeoPoint(37.40938, -122.62154); + GeoPoint location1 = new GeoPoint(37.40964, -122.62196); + GeoPoint location2 = new GeoPoint(37.40910, -122.62189); + GeoPoint location3 = new GeoPoint(37.40949, -122.62202); + GeoPoint location4 = new GeoPoint(34.40955, -122.62176); + GeoPoint location5 = new GeoPoint(37.40927, -122.62152); + GeoPoint location6 = new GeoPoint(34.40933, -122.62163); + + assertTrue(GeoUtility.checkCrossedLine(mark1, mark2, location1, location2)); + assertFalse(GeoUtility.checkCrossedLine(mark1, mark2, location4, location3)); + assertFalse(GeoUtility.checkCrossedLine(mark1, mark2, location1, location3)); + assertFalse(GeoUtility.checkCrossedLine(mark1, mark2, location5, location6)); + } } \ No newline at end of file