From 3176e76c8cd1b0350327040213d805029d263c90 Mon Sep 17 00:00:00 2001 From: fjc40 Date: Thu, 31 Aug 2017 21:06:13 +1200 Subject: [PATCH 1/9] MockRace: Now uses RaceState as its base class, rather than Race. This aligns it with VisualiserRace. RaceState contains the shared race state between the client and server, and stores most of its data in RaceDataSource etc..., instead of maintaining its own copy. Moved collider registry member to MockRace. XMLUtilities: Added documentation to two important functions, and updated them to use generics instead of Objects. #story[1188] --- .../src/main/java/mock/app/Event.java | 5 +- .../src/main/java/mock/model/MockRace.java | 60 ++-- .../main/java/mock/xml/RaceXMLCreator.java | 12 +- .../src/main/java/shared/model/Race.java | 318 ------------------ .../main/java/shared/xml/XMLUtilities.java | 27 +- 5 files changed, 71 insertions(+), 351 deletions(-) delete mode 100644 racevisionGame/src/main/java/shared/model/Race.java diff --git a/racevisionGame/src/main/java/mock/app/Event.java b/racevisionGame/src/main/java/mock/app/Event.java index c054e2fb..526223ba 100644 --- a/racevisionGame/src/main/java/mock/app/Event.java +++ b/racevisionGame/src/main/java/mock/app/Event.java @@ -25,6 +25,8 @@ import java.nio.charset.StandardCharsets; import java.time.Duration; import java.time.ZonedDateTime; import java.time.format.DateTimeFormatter; +import java.util.ArrayList; +import java.util.List; import java.util.concurrent.TimeUnit; import java.util.logging.Level; import java.util.logging.Logger; @@ -118,7 +120,8 @@ public class Event { } - this.sourceIdAllocator = new SourceIdAllocator(raceDataSource.getParticipants()); + List potentialParticipants = new ArrayList<>(boatDataSource.getBoats().keySet()); + this.sourceIdAllocator = new SourceIdAllocator(potentialParticipants); this.compositeCommand = new CompositeCommand(); this.latestMessages = new LatestMessages(); diff --git a/racevisionGame/src/main/java/mock/model/MockRace.java b/racevisionGame/src/main/java/mock/model/MockRace.java index 379123af..357d34ce 100644 --- a/racevisionGame/src/main/java/mock/model/MockRace.java +++ b/racevisionGame/src/main/java/mock/model/MockRace.java @@ -1,6 +1,7 @@ package mock.model; import javafx.animation.AnimationTimer; +import mock.model.collider.ColliderRegistry; import mock.xml.*; import network.Messages.BoatLocation; import network.Messages.BoatStatus; @@ -13,7 +14,6 @@ import shared.exceptions.BoatNotFoundException; import shared.enums.RoundingType; import shared.model.*; import shared.model.Bearing; -import shared.model.Race; import java.time.ZonedDateTime; import java.time.temporal.ChronoUnit; @@ -27,7 +27,7 @@ import static java.lang.Math.cos; * Has a course, boats, boundaries, etc... * Is responsible for simulating the race, and sending messages to a MockOutput instance. */ -public class MockRace extends Race { +public class MockRace extends RaceState { /** * An observable list of boats in the race. @@ -40,6 +40,12 @@ public class MockRace extends Race { private List shrinkBoundary; + /** + * Registry for all collider object in this race + */ + protected ColliderRegistry colliderRegistry; + + /** * The scale factor of the race. * See {@link Constants#RaceTimeScale}. @@ -51,6 +57,8 @@ public class MockRace extends Race { */ private WindGenerator windGenerator; + + /** * Constructs a race object with a given RaceDataSource, BoatDataSource, and RegattaDataSource and sends events to the given mockOutput. * @param boatDataSource Data source for boat related data (yachts and marker boats). @@ -62,13 +70,15 @@ public class MockRace extends Race { */ public MockRace(BoatDataSource boatDataSource, RaceDataSource raceDataSource, RegattaDataSource regattaDataSource, Polars polars, int timeScale, WindGenerator windGenerator) { - super(boatDataSource, raceDataSource, regattaDataSource); + this.setBoatDataSource(boatDataSource); + this.setRaceDataSource(raceDataSource); + this.setRegattaDataSource(regattaDataSource); this.scaleFactor = timeScale; this.boats = this.generateMockBoats(boatDataSource.getBoats(), raceDataSource.getParticipants(), polars); - this.shrinkBoundary = GPSCoordinate.getShrinkBoundary(this.boundary); + this.shrinkBoundary = GPSCoordinate.getShrinkBoundary(this.getBoundary()); this.windGenerator = windGenerator; @@ -76,9 +86,19 @@ public class MockRace extends Race { //Wind. this.setWind(windGenerator.generateBaselineWind()); + + // Set up colliders + this.colliderRegistry = new ColliderRegistry(); + + for(CompoundMark mark: this.getCompoundMarks()) { + colliderRegistry.addCollider(mark.getMark1()); + if(mark.getMark2() != null) colliderRegistry.addCollider(mark.getMark2()); + } + this.colliderRegistry.addAllColliders(boats); } + /** * Generates a list of MockBoats given a list of Boats, and a list of participating boats. * @param boats The map of Boats describing boats that are potentially in the race. Maps boat sourceID to boat. @@ -108,12 +128,17 @@ public class MockRace extends Race { } + public ColliderRegistry getColliderRegistry() { + return colliderRegistry; + } + + /** * Updates the race time to a specified value, in milliseconds since the unix epoch. * @param currentTime Milliseconds since unix epoch. */ public void updateRaceTime(long currentTime) { - this.raceClock.setUTCTime(currentTime); + this.getRaceClock().setUTCTime(currentTime); } @@ -123,7 +148,7 @@ public class MockRace extends Race { public void updateRaceStatusEnum() { //The millisecond duration of the race. Negative means it hasn't started, so we flip sign. - long timeToStart = - this.raceClock.getDurationMilli(); + long timeToStart = - this.getRaceClock().getDurationMilli(); if (timeToStart > Constants.RacePreStartTime) { @@ -194,7 +219,7 @@ public class MockRace extends Race { //The boat starts on the first leg of the race. - boat.setCurrentLeg(this.legs.get(0)); + boat.setCurrentLeg(this.getLegs().get(0)); //Boats start with 0 knots speed. boat.setCurrentSpeed(0d); @@ -223,7 +248,7 @@ public class MockRace extends Race { private List getSpreadStartingPositions() { //The first compound marker of the race - the starting gate. - CompoundMark compoundMark = this.legs.get(0).getStartCompoundMark(); + CompoundMark compoundMark = this.getLegs().get(0).getStartCompoundMark(); //The position of the two markers from the compound marker. GPSCoordinate mark1Position = compoundMark.getMark1Position(); @@ -485,7 +510,7 @@ public class MockRace extends Race { roundingChecks.get(0), boat.getPosition(), legBearing) && gateCheck && boat.isBetweenGate(roundingMark, Mark.tempMark(roundingChecks.get(0)))) { boat.increaseRoundingStatus(); - if (boat.getCurrentLeg().getLegNumber() + 2 >= legs.size()){ + if (boat.getCurrentLeg().getLegNumber() + 2 >= getLegs().size()){ //boat has finished race boat.increaseRoundingStatus(); } @@ -503,7 +528,7 @@ public class MockRace extends Race { case 2://has traveled 180 degrees around the mark //Move boat on to next leg. boat.resetRoundingStatus(); - Leg nextLeg = this.legs.get(boat.getCurrentLeg().getLegNumber() + 1); + Leg nextLeg = this.getLegs().get(boat.getCurrentLeg().getLegNumber() + 1); boat.setCurrentLeg(nextLeg); break; } @@ -530,7 +555,7 @@ public class MockRace extends Race { gateCheck && boat.isBetweenGate(roundingMark, Mark.tempMark(roundingChecks.get(0)))) { boat.increaseRoundingStatus(); - if (boat.getCurrentLeg().getLegNumber() + 2 >= legs.size()){ + if (boat.getCurrentLeg().getLegNumber() + 2 >= getLegs().size()){ //boat has finished race boat.increaseRoundingStatus(); } @@ -547,7 +572,7 @@ public class MockRace extends Race { case 2://has traveled 180 degrees around the mark //Move boat on to next leg. boat.resetRoundingStatus(); - Leg nextLeg = this.legs.get(boat.getCurrentLeg().getLegNumber() + 1); + Leg nextLeg = this.getLegs().get(boat.getCurrentLeg().getLegNumber() + 1); boat.setCurrentLeg(nextLeg); break; } @@ -585,7 +610,7 @@ public class MockRace extends Race { GPSCoordinate roundCheck2; try{ - Leg nextLeg = legs.get(legs.indexOf(boat.getCurrentLeg()) + 1); + Leg nextLeg = getLegs().get(getLegs().indexOf(boat.getCurrentLeg()) + 1); GPSCoordinate startNextDirectionLinePoint = nextLeg.getStartCompoundMark().getMark1Position(); GPSCoordinate endNextDirectionLinePoint = nextLeg.getEndCompoundMark().getMark1Position(); @@ -681,7 +706,7 @@ public class MockRace extends Race { */ public void changeWindDirection() { - Wind nextWind = windGenerator.generateNextWind(raceWind.getValue()); + Wind nextWind = windGenerator.generateNextWind(windProperty().getValue()); setWind(nextWind); } @@ -702,13 +727,10 @@ public class MockRace extends Race { long timeFromNow = (long) (1000 * boat.calculateDistanceToNextMarker() / velocityToMark); //Calculate time at which it will reach mark. - ZonedDateTime timeAtMark = this.raceClock.getCurrentTime().plus(timeFromNow, ChronoUnit.MILLIS); + ZonedDateTime timeAtMark = this.getRaceClock().getCurrentTime().plus(timeFromNow, ChronoUnit.MILLIS); boat.setEstimatedTimeAtNextMark(timeAtMark); } } - public List getCompoundMarks() { - return compoundMarks; - } -} \ No newline at end of file +} diff --git a/racevisionGame/src/main/java/mock/xml/RaceXMLCreator.java b/racevisionGame/src/main/java/mock/xml/RaceXMLCreator.java index f1b83479..5cb74625 100644 --- a/racevisionGame/src/main/java/mock/xml/RaceXMLCreator.java +++ b/racevisionGame/src/main/java/mock/xml/RaceXMLCreator.java @@ -77,7 +77,8 @@ public class RaceXMLCreator { public static String alterRaceToWind(String s, double degrees) throws XMLReaderException, InvalidRaceDataException, JAXBException, IOException, SAXException, ParserConfigurationException { RaceXMLReader reader = new RaceXMLReader(s, XMLFileType.ResourcePath); - XMLRace race = (XMLRace) XMLUtilities.xmlToClass(RaceXMLCreator.class.getClassLoader().getResourceAsStream(s), + XMLRace race = XMLUtilities.xmlToClass( + RaceXMLCreator.class.getClassLoader().getResourceAsStream(s), RaceXMLCreator.class.getClassLoader().getResource("mock/mockXML/schema/raceSchema.xsd"), XMLRace.class); @@ -89,14 +90,7 @@ public class RaceXMLCreator { alterRaceRotation(race, degreesToRotate); - JAXBContext context = JAXBContext.newInstance(XMLRace.class); - Marshaller jaxbMarshaller = context.createMarshaller(); - jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); - - StringWriter sw = new StringWriter(); - - jaxbMarshaller.marshal(race, sw); - return sw.toString(); + return XMLUtilities.classToXML(race); } /** diff --git a/racevisionGame/src/main/java/shared/model/Race.java b/racevisionGame/src/main/java/shared/model/Race.java deleted file mode 100644 index a15e2edd..00000000 --- a/racevisionGame/src/main/java/shared/model/Race.java +++ /dev/null @@ -1,318 +0,0 @@ -package shared.model; - -import javafx.beans.property.IntegerProperty; -import javafx.beans.property.Property; -import javafx.beans.property.SimpleIntegerProperty; -import javafx.beans.property.SimpleObjectProperty; -import mock.model.collider.ColliderRegistry; -import network.Messages.Enums.RaceStatusEnum; -import network.Messages.Enums.RaceTypeEnum; -import shared.dataInput.BoatDataSource; -import shared.dataInput.RaceDataSource; -import shared.dataInput.RegattaDataSource; - -import java.util.List; - - -/** - * Represents a yacht race. - * Has a course, state, wind, boundaries, etc.... Boats are added by inheriting classes (see {@link Boat}, {@link mock.model.MockBoat}, {@link visualiser.model.VisualiserBoat}. - */ -public abstract class Race { - /** - * The source of race related data. - */ - protected RaceDataSource raceDataSource; - /** - * The source of boat related data. - */ - protected BoatDataSource boatDataSource; - /** - * The source of regatta related data. - */ - protected RegattaDataSource regattaDataSource; - /** - * A list of compound marks in the race. - */ - protected List compoundMarks; - /** - * A list of legs in the race. - */ - protected List legs; - /** - * A list of coordinates describing the boundary of the course. - */ - protected List boundary; - /** - * The clock which tracks the race's start time, current time, and elapsed duration. - */ - protected RaceClock raceClock; - /** - * The race ID of the course. - */ - protected int raceId; - /** - * The name of the regatta. - */ - protected String regattaName; - /** - * The current status of the race. - */ - protected RaceStatusEnum raceStatusEnum; - /** - * The type of race this is. - */ - protected RaceTypeEnum raceType; - /** - * The race's wind. - */ - protected Property raceWind = new SimpleObjectProperty<>(); - /** - * Registry for all collider object in this race - */ - protected ColliderRegistry colliderRegistry; - /** - * The number of frames per second. - * We essentially track the number of frames generated per second, over a one second period. When {@link #lastFpsResetTime} reaches 1 second, currentFps is reset. - */ - private int currentFps = 0; - /** - * The number of frames per second we generated over the last 1 second period. - */ - private IntegerProperty lastFps = new SimpleIntegerProperty(0); - /** - * The time, in milliseconds, since we last reset our {@link #currentFps} counter. - */ - private long lastFpsResetTime; - - /** - * Constructs a race object with a given BoatDataSource, RaceDataSource, and RegattaDataSource. - * @param boatDataSource Data source for boat related data (yachts and marker boats). - * @param raceDataSource Data source for race related data (participating boats, legs, etc...). - * @param regattaDataSource Data source for race related data (course name, location, timezone, etc...). - */ - public Race(BoatDataSource boatDataSource, RaceDataSource raceDataSource, RegattaDataSource regattaDataSource) { - - //Keep a reference to data sources. - this.raceDataSource = raceDataSource; - this.boatDataSource = boatDataSource; - this.regattaDataSource = regattaDataSource; - - //Marks. - this.compoundMarks = raceDataSource.getCompoundMarks(); - //Boundaries. - this.boundary = raceDataSource.getBoundary(); - //Legs. - this.useLegsList(raceDataSource.getLegs()); - //Race ID. - this.raceId = raceDataSource.getRaceId(); - //Regatta name. - this.regattaName = regattaDataSource.getRegattaName(); - //Race clock. - this.raceClock = new RaceClock(this.raceDataSource.getStartDateTime()); - //Race status. - this.setRaceStatusEnum(RaceStatusEnum.NOT_ACTIVE); - //Race type. - this.raceType = raceDataSource.getRaceType(); - //Wind. - this.setWind(Bearing.fromDegrees(0), 0); - // Set up colliders - this.colliderRegistry = new ColliderRegistry(); - - for(CompoundMark mark: compoundMarks) { - colliderRegistry.addCollider(mark.getMark1()); - if(mark.getMark2() != null) colliderRegistry.addCollider(mark.getMark2()); - } - } - - public ColliderRegistry getColliderRegistry() { - return colliderRegistry; - } - - /** - * Initialise the boats in the race. - * This sets their starting positions and current legs. - */ - protected abstract void initialiseBoats(); - - /** - * Updates the race to use a new list of legs, and adds a dummy "Finish" leg at the end. - * @param legs The new list of legs to use. - */ - protected void useLegsList(List legs) { - //We add a "dummy" leg at the end of the race. - this.legs = legs; - this.legs.add(new Leg("Finish", this.legs.size())); - } - - /** - * Determines whether or not a specific leg is the last leg in the race. - * @param leg The leg to check. - * @return Returns true if it is the last, false otherwise. - */ - protected boolean isLastLeg(Leg leg) { - - //Get the last leg. - Leg lastLeg = this.legs.get(this.legs.size() - 1); - - //Check its ID. - int lastLegID = lastLeg.getLegNumber(); - - //Get the specified leg's ID. - int legID = leg.getLegNumber(); - - - //Check if they are the same. - return legID == lastLegID; - } - - /** - * Returns the current race status. - * @return The current race status. - */ - public RaceStatusEnum getRaceStatusEnum() { - return raceStatusEnum; - } - - /** - * Sets the current race status. - * @param raceStatusEnum The new status of the race. - */ - public void setRaceStatusEnum(RaceStatusEnum raceStatusEnum) { - this.raceStatusEnum = raceStatusEnum; - } - - /** - * Returns the type of race this is. - * @return The type of race this is. - */ - public RaceTypeEnum getRaceType() { - return raceType; - } - - /** - * Returns the name of the regatta. - * @return The name of the regatta. - */ - public String getRegattaName() { - return regattaName; - } - - /** - * Updates the race to have a specified wind bearing and speed. - * @param windBearing New wind bearing. - * @param windSpeedKnots New wind speed, in knots. - */ - protected void setWind(Bearing windBearing, double windSpeedKnots) { - Wind wind = new Wind(windBearing, windSpeedKnots); - setWind(wind); - } - - /** - * Updates the race to have a specified wind (bearing and speed). - * @param wind New wind. - */ - protected void setWind(Wind wind) { - this.raceWind.setValue(wind); - } - - /** - * Returns the wind bearing. - * @return The wind bearing. - */ - public Bearing getWindDirection() { - return raceWind.getValue().getWindDirection(); - } - - /** - * Returns the wind speed. - * Measured in knots. - * @return The wind speed. - */ - public double getWindSpeed() { - return raceWind.getValue().getWindSpeed(); - } - - /** - * Returns the RaceClock for this race. - * This is used to track the start time, current time, and elapsed duration of the race. - * @return The RaceClock for the race. - */ - public RaceClock getRaceClock() { - return raceClock; - } - - /** - * Returns the RaceDataSource used for the race. - * @return The RaceDataSource used for the race. - */ - public RaceDataSource getRaceDataSource() { - return raceDataSource; - } - - /** - * Returns the number of legs in the race. - * @return The number of legs in the race. - */ - public int getLegCount() { - //We minus one, as we have added an extra "dummy" leg. - return legs.size() - 1; - } - - /** - * Returns the race boundary. - * @return The race boundary. - */ - public List getBoundary() { - return boundary; - } - - - /** - * Returns the marks of the race. - * @return Marks of the race. - */ - public List getCompoundMarks() { - return compoundMarks; - } - - /** - * Returns the legs of the race. - * @return Legs of the race. - */ - public List getLegs() { - return legs; - } - - /** - * Returns the fps property. - * @return The fps property. - */ - public IntegerProperty fpsProperty() { - return lastFps; - } - - /** - * Increments the FPS counter, and adds timePeriod milliseconds to our FPS reset timer. - * @param timePeriod Time, in milliseconds, to add to {@link #lastFpsResetTime}. - */ - protected void incrementFps(long timePeriod) { - //Increment. - this.currentFps++; - - //Add period to timer. - this.lastFpsResetTime += timePeriod; - - //If we have reached 1 second period, snapshot the framerate and reset. - if (this.lastFpsResetTime > 1000) { - this.lastFps.set(this.currentFps); - - this.currentFps = 0; - this.lastFpsResetTime = 0; - } - } - - public int getRaceId() { - return raceId; - } -} diff --git a/racevisionGame/src/main/java/shared/xml/XMLUtilities.java b/racevisionGame/src/main/java/shared/xml/XMLUtilities.java index 8e01cb76..0a50f77d 100644 --- a/racevisionGame/src/main/java/shared/xml/XMLUtilities.java +++ b/racevisionGame/src/main/java/shared/xml/XMLUtilities.java @@ -20,10 +20,17 @@ import java.io.*; import java.net.URL; /** - * Created by fwy13 on 13/08/17. + * Contains utility functions to convert between xml files and xml class objects. */ public class XMLUtilities { + + /** + * Converts an XML class object to an XML string. + * @param o The XML class object to convert. + * @return String containing the serialised XML data. + * @throws JAXBException Thrown if the object is cannot be serialised to XML. + */ public static String classToXML(Object o) throws JAXBException { JAXBContext context = JAXBContext.newInstance(o.getClass()); Marshaller jaxbMarshaller = context.createMarshaller(); @@ -49,14 +56,26 @@ public class XMLUtilities { return xmlToClass(document, schemaURL, c); } - public static Object xmlToClass(InputStream i, URL schemaURL, Class c) throws ParserConfigurationException, IOException, SAXException, JAXBException { + /** + * Converts an XML file to an XML class (e.g., {@link shared.xml.Race.XMLRace}). + * @param i The input stream for the XML file. + * @param schemaURL URL for the XML schema. + * @param c The XML class to convert to. + * @param The XML class to convert to. + * @return The XML class object. + * @throws ParserConfigurationException + * @throws IOException + * @throws SAXException + * @throws JAXBException + */ + public static T xmlToClass(InputStream i, URL schemaURL, Class c) throws ParserConfigurationException, IOException, SAXException, JAXBException { DocumentBuilder parser = DocumentBuilderFactory.newInstance().newDocumentBuilder(); Document document = parser.parse(i); return xmlToClass(document, schemaURL, c); } - public static Object xmlToClass(Document document, URL schemaURL, Class c) throws ParserConfigurationException, IOException, SAXException, JAXBException { + public static T xmlToClass(Document document, URL schemaURL, Class c) throws ParserConfigurationException, IOException, SAXException, JAXBException { JAXBContext jc = JAXBContext.newInstance(c); Unmarshaller unmarshaller = jc.createUnmarshaller(); @@ -64,7 +83,7 @@ public class XMLUtilities { Schema schema = sf.newSchema(schemaURL); unmarshaller.setSchema(schema); - return unmarshaller.unmarshal(new DOMSource(document)); + return (T) unmarshaller.unmarshal(new DOMSource(document)); } public static boolean validateXML(String file, URL schemaURL){ From d0eebcdb2f86ab03c3af53f43124068e706e660d Mon Sep 17 00:00:00 2001 From: fjc40 Date: Fri, 1 Sep 2017 01:14:43 +1200 Subject: [PATCH 2/9] SourceIdAllocator now allocates from the BoatDataSource and RaceDataSource exposed by MockRace, instead of having its own source IDs. Can only allocate ids during PRESTART period. RaceLogic now calls MockRace.initialiseBoats() after the prestart period has finished. MockRace create a VisualiserBoat when a source ID is allocated. MockOutput now sends updated XML messages during the race, instead of only at the start. #story[1188] --- .../src/main/java/mock/app/MockOutput.java | 24 +++++++-- .../src/main/java/mock/model/MockRace.java | 51 +++++++++++-------- .../src/main/java/mock/model/RaceLogic.java | 32 ++++++++++++ .../java/mock/model/SourceIdAllocator.java | 39 +++++++------- .../src/main/java/shared/model/RaceState.java | 15 +++++- 5 files changed, 117 insertions(+), 44 deletions(-) diff --git a/racevisionGame/src/main/java/mock/app/MockOutput.java b/racevisionGame/src/main/java/mock/app/MockOutput.java index 68136ea0..023235cc 100644 --- a/racevisionGame/src/main/java/mock/app/MockOutput.java +++ b/racevisionGame/src/main/java/mock/app/MockOutput.java @@ -27,7 +27,12 @@ public class MockOutput implements RunnableWithFramePeriod { */ private LatestMessages latestMessages; + //These sequence number track the last race/boat/regatta xml message we've sent. + private int lastSentRaceNumber = -1; + private int lastSentBoatNumber = -1; + + private int lastSentRegattaNumber = -1; @@ -69,7 +74,6 @@ public class MockOutput implements RunnableWithFramePeriod { long previousFrameTime = System.currentTimeMillis(); - boolean sentXMLs = false; @@ -82,16 +86,26 @@ public class MockOutput implements RunnableWithFramePeriod { previousFrameTime = currentFrameTime; - //Send XML messages. - if (!sentXMLs) { + //Send XML messages if needed. + + if (lastSentRaceNumber != latestMessages.getRaceXMLMessage().getSequenceNumber()) { + lastSentRaceNumber = latestMessages.getRaceXMLMessage().getSequenceNumber(); outgoingMessages.put(latestMessages.getRaceXMLMessage()); - outgoingMessages.put(latestMessages.getRegattaXMLMessage()); + } + + if (lastSentBoatNumber != latestMessages.getBoatXMLMessage().getSequenceNumber()) { + lastSentBoatNumber = latestMessages.getBoatXMLMessage().getSequenceNumber(); outgoingMessages.put(latestMessages.getBoatXMLMessage()); + } - sentXMLs = true; + if (lastSentRegattaNumber != latestMessages.getRegattaXMLMessage().getSequenceNumber()) { + lastSentRegattaNumber = latestMessages.getRegattaXMLMessage().getSequenceNumber(); + outgoingMessages.put(latestMessages.getRegattaXMLMessage()); } + + List snapshot = latestMessages.getSnapshot(); for (AC35Data message : snapshot) { outgoingMessages.put(message); diff --git a/racevisionGame/src/main/java/mock/model/MockRace.java b/racevisionGame/src/main/java/mock/model/MockRace.java index 357d34ce..9bcece2c 100644 --- a/racevisionGame/src/main/java/mock/model/MockRace.java +++ b/racevisionGame/src/main/java/mock/model/MockRace.java @@ -43,7 +43,7 @@ public class MockRace extends RaceState { /** * Registry for all collider object in this race */ - protected ColliderRegistry colliderRegistry; + private ColliderRegistry colliderRegistry; /** @@ -58,6 +58,12 @@ public class MockRace extends RaceState { private WindGenerator windGenerator; + /** + * The polars file to use for each boat. + */ + private Polars polars; + + /** * Constructs a race object with a given RaceDataSource, BoatDataSource, and RegattaDataSource and sends events to the given mockOutput. @@ -74,9 +80,10 @@ public class MockRace extends RaceState { this.setRaceDataSource(raceDataSource); this.setRegattaDataSource(regattaDataSource); + this.polars = polars; this.scaleFactor = timeScale; - this.boats = this.generateMockBoats(boatDataSource.getBoats(), raceDataSource.getParticipants(), polars); + this.boats = new ArrayList<>(); this.shrinkBoundary = GPSCoordinate.getShrinkBoundary(this.getBoundary()); @@ -100,31 +107,35 @@ public class MockRace extends RaceState { /** - * Generates a list of MockBoats given a list of Boats, and a list of participating boats. - * @param boats The map of Boats describing boats that are potentially in the race. Maps boat sourceID to boat. - * @param sourceIDs The list of boat sourceIDs describing which specific boats are actually participating. - * @param polars The polars table to be used for boat simulation. - * @return A list of MockBoats that are participating in the race. + * Generates a MockBoat from the BoatDataSource, given a source ID. Also adds it to the participant list. + * @param sourceID The source ID to assign the boat. + * @return A MockBoat that is now participating in the race. */ - private List generateMockBoats(Map boats, List sourceIDs, Polars polars) { - - List mockBoats = new ArrayList<>(sourceIDs.size()); + public void generateMockBoat(Integer sourceID) { - //For each sourceID participating... - for (int sourceID : sourceIDs) { + //Get the boat associated with the sourceID. + Boat boat = getBoatDataSource().getBoats().get(sourceID); - //Get the boat associated with the sourceID. - Boat boat = boats.get(sourceID); + //Construct a MockBoat using the Boat and Polars. + MockBoat mockBoat = new MockBoat(boat, polars); + mockBoat.setCurrentLeg(this.getLegs().get(0)); - //Construct a MockBoat using the Boat and Polars. - MockBoat mockBoat = new MockBoat(boat, polars); + //Update participant list. + getRaceDataSource().getParticipants().add(sourceID); - mockBoats.add(mockBoat); + this.boats.add(mockBoat); - } - - return mockBoats; + getRaceDataSource().incrementSequenceNumber(); + } + /** + * Removes a MockBoat from the race, by sourceID. Also removes it from the participant list. + * @param sourceID Source ID of boat to remove. + */ + public void removeMockBoat(Integer sourceID) { + this.boats.removeIf(mockBoat -> mockBoat.getSourceID() == sourceID); + getRaceDataSource().getParticipants().remove(sourceID); + getRaceDataSource().incrementSequenceNumber(); } diff --git a/racevisionGame/src/main/java/mock/model/RaceLogic.java b/racevisionGame/src/main/java/mock/model/RaceLogic.java index 5b35d449..a1bddd9a 100644 --- a/racevisionGame/src/main/java/mock/model/RaceLogic.java +++ b/racevisionGame/src/main/java/mock/model/RaceLogic.java @@ -48,6 +48,9 @@ public class RaceLogic implements RunnableWithFramePeriod, Observer { */ @Override public void run() { + + prestartCountdown(); + race.initialiseBoats(); countdown(); @@ -60,6 +63,35 @@ public class RaceLogic implements RunnableWithFramePeriod, Observer { } + /** + * The countdown timer until the prestart period is finished. This timer will stop 3 minutes before the race starts, and players can no longer start participating. + */ + private void prestartCountdown() { + + long previousFrameTime = System.currentTimeMillis(); + + while (((race.getRaceStatusEnum() == RaceStatusEnum.PRESTART) + || (race.getRaceStatusEnum() == RaceStatusEnum.NOT_ACTIVE)) && loopBool) { + + long currentTime = System.currentTimeMillis(); + + //Update race time. + race.updateRaceTime(currentTime); + + //Update the race status based on the current time. + race.updateRaceStatusEnum(); + + //Provide boat's with an estimated time at next mark until the race starts. + race.setBoatsTimeNextMark(race.getRaceClock().getCurrentTime()); + + //Parse the race snapshot. + server.parseSnapshot(); + + waitForFramePeriod(previousFrameTime, currentTime, 50); + previousFrameTime = currentTime; + } + } + /** * Countdown timer until race starts. */ diff --git a/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java b/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java index 3b62a8a7..b609e5a5 100644 --- a/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java +++ b/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java @@ -2,6 +2,7 @@ package mock.model; import mock.exceptions.SourceIDAllocationException; +import network.Messages.Enums.RaceStatusEnum; import java.util.ArrayList; import java.util.List; @@ -13,24 +14,18 @@ public class SourceIdAllocator { /** - * This list contains all unallocated source IDs. + * The race we are allocating for. */ - List unallocatedIDs = new ArrayList<>(); + private MockRace mockRace; - /** - * This list contains all allocated source IDs. - */ - List allocatedIDs = new ArrayList<>(); - /** - * Creates a source ID allocator, using the given list of unallocated source IDs. - * @param unallocatedIDs List of unallocated source IDs. + * Creates a SourceIdAllocator for a given race. + * @param mockRace Race to allocate source IDs for. */ - public SourceIdAllocator(List unallocatedIDs) { - //We need to copy the list. - this.unallocatedIDs.addAll(unallocatedIDs); + public SourceIdAllocator(MockRace mockRace) { + this.mockRace = mockRace; } @@ -41,11 +36,23 @@ public class SourceIdAllocator { */ public synchronized int allocateSourceID() throws SourceIDAllocationException { + if (mockRace.getRaceStatusEnum() != RaceStatusEnum.PRESTART) { + throw new SourceIDAllocationException("Could not allocate a source ID. Can only allocate during pre-start period. It is currently: " + mockRace.getRaceStatusEnum()); + } + + List allocatedIDs = mockRace.getRaceDataSource().getParticipants(); + List allIDs = new ArrayList<>(mockRace.getBoatDataSource().getBoats().keySet()); + + //Get list of unallocated ids. + List unallocatedIDs = new ArrayList<>(allIDs); + unallocatedIDs.removeAll(allocatedIDs); + + if (!unallocatedIDs.isEmpty()) { int sourceID = unallocatedIDs.remove(0); - allocatedIDs.add(sourceID); + mockRace.generateMockBoat(sourceID); return sourceID; @@ -61,10 +68,6 @@ public class SourceIdAllocator { * @param sourceID Source ID to return. */ public void returnSourceID(Integer sourceID) { - - //We remove an Integer, not an int, so that we remove by value not by index. - allocatedIDs.remove(sourceID); - - unallocatedIDs.add(sourceID); + mockRace.removeMockBoat(sourceID); } } diff --git a/racevisionGame/src/main/java/shared/model/RaceState.java b/racevisionGame/src/main/java/shared/model/RaceState.java index 19a1a52c..48361da2 100644 --- a/racevisionGame/src/main/java/shared/model/RaceState.java +++ b/racevisionGame/src/main/java/shared/model/RaceState.java @@ -188,7 +188,20 @@ public abstract class RaceState { * @return List of mark boats. */ public List getMarks() { - return new ArrayList<>(boatDataSource.getMarkerBoats().values()); + //BoatDataSource contains a collection of Marks, and RaceDataSource contains a collection of Compound marks (which contain marks). RaceDataSource is the "definitive" source of mark data. + List marks = new ArrayList<>(getCompoundMarks().size() * 2); + + for (CompoundMark compoundMark : getCompoundMarks()) { + if (compoundMark.getMark1() != null) { + marks.add(compoundMark.getMark1()); + } + + if (compoundMark.getMark2() != null) { + marks.add(compoundMark.getMark2()); + } + } + + return marks; } /** From 9156bde8af94a2eb9e10d8b6a35cf5bdc46c8de4 Mon Sep 17 00:00:00 2001 From: fjc40 Date: Fri, 1 Sep 2017 01:19:17 +1200 Subject: [PATCH 3/9] Moved XML message creation to RaceServer instead of ConnectionAcceptor. RaceServer does not currently generate new XMLMessages - NYI. Added a sequence number to RaceDataSource - this is used to indicate that the data source has been modified. #story[1188] --- .../java/mock/app/ConnectionAcceptor.java | 78 +-------------- .../src/main/java/mock/app/Event.java | 4 +- .../src/main/java/mock/model/RaceServer.java | 96 +++++++++++++++++++ .../java/network/Messages/LatestMessages.java | 1 + .../shared/dataInput/EmptyRaceDataSource.java | 12 +++ .../java/shared/dataInput/RaceDataSource.java | 12 +++ .../java/shared/dataInput/RaceXMLReader.java | 12 +++ .../src/main/java/shared/model/Constants.java | 9 +- .../Controllers/FinishController.java | 6 +- .../main/resources/mock/mockXML/raceTest.xml | 7 +- .../mock/model/SourceIdAllocatorTest.java | 29 ++---- .../test/resources/mock/mockXML/raceTest.xml | 8 +- 12 files changed, 154 insertions(+), 120 deletions(-) diff --git a/racevisionGame/src/main/java/mock/app/ConnectionAcceptor.java b/racevisionGame/src/main/java/mock/app/ConnectionAcceptor.java index ee8ea216..b4ed1d2a 100644 --- a/racevisionGame/src/main/java/mock/app/ConnectionAcceptor.java +++ b/racevisionGame/src/main/java/mock/app/ConnectionAcceptor.java @@ -61,12 +61,7 @@ public class ConnectionAcceptor implements Runnable { */ private SourceIdAllocator sourceIdAllocator; - //race xml sequence number - private short raceXMLSequenceNumber; - //boat xml sequence number - private short boatXMLSequenceNumber; - //regatta xml sequence number - private short regattaXMLSequenceNumber; + // private RaceLogic raceLogic = null; @@ -209,77 +204,6 @@ public class ConnectionAcceptor implements Runnable { } } } - - /** - * Sets the Race XML to send. - * @param raceXml XML to send to the Client. - */ - public void setRaceXml(String raceXml) { - //Create the message. - XMLMessage message = this.createXMLMessage(raceXml, XMLMessageType.RACE); - //Place it in LatestMessages. - this.latestMessages.setRaceXMLMessage(message); - } - - /** - * Sets the Regatta XMl to send. - * @param regattaXml XML to send to Client. - */ - public void setRegattaXml(String regattaXml) { - //Create the message. - XMLMessage message = this.createXMLMessage(regattaXml, XMLMessageType.REGATTA); - //Place it in LatestMessages. - this.latestMessages.setRegattaXMLMessage(message); - } - - /** - * Sets the Boats XML to send. - * @param boatsXml XMl to send to the Client. - */ - public void setBoatsXml(String boatsXml) { - //Create the message. - XMLMessage message = this.createXMLMessage(boatsXml, XMLMessageType.BOAT); - - //Place it in LatestMessages. - this.latestMessages.setBoatXMLMessage(message); - } - - /** - * Creates an XMLMessage of a specified subtype using the xml contents string. - * @param xmlString The contents of the xml file. - * @param messageType The subtype of xml message (race, regatta, boat). - * @return The created XMLMessage object. - */ - private XMLMessage createXMLMessage(String xmlString, XMLMessageType messageType) { - - //Get the correct sequence number to use, and increment it. - short sequenceNumber = 0; - if (messageType == XMLMessageType.RACE) { - sequenceNumber = this.raceXMLSequenceNumber; - this.raceXMLSequenceNumber++; - - } else if (messageType == XMLMessageType.BOAT) { - sequenceNumber = this.boatXMLSequenceNumber; - this.boatXMLSequenceNumber++; - - } else if (messageType == XMLMessageType.REGATTA) { - sequenceNumber = this.regattaXMLSequenceNumber; - this.regattaXMLSequenceNumber++; - - } - - //Create the message. - XMLMessage message = new XMLMessage( - XMLMessage.currentVersionNumber, - AckSequencer.getNextAckNum(), - System.currentTimeMillis(), - messageType, - sequenceNumber, - xmlString); - - - return message; - } } diff --git a/racevisionGame/src/main/java/mock/app/Event.java b/racevisionGame/src/main/java/mock/app/Event.java index 526223ba..27e2103c 100644 --- a/racevisionGame/src/main/java/mock/app/Event.java +++ b/racevisionGame/src/main/java/mock/app/Event.java @@ -120,8 +120,7 @@ public class Event { } - List potentialParticipants = new ArrayList<>(boatDataSource.getBoats().keySet()); - this.sourceIdAllocator = new SourceIdAllocator(potentialParticipants); + this.compositeCommand = new CompositeCommand(); this.latestMessages = new LatestMessages(); @@ -149,6 +148,7 @@ public class Event { //Create connection acceptor. + this.sourceIdAllocator = new SourceIdAllocator(newRace.getRace()); try { this.connectionAcceptor = new ConnectionAcceptor(latestMessages, compositeCommand, sourceIdAllocator, newRace); diff --git a/racevisionGame/src/main/java/mock/model/RaceServer.java b/racevisionGame/src/main/java/mock/model/RaceServer.java index cbbe1971..45a4f6e0 100644 --- a/racevisionGame/src/main/java/mock/model/RaceServer.java +++ b/racevisionGame/src/main/java/mock/model/RaceServer.java @@ -1,7 +1,9 @@ package mock.model; +import network.AckSequencer; import network.Messages.*; import network.Messages.Enums.BoatLocationDeviceEnum; +import network.Messages.Enums.XMLMessageType; import shared.model.Bearing; import shared.model.CompoundMark; import shared.model.Mark; @@ -22,10 +24,29 @@ public class RaceServer { */ private int boatLocationSequenceNumber = 1; + /** + * The sequence number of race XML messages. + */ + private int raceXMLSeqNumber; + + /** + * The sequence number of boat XML messages. + */ + private int boatXMLSeqNumber; + + /** + * The sequence number of regatta XML messages. + */ + private int regattaXMLSeqNumber; + public RaceServer(MockRace race, LatestMessages latestMessages) { this.race = race; this.latestMessages = latestMessages; + + this.raceXMLSeqNumber = race.getRaceDataSource().getSequenceNumber(); + //this.boatXMLSeqNumber = race.getBoatDataSource().getSequenceNumber(); + //this.regattaXMLSeqNumber = race.getRegattaDataSource().getSequenceNumber(); } /** @@ -45,8 +66,46 @@ public class RaceServer { snapshotMessages.add(parseRaceStatus()); latestMessages.setSnapshot(snapshotMessages); + + updateXMLFiles(); + } + + + /** + * Checks if the race/boat/regatta data sources have changed, and if they have, update their xml representations. + */ + private void updateXMLFiles() { + updateRaceXMLFile(); + //updateBoatXMLFile(); + //updateRegattaXMLFile(); + } + + /** + * Checks if the race data source has changed, and if it has, updates LatestMessages' race xml message. + */ + private void updateRaceXMLFile() { + if (raceXMLSeqNumber != race.getRaceDataSource().getSequenceNumber()) { + //TODO generate XML string from race data source + String raceXMLString = "test";//TODO + XMLMessage message = createXMLMessage(raceXMLString, XMLMessageType.RACE); + latestMessages.setXMLMessage(message); + raceXMLSeqNumber = race.getRaceDataSource().getSequenceNumber(); + } + } + + /** + * Checks if the boat data source has changed, and if it has, updates LatestMessages' boat xml message. + */ + private void updateBoatXMLFile() { + } + /** + * Checks if the regatta data source has changed, and if it has, updates LatestMessages' regatta xml message. + */ + private void updateRegattaXMLFile() { + + } /** * Parses an individual marker boat, and returns it. @@ -178,4 +237,41 @@ public class RaceServer { return raceStatus; } + + + + + /** + * Creates an XMLMessage of a specified subtype using the xml contents string. + * @param xmlString The contents of the xml file. + * @param messageType The subtype of xml message (race, regatta, boat). + * @return The created XMLMessage object. + */ + private XMLMessage createXMLMessage(String xmlString, XMLMessageType messageType) { + + //Get the correct sequence number to use. + int sequenceNumber = 0; + if (messageType == XMLMessageType.RACE) { + sequenceNumber = this.raceXMLSeqNumber; + + } else if (messageType == XMLMessageType.BOAT) { + sequenceNumber = this.boatXMLSeqNumber; + + } else if (messageType == XMLMessageType.REGATTA) { + sequenceNumber = this.regattaXMLSeqNumber; + + } + + //Create the message. + XMLMessage message = new XMLMessage( + XMLMessage.currentVersionNumber, + AckSequencer.getNextAckNum(), + System.currentTimeMillis(), + messageType, + sequenceNumber, + xmlString); + + + return message; + } } diff --git a/racevisionGame/src/main/java/network/Messages/LatestMessages.java b/racevisionGame/src/main/java/network/Messages/LatestMessages.java index 738b3ae6..c16d722f 100644 --- a/racevisionGame/src/main/java/network/Messages/LatestMessages.java +++ b/racevisionGame/src/main/java/network/Messages/LatestMessages.java @@ -35,6 +35,7 @@ public class LatestMessages extends Observable { + /** * Ctor. */ diff --git a/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java b/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java index 74ccbaf5..ffacaa93 100644 --- a/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java @@ -76,6 +76,8 @@ public class EmptyRaceDataSource implements RaceDataSource { private RaceTypeEnum raceType = RaceTypeEnum.NOT_A_RACE_TYPE; + private int sequenceNumber = 0; + public EmptyRaceDataSource() { } @@ -126,4 +128,14 @@ public class EmptyRaceDataSource implements RaceDataSource { public List getParticipants() { return participants; } + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java b/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java index b89dc45d..c1a4b370 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java @@ -83,4 +83,16 @@ public interface RaceDataSource { * @return Bottom right GPS coordinate. */ GPSCoordinate getMapBottomRight(); + + + /** + * Returns the sequence number associated with this data source. Used to indicate when it has changed. + * @return Sequence number. + */ + int getSequenceNumber(); + + /** + * Increments the sequence number for this data source. Used to indicate that it has changed. + */ + void incrementSequenceNumber(); } diff --git a/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java b/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java index c2faea69..6165bf44 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java +++ b/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java @@ -84,6 +84,8 @@ public class RaceXMLReader extends XMLReader implements RaceDataSource { private RaceTypeEnum raceType; + private int sequenceNumber = 0; + /** @@ -491,4 +493,14 @@ public class RaceXMLReader extends XMLReader implements RaceDataSource { public List getCornersList() { return cornersList; } + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/model/Constants.java b/racevisionGame/src/main/java/shared/model/Constants.java index a6fe3844..c5595d7a 100644 --- a/racevisionGame/src/main/java/shared/model/Constants.java +++ b/racevisionGame/src/main/java/shared/model/Constants.java @@ -33,20 +33,23 @@ public class Constants { * Frame periods are multiplied by this to get the amount of time a single frame represents. * E.g., frame period = 20ms, scale = 5, frame represents 20 * 5 = 100ms, and so boats are simulated for 100ms, even though only 20ms actually occurred. */ - public static final int RaceTimeScale = 10; + public static final int RaceTimeScale = 1;//10; /** * The race pre-start time, in milliseconds. 3 minutes. */ - public static final long RacePreStartTime = 1 * 10 * 1000; + public static final long RacePreStartTime = 3 * 60 * 1000; /** - * The race preparatory time, in milliseconds. 1 minutes. + * The race preparatory time, in milliseconds. 1 minute. */ public static final long RacePreparatoryTime = 1 * 60 * 1000; + + + /** * The number of milliseconds in one hour. *
diff --git a/racevisionGame/src/main/java/visualiser/Controllers/FinishController.java b/racevisionGame/src/main/java/visualiser/Controllers/FinishController.java index c5356495..6de6dcdf 100644 --- a/racevisionGame/src/main/java/visualiser/Controllers/FinishController.java +++ b/racevisionGame/src/main/java/visualiser/Controllers/FinishController.java @@ -71,8 +71,10 @@ public class FinishController extends Controller { //Winner label. - raceWinnerLabel.setText("Winner: "+ boatNameColumn.getCellObservableValue(0).getValue()); - raceWinnerLabel.setWrapText(true); + if (boats.size() > 0) { + raceWinnerLabel.setText("Winner: " + boatNameColumn.getCellObservableValue(0).getValue()); + raceWinnerLabel.setWrapText(true); + } } diff --git a/racevisionGame/src/main/resources/mock/mockXML/raceTest.xml b/racevisionGame/src/main/resources/mock/mockXML/raceTest.xml index ad14d931..6ae04ef8 100644 --- a/racevisionGame/src/main/resources/mock/mockXML/raceTest.xml +++ b/racevisionGame/src/main/resources/mock/mockXML/raceTest.xml @@ -5,12 +5,7 @@ RACE_CREATION_TIME - - - - - - + diff --git a/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java b/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java index 7240e01b..a1568044 100644 --- a/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java +++ b/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java @@ -15,30 +15,16 @@ import static org.junit.Assert.*; */ public class SourceIdAllocatorTest { - /** - * This is the list of source IDs that we start with. - */ - private List originalSourceIDs; - - /** - * Used to allocate source IDs. - */ + private MockRace mockRace; private SourceIdAllocator sourceIdAllocator; @Before public void setUp() throws Exception { - originalSourceIDs = new ArrayList<>(); - originalSourceIDs.add(120); - originalSourceIDs.add(121); - originalSourceIDs.add(122); - originalSourceIDs.add(123); - originalSourceIDs.add(124); - originalSourceIDs.add(125); - + mockRace = MockRaceTest.createMockRace(); - sourceIdAllocator = new SourceIdAllocator(originalSourceIDs); + sourceIdAllocator = new SourceIdAllocator(mockRace); } @@ -49,11 +35,12 @@ public class SourceIdAllocatorTest { @Test public void emptyAllocationTest() { - SourceIdAllocator allocator = new SourceIdAllocator(new ArrayList<>()); + mockRace.getRaceDataSource().getParticipants().removeAll(mockRace.getBoatDataSource().getBoats().keySet()); + mockRace.getRaceDataSource().getParticipants().addAll(mockRace.getBoatDataSource().getBoats().keySet()); try { - int sourceID = allocator.allocateSourceID(); + int sourceID = sourceIdAllocator.allocateSourceID(); fail("Exception should have been thrown, but wasn't."); @@ -108,10 +95,6 @@ public class SourceIdAllocatorTest { @Test public void reallocationTest() throws Exception { - List sourceIDList = new ArrayList<>(); - sourceIDList.add(123); - - SourceIdAllocator sourceIdAllocator = new SourceIdAllocator(sourceIDList); //Allocate. int sourceID = sourceIdAllocator.allocateSourceID(); diff --git a/racevisionGame/src/test/resources/mock/mockXML/raceTest.xml b/racevisionGame/src/test/resources/mock/mockXML/raceTest.xml index 4ad5f88f..b10a0158 100644 --- a/racevisionGame/src/test/resources/mock/mockXML/raceTest.xml +++ b/racevisionGame/src/test/resources/mock/mockXML/raceTest.xml @@ -5,12 +5,6 @@ 2017-04-19T15:30:00+1200 - - - - - - @@ -54,4 +48,4 @@ - \ No newline at end of file + From ec58f0c847a3cdba2a1b8c76c5ae92060d1afc0e Mon Sep 17 00:00:00 2001 From: fjc40 Date: Sat, 2 Sep 2017 00:27:44 +1200 Subject: [PATCH 4/9] Participants can now join during the warning period as well. Added RaceDataSourceToXML. RaceServer now create an XMLMessage when the race's RaceDataSource changes. #story[1188] --- .../src/main/java/mock/app/Event.java | 14 -- .../java/mock/model/ClientConnection.java | 11 +- .../src/main/java/mock/model/RaceLogic.java | 4 +- .../src/main/java/mock/model/RaceServer.java | 30 ++-- .../java/mock/model/SourceIdAllocator.java | 3 +- .../network/Messages/Enums/RaceTypeEnum.java | 12 ++ .../java/shared/dataInput/BoatDataSource.java | 12 ++ .../java/shared/dataInput/BoatXMLReader.java | 13 ++ .../shared/dataInput/EmptyBoatDataSource.java | 13 ++ .../shared/dataInput/EmptyRaceDataSource.java | 13 ++ .../dataInput/EmptyRegattaDataSource.java | 13 ++ .../java/shared/dataInput/RaceDataSource.java | 8 ++ .../java/shared/dataInput/RaceXMLReader.java | 6 +- .../shared/dataInput/RegattaDataSource.java | 10 ++ .../shared/dataInput/RegattaXMLReader.java | 12 ++ .../main/java/shared/enums/RoundingType.java | 15 ++ .../shared/xml/Race/RaceDataSourceToXML.java | 131 ++++++++++++++++++ .../main/resources/mock/mockXML/boatTest.xml | 1 - 18 files changed, 289 insertions(+), 32 deletions(-) create mode 100644 racevisionGame/src/main/java/shared/xml/Race/RaceDataSourceToXML.java diff --git a/racevisionGame/src/main/java/mock/app/Event.java b/racevisionGame/src/main/java/mock/app/Event.java index 27e2103c..dcc5b407 100644 --- a/racevisionGame/src/main/java/mock/app/Event.java +++ b/racevisionGame/src/main/java/mock/app/Event.java @@ -161,8 +161,6 @@ public class Event { this.connectionThread = new Thread(connectionAcceptor, "Event.Start()->ConnectionAcceptor thread"); connectionThread.start(); - sendXMLs(); - } @@ -175,18 +173,6 @@ public class Event { - /** - * Sends out each xml string, via the mock output - */ - private void sendXMLs() { - - connectionAcceptor.setRegattaXml(regattaXML); - - connectionAcceptor.setRaceXml(raceXML); - - connectionAcceptor.setBoatsXml(boatXML); - } - //TODO remove this after demo on 18th august! /** diff --git a/racevisionGame/src/main/java/mock/model/ClientConnection.java b/racevisionGame/src/main/java/mock/model/ClientConnection.java index d2ca7609..2b0caacf 100644 --- a/racevisionGame/src/main/java/mock/model/ClientConnection.java +++ b/racevisionGame/src/main/java/mock/model/ClientConnection.java @@ -109,6 +109,11 @@ public class ClientConnection implements Runnable { */ private ConnectionStateEnum connectionState = ConnectionStateEnum.UNKNOWN; + /** + * The source ID that has been allocated to the client. + * 0 means not allocated. + */ + private int allocatedSourceID = 0; @@ -178,7 +183,7 @@ public class ClientConnection implements Runnable { RequestToJoin requestToJoin = waitForRequestToJoin(); - int allocatedSourceID = 0; + allocatedSourceID = 0; //If they want to participate, give them a source ID number. if (requestToJoin.getRequestType() == RequestToJoinEnum.PARTICIPANT) { @@ -283,6 +288,10 @@ public class ClientConnection implements Runnable { if (this.controllerServerThread != null) { this.controllerServerThread.interrupt(); } + + if (allocatedSourceID != 0) { + sourceIdAllocator.returnSourceID(allocatedSourceID); + } } } diff --git a/racevisionGame/src/main/java/mock/model/RaceLogic.java b/racevisionGame/src/main/java/mock/model/RaceLogic.java index a1bddd9a..d1ef39e0 100644 --- a/racevisionGame/src/main/java/mock/model/RaceLogic.java +++ b/racevisionGame/src/main/java/mock/model/RaceLogic.java @@ -71,7 +71,8 @@ public class RaceLogic implements RunnableWithFramePeriod, Observer { long previousFrameTime = System.currentTimeMillis(); while (((race.getRaceStatusEnum() == RaceStatusEnum.PRESTART) - || (race.getRaceStatusEnum() == RaceStatusEnum.NOT_ACTIVE)) && loopBool) { + || (race.getRaceStatusEnum() == RaceStatusEnum.NOT_ACTIVE) + || (race.getRaceStatusEnum() == RaceStatusEnum.WARNING)) && loopBool) { long currentTime = System.currentTimeMillis(); @@ -87,6 +88,7 @@ public class RaceLogic implements RunnableWithFramePeriod, Observer { //Parse the race snapshot. server.parseSnapshot(); + waitForFramePeriod(previousFrameTime, currentTime, 50); previousFrameTime = currentTime; } diff --git a/racevisionGame/src/main/java/mock/model/RaceServer.java b/racevisionGame/src/main/java/mock/model/RaceServer.java index 45a4f6e0..37c21194 100644 --- a/racevisionGame/src/main/java/mock/model/RaceServer.java +++ b/racevisionGame/src/main/java/mock/model/RaceServer.java @@ -7,9 +7,15 @@ import network.Messages.Enums.XMLMessageType; import shared.model.Bearing; import shared.model.CompoundMark; import shared.model.Mark; +import shared.xml.Race.RaceDataSourceToXML; +import shared.xml.boats.BoatDataSourceToXML; +import shared.xml.regatta.RegattaDataSourceToXML; +import javax.xml.bind.JAXBException; import java.util.ArrayList; import java.util.List; +import java.util.logging.Level; +import java.util.logging.Logger; /** * Created by connortaylorbrown on 2/08/17. @@ -27,26 +33,22 @@ public class RaceServer { /** * The sequence number of race XML messages. */ - private int raceXMLSeqNumber; + private int raceXMLSeqNumber = -1; /** * The sequence number of boat XML messages. */ - private int boatXMLSeqNumber; + private int boatXMLSeqNumber = -1; /** * The sequence number of regatta XML messages. */ - private int regattaXMLSeqNumber; + private int regattaXMLSeqNumber = -1; public RaceServer(MockRace race, LatestMessages latestMessages) { this.race = race; this.latestMessages = latestMessages; - - this.raceXMLSeqNumber = race.getRaceDataSource().getSequenceNumber(); - //this.boatXMLSeqNumber = race.getBoatDataSource().getSequenceNumber(); - //this.regattaXMLSeqNumber = race.getRegattaDataSource().getSequenceNumber(); } /** @@ -85,11 +87,17 @@ public class RaceServer { */ private void updateRaceXMLFile() { if (raceXMLSeqNumber != race.getRaceDataSource().getSequenceNumber()) { - //TODO generate XML string from race data source - String raceXMLString = "test";//TODO - XMLMessage message = createXMLMessage(raceXMLString, XMLMessageType.RACE); - latestMessages.setXMLMessage(message); + raceXMLSeqNumber = race.getRaceDataSource().getSequenceNumber(); + try { + String raceXMLString = RaceDataSourceToXML.toString(race.getRaceDataSource()); + XMLMessage message = createXMLMessage(raceXMLString, XMLMessageType.RACE); + latestMessages.setXMLMessage(message); + + } catch (JAXBException e) { + Logger.getGlobal().log(Level.WARNING, "Could not serialise: " + race.getRaceDataSource(), e); + } + } } diff --git a/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java b/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java index b609e5a5..17a7e85f 100644 --- a/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java +++ b/racevisionGame/src/main/java/mock/model/SourceIdAllocator.java @@ -36,7 +36,8 @@ public class SourceIdAllocator { */ public synchronized int allocateSourceID() throws SourceIDAllocationException { - if (mockRace.getRaceStatusEnum() != RaceStatusEnum.PRESTART) { + if (!((mockRace.getRaceStatusEnum() == RaceStatusEnum.PRESTART) + || (mockRace.getRaceStatusEnum() == RaceStatusEnum.WARNING))) { throw new SourceIDAllocationException("Could not allocate a source ID. Can only allocate during pre-start period. It is currently: " + mockRace.getRaceStatusEnum()); } diff --git a/racevisionGame/src/main/java/network/Messages/Enums/RaceTypeEnum.java b/racevisionGame/src/main/java/network/Messages/Enums/RaceTypeEnum.java index 6a03b37e..4c75cc52 100644 --- a/racevisionGame/src/main/java/network/Messages/Enums/RaceTypeEnum.java +++ b/racevisionGame/src/main/java/network/Messages/Enums/RaceTypeEnum.java @@ -71,6 +71,8 @@ public enum RaceTypeEnum { } + + /** * Stores a mapping between Byte values and RaceStatusEnum values. */ @@ -107,4 +109,14 @@ public enum RaceTypeEnum { } + @Override + public String toString() { + if (fromByte(value) == FLEET_RACE) { + return "fleet"; + } else if (fromByte(value) == MATCH_RACE) { + return "match"; + } else { + return super.toString(); + } + } } diff --git a/racevisionGame/src/main/java/shared/dataInput/BoatDataSource.java b/racevisionGame/src/main/java/shared/dataInput/BoatDataSource.java index 40f12c75..17bb7c45 100644 --- a/racevisionGame/src/main/java/shared/dataInput/BoatDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/BoatDataSource.java @@ -22,4 +22,16 @@ public interface BoatDataSource { * @return Map between source ID and mark. */ Map getMarkerBoats(); + + + /** + * Returns the sequence number associated with this data source. Used to indicate when it has changed. + * @return Sequence number. + */ + int getSequenceNumber(); + + /** + * Increments the sequence number for this data source. Used to indicate that it has changed. + */ + void incrementSequenceNumber(); } diff --git a/racevisionGame/src/main/java/shared/dataInput/BoatXMLReader.java b/racevisionGame/src/main/java/shared/dataInput/BoatXMLReader.java index 885309c0..25c956d9 100644 --- a/racevisionGame/src/main/java/shared/dataInput/BoatXMLReader.java +++ b/racevisionGame/src/main/java/shared/dataInput/BoatXMLReader.java @@ -29,6 +29,8 @@ public class BoatXMLReader extends XMLReader implements BoatDataSource { private final Map markerMap = new HashMap<>(); + private int sequenceNumber = 0; + /** * Constructor for Boat XML using a file. * @@ -174,4 +176,15 @@ public class BoatXMLReader extends XMLReader implements BoatDataSource { public Map getMarkerBoats() { return markerMap; } + + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/dataInput/EmptyBoatDataSource.java b/racevisionGame/src/main/java/shared/dataInput/EmptyBoatDataSource.java index 1de4251e..7a8d2151 100644 --- a/racevisionGame/src/main/java/shared/dataInput/EmptyBoatDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/EmptyBoatDataSource.java @@ -22,6 +22,8 @@ public class EmptyBoatDataSource implements BoatDataSource { private final Map markerMap = new HashMap<>(); + private int sequenceNumber = 0; + public EmptyBoatDataSource() { } @@ -44,4 +46,15 @@ public class EmptyBoatDataSource implements BoatDataSource { public Map getMarkerBoats() { return markerMap; } + + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java b/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java index ffacaa93..676d7e70 100644 --- a/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/EmptyRaceDataSource.java @@ -2,8 +2,10 @@ package shared.dataInput; import network.Messages.Enums.RaceTypeEnum; import shared.model.CompoundMark; +import shared.model.Corner; import shared.model.GPSCoordinate; import shared.model.Leg; +import shared.xml.Race.XMLCorner; import java.time.ZonedDateTime; import java.util.ArrayList; @@ -48,6 +50,12 @@ public class EmptyRaceDataSource implements RaceDataSource { */ private final List legs = new ArrayList<>(); + /** + * Corners in race. + */ + private final List corners = new ArrayList<>(); + + /** * The time that the race.xml file was created. @@ -100,6 +108,11 @@ public class EmptyRaceDataSource implements RaceDataSource { return legs; } + @Override + public List getCorners() { + return corners; + } + public List getCompoundMarks() { return new ArrayList<>(compoundMarkMap.values()); } diff --git a/racevisionGame/src/main/java/shared/dataInput/EmptyRegattaDataSource.java b/racevisionGame/src/main/java/shared/dataInput/EmptyRegattaDataSource.java index 05a0fcf9..1546972e 100644 --- a/racevisionGame/src/main/java/shared/dataInput/EmptyRegattaDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/EmptyRegattaDataSource.java @@ -60,6 +60,8 @@ public class EmptyRegattaDataSource implements RegattaDataSource { + private int sequenceNumber = 0; + public EmptyRegattaDataSource() { } @@ -119,4 +121,15 @@ public class EmptyRegattaDataSource implements RegattaDataSource { public GPSCoordinate getGPSCoordinate() { return new GPSCoordinate(centralLatitude, centralLongitude); } + + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java b/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java index c1a4b370..765098f2 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/RaceDataSource.java @@ -2,8 +2,10 @@ package shared.dataInput; import network.Messages.Enums.RaceTypeEnum; import shared.model.CompoundMark; +import shared.model.Corner; import shared.model.GPSCoordinate; import shared.model.Leg; +import shared.xml.Race.XMLCorner; import java.time.ZonedDateTime; import java.util.List; @@ -27,6 +29,12 @@ public interface RaceDataSource { */ List getLegs(); + /** + * Returns the list of corners in the race - two adjacent corners form a leg. + * @return List of corners in race. + */ + List getCorners(); + /** * Returns a list of coordinates representing the boundary of the race. * @return The boundary of the race. diff --git a/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java b/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java index 6165bf44..41d60e5f 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java +++ b/racevisionGame/src/main/java/shared/dataInput/RaceXMLReader.java @@ -345,7 +345,7 @@ public class RaceXMLReader extends XMLReader implements RaceDataSource { int cornerSeq = Integer.parseInt(getAttribute(cornerElement, "SeqID")); - cornersList.add(new Corner(cornerID, cornerSeq, "SP", 3)); + cornersList.add(new Corner(cornerID, cornerSeq, cornerRounding, 3)); //Gets the CompoundMark associated with this corner. CompoundMark lastCompoundMark = this.compoundMarkMap.get(cornerID); @@ -368,7 +368,7 @@ public class RaceXMLReader extends XMLReader implements RaceDataSource { cornerSeq = Integer.parseInt(getAttribute(cornerElement, "SeqID")); - cornersList.add(new Corner(cornerID, cornerSeq, "Port", 3)); + cornersList.add(new Corner(cornerID, cornerSeq, getCompoundMarkRounding(cornerElement), 3)); //gets the Rounding of this corner element cornerRounding = getCompoundMarkRounding(cornerElement); @@ -490,7 +490,7 @@ public class RaceXMLReader extends XMLReader implements RaceDataSource { return participants; } - public List getCornersList() { + public List getCorners() { return cornersList; } diff --git a/racevisionGame/src/main/java/shared/dataInput/RegattaDataSource.java b/racevisionGame/src/main/java/shared/dataInput/RegattaDataSource.java index eb198cb2..9af55217 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RegattaDataSource.java +++ b/racevisionGame/src/main/java/shared/dataInput/RegattaDataSource.java @@ -66,5 +66,15 @@ public interface RegattaDataSource { float getMagneticVariation(); + /** + * Returns the sequence number associated with this data source. Used to indicate when it has changed. + * @return Sequence number. + */ + int getSequenceNumber(); + + /** + * Increments the sequence number for this data source. Used to indicate that it has changed. + */ + void incrementSequenceNumber(); } diff --git a/racevisionGame/src/main/java/shared/dataInput/RegattaXMLReader.java b/racevisionGame/src/main/java/shared/dataInput/RegattaXMLReader.java index 0a756b03..36743105 100644 --- a/racevisionGame/src/main/java/shared/dataInput/RegattaXMLReader.java +++ b/racevisionGame/src/main/java/shared/dataInput/RegattaXMLReader.java @@ -59,6 +59,8 @@ public class RegattaXMLReader extends XMLReader implements RegattaDataSource { private float magneticVariation; + private int sequenceNumber = 0; + /** * Constructor for Regatta XML using a file. @@ -209,4 +211,14 @@ public class RegattaXMLReader extends XMLReader implements RegattaDataSource { public GPSCoordinate getGPSCoordinate() { return new GPSCoordinate(centralLatitude, centralLongitude); } + + @Override + public int getSequenceNumber() { + return sequenceNumber; + } + + @Override + public void incrementSequenceNumber() { + sequenceNumber++; + } } diff --git a/racevisionGame/src/main/java/shared/enums/RoundingType.java b/racevisionGame/src/main/java/shared/enums/RoundingType.java index 8f8e719a..e9faef80 100644 --- a/racevisionGame/src/main/java/shared/enums/RoundingType.java +++ b/racevisionGame/src/main/java/shared/enums/RoundingType.java @@ -46,4 +46,19 @@ public enum RoundingType { return null; } } + + public static String getStringOf(RoundingType value) { + switch (value) { + case Port: + return "Port"; + case Starboard: + return "Starboard"; + case SP: + return "SP"; + case PS: + return "PS"; + default: + return null; + } + } } diff --git a/racevisionGame/src/main/java/shared/xml/Race/RaceDataSourceToXML.java b/racevisionGame/src/main/java/shared/xml/Race/RaceDataSourceToXML.java new file mode 100644 index 00000000..3e3b5f8c --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/Race/RaceDataSourceToXML.java @@ -0,0 +1,131 @@ +package shared.xml.Race; + +import shared.dataInput.RaceDataSource; +import shared.enums.RoundingType; +import shared.model.CompoundMark; +import shared.model.Corner; +import shared.model.GPSCoordinate; +import shared.model.Leg; +import shared.xml.XMLUtilities; + +import javax.xml.bind.JAXBException; +import java.time.format.DateTimeFormatter; +import java.util.ArrayList; + +/** + * Has functions to convert a {@link shared.dataInput.RaceDataSource} to an {@link XMLRace} object. + */ +public class RaceDataSourceToXML { + + + /** + * Converts a race data source to an XMLRace object. + * @param raceDataSource The data source to convert. + * @return The XMLRace file. + */ + public static XMLRace toXML(RaceDataSource raceDataSource) { + + //Kind of ugly. Could be refactored/split up a bit. + + + XMLRace race = new XMLRace(); + + + race.setRaceID(raceDataSource.getRaceId()); + race.setRaceType(raceDataSource.getRaceType().toString()); + + + race.setCreationTimeDate(raceDataSource.getCreationDateTime().format(DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZ"))); + + + XMLRaceStartTime startTime = new XMLRaceStartTime(); + startTime.setPostpone(String.valueOf(raceDataSource.getPostponed())); + startTime.setTime(raceDataSource.getStartDateTime().format(DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZ"))); + race.setRaceStartTime(startTime); + + + XMLParticipants participants = new XMLParticipants(); + participants.yacht = new ArrayList<>(); + for (int i : raceDataSource.getParticipants()) { + XMLYacht yacht = new XMLYacht(); + yacht.setSourceID(i); + participants.yacht.add(yacht); + } + race.setParticipants(participants); + + + XMLCourseLimit courseLimit = new XMLCourseLimit(); + courseLimit.limit = new ArrayList<>(); + for (int i = 0; i < raceDataSource.getBoundary().size(); i++) { + XMLLimit limit = new XMLLimit(); + limit.setLat(raceDataSource.getBoundary().get(i).getLatitude()); + limit.setLon(raceDataSource.getBoundary().get(i).getLongitude()); + limit.setSeqID(i + 1); + courseLimit.limit.add(limit); + } + race.setCourseLimit(courseLimit); + + + XMLCourse course = new XMLCourse(); + course.compoundMark = new ArrayList<>(); + for (CompoundMark compoundMark : raceDataSource.getCompoundMarks()) { + XMLCompoundMark xmlCompoundMark = new XMLCompoundMark(); + xmlCompoundMark.setCompoundMarkID(compoundMark.getCompoundMarkID()); + xmlCompoundMark.setName(compoundMark.getName()); + + if (compoundMark.getMark1() != null) { + XMLMark xmlMark = new XMLMark(); + xmlMark.setName(compoundMark.getMark1().getName()); + xmlMark.setSourceID(compoundMark.getMark1().getSourceID()); + xmlMark.setSeqId(1); + xmlMark.setTargetLat(compoundMark.getMark1().getPosition().getLatitude()); + xmlMark.setTargetLng(compoundMark.getMark1().getPosition().getLongitude()); + + xmlCompoundMark.getMark().add(xmlMark); + } + if (compoundMark.getMark2() != null) { + XMLMark xmlMark = new XMLMark(); + xmlMark.setName(compoundMark.getMark2().getName()); + xmlMark.setSourceID(compoundMark.getMark2().getSourceID()); + xmlMark.setSeqId(2); + xmlMark.setTargetLat(compoundMark.getMark2().getPosition().getLatitude()); + xmlMark.setTargetLng(compoundMark.getMark2().getPosition().getLongitude()); + + xmlCompoundMark.getMark().add(xmlMark); + } + + course.compoundMark.add(xmlCompoundMark); + } + race.setCourse(course); + + XMLCompoundMarkSequence compoundMarkSequence = new XMLCompoundMarkSequence(); + compoundMarkSequence.corner = new ArrayList<>(); + for (Corner corner : raceDataSource.getCorners()) { + XMLCorner xmlCorner = new XMLCorner(); + xmlCorner.setZoneSize(corner.getZoneSize()); + xmlCorner.setSeqID(corner.getSeqID()); + xmlCorner.setCompoundMarkID(corner.getCompoundMarkID()); + xmlCorner.setRounding(corner.getRounding()); + + compoundMarkSequence.corner.add(xmlCorner); + } + race.setCompoundMarkSequence(compoundMarkSequence); + + + return race; + } + + + /** + * Converts a race data source to an xml string. + * @param raceDataSource Data source to convert. + * @return String containing xml file. + * @throws JAXBException Thrown if it cannot be converted. + */ + public static String toString(RaceDataSource raceDataSource) throws JAXBException { + XMLRace race = toXML(raceDataSource); + return XMLUtilities.classToXML(race); + } + + +} diff --git a/racevisionGame/src/main/resources/mock/mockXML/boatTest.xml b/racevisionGame/src/main/resources/mock/mockXML/boatTest.xml index 9295dc07..59e2f79d 100644 --- a/racevisionGame/src/main/resources/mock/mockXML/boatTest.xml +++ b/racevisionGame/src/main/resources/mock/mockXML/boatTest.xml @@ -32,7 +32,6 @@ - From 298fcd03dc3b87979d4dd497a880e3cfb36d470e Mon Sep 17 00:00:00 2001 From: fjc40 Date: Sat, 2 Sep 2017 00:33:09 +1200 Subject: [PATCH 5/9] Added regatta schema. RaceServer now creates an XMLMessage when the race's RegattaDataSource changes. #story[1188] --- .../src/main/java/mock/model/RaceServer.java | 13 ++ .../shared/xml/regatta/ObjectFactory.java | 47 ++++ .../shared/xml/regatta/RegattaConfig.java | 219 ++++++++++++++++++ .../xml/regatta/RegattaDataSourceToXML.java | 54 +++++ .../mock/mockXML/schema/regattaSchema.xsd | 17 ++ 5 files changed, 350 insertions(+) create mode 100644 racevisionGame/src/main/java/shared/xml/regatta/ObjectFactory.java create mode 100644 racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java create mode 100644 racevisionGame/src/main/java/shared/xml/regatta/RegattaDataSourceToXML.java create mode 100644 racevisionGame/src/main/resources/mock/mockXML/schema/regattaSchema.xsd diff --git a/racevisionGame/src/main/java/mock/model/RaceServer.java b/racevisionGame/src/main/java/mock/model/RaceServer.java index 37c21194..585fe615 100644 --- a/racevisionGame/src/main/java/mock/model/RaceServer.java +++ b/racevisionGame/src/main/java/mock/model/RaceServer.java @@ -112,7 +112,20 @@ public class RaceServer { * Checks if the regatta data source has changed, and if it has, updates LatestMessages' regatta xml message. */ private void updateRegattaXMLFile() { + if (regattaXMLSeqNumber != race.getRegattaDataSource().getSequenceNumber()) { + regattaXMLSeqNumber = race.getRegattaDataSource().getSequenceNumber(); + + try { + String regattaXMLString = RegattaDataSourceToXML.toString(race.getRegattaDataSource()); + XMLMessage message = createXMLMessage(regattaXMLString, XMLMessageType.REGATTA); + latestMessages.setXMLMessage(message); + + } catch (JAXBException e) { + Logger.getGlobal().log(Level.WARNING, "Could not serialise: " + race.getRegattaDataSource(), e); + } + + } } /** diff --git a/racevisionGame/src/main/java/shared/xml/regatta/ObjectFactory.java b/racevisionGame/src/main/java/shared/xml/regatta/ObjectFactory.java new file mode 100644 index 00000000..7fc72202 --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/regatta/ObjectFactory.java @@ -0,0 +1,47 @@ +// +// This file was generated by the JavaTM Architecture for XML Binding(JAXB) Reference Implementation, v2.2.8-b130911.1802 +// See http://java.sun.com/xml/jaxb +// Any modifications to this file will be lost upon recompilation of the source schema. +// Generated on: 2017.09.01 at 10:37:23 PM NZST +// + + +package shared.xml.regatta; + +import javax.xml.bind.annotation.XmlRegistry; + + +/** + * This object contains factory methods for each + * Java content interface and Java element interface + * generated in the aaa package. + *

An ObjectFactory allows you to programatically + * construct new instances of the Java representation + * for XML content. The Java representation of XML + * content can consist of schema derived interfaces + * and classes representing the binding of schema + * type definitions, element declarations and model + * groups. Factory methods for each of these are + * provided in this class. + * + */ +@XmlRegistry +public class ObjectFactory { + + + /** + * Create a new ObjectFactory that can be used to create new instances of schema derived classes for package: aaa + * + */ + public ObjectFactory() { + } + + /** + * Create an instance of {@link RegattaConfig } + * + */ + public RegattaConfig createRegattaConfig() { + return new RegattaConfig(); + } + +} diff --git a/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java b/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java new file mode 100644 index 00000000..cf72ed5b --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java @@ -0,0 +1,219 @@ +// +// This file was generated by the JavaTM Architecture for XML Binding(JAXB) Reference Implementation, v2.2.8-b130911.1802 +// See http://java.sun.com/xml/jaxb +// Any modifications to this file will be lost upon recompilation of the source schema. +// Generated on: 2017.09.01 at 10:37:23 PM NZST +// + + +package shared.xml.regatta; + +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; +import javax.xml.bind.annotation.XmlType; + + +/** + *

Java class for anonymous complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+ * <complexType>
+ *   <complexContent>
+ *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *       <sequence>
+ *         <element name="RegattaID" type="{http://www.w3.org/2001/XMLSchema}int"/>
+ *         <element name="RegattaName" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ *         <element name="CourseName" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ *         <element name="CentralLatitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="CentralLongitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="CentralAltitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="UtcOffset" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="MagneticVariation" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *       </sequence>
+ *     </restriction>
+ *   </complexContent>
+ * </complexType>
+ * 
+ * + * + */ +@XmlAccessorType(XmlAccessType.FIELD) +@XmlType(name = "", propOrder = { + "regattaID", + "regattaName", + "courseName", + "centralLatitude", + "centralLongitude", + "centralAltitude", + "utcOffset", + "magneticVariation" +}) +@XmlRootElement(name = "RegattaConfig") +public class RegattaConfig { + + @XmlElement(name = "RegattaID") + protected int regattaID; + @XmlElement(name = "RegattaName", required = true) + protected String regattaName; + @XmlElement(name = "CourseName", required = true) + protected String courseName; + @XmlElement(name = "CentralLatitude") + protected double centralLatitude; + @XmlElement(name = "CentralLongitude") + protected double centralLongitude; + @XmlElement(name = "CentralAltitude") + protected double centralAltitude; + @XmlElement(name = "UtcOffset") + protected double utcOffset; + @XmlElement(name = "MagneticVariation") + protected double magneticVariation; + + /** + * Gets the value of the regattaID property. + * + */ + public int getRegattaID() { + return regattaID; + } + + /** + * Sets the value of the regattaID property. + * + */ + public void setRegattaID(int value) { + this.regattaID = value; + } + + /** + * Gets the value of the regattaName property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getRegattaName() { + return regattaName; + } + + /** + * Sets the value of the regattaName property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setRegattaName(String value) { + this.regattaName = value; + } + + /** + * Gets the value of the courseName property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getCourseName() { + return courseName; + } + + /** + * Sets the value of the courseName property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setCourseName(String value) { + this.courseName = value; + } + + /** + * Gets the value of the centralLatitude property. + * + */ + public double getCentralLatitude() { + return centralLatitude; + } + + /** + * Sets the value of the centralLatitude property. + * + */ + public void setCentralLatitude(double value) { + this.centralLatitude = value; + } + + /** + * Gets the value of the centralLongitude property. + * + */ + public double getCentralLongitude() { + return centralLongitude; + } + + /** + * Sets the value of the centralLongitude property. + * + */ + public void setCentralLongitude(double value) { + this.centralLongitude = value; + } + + /** + * Gets the value of the centralAltitude property. + * + */ + public double getCentralAltitude() { + return centralAltitude; + } + + /** + * Sets the value of the centralAltitude property. + * + */ + public void setCentralAltitude(double value) { + this.centralAltitude = value; + } + + /** + * Gets the value of the utcOffset property. + * + */ + public double getUtcOffset() { + return utcOffset; + } + + /** + * Sets the value of the utcOffset property. + * + */ + public void setUtcOffset(double value) { + this.utcOffset = value; + } + + /** + * Gets the value of the magneticVariation property. + * + */ + public double getMagneticVariation() { + return magneticVariation; + } + + /** + * Sets the value of the magneticVariation property. + * + */ + public void setMagneticVariation(double value) { + this.magneticVariation = value; + } + +} diff --git a/racevisionGame/src/main/java/shared/xml/regatta/RegattaDataSourceToXML.java b/racevisionGame/src/main/java/shared/xml/regatta/RegattaDataSourceToXML.java new file mode 100644 index 00000000..bbe1dce6 --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/regatta/RegattaDataSourceToXML.java @@ -0,0 +1,54 @@ +package shared.xml.regatta; + +import shared.dataInput.RegattaDataSource; +import shared.xml.Race.XMLRace; +import shared.xml.XMLUtilities; + +import javax.xml.bind.JAXBException; + +/** + * Has functions to convert a {@link shared.dataInput.RegattaDataSource} to an {@link RegattaConfig} object. + */ +public class RegattaDataSourceToXML { + + + /** + * Converts a regatta data source to an XMLRace object. + * @param regattaDataSource The data source to convert. + * @return The XMLRace file. + */ + public static RegattaConfig toXML(RegattaDataSource regattaDataSource) { + + RegattaConfig regatta = new RegattaConfig(); + + regatta.setCentralAltitude(regattaDataSource.getCentralAltitude()); + regatta.setCentralLatitude(regattaDataSource.getCentralLatitude()); + regatta.setCentralLongitude(regattaDataSource.getCentralLongitude()); + + regatta.setCourseName(regattaDataSource.getCourseName()); + + regatta.setRegattaName(regattaDataSource.getRegattaName()); + + regatta.setMagneticVariation(regattaDataSource.getMagneticVariation()); + + regatta.setRegattaID(regattaDataSource.getRegattaID()); + + regatta.setUtcOffset(regattaDataSource.getUtcOffset()); + + return regatta; + } + + + /** + * Converts a regatta data source to an xml string. + * @param regattaDataSource Data source to convert. + * @return String containing xml file. + * @throws JAXBException Thrown if it cannot be converted. + */ + public static String toString(RegattaDataSource regattaDataSource) throws JAXBException { + RegattaConfig regatta = toXML(regattaDataSource); + return XMLUtilities.classToXML(regatta); + } + + +} diff --git a/racevisionGame/src/main/resources/mock/mockXML/schema/regattaSchema.xsd b/racevisionGame/src/main/resources/mock/mockXML/schema/regattaSchema.xsd new file mode 100644 index 00000000..5c9fb774 --- /dev/null +++ b/racevisionGame/src/main/resources/mock/mockXML/schema/regattaSchema.xsd @@ -0,0 +1,17 @@ + + + + + + + + + + + + + + + + + From 8c76d6c26ef3c21f46c473ea171d6426b87709da Mon Sep 17 00:00:00 2001 From: fjc40 Date: Sat, 2 Sep 2017 00:34:41 +1200 Subject: [PATCH 6/9] Added boats.xml schema. RaceServer now creates an XMLMessage when the race's BoatDataSource changes. #story[1188] --- .../src/main/java/mock/model/RaceServer.java | 16 +- .../java/shared/xml/boats/BoatConfig.java | 533 ++++++++++++++++++ .../shared/xml/boats/BoatDataSourceToXML.java | 86 +++ .../java/shared/xml/boats/ObjectFactory.java | 71 +++ .../mock/mockXML/schema/boatsSchema.xsd | 36 ++ 5 files changed, 740 insertions(+), 2 deletions(-) create mode 100644 racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java create mode 100644 racevisionGame/src/main/java/shared/xml/boats/BoatDataSourceToXML.java create mode 100644 racevisionGame/src/main/java/shared/xml/boats/ObjectFactory.java create mode 100644 racevisionGame/src/main/resources/mock/mockXML/schema/boatsSchema.xsd diff --git a/racevisionGame/src/main/java/mock/model/RaceServer.java b/racevisionGame/src/main/java/mock/model/RaceServer.java index 585fe615..b7ccef12 100644 --- a/racevisionGame/src/main/java/mock/model/RaceServer.java +++ b/racevisionGame/src/main/java/mock/model/RaceServer.java @@ -78,8 +78,8 @@ public class RaceServer { */ private void updateXMLFiles() { updateRaceXMLFile(); - //updateBoatXMLFile(); - //updateRegattaXMLFile(); + updateBoatXMLFile(); + updateRegattaXMLFile(); } /** @@ -105,7 +105,19 @@ public class RaceServer { * Checks if the boat data source has changed, and if it has, updates LatestMessages' boat xml message. */ private void updateBoatXMLFile() { + if (boatXMLSeqNumber != race.getBoatDataSource().getSequenceNumber()) { + boatXMLSeqNumber = race.getBoatDataSource().getSequenceNumber(); + try { + String boatXMLString = BoatDataSourceToXML.toString(race.getBoatDataSource()); + XMLMessage message = createXMLMessage(boatXMLString, XMLMessageType.BOAT); + latestMessages.setXMLMessage(message); + + } catch (JAXBException e) { + Logger.getGlobal().log(Level.WARNING, "Could not serialise: " + race.getBoatDataSource(), e); + } + + } } /** diff --git a/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java b/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java new file mode 100644 index 00000000..c517c830 --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java @@ -0,0 +1,533 @@ +// +// This file was generated by the JavaTM Architecture for XML Binding(JAXB) Reference Implementation, v2.2.8-b130911.1802 +// See http://java.sun.com/xml/jaxb +// Any modifications to this file will be lost upon recompilation of the source schema. +// Generated on: 2017.09.01 at 11:12:43 PM NZST +// + + +package shared.xml.boats; + +import java.util.ArrayList; +import java.util.List; +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlAttribute; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; +import javax.xml.bind.annotation.XmlType; + + +/** + *

Java class for anonymous complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+ * <complexType>
+ *   <complexContent>
+ *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *       <sequence>
+ *         <element name="Boats">
+ *           <complexType>
+ *             <complexContent>
+ *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                 <sequence>
+ *                   <element name="Boat" maxOccurs="unbounded">
+ *                     <complexType>
+ *                       <complexContent>
+ *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                           <sequence>
+ *                             <element name="GPSposition">
+ *                               <complexType>
+ *                                 <complexContent>
+ *                                   <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                                     <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                     <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                     <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                   </restriction>
+ *                                 </complexContent>
+ *                               </complexType>
+ *                             </element>
+ *                           </sequence>
+ *                           <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+ *                           <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+ *                           <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                         </restriction>
+ *                       </complexContent>
+ *                     </complexType>
+ *                   </element>
+ *                 </sequence>
+ *               </restriction>
+ *             </complexContent>
+ *           </complexType>
+ *         </element>
+ *       </sequence>
+ *     </restriction>
+ *   </complexContent>
+ * </complexType>
+ * 
+ * + * + */ +@XmlAccessorType(XmlAccessType.FIELD) +@XmlType(name = "", propOrder = { + "boats" +}) +@XmlRootElement(name = "BoatConfig") +public class BoatConfig { + + @XmlElement(name = "Boats", required = true) + protected BoatConfig.Boats boats; + + /** + * Gets the value of the boats property. + * + * @return + * possible object is + * {@link BoatConfig.Boats } + * + */ + public BoatConfig.Boats getBoats() { + return boats; + } + + /** + * Sets the value of the boats property. + * + * @param value + * allowed object is + * {@link BoatConfig.Boats } + * + */ + public void setBoats(BoatConfig.Boats value) { + this.boats = value; + } + + + /** + *

Java class for anonymous complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+     * <complexType>
+     *   <complexContent>
+     *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *       <sequence>
+     *         <element name="Boat" maxOccurs="unbounded">
+     *           <complexType>
+     *             <complexContent>
+     *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *                 <sequence>
+     *                   <element name="GPSposition">
+     *                     <complexType>
+     *                       <complexContent>
+     *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *                           <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                           <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                           <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                         </restriction>
+     *                       </complexContent>
+     *                     </complexType>
+     *                   </element>
+     *                 </sequence>
+     *                 <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+     *                 <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+     *                 <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *               </restriction>
+     *             </complexContent>
+     *           </complexType>
+     *         </element>
+     *       </sequence>
+     *     </restriction>
+     *   </complexContent>
+     * </complexType>
+     * 
+ * + * + */ + @XmlAccessorType(XmlAccessType.FIELD) + @XmlType(name = "", propOrder = { + "boat" + }) + public static class Boats { + + @XmlElement(name = "Boat", required = true) + protected List boat; + + /** + * Gets the value of the boat property. + * + *

+ * This accessor method returns a reference to the live list, + * not a snapshot. Therefore any modification you make to the + * returned list will be present inside the JAXB object. + * This is why there is not a set method for the boat property. + * + *

+ * For example, to add a new item, do as follows: + *

+         *    getBoat().add(newItem);
+         * 
+ * + * + *

+ * Objects of the following type(s) are allowed in the list + * {@link BoatConfig.Boats.Boat } + * + * + */ + public List getBoat() { + if (boat == null) { + boat = new ArrayList(); + } + return this.boat; + } + + + /** + *

Java class for anonymous complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+         * <complexType>
+         *   <complexContent>
+         *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+         *       <sequence>
+         *         <element name="GPSposition">
+         *           <complexType>
+         *             <complexContent>
+         *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+         *                 <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *                 <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *                 <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *               </restriction>
+         *             </complexContent>
+         *           </complexType>
+         *         </element>
+         *       </sequence>
+         *       <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+         *       <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+         *       <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *     </restriction>
+         *   </complexContent>
+         * </complexType>
+         * 
+ * + * + */ + @XmlAccessorType(XmlAccessType.FIELD) + @XmlType(name = "", propOrder = { + "gpSposition" + }) + public static class Boat { + + @XmlElement(name = "GPSposition", required = true) + protected BoatConfig.Boats.Boat.GPSposition gpSposition; + @XmlAttribute(name = "Type", required = true) + protected String type; + @XmlAttribute(name = "BoatName", required = true) + protected String boatName; + @XmlAttribute(name = "SourceID", required = true) + protected int sourceID; + @XmlAttribute(name = "HullNum") + protected String hullNum; + @XmlAttribute(name = "ShortName") + protected String shortName; + @XmlAttribute(name = "ShapeID") + protected Integer shapeID; + @XmlAttribute(name = "StoweName") + protected String stoweName; + + /** + * Gets the value of the gpSposition property. + * + * @return + * possible object is + * {@link BoatConfig.Boats.Boat.GPSposition } + * + */ + public BoatConfig.Boats.Boat.GPSposition getGPSposition() { + return gpSposition; + } + + /** + * Sets the value of the gpSposition property. + * + * @param value + * allowed object is + * {@link BoatConfig.Boats.Boat.GPSposition } + * + */ + public void setGPSposition(BoatConfig.Boats.Boat.GPSposition value) { + this.gpSposition = value; + } + + /** + * Gets the value of the type property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getType() { + return type; + } + + /** + * Sets the value of the type property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setType(String value) { + this.type = value; + } + + /** + * Gets the value of the boatName property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getBoatName() { + return boatName; + } + + /** + * Sets the value of the boatName property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setBoatName(String value) { + this.boatName = value; + } + + /** + * Gets the value of the sourceID property. + * + */ + public int getSourceID() { + return sourceID; + } + + /** + * Sets the value of the sourceID property. + * + */ + public void setSourceID(int value) { + this.sourceID = value; + } + + /** + * Gets the value of the hullNum property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getHullNum() { + return hullNum; + } + + /** + * Sets the value of the hullNum property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setHullNum(String value) { + this.hullNum = value; + } + + /** + * Gets the value of the shortName property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getShortName() { + return shortName; + } + + /** + * Sets the value of the shortName property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setShortName(String value) { + this.shortName = value; + } + + /** + * Gets the value of the shapeID property. + * + * @return + * possible object is + * {@link Integer } + * + */ + public Integer getShapeID() { + return shapeID; + } + + /** + * Sets the value of the shapeID property. + * + * @param value + * allowed object is + * {@link Integer } + * + */ + public void setShapeID(Integer value) { + this.shapeID = value; + } + + /** + * Gets the value of the stoweName property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getStoweName() { + return stoweName; + } + + /** + * Sets the value of the stoweName property. + * + * @param value + * allowed object is + * {@link String } + * + */ + public void setStoweName(String value) { + this.stoweName = value; + } + + + /** + *

Java class for anonymous complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+             * <complexType>
+             *   <complexContent>
+             *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+             *       <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *       <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *       <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *     </restriction>
+             *   </complexContent>
+             * </complexType>
+             * 
+ * + * + */ + @XmlAccessorType(XmlAccessType.FIELD) + @XmlType(name = "") + public static class GPSposition { + + @XmlAttribute(name = "X", required = true) + protected Double x; + @XmlAttribute(name = "Y", required = true) + protected double y; + @XmlAttribute(name = "Z", required = true) + protected double z; + + /** + * Gets the value of the x property. + * + * @return + * possible object is + * {@link Double } + * + */ + public Double getX() { + return x; + } + + /** + * Sets the value of the x property. + * + * @param value + * allowed object is + * {@link Double } + * + */ + public void setX(Double value) { + this.x = value; + } + + /** + * Gets the value of the y property. + * + */ + public double getY() { + return y; + } + + /** + * Sets the value of the y property. + * + */ + public void setY(double value) { + this.y = value; + } + + /** + * Gets the value of the z property. + * + */ + public double getZ() { + return z; + } + + /** + * Sets the value of the z property. + * + */ + public void setZ(double value) { + this.z = value; + } + + } + + } + + } + +} diff --git a/racevisionGame/src/main/java/shared/xml/boats/BoatDataSourceToXML.java b/racevisionGame/src/main/java/shared/xml/boats/BoatDataSourceToXML.java new file mode 100644 index 00000000..d24bee56 --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/boats/BoatDataSourceToXML.java @@ -0,0 +1,86 @@ +package shared.xml.boats; + +import shared.dataInput.BoatDataSource; +import shared.dataInput.RaceDataSource; +import shared.enums.RoundingType; +import shared.model.Boat; +import shared.model.CompoundMark; +import shared.model.Leg; +import shared.model.Mark; +import shared.xml.Race.*; +import shared.xml.XMLUtilities; + +import javax.xml.bind.JAXBException; +import java.time.format.DateTimeFormatter; +import java.util.ArrayList; + +/** + * Has functions to convert a {@link shared.dataInput.BoatDataSource} to an {@link BoatConfig} object. + */ +public class BoatDataSourceToXML { + + + /** + * Converts a boat data source to an XMLRace object. + * @param boatDataSource The data source to convert. + * @return The XMLRace file. + */ + public static BoatConfig toXML(BoatDataSource boatDataSource) { + BoatConfig boatConfig = new BoatConfig(); + + boatConfig.boats = new BoatConfig.Boats(); + boatConfig.boats.boat = new ArrayList<>(); + + + for (Boat boat : boatDataSource.getBoats().values()) { + BoatConfig.Boats.Boat xmlBoat = new BoatConfig.Boats.Boat(); + + xmlBoat.setType("Yacht"); + xmlBoat.setBoatName(boat.getName()); + xmlBoat.setSourceID(boat.getSourceID()); + xmlBoat.setStoweName(boat.getCountry()); + xmlBoat.setShortName(boat.getCountry()); + + BoatConfig.Boats.Boat.GPSposition position = new BoatConfig.Boats.Boat.GPSposition(); + position.setX(boat.getPosition().getLongitude()); + position.setY(boat.getPosition().getLatitude()); + position.setZ(0); + xmlBoat.setGPSposition(position); + + boatConfig.boats.boat.add(xmlBoat); + } + + + for (Mark mark : boatDataSource.getMarkerBoats().values()) { + BoatConfig.Boats.Boat xmlBoat = new BoatConfig.Boats.Boat(); + + xmlBoat.setType("Mark"); + xmlBoat.setBoatName(mark.getName()); + xmlBoat.setSourceID(mark.getSourceID()); + + BoatConfig.Boats.Boat.GPSposition position = new BoatConfig.Boats.Boat.GPSposition(); + position.setX(mark.getPosition().getLongitude()); + position.setY(mark.getPosition().getLatitude()); + position.setZ(0); + xmlBoat.setGPSposition(position); + + boatConfig.boats.boat.add(xmlBoat); + } + + return boatConfig; + } + + + /** + * Converts a boat data source to an xml string. + * @param boatDataSource Data source to convert. + * @return String containing xml file. + * @throws JAXBException Thrown if it cannot be converted. + */ + public static String toString(BoatDataSource boatDataSource) throws JAXBException { + BoatConfig boats = toXML(boatDataSource); + return XMLUtilities.classToXML(boats); + } + + +} diff --git a/racevisionGame/src/main/java/shared/xml/boats/ObjectFactory.java b/racevisionGame/src/main/java/shared/xml/boats/ObjectFactory.java new file mode 100644 index 00000000..0319de9a --- /dev/null +++ b/racevisionGame/src/main/java/shared/xml/boats/ObjectFactory.java @@ -0,0 +1,71 @@ +// +// This file was generated by the JavaTM Architecture for XML Binding(JAXB) Reference Implementation, v2.2.8-b130911.1802 +// See http://java.sun.com/xml/jaxb +// Any modifications to this file will be lost upon recompilation of the source schema. +// Generated on: 2017.09.01 at 11:12:43 PM NZST +// + + +package shared.xml.boats; + +import javax.xml.bind.annotation.XmlRegistry; + + +/** + * This object contains factory methods for each + * Java content interface and Java element interface + * generated in the aaa package. + *

An ObjectFactory allows you to programatically + * construct new instances of the Java representation + * for XML content. The Java representation of XML + * content can consist of schema derived interfaces + * and classes representing the binding of schema + * type definitions, element declarations and model + * groups. Factory methods for each of these are + * provided in this class. + * + */ +@XmlRegistry +public class ObjectFactory { + + + /** + * Create a new ObjectFactory that can be used to create new instances of schema derived classes for package: aaa + * + */ + public ObjectFactory() { + } + + /** + * Create an instance of {@link BoatConfig } + * + */ + public BoatConfig createBoatConfig() { + return new BoatConfig(); + } + + /** + * Create an instance of {@link BoatConfig.Boats } + * + */ + public BoatConfig.Boats createBoatConfigBoats() { + return new BoatConfig.Boats(); + } + + /** + * Create an instance of {@link BoatConfig.Boats.Boat } + * + */ + public BoatConfig.Boats.Boat createBoatConfigBoatsBoat() { + return new BoatConfig.Boats.Boat(); + } + + /** + * Create an instance of {@link BoatConfig.Boats.Boat.GPSposition } + * + */ + public BoatConfig.Boats.Boat.GPSposition createBoatConfigBoatsBoatGPSposition() { + return new BoatConfig.Boats.Boat.GPSposition(); + } + +} diff --git a/racevisionGame/src/main/resources/mock/mockXML/schema/boatsSchema.xsd b/racevisionGame/src/main/resources/mock/mockXML/schema/boatsSchema.xsd new file mode 100644 index 00000000..6d5af617 --- /dev/null +++ b/racevisionGame/src/main/resources/mock/mockXML/schema/boatsSchema.xsd @@ -0,0 +1,36 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + From 16bf57e3331e73e49289d2a396a1cac3b1e7b92b Mon Sep 17 00:00:00 2001 From: fjc40 Date: Sat, 2 Sep 2017 00:45:08 +1200 Subject: [PATCH 7/9] javadoc fixes. --- .../src/main/java/mock/model/MockRace.java | 1 - .../java/shared/xml/boats/BoatConfig.java | 234 +++++++++--------- .../shared/xml/regatta/RegattaConfig.java | 32 +-- 3 files changed, 133 insertions(+), 134 deletions(-) diff --git a/racevisionGame/src/main/java/mock/model/MockRace.java b/racevisionGame/src/main/java/mock/model/MockRace.java index 9bcece2c..f606c29d 100644 --- a/racevisionGame/src/main/java/mock/model/MockRace.java +++ b/racevisionGame/src/main/java/mock/model/MockRace.java @@ -109,7 +109,6 @@ public class MockRace extends RaceState { /** * Generates a MockBoat from the BoatDataSource, given a source ID. Also adds it to the participant list. * @param sourceID The source ID to assign the boat. - * @return A MockBoat that is now participating in the race. */ public void generateMockBoat(Integer sourceID) { diff --git a/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java b/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java index c517c830..c0361b52 100644 --- a/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java +++ b/racevisionGame/src/main/java/shared/xml/boats/BoatConfig.java @@ -24,52 +24,52 @@ import javax.xml.bind.annotation.XmlType; *

The following schema fragment specifies the expected content contained within this class. * *

- * <complexType>
- *   <complexContent>
- *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
- *       <sequence>
- *         <element name="Boats">
- *           <complexType>
- *             <complexContent>
- *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
- *                 <sequence>
- *                   <element name="Boat" maxOccurs="unbounded">
- *                     <complexType>
- *                       <complexContent>
- *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
- *                           <sequence>
- *                             <element name="GPSposition">
- *                               <complexType>
- *                                 <complexContent>
- *                                   <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
- *                                     <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
- *                                     <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
- *                                     <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
- *                                   </restriction>
- *                                 </complexContent>
- *                               </complexType>
- *                             </element>
- *                           </sequence>
- *                           <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
- *                           <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
- *                           <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
- *                           <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
- *                           <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
- *                           <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
- *                           <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
- *                         </restriction>
- *                       </complexContent>
- *                     </complexType>
- *                   </element>
- *                 </sequence>
- *               </restriction>
- *             </complexContent>
- *           </complexType>
- *         </element>
- *       </sequence>
- *     </restriction>
- *   </complexContent>
- * </complexType>
+ * <complexType>
+ *   <complexContent>
+ *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *       <sequence>
+ *         <element name="Boats">
+ *           <complexType>
+ *             <complexContent>
+ *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                 <sequence>
+ *                   <element name="Boat" maxOccurs="unbounded">
+ *                     <complexType>
+ *                       <complexContent>
+ *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                           <sequence>
+ *                             <element name="GPSposition">
+ *                               <complexType>
+ *                                 <complexContent>
+ *                                   <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *                                     <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                     <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                     <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+ *                                   </restriction>
+ *                                 </complexContent>
+ *                               </complexType>
+ *                             </element>
+ *                           </sequence>
+ *                           <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+ *                           <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                           <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+ *                           <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+ *                         </restriction>
+ *                       </complexContent>
+ *                     </complexType>
+ *                   </element>
+ *                 </sequence>
+ *               </restriction>
+ *             </complexContent>
+ *           </complexType>
+ *         </element>
+ *       </sequence>
+ *     </restriction>
+ *   </complexContent>
+ * </complexType>
  * 
* * @@ -115,42 +115,42 @@ public class BoatConfig { *

The following schema fragment specifies the expected content contained within this class. * *

-     * <complexType>
-     *   <complexContent>
-     *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-     *       <sequence>
-     *         <element name="Boat" maxOccurs="unbounded">
-     *           <complexType>
-     *             <complexContent>
-     *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-     *                 <sequence>
-     *                   <element name="GPSposition">
-     *                     <complexType>
-     *                       <complexContent>
-     *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-     *                           <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
-     *                           <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-     *                           <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-     *                         </restriction>
-     *                       </complexContent>
-     *                     </complexType>
-     *                   </element>
-     *                 </sequence>
-     *                 <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
-     *                 <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
-     *                 <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
-     *                 <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
-     *                 <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
-     *                 <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
-     *                 <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
-     *               </restriction>
-     *             </complexContent>
-     *           </complexType>
-     *         </element>
-     *       </sequence>
-     *     </restriction>
-     *   </complexContent>
-     * </complexType>
+     * <complexType>
+     *   <complexContent>
+     *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *       <sequence>
+     *         <element name="Boat" maxOccurs="unbounded">
+     *           <complexType>
+     *             <complexContent>
+     *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *                 <sequence>
+     *                   <element name="GPSposition">
+     *                     <complexType>
+     *                       <complexContent>
+     *                         <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+     *                           <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                           <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                           <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+     *                         </restriction>
+     *                       </complexContent>
+     *                     </complexType>
+     *                   </element>
+     *                 </sequence>
+     *                 <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+     *                 <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *                 <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+     *                 <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+     *               </restriction>
+     *             </complexContent>
+     *           </complexType>
+     *         </element>
+     *       </sequence>
+     *     </restriction>
+     *   </complexContent>
+     * </complexType>
      * 
* * @@ -200,32 +200,32 @@ public class BoatConfig { *

The following schema fragment specifies the expected content contained within this class. * *

-         * <complexType>
-         *   <complexContent>
-         *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-         *       <sequence>
-         *         <element name="GPSposition">
-         *           <complexType>
-         *             <complexContent>
-         *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-         *                 <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
-         *                 <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-         *                 <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-         *               </restriction>
-         *             </complexContent>
-         *           </complexType>
-         *         </element>
-         *       </sequence>
-         *       <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
-         *       <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
-         *       <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
-         *       <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
-         *       <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
-         *       <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
-         *       <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
-         *     </restriction>
-         *   </complexContent>
-         * </complexType>
+         * <complexType>
+         *   <complexContent>
+         *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+         *       <sequence>
+         *         <element name="GPSposition">
+         *           <complexType>
+         *             <complexContent>
+         *               <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+         *                 <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *                 <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *                 <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+         *               </restriction>
+         *             </complexContent>
+         *           </complexType>
+         *         </element>
+         *       </sequence>
+         *       <attribute name="Type" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="BoatName" use="required" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="SourceID" use="required" type="{http://www.w3.org/2001/XMLSchema}int" />
+         *       <attribute name="HullNum" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="ShortName" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *       <attribute name="ShapeID" type="{http://www.w3.org/2001/XMLSchema}int" />
+         *       <attribute name="StoweName" type="{http://www.w3.org/2001/XMLSchema}string" />
+         *     </restriction>
+         *   </complexContent>
+         * </complexType>
          * 
* * @@ -444,15 +444,15 @@ public class BoatConfig { *

The following schema fragment specifies the expected content contained within this class. * *

-             * <complexType>
-             *   <complexContent>
-             *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
-             *       <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
-             *       <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-             *       <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
-             *     </restriction>
-             *   </complexContent>
-             * </complexType>
+             * <complexType>
+             *   <complexContent>
+             *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+             *       <attribute name="X" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *       <attribute name="Y" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *       <attribute name="Z" use="required" type="{http://www.w3.org/2001/XMLSchema}double" />
+             *     </restriction>
+             *   </complexContent>
+             * </complexType>
              * 
* * diff --git a/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java b/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java index cf72ed5b..d8cc1613 100644 --- a/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java +++ b/racevisionGame/src/main/java/shared/xml/regatta/RegattaConfig.java @@ -21,22 +21,22 @@ import javax.xml.bind.annotation.XmlType; *

The following schema fragment specifies the expected content contained within this class. * *

- * <complexType>
- *   <complexContent>
- *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
- *       <sequence>
- *         <element name="RegattaID" type="{http://www.w3.org/2001/XMLSchema}int"/>
- *         <element name="RegattaName" type="{http://www.w3.org/2001/XMLSchema}string"/>
- *         <element name="CourseName" type="{http://www.w3.org/2001/XMLSchema}string"/>
- *         <element name="CentralLatitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
- *         <element name="CentralLongitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
- *         <element name="CentralAltitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
- *         <element name="UtcOffset" type="{http://www.w3.org/2001/XMLSchema}double"/>
- *         <element name="MagneticVariation" type="{http://www.w3.org/2001/XMLSchema}double"/>
- *       </sequence>
- *     </restriction>
- *   </complexContent>
- * </complexType>
+ * <complexType>
+ *   <complexContent>
+ *     <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ *       <sequence>
+ *         <element name="RegattaID" type="{http://www.w3.org/2001/XMLSchema}int"/>
+ *         <element name="RegattaName" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ *         <element name="CourseName" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ *         <element name="CentralLatitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="CentralLongitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="CentralAltitude" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="UtcOffset" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *         <element name="MagneticVariation" type="{http://www.w3.org/2001/XMLSchema}double"/>
+ *       </sequence>
+ *     </restriction>
+ *   </complexContent>
+ * </complexType>
  * 
* * From ac891fa91cb9d51d354aa6f981adae01d118cf73 Mon Sep 17 00:00:00 2001 From: fjc40 Date: Sat, 2 Sep 2017 01:03:47 +1200 Subject: [PATCH 8/9] Fixed tests. --- .../src/test/java/mock/model/MockBoatTest.java | 8 ++++++++ .../java/mock/model/SourceIdAllocatorTest.java | 3 +++ .../mock/model/commandFactory/WindCommandTest.java | 14 +++++++++----- .../network/ConnectionToServerParticipantTest.java | 2 +- 4 files changed, 21 insertions(+), 6 deletions(-) diff --git a/racevisionGame/src/test/java/mock/model/MockBoatTest.java b/racevisionGame/src/test/java/mock/model/MockBoatTest.java index 8d1f45ee..98b4ca27 100644 --- a/racevisionGame/src/test/java/mock/model/MockBoatTest.java +++ b/racevisionGame/src/test/java/mock/model/MockBoatTest.java @@ -3,6 +3,7 @@ package mock.model; import org.junit.Before; import org.junit.Test; import shared.model.Bearing; +import shared.model.Boat; import shared.model.GPSCoordinate; import shared.model.Mark; @@ -13,6 +14,13 @@ public class MockBoatTest { private Mark near; private Mark far; + + public static MockBoat createMockBoat() { + Boat boat = new Boat(121, "Test boat", "TS"); + MockBoat mockBoat = new MockBoat(boat, null); + return mockBoat; + } + @Before public void setUp() { boat = new MockBoat(0, "Bob", "NZ", null); diff --git a/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java b/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java index a1568044..ad310540 100644 --- a/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java +++ b/racevisionGame/src/test/java/mock/model/SourceIdAllocatorTest.java @@ -1,6 +1,7 @@ package mock.model; import mock.exceptions.SourceIDAllocationException; +import network.Messages.Enums.RaceStatusEnum; import org.junit.Before; import org.junit.Test; @@ -60,6 +61,7 @@ public class SourceIdAllocatorTest { @Test public void allocationTest() throws Exception { + mockRace.setRaceStatusEnum(RaceStatusEnum.PRESTART); int sourceID = sourceIdAllocator.allocateSourceID(); @@ -95,6 +97,7 @@ public class SourceIdAllocatorTest { @Test public void reallocationTest() throws Exception { + mockRace.setRaceStatusEnum(RaceStatusEnum.PRESTART); //Allocate. int sourceID = sourceIdAllocator.allocateSourceID(); diff --git a/racevisionGame/src/test/java/mock/model/commandFactory/WindCommandTest.java b/racevisionGame/src/test/java/mock/model/commandFactory/WindCommandTest.java index 2193eb7a..158c43d6 100644 --- a/racevisionGame/src/test/java/mock/model/commandFactory/WindCommandTest.java +++ b/racevisionGame/src/test/java/mock/model/commandFactory/WindCommandTest.java @@ -1,11 +1,11 @@ package mock.model.commandFactory; import mock.exceptions.CommandConstructionException; -import mock.model.MockBoat; -import mock.model.MockRace; -import mock.model.MockRaceTest; +import mock.exceptions.SourceIDAllocationException; +import mock.model.*; import network.Messages.BoatAction; import network.Messages.Enums.BoatActionEnum; +import network.Messages.Enums.RaceStatusEnum; import org.junit.Before; import org.junit.Test; import shared.exceptions.InvalidBoatDataException; @@ -21,6 +21,7 @@ import static org.mockito.Mockito.mock; */ public class WindCommandTest { private MockRace race; + private SourceIdAllocator allocator; private MockBoat boat; private Command upwind; private Command downwind; @@ -29,12 +30,15 @@ public class WindCommandTest { private double offset = 3.0; @Before - public void setUp() throws CommandConstructionException, InvalidBoatDataException, InvalidRegattaDataException, InvalidRaceDataException { + public void setUp() throws CommandConstructionException, InvalidBoatDataException, InvalidRegattaDataException, InvalidRaceDataException, SourceIDAllocationException { race = MockRaceTest.createMockRace(); - + allocator = new SourceIdAllocator(race); + race.setRaceStatusEnum(RaceStatusEnum.PRESTART); + allocator.allocateSourceID(); boat = race.getBoats().get(0); + //when(race.getWindDirection()).thenReturn(Bearing.fromDegrees(0.0)); boat.setBearing(Bearing.fromDegrees(45.0)); diff --git a/racevisionGame/src/test/java/visualiser/network/ConnectionToServerParticipantTest.java b/racevisionGame/src/test/java/visualiser/network/ConnectionToServerParticipantTest.java index 64fdfcb5..4b6ed5e3 100644 --- a/racevisionGame/src/test/java/visualiser/network/ConnectionToServerParticipantTest.java +++ b/racevisionGame/src/test/java/visualiser/network/ConnectionToServerParticipantTest.java @@ -94,7 +94,7 @@ public class ConnectionToServerParticipantTest { incomingCommands.put(command); //Need to wait for connection thread to execute commands. - Thread.sleep(250); + Thread.sleep(500); assertEquals(ConnectionToServerState.CONNECTED, connectionToServer.getConnectionState()); assertTrue(connectionToServer.getJoinAcceptance() != null); From 361856ea1db17d864a9e0dc03b6410a8884e1445 Mon Sep 17 00:00:00 2001 From: fjc40 Date: Mon, 4 Sep 2017 11:38:45 +1200 Subject: [PATCH 9/9] Updated timescale. --- racevisionGame/src/main/java/shared/model/Constants.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/racevisionGame/src/main/java/shared/model/Constants.java b/racevisionGame/src/main/java/shared/model/Constants.java index c5595d7a..bb7ec598 100644 --- a/racevisionGame/src/main/java/shared/model/Constants.java +++ b/racevisionGame/src/main/java/shared/model/Constants.java @@ -33,7 +33,7 @@ public class Constants { * Frame periods are multiplied by this to get the amount of time a single frame represents. * E.g., frame period = 20ms, scale = 5, frame represents 20 * 5 = 100ms, and so boats are simulated for 100ms, even though only 20ms actually occurred. */ - public static final int RaceTimeScale = 1;//10; + public static final int RaceTimeScale = 2;//10; /** * The race pre-start time, in milliseconds. 3 minutes.