@@ -0,0 +1,5 @@ | |||||
bin/ | |||||
doc/ | |||||
deliverable/ | |||||
.classpath | |||||
.project |
@@ -0,0 +1,14 @@ | |||||
package net.hoo2.auth.labyrinth; | |||||
public class Board { | |||||
int size() { return N; } | |||||
private int N; | |||||
private int S; | |||||
private int W; | |||||
private Tile[] tiles; | |||||
private Supply[] supplies; | |||||
} |
@@ -0,0 +1,99 @@ | |||||
/** | |||||
* @file Common.java | |||||
* | |||||
* @author Christos Choutouridis AEM:8997 | |||||
* @email cchoutou@ece.auth.gr | |||||
*/ | |||||
package net.hoo2.auth.labyrinth; | |||||
/** | |||||
* Application wide object to hold settings like values for the session. | |||||
*/ | |||||
class Defaults { | |||||
static int boardSize = 15; /**@< Default board's size (if no one set it via command line) */ | |||||
} | |||||
/** | |||||
* Helper C++-like enumerator class to hold direction | |||||
*/ | |||||
class Direction { | |||||
static final int UP =1; /**< North direction */ | |||||
static final int RIGHT =3; /**< East direction */ | |||||
static final int DOWN =5; /**< South direction */ | |||||
static final int LEFT =7; /**< West direction */ | |||||
} | |||||
/** | |||||
* @brief | |||||
* An Application wide board position implementation holding just the coordinates | |||||
* | |||||
* Position is a helper class to enable us cope with the redundant position data (id and coordinates). | |||||
* This class provide both static conversion functionalities between id and coordinates | |||||
* and data representation in the coordinates system. | |||||
*/ | |||||
class Position { | |||||
/** | |||||
* Basic constructor from coordinates | |||||
* @param x The x coordinate | |||||
* @param y The y coordinate | |||||
*/ | |||||
protected Position(int x, int y) { | |||||
this.x = x; | |||||
this.y = y; | |||||
} | |||||
/** | |||||
* Basic constructor from Id | |||||
* @param tileId The id of tile | |||||
*/ | |||||
protected Position(int tileId) { | |||||
this.x = toX(tileId); | |||||
this.y = toY(tileId); | |||||
} | |||||
/** @name non-static API */ | |||||
/** @{ */ | |||||
protected int getX() { return x; } /**< Read access to x coordinate */ | |||||
protected int getY() { return y; } /**< Read access to y coordinate */ | |||||
protected int getID(){ return toID(x, y); } /**< Virtual read access to id coordinate */ | |||||
/** @} */ | |||||
/** @name Static convention utilities */ | |||||
/** @{ */ | |||||
/** | |||||
* Takes x and y coordinates and return the calculated Id coordinate | |||||
* @param x The x coordinate | |||||
* @param y The y coordinate | |||||
* @return The converted value | |||||
*/ | |||||
protected static int toID(int x, int y) { | |||||
return y * Defaults.boardSize + x; | |||||
} | |||||
/** | |||||
* Takes Id coordinate and return the corresponding x coordinate | |||||
* @param id The id coordinate | |||||
* @return The x coordinate | |||||
*/ | |||||
protected static int toX(int id){ | |||||
return id % Defaults.boardSize; | |||||
} | |||||
/** | |||||
* Takes Id coordinate and return the corresponding y coordinate | |||||
* @param id The id coordinate | |||||
* @return The y coordinate | |||||
*/ | |||||
protected static int toY(int id) { | |||||
return id / Defaults.boardSize; | |||||
} | |||||
/** @} */ | |||||
/** @name private data types */ | |||||
/** @{ */ | |||||
private int x; /**< The x coordinate of the constructed Position object */ | |||||
private int y; /**< The y coordinate of the constructed Position object */ | |||||
/** @} */ | |||||
} | |||||
@@ -0,0 +1,21 @@ | |||||
/** | |||||
* @file Game.java | |||||
* | |||||
* @author Christos Choutouridis AEM:8997 | |||||
* @email cchoutou@ece.auth.gr | |||||
*/ | |||||
package net.hoo2.auth.labyrinth; | |||||
/** | |||||
* | |||||
*/ | |||||
public class Game { | |||||
public static void main(String[] args) { | |||||
// TODO Auto-generated method stub | |||||
System.out.println("Lets begin"); | |||||
} | |||||
} |
@@ -0,0 +1,5 @@ | |||||
package net.hoo2.auth.labyrinth; | |||||
class Player { | |||||
} |
@@ -0,0 +1,178 @@ | |||||
/** | |||||
* @file Supply.java | |||||
* | |||||
* @author Christos Choutouridis AEM:8997 | |||||
* @email cchoutou@ece.auth.gr | |||||
*/ | |||||
package net.hoo2.auth.labyrinth; | |||||
/** | |||||
* @brief | |||||
* This class is the representation of the supplies in the game | |||||
* | |||||
* Supplies are the game "goodies". They placed randomly in the board. | |||||
* In each tile there can be only one supply. The player has to collect all | |||||
* of them in order to complete the game successfully. | |||||
*/ | |||||
class Supply { | |||||
/** @name Constructors */ | |||||
/** @{ */ | |||||
/** | |||||
* The main constructor of the Supply constructed from (x,y) | |||||
* | |||||
* @param id The Id of the created supply | |||||
* @param x The x coordinate to place the supply | |||||
* @param y The y coordinate to place the supply | |||||
*/ | |||||
protected Supply(int id, int x, int y) { | |||||
// Boundary checks | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
assert (x >= 0 && x< Defaults.boardSize) : "Y coordinate must be in the range [0, Defaults.boardSize)"; | |||||
// Initialization | |||||
this.supplyId =id; | |||||
this.x =x; | |||||
this.y =y; | |||||
this.supplyTileId = Position.toID(x, y); | |||||
} | |||||
/** | |||||
* A second constructor of the Supply constructed from supplyTileId | |||||
* | |||||
* @param id The Id of the created supply | |||||
* @param tileId The linear combination of (x, y) | |||||
*/ | |||||
protected Supply(int id, int tileId) { | |||||
// Boundary check | |||||
assert (id >= 0 && id <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
// Initialization | |||||
this.supplyId =id; | |||||
this.supplyTileId = tileId; | |||||
this.x = Position.toX(tileId); | |||||
this.y = Position.toY(tileId); | |||||
} | |||||
/** | |||||
* A deep copy constructor. | |||||
*/ | |||||
protected Supply (Supply s) { | |||||
this.supplyId = s.supplyId; | |||||
this.x = s.x; | |||||
this.y = s.y; | |||||
this.supplyTileId = s.supplyTileId; | |||||
// We achieve deep copy as the members are all primitives. | |||||
} | |||||
/** @} */ | |||||
/** @name Supply's main application interface */ | |||||
/** @{ */ | |||||
/** @return the supplyId */ | |||||
protected int supplyId () { return supplyId; } | |||||
/** | |||||
* Set the supplyId | |||||
* @param sId The Id to set | |||||
* @return The supplyId | |||||
* @note This function also returns the supplyId to help in chained expressions. | |||||
*/ | |||||
protected int supplyId (int sID) { return supplyId = sID; } | |||||
/** | |||||
* @return the position of the supply as a Position object | |||||
* @see Position | |||||
*/ | |||||
protected Position position () { return new Position (x, y); } | |||||
/** | |||||
* Set the position of the supply from a (x, y) pair | |||||
* @param x The x coordinate of the tile | |||||
* @param y The y coordinate of the tile | |||||
* @return the position of the supply as a Position object | |||||
* @note This function also returns the supplyId to help in chained expressions. | |||||
* @see Position | |||||
*/ | |||||
protected Position position (int x, int y) { | |||||
// Boundary checks | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
assert (x >= 0 && x< Defaults.boardSize) : "Y coordinate must be in the range [0, Defaults.boardSize)"; | |||||
Position p = new Position (x, y); | |||||
this.x = x; | |||||
this.y = y; | |||||
this.supplyTileId = p.getID(); | |||||
return p; | |||||
} | |||||
/** | |||||
* Set the position of the supply from a tileId | |||||
* @param tileId The tileId position | |||||
* @return The position of the supply as Position object | |||||
* @note This function also returns the supplyId to help in chained expressions. | |||||
* @see Position | |||||
*/ | |||||
protected int position (int tileId) { | |||||
// Boundary check | |||||
assert (tileId >= 0 && tileId <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
this.x = Position.toX(tileId); | |||||
this.y = Position.toY(tileId); | |||||
this.supplyTileId = tileId; | |||||
return supplyTileId; | |||||
} | |||||
/** @return The supplyTileId */ | |||||
protected int positionId () { return supplyTileId; } | |||||
/** @} */ | |||||
/** | |||||
* @name Accessor/Mutator interface | |||||
* @note | |||||
* Please consider not to use mutator interface. Its the abstraction killer :( | |||||
* We have added a bit of logic however, in order to make it a bit more safe. | |||||
*/ | |||||
/** @{ */ | |||||
protected int getSupplyId () { return supplyId; } | |||||
protected int getX() { return x; } | |||||
protected int getY() { return y; } | |||||
protected int getSupplyTileId(){ return supplyTileId; } | |||||
protected void setSupplyId(int Id) { supplyId = Id; } | |||||
protected void setX(int x) { | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
this.x = x; | |||||
this.supplyTileId = Position.toID(this.x, this.y); | |||||
} | |||||
protected void setY(int y) { | |||||
assert (y >= 0 && y< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
this.y = y; | |||||
this.supplyTileId = Position.toID(this.x, this.y); | |||||
} | |||||
protected void setSupplyTileId(int tileId) { | |||||
assert (tileId >= 0 && tileId <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
this.supplyTileId = tileId; | |||||
this.x = Position.toX(tileId); | |||||
this.y = Position.toY(tileId); | |||||
} | |||||
/** @} */ | |||||
/** @name Class data */ | |||||
/** @{ */ | |||||
private int supplyId; /**< The unique identifier of the tile. This must not be confused with TileID */ | |||||
private int x; /**< The x coordinate of the tile as if the board lies in the 1st quadrant */ | |||||
private int y; /**< The y coordinate of the tile as if the board lies in the 1st quadrant */ | |||||
private int supplyTileId; /**< The Id of the tile on the board, in witch the supply is located */ | |||||
/** | |||||
* @warning | |||||
* We can calculate tileId from (x,y) so having both (x,y) and tile ID is error | |||||
* prone and not a good practice. Its easy to get them out of sync (code smell). | |||||
* We implement it just because its in the requirements of the assignment. | |||||
* @see Tile.tileId | |||||
*/ | |||||
/** @} */ | |||||
} |
@@ -0,0 +1,224 @@ | |||||
/** | |||||
* @file Tile.java | |||||
* | |||||
* @author Christos Choutouridis AEM:8997 | |||||
* @email cchoutou@ece.auth.gr | |||||
*/ | |||||
package net.hoo2.auth.labyrinth; | |||||
/** | |||||
* @brief | |||||
* This class is the representation of the board's tile | |||||
* | |||||
* Tiles are arranged on the board in square shape and they're identified by | |||||
* an ID. This ID is the linear combination of x and y coordinate of the tile. | |||||
*/ | |||||
class Tile { | |||||
/** @name Constructors */ | |||||
/** @{ */ | |||||
/** | |||||
* The main constructor of the Tile constructed from (x,y) | |||||
* | |||||
* @param x The x coordinate to place the Tile | |||||
* @param y The y coordinate to place the Tile | |||||
* @param up The existence of wall north of the tile | |||||
* @param down The existence of wall south of the tile | |||||
* @param left The existence of wall left of the tile | |||||
* @param right The existence of wall right of the tile | |||||
*/ | |||||
protected Tile(int x, int y, boolean up, boolean down, boolean left, boolean right) { | |||||
// Boundary checks | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
assert (x >= 0 && x< Defaults.boardSize) : "Y coordinate must be in the range [0, Defaults.boardSize)"; | |||||
// Initialization | |||||
this.tileId = Position.toID(x, y); | |||||
this.x =x; | |||||
this.y =y; | |||||
this.up = up; | |||||
this.down = down; | |||||
this.left = left; | |||||
this.right = right; | |||||
} | |||||
/** | |||||
* The main constructor of the Tile constructed from tileId | |||||
* | |||||
* @param id The tileId to place the Tile | |||||
* @param up The existence of wall north of the tile | |||||
* @param down The existence of wall south of the tile | |||||
* @param left The existence of wall left of the tile | |||||
* @param right The existence of wall right of the tile | |||||
*/ | |||||
protected Tile(int id, boolean up, boolean down, boolean left, boolean right) { | |||||
// Boundary check | |||||
assert (id >= 0 && id <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
// Initialization | |||||
this.tileId = id; | |||||
this.x =Position.toX(id); | |||||
this.y =Position.toY(id); | |||||
this.up = up; | |||||
this.down = down; | |||||
this.left = left; | |||||
this.right = right; | |||||
} | |||||
/** | |||||
* A deep copy constructor. | |||||
*/ | |||||
protected Tile (Tile t) { | |||||
this.tileId = t.tileId; | |||||
this.x = t.x; | |||||
this.y = t.y; | |||||
this.up = t.up; | |||||
this.down = t.down; | |||||
this.left = t.left; | |||||
this.right = t.right; | |||||
// We achieve deep copy as the members are all primitives. | |||||
} | |||||
/** @} */ | |||||
/** @name Supply's main application interface */ | |||||
/** @{ */ | |||||
/** | |||||
* @return the position of the tile as a Position object | |||||
* @see Position | |||||
*/ | |||||
protected Position position () { return new Position (x, y); } | |||||
/** | |||||
* Set the position of the tile from a (x, y) pair | |||||
* @param x The x coordinate of the tile | |||||
* @param y The y coordinate of the tile | |||||
* @return the position of the supply as a Position object | |||||
* @note This function also returns the supplyId to help in chained expressions. | |||||
* @see Position | |||||
*/ | |||||
protected Position position (int x, int y) { | |||||
// Boundary checks | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
assert (x >= 0 && x< Defaults.boardSize) : "Y coordinate must be in the range [0, Defaults.boardSize)"; | |||||
Position p = new Position (x, y); | |||||
this.x = x; | |||||
this.y = y; | |||||
this.tileId = p.getID(); | |||||
return p; | |||||
} | |||||
/** | |||||
* Set the position of the tile from a tileId | |||||
* @param tileId The tileId position | |||||
* @return The position of the supply as Position object | |||||
* @note This function also returns the supplyId to help in chained expressions. | |||||
* @see Position | |||||
*/ | |||||
protected int position (int tileId) { | |||||
// Boundary check | |||||
assert (tileId >= 0 && tileId <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
this.x = Position.toX(tileId); | |||||
this.y = Position.toY(tileId); | |||||
this.tileId = tileId; | |||||
return tileId; | |||||
} | |||||
/** @return The tileId */ | |||||
protected int positionId () { return tileId; } | |||||
/** | |||||
* Set the tile's walls | |||||
* @param up Request for north wall (winter is coming) | |||||
* @param down Request for south wall | |||||
* @param left Request for west wall | |||||
* @param right Request for east wall | |||||
*/ | |||||
protected void setWalls (boolean up, boolean down, boolean left, boolean right) { | |||||
assert ( | |||||
((up?1:0) + (down?1:0) + (left?1:0) + (right?1:0)) <=2 | |||||
) : "A tile can have at most 2 walls"; | |||||
this.up = up; | |||||
this.down = down; | |||||
this.left = left; | |||||
this.right = right; | |||||
} | |||||
/** | |||||
* Checks if the tile has wall in the requested direction | |||||
* @param direction The direction to check | |||||
* @return True if there is a wall | |||||
*/ | |||||
protected boolean hasWall (int direction) { | |||||
switch (direction) { | |||||
case Direction.UP: return up; | |||||
case Direction.RIGHT: return right; | |||||
case Direction.DOWN: return down; | |||||
case Direction.LEFT: return left; | |||||
} | |||||
return false; | |||||
} | |||||
/** @} */ | |||||
/** | |||||
* @name Accessor/Mutator interface | |||||
* @note | |||||
* Please consider not to use mutator interface. Its the abstraction killer :( | |||||
* We have added a bit of logic however, in order to make it a bit more safe. | |||||
*/ | |||||
/** @{ */ | |||||
protected int getTileId () { return tileId; } | |||||
protected int getX () { return x; } | |||||
protected int getY () { return y; } | |||||
protected boolean getUp () { return up; } | |||||
protected boolean getDown () { return down; } | |||||
protected boolean getLeft () { return left; } | |||||
protected boolean getRight () { return right; } | |||||
protected void setTileId(int tileId) { | |||||
assert (tileId >= 0 && tileId <= Position.toID(Defaults.boardSize-1, Defaults.boardSize-1)) | |||||
: "TileId must be in the range of [0, Defaults.boardSize^2)"; | |||||
this.tileId = tileId; | |||||
this.x = Position.toX(tileId); | |||||
this.y = Position.toY(tileId); | |||||
} | |||||
protected void setX(int x) { | |||||
assert (x >= 0 && x< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
this.x = x; | |||||
this.tileId = Position.toID(this.x, this.y); | |||||
} | |||||
protected void setY(int y) { | |||||
assert (y >= 0 && y< Defaults.boardSize) : "X coordinate must be in the range [0, Defaults.boardSize)"; | |||||
this.y = y; | |||||
this.tileId = Position.toID(this.x, this.y); | |||||
} | |||||
protected void setUp(boolean up) { this.up = up; } | |||||
protected void setDown(boolean down) { this.down = down; } | |||||
protected void setRight(boolean right) { this.right = right; } | |||||
protected void setLeft(boolean left) { this.left = left; } | |||||
/** @} */ | |||||
/** @name Class data */ | |||||
/** @{ */ | |||||
private int tileId; /**< | |||||
* The unique identifier of the tile. This is the linear combination of | |||||
* x and y coordinates of the tile | |||||
*/ | |||||
private int x; /**< The x coordinate of the tile as if the board lies in the 1st quadrant */ | |||||
private int y; /**< The y coordinate of the tile as if the board lies in the 1st quadrant */ | |||||
private boolean up; /**< Indicator of a wall in the north side of the tile */ | |||||
private boolean down; /**< Indicator of a wall in the south side of the tile */ | |||||
private boolean left; /**< Indicator of a wall in the left side of the tile */ | |||||
private boolean right; /**< Indicator of a wall in the right side of the tile */ | |||||
/** | |||||
* @warning | |||||
* We can calculate tileId from (x,y) so having both (x,y) and tile ID is error | |||||
* prone and not a good practice. Its easy to get them out of sync(code smell). | |||||
* We implement it just because its in the requirements of the assignment. | |||||
* @see Supply.supplyTileId | |||||
*/ | |||||
} |