Compare commits
17 commits
Author | SHA1 | Date | |
---|---|---|---|
136e4a8e69 | |||
5016c1a888 | |||
ae86967b79 | |||
6c65f8d551 | |||
bb09c5afca | |||
42746ad5b0 | |||
2f51df0d82 | |||
9afffd4297 | |||
3068c5ba94 | |||
fc18dea7f4 | |||
491cd35136 | |||
29ce62150e | |||
b05b7cd13c | |||
4a63c7c01e | |||
8dce30c382 | |||
02e5e9c6c9 | |||
556869ebb8 |
|
@ -9,6 +9,11 @@ import java.util.Set;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
import userInterface.UserInterface;
|
||||||
|
import universe.Universe;
|
||||||
|
import universe.Stack;
|
||||||
|
import universe.Situation;
|
||||||
|
|
||||||
public class AppLaser {
|
public class AppLaser {
|
||||||
public static void main(String [] args) {
|
public static void main(String [] args) {
|
||||||
|
|
||||||
|
@ -44,11 +49,9 @@ public class AppLaser {
|
||||||
else if (start_dir == 13) firstState_j = start_j - 1;
|
else if (start_dir == 13) firstState_j = start_j - 1;
|
||||||
|
|
||||||
if (cli == true) {
|
if (cli == true) {
|
||||||
|
|
||||||
Stack <Situation> stack = new Stack <Situation>();
|
Stack <Situation> stack = new Stack <Situation>();
|
||||||
Universe universe = new Universe(universe_width + 2, universe_height + 2, start_i + 1, start_j + 1, start_dir);
|
Universe universe = new Universe(universe_width + 2, universe_height + 2, start_i + 1, start_j + 1, start_dir);
|
||||||
Situation currentState = new Situation(firstState_i + 1, firstState_j + 1, start_dir, 0);
|
Situation currentState = new Situation(firstState_i + 1, firstState_j + 1, start_dir, 0);
|
||||||
|
|
||||||
Scanner scanner = new Scanner(System.in);
|
Scanner scanner = new Scanner(System.in);
|
||||||
|
|
||||||
int choice;
|
int choice;
|
||||||
|
@ -62,7 +65,7 @@ public class AppLaser {
|
||||||
|
|
||||||
// print the universe
|
// print the universe
|
||||||
|
|
||||||
universe.print(2, 4);
|
Universe.print(universe.getGrid(), universe_width + 2, universe_height + 2, 2, 4);
|
||||||
|
|
||||||
// print the menu
|
// print the menu
|
||||||
|
|
||||||
|
@ -184,7 +187,7 @@ public class AppLaser {
|
||||||
start_j = Integer.valueOf(reader.readLine());
|
start_j = Integer.valueOf(reader.readLine());
|
||||||
|
|
||||||
|
|
||||||
universe.changeUniverseDim(universe_width, universe_height);
|
universe.changeUniverseDim(universe_width + 2, universe_height + 2);
|
||||||
|
|
||||||
firstState_i = start_i;
|
firstState_i = start_i;
|
||||||
firstState_j = start_j;
|
firstState_j = start_j;
|
||||||
|
@ -252,22 +255,35 @@ public class AppLaser {
|
||||||
|
|
||||||
universe.resetUniverse();
|
universe.resetUniverse();
|
||||||
|
|
||||||
universe.print(2, 4);
|
Universe.print(universe.getGrid(), universe_width + 2, universe_height + 2, 2, 4);
|
||||||
|
|
||||||
int start_time = (int) Instant.now().getEpochSecond();
|
int start_time = (int) Instant.now().getEpochSecond();
|
||||||
|
|
||||||
while (!universe.isSolved()) {
|
int [][] bestGrid = universe.copyGrid();
|
||||||
|
int best_filled_boxes = 0;
|
||||||
|
int best_nb_mirrors = 0;
|
||||||
|
|
||||||
|
do {
|
||||||
if (universe.canEvolve(currentState)) {
|
if (universe.canEvolve(currentState)) {
|
||||||
stack.push(currentState.copy(universe.possibleChoices(currentState)));
|
stack.push(currentState.copy(universe.possibleChoices(currentState)));
|
||||||
currentState = universe.evolve(currentState);
|
currentState = universe.evolve(currentState);
|
||||||
|
|
||||||
if (display_progress == true) universe.print(universe_height + 6, 4);
|
if (display_progress == true) Universe.print(universe.getGrid(), universe_width + 2, universe_height + 2, universe_height + 6, 4);
|
||||||
|
|
||||||
|
if ((universe.getFilledBoxes() > best_filled_boxes) || (universe.getFilledBoxes() == best_filled_boxes && universe.getNbMirrors() < best_nb_mirrors)) {
|
||||||
|
bestGrid = universe.copyGrid();
|
||||||
|
best_filled_boxes = universe.getFilledBoxes();
|
||||||
|
best_nb_mirrors = universe.getNbMirrors();
|
||||||
|
|
||||||
|
Universe.print(bestGrid, universe_width + 2, universe_height + 2, 2, 2 * universe_width + 10);
|
||||||
|
System.out.println("Miroirs: " + best_nb_mirrors + " Cases: " + best_filled_boxes);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else if (stack.size() > 0) {
|
else if (stack.size() > 0) {
|
||||||
currentState = stack.pop();
|
currentState = stack.pop();
|
||||||
universe.reset(currentState);
|
universe.reset(currentState);
|
||||||
|
|
||||||
if (display_regress == true) universe.print(universe_height + 6, 4);
|
if (display_regress == true) Universe.print(universe.getGrid(), universe_width + 2, universe_height + 2, universe_height + 6, 4);
|
||||||
} else {
|
} else {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -278,11 +294,11 @@ public class AppLaser {
|
||||||
if ((int) Instant.now().getEpochSecond() - start_time > 2 * 60 && optimize_duration == true) {
|
if ((int) Instant.now().getEpochSecond() - start_time > 2 * 60 && optimize_duration == true) {
|
||||||
display_regress = false;
|
display_regress = false;
|
||||||
}
|
}
|
||||||
}
|
} while (stack.size() != 0);
|
||||||
|
|
||||||
System.out.println("\n\n");
|
System.out.println("\n\n");
|
||||||
|
|
||||||
universe.print(universe_height + 6, 4);
|
Universe.print(bestGrid, universe_width + 2, universe_height + 2, universe_height + 6, 4);
|
||||||
|
|
||||||
System.out.println("\nSolved in " + ((int) Instant.now().getEpochSecond() - start_time) + " secconds");
|
System.out.println("\nSolved in " + ((int) Instant.now().getEpochSecond() - start_time) + " secconds");
|
||||||
|
|
||||||
|
@ -299,7 +315,9 @@ public class AppLaser {
|
||||||
} while (choice != 0);
|
} while (choice != 0);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
System.out.println("there is no GUI yet.");
|
Universe universe = new Universe(universe_width + 2, universe_height + 2, start_i + 1, start_j + 1, start_dir);
|
||||||
|
UserInterface userInterface = new UserInterface(universe);
|
||||||
|
userInterface.start();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
373
Universe.java
|
@ -1,373 +0,0 @@
|
||||||
// Antoine CRETUAL, Lukian LEIZOUR, 14/02/2024
|
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.FileWriter;
|
|
||||||
|
|
||||||
public class Universe {
|
|
||||||
// Atributes
|
|
||||||
|
|
||||||
private int[][] grid;
|
|
||||||
private int width, height;
|
|
||||||
private int boxes_to_fill;
|
|
||||||
|
|
||||||
// Constructors
|
|
||||||
|
|
||||||
public Universe(int width, int height, int i_start, int j_start, int dir_start) {
|
|
||||||
this.grid = new int[height][width];
|
|
||||||
this.height = height;
|
|
||||||
this.width = width;
|
|
||||||
this.boxes_to_fill = (width - 2) * (height - 2) - 1;
|
|
||||||
|
|
||||||
int i, j;
|
|
||||||
for (i = 1; i < this.height - 1; i++) {
|
|
||||||
for (j = 1; j < this.width - 1; j++) {
|
|
||||||
this.grid[i][j] = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (i = 0; i < this.height; i++) {
|
|
||||||
this.grid[i][0] = -1;
|
|
||||||
this.grid[i][width - 1] = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (j = 0; j < this.width; j++) {
|
|
||||||
this.grid[0][j] = -1;
|
|
||||||
this.grid[height - 1][j] = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.grid[i_start][j_start] = dir_start;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods
|
|
||||||
|
|
||||||
public void print(int pos_i, int pos_j) {
|
|
||||||
int i, j;
|
|
||||||
for (i = 0; i < this.height; i++) {
|
|
||||||
for (j = 0; j < this.width; j++) {
|
|
||||||
System.out.print("\033[" + (i + pos_i) + ";" + (j*2 + pos_j) + "H");
|
|
||||||
switch (this.grid[i][j]) {
|
|
||||||
case -1:
|
|
||||||
System.out.printf(" X");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0:
|
|
||||||
System.out.printf(" ");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 1:
|
|
||||||
System.out.printf(" |");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 2:
|
|
||||||
System.out.printf(" -");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 3:
|
|
||||||
System.out.printf(" +");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 4:
|
|
||||||
System.out.printf(" /");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 5:
|
|
||||||
System.out.printf(" \\");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 10:
|
|
||||||
System.out.printf(" ^");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 11:
|
|
||||||
System.out.printf(" v");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 12:
|
|
||||||
System.out.printf(" >");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 13:
|
|
||||||
System.out.printf(" <");
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
System.out.printf("%2d", this.grid[i][j]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
System.out.print("\n");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void resetUniverse() {
|
|
||||||
for (int i = 1; i < this.height - 1; i++) {
|
|
||||||
for (int j = 1; j < this.width - 1; j++) {
|
|
||||||
if (this.grid[i][j] != 10 && this.grid[i][j] != 11 && this.grid[i][j] != 12 && this.grid[i][j] != 13 && this.grid[i][j] != 0 && this.grid[i][j] != -1) {
|
|
||||||
this.grid[i][j] = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void resetUniverseObstacles() {
|
|
||||||
for (int i = 1; i < this.height - 1; i++) {
|
|
||||||
for (int j = 1; j < this.width - 1; j++) {
|
|
||||||
if (this.grid[i][j] != 10 && this.grid[i][j] != 11 && this.grid[i][j] != 12 && this.grid[i][j] != 13 && this.grid[i][j] != 0) {
|
|
||||||
this.grid[i][j] = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
this.boxes_to_fill = ((this.height - 2) * (this.width - 2)) - 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void changeUniverseDim(int width, int height) {
|
|
||||||
int [][] newgrid = new int[width][height];
|
|
||||||
|
|
||||||
for (int i = 1; i < height - 1; i++) {
|
|
||||||
for (int j = 1; j < width - 1; j++) {
|
|
||||||
newgrid[i][j] = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int i = 1; i < height - 1 && i < this.height - 1; i++) {
|
|
||||||
for (int j = 1; j < width - 1 && j < this.width - 1; j++) {
|
|
||||||
newgrid[i][j] = this.grid[i][j];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int i = 0; i < height; i++) {
|
|
||||||
newgrid[i][0] = -1;
|
|
||||||
newgrid[i][width - 1] = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int j = 0; j < width; j++) {
|
|
||||||
newgrid[height - 1][j] = -1;
|
|
||||||
newgrid[0][j] = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.grid = newgrid;
|
|
||||||
this.width = width;
|
|
||||||
this.height = height;
|
|
||||||
|
|
||||||
this.boxes_to_fill = 0;
|
|
||||||
|
|
||||||
for (int i = 1; i < height - 1; i++) {
|
|
||||||
for (int j = 1; j < width - 1; j++) {
|
|
||||||
if (this.grid[i][j] == 0) {
|
|
||||||
this.boxes_to_fill ++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void changeUniverseStart(int pos_i, int pos_j, int dir) {
|
|
||||||
for (int i = 0; i < this.height; i++) {
|
|
||||||
for (int j = 0; j < this.width; j++) {
|
|
||||||
if (this.grid[i][j] == 10 || this.grid[i][j] == 11 || this.grid[i][j] == 12|| this.grid[i][j] == 13) {
|
|
||||||
this.grid[i][j] = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
this.grid[pos_i][pos_j] = dir;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addObstacle(int pos_i, int pos_j) {
|
|
||||||
if (this.grid[pos_i][pos_j] == 0) {
|
|
||||||
this.grid[pos_i][pos_j] = -1;
|
|
||||||
this.boxes_to_fill--;
|
|
||||||
}
|
|
||||||
else {}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int possibleChoices(Situation s) {
|
|
||||||
int i = s.pos_i;
|
|
||||||
int j = s.pos_j;
|
|
||||||
int d = s.direction;
|
|
||||||
int c = s.nb_choix;
|
|
||||||
|
|
||||||
switch (c) {
|
|
||||||
case 0: {
|
|
||||||
switch (d) {
|
|
||||||
case 10: // north
|
|
||||||
if (this.grid[i - 1][j] == 0 || this.grid[i - 1][j] == 2) return 1; // front
|
|
||||||
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 11: // south
|
|
||||||
if (this.grid[i + 1][j] == 0 || this.grid[i + 1][j] == 2) return 1; // front
|
|
||||||
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 12: // east
|
|
||||||
if (this.grid[i][j + 1] == 0 || this.grid[i][j + 1] == 1) return 1; // front
|
|
||||||
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 13: //west
|
|
||||||
if (this.grid[i][j - 1] == 0 || this.grid[i][j - 1] == 1) return 1; // front
|
|
||||||
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
default: {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
case 1: {
|
|
||||||
switch (d) {
|
|
||||||
case 10: // north
|
|
||||||
if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 11: // south
|
|
||||||
if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 12: // east
|
|
||||||
if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 13: //west
|
|
||||||
if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
|
||||||
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
default: {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
case 2: {
|
|
||||||
switch (d) {
|
|
||||||
case 10: // north
|
|
||||||
if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 11: // south
|
|
||||||
if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 12: // east
|
|
||||||
if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
case 13: //west
|
|
||||||
if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
|
||||||
else return -1; // back
|
|
||||||
|
|
||||||
default: {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
case 3:
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
default: return -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean canEvolve(Situation s) {
|
|
||||||
return possibleChoices(s) != -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Situation evolve(Situation s) {
|
|
||||||
int i = s.pos_i;
|
|
||||||
int j = s.pos_j;
|
|
||||||
int d = s.direction;
|
|
||||||
int c = possibleChoices(s);
|
|
||||||
|
|
||||||
// new status of the box
|
|
||||||
|
|
||||||
if (c == 1 && (d == 10 || d == 11)) {
|
|
||||||
if (this.grid[i][j] == 0) {
|
|
||||||
this.grid[i][j] = 1;
|
|
||||||
} else {
|
|
||||||
this.grid[i][j] = 3;
|
|
||||||
this.boxes_to_fill++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (c == 1 && (d == 12 || d == 13)) {
|
|
||||||
if (this.grid[i][j] == 0) {
|
|
||||||
this.grid[i][j] = 2;
|
|
||||||
} else {
|
|
||||||
this.grid[i][j] = 3;
|
|
||||||
this.boxes_to_fill++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if ((c == 3 && d == 10) || (c == 3 && d == 11) || (c == 2 && d == 12) || (c == 2 && d == 13)) this.grid[i][j] = 4;
|
|
||||||
if ((c == 2 && d == 10) || (c == 2 && d == 11) || (c == 3 && d == 12) || (c == 3 && d == 13)) this.grid[i][j] = 5;
|
|
||||||
|
|
||||||
// changing the position of the situation
|
|
||||||
|
|
||||||
if (c == 1 && d == 10 || c == 2 && d == 12 || c == 3 && d == 13) {
|
|
||||||
i --;
|
|
||||||
d = 10;
|
|
||||||
}
|
|
||||||
else if (c == 1 && d == 11 || c == 2 && d == 13 || c == 3 && d == 12) {
|
|
||||||
i ++;
|
|
||||||
d = 11;
|
|
||||||
}
|
|
||||||
else if (c == 1 && d == 12 || c == 2 && d == 11 || c == 3 && d == 10) {
|
|
||||||
j ++;
|
|
||||||
d = 12;
|
|
||||||
}
|
|
||||||
else if (c == 1 && d == 13 || c == 2 && d == 10 || c == 3 && d == 11) {
|
|
||||||
j --;
|
|
||||||
d = 13;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.boxes_to_fill--;
|
|
||||||
|
|
||||||
return new Situation(i, j, d, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void reset(Situation s) {
|
|
||||||
int i = s.pos_i;
|
|
||||||
int j = s.pos_j;
|
|
||||||
int d = s.direction;
|
|
||||||
|
|
||||||
if (this.grid[i][j] == 3) {
|
|
||||||
if (d == 10 || d == 11) {
|
|
||||||
this.grid[i][j] = 2;
|
|
||||||
} else {
|
|
||||||
this.grid[i][j] = 1;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
this.grid[s.pos_i][s.pos_j] = 0;
|
|
||||||
this.boxes_to_fill++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isSolved() {
|
|
||||||
return this.boxes_to_fill == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void save(String fileName) {
|
|
||||||
try {
|
|
||||||
File file = new File("./saves/" + fileName + ".txt");
|
|
||||||
|
|
||||||
file.createNewFile();
|
|
||||||
|
|
||||||
FileWriter writer = new FileWriter("./saves/" + fileName + ".txt");
|
|
||||||
writer.write(this.height + "\n" + this.width + "\n");
|
|
||||||
|
|
||||||
for (int i = 1; i < this.height - 1; i++) {
|
|
||||||
for (int j = 1; j < this.width - 1; j++) {
|
|
||||||
if (this.grid[i][j] == 10 || this.grid[i][j] == 11 || this.grid[i][j] == 12 || this.grid[i][j] == 13) writer.write(this.grid[i][j] + "\n" + i + "\n" + j + "\n");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int i = 1; i < this.height - 1; i++) {
|
|
||||||
for (int j = 1; j < this.width - 1; j++) {
|
|
||||||
if (this.grid[i][j] == -1) writer.write(i + "\n" + j + "\n");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
writer.close();
|
|
||||||
}
|
|
||||||
catch (Exception e) {}
|
|
||||||
}
|
|
||||||
}
|
|
BIN
images/blade.png
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
images/crossLaser.png
Normal file
After Width: | Height: | Size: 298 B |
BIN
images/horizontalLaser.png
Normal file
After Width: | Height: | Size: 243 B |
BIN
images/miror1.png
Normal file
After Width: | Height: | Size: 494 B |
BIN
images/miror2.png
Normal file
After Width: | Height: | Size: 520 B |
BIN
images/miror3.png
Normal file
After Width: | Height: | Size: 502 B |
BIN
images/miror4.png
Normal file
After Width: | Height: | Size: 517 B |
BIN
images/new.png
Normal file
After Width: | Height: | Size: 861 B |
BIN
images/open.png
Normal file
After Width: | Height: | Size: 621 B |
BIN
images/save.png
Normal file
After Width: | Height: | Size: 720 B |
BIN
images/startBot.png
Normal file
After Width: | Height: | Size: 428 B |
BIN
images/startLeft.png
Normal file
After Width: | Height: | Size: 428 B |
BIN
images/startRight.png
Normal file
After Width: | Height: | Size: 393 B |
BIN
images/startUp.png
Normal file
After Width: | Height: | Size: 374 B |
BIN
images/verticalLaser.png
Normal file
After Width: | Height: | Size: 247 B |
BIN
images/wall.png
Normal file
After Width: | Height: | Size: 311 B |
10
makefile
|
@ -1,7 +1,17 @@
|
||||||
build:
|
build:
|
||||||
|
javac --source 1.8 --target 1.8 universe/*.java
|
||||||
|
javac --source 1.8 --target 1.8 userInterface/*.java
|
||||||
javac --source 1.8 --target 1.8 AppLaser.java
|
javac --source 1.8 --target 1.8 AppLaser.java
|
||||||
jar cfe AppLaser.jar AppLaser *.class
|
jar cfe AppLaser.jar AppLaser *.class
|
||||||
|
|
||||||
run:
|
run:
|
||||||
|
javac --source 1.8 --target 1.8 universe/*.java
|
||||||
|
javac --source 1.8 --target 1.8 userInterface/*.java
|
||||||
javac --source 1.8 --target 1.8 AppLaser.java
|
javac --source 1.8 --target 1.8 AppLaser.java
|
||||||
java AppLaser -cli --optimize-duration
|
java AppLaser -cli --optimize-duration
|
||||||
|
|
||||||
|
run_gui:
|
||||||
|
javac --source 1.8 --target 1.8 universe/*.java
|
||||||
|
javac --source 1.8 --target 1.8 userInterface/*.java
|
||||||
|
javac --source 1.8 --target 1.8 AppLaser.java
|
||||||
|
java AppLaser
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
5
|
3
|
||||||
5
|
3
|
||||||
11
|
11
|
||||||
1
|
1
|
||||||
1
|
1
|
||||||
|
|
187
saves/maze1.txt
Normal file
|
@ -0,0 +1,187 @@
|
||||||
|
10
|
||||||
|
20
|
||||||
|
11
|
||||||
|
1
|
||||||
|
1
|
||||||
|
1
|
||||||
|
2
|
||||||
|
1
|
||||||
|
6
|
||||||
|
1
|
||||||
|
10
|
||||||
|
1
|
||||||
|
14
|
||||||
|
1
|
||||||
|
18
|
||||||
|
1
|
||||||
|
20
|
||||||
|
2
|
||||||
|
2
|
||||||
|
2
|
||||||
|
4
|
||||||
|
2
|
||||||
|
6
|
||||||
|
2
|
||||||
|
8
|
||||||
|
2
|
||||||
|
10
|
||||||
|
2
|
||||||
|
12
|
||||||
|
2
|
||||||
|
14
|
||||||
|
2
|
||||||
|
16
|
||||||
|
2
|
||||||
|
18
|
||||||
|
2
|
||||||
|
20
|
||||||
|
3
|
||||||
|
2
|
||||||
|
3
|
||||||
|
4
|
||||||
|
3
|
||||||
|
6
|
||||||
|
3
|
||||||
|
8
|
||||||
|
3
|
||||||
|
10
|
||||||
|
3
|
||||||
|
12
|
||||||
|
3
|
||||||
|
14
|
||||||
|
3
|
||||||
|
16
|
||||||
|
3
|
||||||
|
18
|
||||||
|
3
|
||||||
|
20
|
||||||
|
4
|
||||||
|
2
|
||||||
|
4
|
||||||
|
4
|
||||||
|
4
|
||||||
|
6
|
||||||
|
4
|
||||||
|
8
|
||||||
|
4
|
||||||
|
10
|
||||||
|
4
|
||||||
|
12
|
||||||
|
4
|
||||||
|
14
|
||||||
|
4
|
||||||
|
16
|
||||||
|
4
|
||||||
|
18
|
||||||
|
4
|
||||||
|
20
|
||||||
|
5
|
||||||
|
2
|
||||||
|
5
|
||||||
|
4
|
||||||
|
5
|
||||||
|
6
|
||||||
|
5
|
||||||
|
8
|
||||||
|
5
|
||||||
|
10
|
||||||
|
5
|
||||||
|
12
|
||||||
|
5
|
||||||
|
14
|
||||||
|
5
|
||||||
|
16
|
||||||
|
5
|
||||||
|
18
|
||||||
|
5
|
||||||
|
20
|
||||||
|
6
|
||||||
|
2
|
||||||
|
6
|
||||||
|
4
|
||||||
|
6
|
||||||
|
6
|
||||||
|
6
|
||||||
|
8
|
||||||
|
6
|
||||||
|
10
|
||||||
|
6
|
||||||
|
12
|
||||||
|
6
|
||||||
|
14
|
||||||
|
6
|
||||||
|
16
|
||||||
|
6
|
||||||
|
18
|
||||||
|
6
|
||||||
|
20
|
||||||
|
7
|
||||||
|
2
|
||||||
|
7
|
||||||
|
4
|
||||||
|
7
|
||||||
|
6
|
||||||
|
7
|
||||||
|
8
|
||||||
|
7
|
||||||
|
10
|
||||||
|
7
|
||||||
|
12
|
||||||
|
7
|
||||||
|
14
|
||||||
|
7
|
||||||
|
16
|
||||||
|
7
|
||||||
|
18
|
||||||
|
7
|
||||||
|
20
|
||||||
|
8
|
||||||
|
2
|
||||||
|
8
|
||||||
|
4
|
||||||
|
8
|
||||||
|
6
|
||||||
|
8
|
||||||
|
8
|
||||||
|
8
|
||||||
|
10
|
||||||
|
8
|
||||||
|
12
|
||||||
|
8
|
||||||
|
14
|
||||||
|
8
|
||||||
|
16
|
||||||
|
8
|
||||||
|
18
|
||||||
|
8
|
||||||
|
20
|
||||||
|
9
|
||||||
|
2
|
||||||
|
9
|
||||||
|
4
|
||||||
|
9
|
||||||
|
6
|
||||||
|
9
|
||||||
|
8
|
||||||
|
9
|
||||||
|
10
|
||||||
|
9
|
||||||
|
12
|
||||||
|
9
|
||||||
|
14
|
||||||
|
9
|
||||||
|
16
|
||||||
|
9
|
||||||
|
18
|
||||||
|
9
|
||||||
|
20
|
||||||
|
10
|
||||||
|
4
|
||||||
|
10
|
||||||
|
8
|
||||||
|
10
|
||||||
|
12
|
||||||
|
10
|
||||||
|
16
|
||||||
|
10
|
||||||
|
20
|
155
saves/maze2.txt
Normal file
|
@ -0,0 +1,155 @@
|
||||||
|
10
|
||||||
|
20
|
||||||
|
11
|
||||||
|
1
|
||||||
|
1
|
||||||
|
1
|
||||||
|
2
|
||||||
|
1
|
||||||
|
6
|
||||||
|
1
|
||||||
|
10
|
||||||
|
1
|
||||||
|
14
|
||||||
|
1
|
||||||
|
18
|
||||||
|
1
|
||||||
|
20
|
||||||
|
2
|
||||||
|
2
|
||||||
|
2
|
||||||
|
4
|
||||||
|
2
|
||||||
|
6
|
||||||
|
2
|
||||||
|
7
|
||||||
|
2
|
||||||
|
8
|
||||||
|
2
|
||||||
|
10
|
||||||
|
2
|
||||||
|
12
|
||||||
|
2
|
||||||
|
13
|
||||||
|
2
|
||||||
|
14
|
||||||
|
2
|
||||||
|
15
|
||||||
|
2
|
||||||
|
16
|
||||||
|
2
|
||||||
|
18
|
||||||
|
2
|
||||||
|
20
|
||||||
|
3
|
||||||
|
4
|
||||||
|
3
|
||||||
|
18
|
||||||
|
4
|
||||||
|
2
|
||||||
|
4
|
||||||
|
4
|
||||||
|
4
|
||||||
|
5
|
||||||
|
4
|
||||||
|
6
|
||||||
|
4
|
||||||
|
8
|
||||||
|
4
|
||||||
|
9
|
||||||
|
4
|
||||||
|
10
|
||||||
|
4
|
||||||
|
12
|
||||||
|
4
|
||||||
|
14
|
||||||
|
4
|
||||||
|
16
|
||||||
|
4
|
||||||
|
18
|
||||||
|
4
|
||||||
|
19
|
||||||
|
4
|
||||||
|
20
|
||||||
|
5
|
||||||
|
12
|
||||||
|
5
|
||||||
|
14
|
||||||
|
6
|
||||||
|
2
|
||||||
|
6
|
||||||
|
4
|
||||||
|
6
|
||||||
|
6
|
||||||
|
6
|
||||||
|
7
|
||||||
|
6
|
||||||
|
8
|
||||||
|
6
|
||||||
|
10
|
||||||
|
6
|
||||||
|
11
|
||||||
|
6
|
||||||
|
12
|
||||||
|
6
|
||||||
|
14
|
||||||
|
6
|
||||||
|
15
|
||||||
|
6
|
||||||
|
16
|
||||||
|
6
|
||||||
|
18
|
||||||
|
6
|
||||||
|
19
|
||||||
|
6
|
||||||
|
20
|
||||||
|
7
|
||||||
|
1
|
||||||
|
7
|
||||||
|
2
|
||||||
|
8
|
||||||
|
2
|
||||||
|
8
|
||||||
|
4
|
||||||
|
8
|
||||||
|
6
|
||||||
|
8
|
||||||
|
8
|
||||||
|
8
|
||||||
|
10
|
||||||
|
8
|
||||||
|
11
|
||||||
|
8
|
||||||
|
12
|
||||||
|
8
|
||||||
|
13
|
||||||
|
8
|
||||||
|
14
|
||||||
|
8
|
||||||
|
16
|
||||||
|
8
|
||||||
|
17
|
||||||
|
8
|
||||||
|
18
|
||||||
|
8
|
||||||
|
20
|
||||||
|
9
|
||||||
|
4
|
||||||
|
9
|
||||||
|
12
|
||||||
|
9
|
||||||
|
16
|
||||||
|
9
|
||||||
|
18
|
||||||
|
10
|
||||||
|
3
|
||||||
|
10
|
||||||
|
4
|
||||||
|
10
|
||||||
|
8
|
||||||
|
10
|
||||||
|
12
|
||||||
|
10
|
||||||
|
16
|
||||||
|
10
|
||||||
|
20
|
83
saves/prof.txt
Normal file
|
@ -0,0 +1,83 @@
|
||||||
|
13
|
||||||
|
20
|
||||||
|
10
|
||||||
|
9
|
||||||
|
1
|
||||||
|
2
|
||||||
|
6
|
||||||
|
2
|
||||||
|
9
|
||||||
|
2
|
||||||
|
10
|
||||||
|
2
|
||||||
|
13
|
||||||
|
2
|
||||||
|
14
|
||||||
|
2
|
||||||
|
15
|
||||||
|
2
|
||||||
|
16
|
||||||
|
2
|
||||||
|
17
|
||||||
|
3
|
||||||
|
3
|
||||||
|
3
|
||||||
|
4
|
||||||
|
3
|
||||||
|
5
|
||||||
|
3
|
||||||
|
6
|
||||||
|
3
|
||||||
|
9
|
||||||
|
3
|
||||||
|
10
|
||||||
|
4
|
||||||
|
19
|
||||||
|
5
|
||||||
|
19
|
||||||
|
6
|
||||||
|
3
|
||||||
|
6
|
||||||
|
4
|
||||||
|
6
|
||||||
|
5
|
||||||
|
6
|
||||||
|
8
|
||||||
|
6
|
||||||
|
9
|
||||||
|
6
|
||||||
|
11
|
||||||
|
6
|
||||||
|
14
|
||||||
|
6
|
||||||
|
15
|
||||||
|
6
|
||||||
|
16
|
||||||
|
7
|
||||||
|
3
|
||||||
|
7
|
||||||
|
8
|
||||||
|
7
|
||||||
|
14
|
||||||
|
8
|
||||||
|
3
|
||||||
|
8
|
||||||
|
8
|
||||||
|
8
|
||||||
|
14
|
||||||
|
9
|
||||||
|
3
|
||||||
|
9
|
||||||
|
8
|
||||||
|
9
|
||||||
|
9
|
||||||
|
9
|
||||||
|
12
|
||||||
|
9
|
||||||
|
13
|
||||||
|
9
|
||||||
|
14
|
||||||
|
10
|
||||||
|
3
|
||||||
|
11
|
||||||
|
3
|
|
@ -1,5 +1,5 @@
|
||||||
12
|
10
|
||||||
12
|
10
|
||||||
10
|
10
|
||||||
6
|
6
|
||||||
1
|
1
|
||||||
|
|
147
saves/roux.txt
Normal file
|
@ -0,0 +1,147 @@
|
||||||
|
20
|
||||||
|
13
|
||||||
|
10
|
||||||
|
20
|
||||||
|
3
|
||||||
|
1
|
||||||
|
1
|
||||||
|
2
|
||||||
|
1
|
||||||
|
2
|
||||||
|
3
|
||||||
|
2
|
||||||
|
12
|
||||||
|
3
|
||||||
|
1
|
||||||
|
3
|
||||||
|
3
|
||||||
|
3
|
||||||
|
12
|
||||||
|
4
|
||||||
|
3
|
||||||
|
4
|
||||||
|
12
|
||||||
|
5
|
||||||
|
3
|
||||||
|
5
|
||||||
|
12
|
||||||
|
6
|
||||||
|
3
|
||||||
|
6
|
||||||
|
4
|
||||||
|
6
|
||||||
|
5
|
||||||
|
6
|
||||||
|
6
|
||||||
|
6
|
||||||
|
7
|
||||||
|
6
|
||||||
|
8
|
||||||
|
6
|
||||||
|
9
|
||||||
|
6
|
||||||
|
10
|
||||||
|
6
|
||||||
|
12
|
||||||
|
7
|
||||||
|
12
|
||||||
|
8
|
||||||
|
12
|
||||||
|
9
|
||||||
|
7
|
||||||
|
9
|
||||||
|
8
|
||||||
|
9
|
||||||
|
9
|
||||||
|
9
|
||||||
|
12
|
||||||
|
10
|
||||||
|
5
|
||||||
|
10
|
||||||
|
9
|
||||||
|
10
|
||||||
|
11
|
||||||
|
10
|
||||||
|
12
|
||||||
|
11
|
||||||
|
2
|
||||||
|
11
|
||||||
|
3
|
||||||
|
11
|
||||||
|
9
|
||||||
|
12
|
||||||
|
2
|
||||||
|
13
|
||||||
|
2
|
||||||
|
14
|
||||||
|
2
|
||||||
|
14
|
||||||
|
12
|
||||||
|
15
|
||||||
|
2
|
||||||
|
15
|
||||||
|
5
|
||||||
|
15
|
||||||
|
6
|
||||||
|
15
|
||||||
|
7
|
||||||
|
15
|
||||||
|
8
|
||||||
|
15
|
||||||
|
9
|
||||||
|
15
|
||||||
|
10
|
||||||
|
15
|
||||||
|
11
|
||||||
|
15
|
||||||
|
12
|
||||||
|
16
|
||||||
|
2
|
||||||
|
16
|
||||||
|
4
|
||||||
|
16
|
||||||
|
5
|
||||||
|
16
|
||||||
|
6
|
||||||
|
16
|
||||||
|
7
|
||||||
|
16
|
||||||
|
8
|
||||||
|
16
|
||||||
|
9
|
||||||
|
16
|
||||||
|
10
|
||||||
|
16
|
||||||
|
11
|
||||||
|
16
|
||||||
|
12
|
||||||
|
17
|
||||||
|
2
|
||||||
|
18
|
||||||
|
2
|
||||||
|
18
|
||||||
|
5
|
||||||
|
18
|
||||||
|
9
|
||||||
|
18
|
||||||
|
10
|
||||||
|
18
|
||||||
|
11
|
||||||
|
18
|
||||||
|
12
|
||||||
|
19
|
||||||
|
5
|
||||||
|
19
|
||||||
|
8
|
||||||
|
19
|
||||||
|
9
|
||||||
|
19
|
||||||
|
10
|
||||||
|
19
|
||||||
|
11
|
||||||
|
19
|
||||||
|
12
|
||||||
|
20
|
||||||
|
1
|
||||||
|
20
|
||||||
|
5
|
|
@ -1,5 +1,7 @@
|
||||||
// Antoine CRETUAL, Lukian LEIZOUR, 21/02/2024
|
// Antoine CRETUAL, Lukian LEIZOUR, 21/02/2024
|
||||||
|
|
||||||
|
package universe;
|
||||||
|
|
||||||
public class Situation {
|
public class Situation {
|
||||||
// Atributes
|
// Atributes
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
// Antoine CRETUAL, Lukian LEIZOUR, 21/02/2024
|
// Antoine CRETUAL, Lukian LEIZOUR, 21/02/2024
|
||||||
|
|
||||||
|
package universe;
|
||||||
|
|
||||||
import java.util.Vector;
|
import java.util.Vector;
|
||||||
|
|
||||||
public class Stack <T> {
|
public class Stack <T> {
|
||||||
|
@ -13,6 +15,10 @@ public class Stack <T> {
|
||||||
array = new Vector<T>();
|
array = new Vector<T>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Stack(Vector<T> array) {
|
||||||
|
array = array;
|
||||||
|
}
|
||||||
|
|
||||||
// Methods
|
// Methods
|
||||||
|
|
||||||
public void push(T x) {
|
public void push(T x) {
|
||||||
|
@ -28,4 +34,8 @@ public class Stack <T> {
|
||||||
public int size() {
|
public int size() {
|
||||||
return this.array.size();
|
return this.array.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Stack copy() {
|
||||||
|
return new Stack(new Vector<T>(this.array));
|
||||||
|
}
|
||||||
}
|
}
|
431
universe/Universe.java
Normal file
|
@ -0,0 +1,431 @@
|
||||||
|
// Antoine CRETUAL, Lukian LEIZOUR, 14/02/2024
|
||||||
|
|
||||||
|
package universe;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileWriter;
|
||||||
|
|
||||||
|
public class Universe {
|
||||||
|
// Atributes
|
||||||
|
|
||||||
|
private int[][] grid;
|
||||||
|
private int width, height;
|
||||||
|
private int start_i, start_j;
|
||||||
|
private int filled_boxes;
|
||||||
|
private int nb_mirors;
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
// Constructors
|
||||||
|
|
||||||
|
public Universe(int width, int height, int i_start, int j_start, int dir_start) {
|
||||||
|
this.grid = new int[height][width];
|
||||||
|
this.height = height;
|
||||||
|
this.width = width;
|
||||||
|
this.start_i = i_start;
|
||||||
|
this.start_j = j_start;
|
||||||
|
this.filled_boxes = 0;
|
||||||
|
this.nb_mirors = 0;
|
||||||
|
|
||||||
|
int i, j;
|
||||||
|
for (i = 1; i < this.height - 1; i++) {
|
||||||
|
for (j = 1; j < this.width - 1; j++) {
|
||||||
|
this.grid[i][j] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < this.height; i++) {
|
||||||
|
this.grid[i][0] = -1;
|
||||||
|
this.grid[i][width - 1] = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (j = 0; j < this.width; j++) {
|
||||||
|
this.grid[0][j] = -1;
|
||||||
|
this.grid[height - 1][j] = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.grid[i_start][j_start] = dir_start;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Methods
|
||||||
|
|
||||||
|
public static void print(int [][] tab, int width, int height, int pos_i, int pos_j) {
|
||||||
|
int i, j;
|
||||||
|
for (i = 0; i < height; i++) {
|
||||||
|
for (j = 0; j < width; j++) {
|
||||||
|
System.out.print("\033[" + (i + pos_i) + ";" + (j*2 + pos_j) + "H");
|
||||||
|
switch (tab[i][j]) {
|
||||||
|
case -1:
|
||||||
|
System.out.printf(" X");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 0:
|
||||||
|
System.out.printf(" ");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
System.out.printf(" |");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 2:
|
||||||
|
System.out.printf(" -");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 3:
|
||||||
|
System.out.printf(" +");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 4:
|
||||||
|
System.out.printf(" /");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 5:
|
||||||
|
System.out.printf(" /");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 6:
|
||||||
|
System.out.printf(" \\");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 7:
|
||||||
|
System.out.printf(" \\");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 10:
|
||||||
|
System.out.printf(" ^");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 11:
|
||||||
|
System.out.printf(" v");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 12:
|
||||||
|
System.out.printf(" >");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 13:
|
||||||
|
System.out.printf(" <");
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
System.out.printf("%2d", tab[i][j]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
System.out.print("\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void resetUniverse() {
|
||||||
|
for (int i = 1; i < this.height - 1; i++) {
|
||||||
|
for (int j = 1; j < this.width - 1; j++) {
|
||||||
|
if (this.grid[i][j] != 10 && this.grid[i][j] != 11 && this.grid[i][j] != 12 && this.grid[i][j] != 13 && this.grid[i][j] != 0 && this.grid[i][j] != -1) {
|
||||||
|
this.grid[i][j] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void resetUniverseObstacles() {
|
||||||
|
for (int i = 1; i < this.height - 1; i++) {
|
||||||
|
for (int j = 1; j < this.width - 1; j++) {
|
||||||
|
if (this.grid[i][j] != 10 && this.grid[i][j] != 11 && this.grid[i][j] != 12 && this.grid[i][j] != 13 && this.grid[i][j] != 0) {
|
||||||
|
this.grid[i][j] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void changeUniverseDim(int width, int height) {
|
||||||
|
int [][] newgrid = new int[height][width];
|
||||||
|
|
||||||
|
for (int i = 1; i < height - 1; i++) {
|
||||||
|
for (int j = 1; j < width - 1; j++) {
|
||||||
|
newgrid[i][j] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 1; i < height - 1 && i < this.height - 1; i++) {
|
||||||
|
for (int j = 1; j < width - 1 && j < this.width - 1; j++) {
|
||||||
|
newgrid[i][j] = this.grid[i][j];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < height; i++) {
|
||||||
|
newgrid[i][0] = -1;
|
||||||
|
newgrid[i][width - 1] = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int j = 0; j < width; j++) {
|
||||||
|
newgrid[height - 1][j] = -1;
|
||||||
|
newgrid[0][j] = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.grid = newgrid;
|
||||||
|
this.width = width;
|
||||||
|
this.height = height;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void changeUniverseStart(int pos_i, int pos_j, int dir) {
|
||||||
|
this.grid[this.start_i][start_j] = 0;
|
||||||
|
this.grid[pos_i][pos_j] = dir;
|
||||||
|
|
||||||
|
this.start_i = pos_i;
|
||||||
|
this.start_j = pos_j;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void addObstacle(int pos_i, int pos_j) {
|
||||||
|
if (this.grid[pos_i][pos_j] == 0) {
|
||||||
|
this.grid[pos_i][pos_j] = -1;
|
||||||
|
}
|
||||||
|
else {}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void removeObstacle(int pos_i, int pos_j) {
|
||||||
|
if (this.grid[pos_i][pos_j] == -1) {
|
||||||
|
this.grid[pos_i][pos_j] = 0;
|
||||||
|
}
|
||||||
|
else {}
|
||||||
|
}
|
||||||
|
|
||||||
|
public int possibleChoices(Situation s) {
|
||||||
|
int i = s.pos_i;
|
||||||
|
int j = s.pos_j;
|
||||||
|
int d = s.direction;
|
||||||
|
int c = s.nb_choix;
|
||||||
|
|
||||||
|
switch (c) {
|
||||||
|
case 0: {
|
||||||
|
switch (d) {
|
||||||
|
case 10: // north
|
||||||
|
if (this.grid[i - 1][j] == 0 || this.grid[i - 1][j] == 2) return 1; // front
|
||||||
|
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 11: // south
|
||||||
|
if (this.grid[i + 1][j] == 0 || this.grid[i + 1][j] == 2) return 1; // front
|
||||||
|
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 12: // east
|
||||||
|
if (this.grid[i][j + 1] == 0 || this.grid[i][j + 1] == 1) return 1; // front
|
||||||
|
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 13: //west
|
||||||
|
if (this.grid[i][j - 1] == 0 || this.grid[i][j - 1] == 1) return 1; // front
|
||||||
|
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
default: {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case 1: {
|
||||||
|
switch (d) {
|
||||||
|
case 10: // north
|
||||||
|
if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 11: // south
|
||||||
|
if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 12: // east
|
||||||
|
if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 13: //west
|
||||||
|
if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 2; // left
|
||||||
|
else if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
default: {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case 2: {
|
||||||
|
switch (d) {
|
||||||
|
case 10: // north
|
||||||
|
if (this.grid[i][j + 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 11: // south
|
||||||
|
if (this.grid[i][j - 1] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 12: // east
|
||||||
|
if (this.grid[i + 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
case 13: //west
|
||||||
|
if (this.grid[i - 1][j] == 0 && this.grid[i][j] == 0) return 3; // right
|
||||||
|
else return -1; // back
|
||||||
|
|
||||||
|
default: {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case 3:
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
default: return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean canEvolve(Situation s) {
|
||||||
|
return possibleChoices(s) != -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Situation evolve(Situation s) {
|
||||||
|
int i = s.pos_i;
|
||||||
|
int j = s.pos_j;
|
||||||
|
int d = s.direction;
|
||||||
|
int c = possibleChoices(s);
|
||||||
|
|
||||||
|
// new status of the box
|
||||||
|
|
||||||
|
if (c == 1 && (d == 10 || d == 11)) {
|
||||||
|
if (this.grid[i][j] == 0) {
|
||||||
|
this.grid[i][j] = 1;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
} else {
|
||||||
|
this.grid[i][j] = 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (c == 1 && (d == 12 || d == 13)) {
|
||||||
|
if (this.grid[i][j] == 0) {
|
||||||
|
this.grid[i][j] = 2;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
} else {
|
||||||
|
this.grid[i][j] = 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ((c == 3 && d == 10) || (c == 2 && d == 13)) {
|
||||||
|
this.grid[i][j] = 4;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
this.nb_mirors ++;
|
||||||
|
}
|
||||||
|
if ((c == 2 && d == 12) || (c == 3 && d == 11)) {
|
||||||
|
this.grid[i][j] = 5;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
this.nb_mirors ++;
|
||||||
|
}
|
||||||
|
if ((c == 2 && d == 10) || (c == 3 && d == 12)) {
|
||||||
|
this.grid[i][j] = 6;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
this.nb_mirors ++;
|
||||||
|
}
|
||||||
|
if ((c == 2 && d == 11) || (c == 3 && d == 13)) {
|
||||||
|
this.grid[i][j] = 7;
|
||||||
|
this.filled_boxes ++;
|
||||||
|
this.nb_mirors ++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// changing the position of the situation
|
||||||
|
|
||||||
|
if (c == 1 && d == 10 || c == 2 && d == 12 || c == 3 && d == 13) {
|
||||||
|
i --;
|
||||||
|
d = 10;
|
||||||
|
}
|
||||||
|
else if (c == 1 && d == 11 || c == 2 && d == 13 || c == 3 && d == 12) {
|
||||||
|
i ++;
|
||||||
|
d = 11;
|
||||||
|
}
|
||||||
|
else if (c == 1 && d == 12 || c == 2 && d == 11 || c == 3 && d == 10) {
|
||||||
|
j ++;
|
||||||
|
d = 12;
|
||||||
|
}
|
||||||
|
else if (c == 1 && d == 13 || c == 2 && d == 10 || c == 3 && d == 11) {
|
||||||
|
j --;
|
||||||
|
d = 13;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new Situation(i, j, d, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void reset(Situation s) {
|
||||||
|
int i = s.pos_i;
|
||||||
|
int j = s.pos_j;
|
||||||
|
int d = s.direction;
|
||||||
|
|
||||||
|
if (this.grid[i][j] == 3) {
|
||||||
|
if (d == 10 || d == 11) {
|
||||||
|
this.grid[i][j] = 2;
|
||||||
|
} else {
|
||||||
|
this.grid[i][j] = 1;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (this.grid[i][j] == 4 || this.grid[i][j] == 5 || this.grid[i][j] == 6 || this.grid[i][j] == 7) {this.nb_mirors--;}
|
||||||
|
this.filled_boxes--;
|
||||||
|
this.grid[i][j] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void save(String fileName) {
|
||||||
|
try {
|
||||||
|
File file = new File("./saves/" + fileName + ".txt");
|
||||||
|
|
||||||
|
file.createNewFile();
|
||||||
|
|
||||||
|
FileWriter writer = new FileWriter("./saves/" + fileName + ".txt");
|
||||||
|
writer.write((this.height - 2) + "\n" + (this.width - 2) + "\n");
|
||||||
|
|
||||||
|
for (int i = 1; i < this.height - 1; i++) {
|
||||||
|
for (int j = 1; j < this.width - 1; j++) {
|
||||||
|
if (this.grid[i][j] == 10 || this.grid[i][j] == 11 || this.grid[i][j] == 12 || this.grid[i][j] == 13) writer.write(this.grid[i][j] + "\n" + i + "\n" + j + "\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 1; i < this.height - 1; i++) {
|
||||||
|
for (int j = 1; j < this.width - 1; j++) {
|
||||||
|
if (this.grid[i][j] == -1) writer.write(i + "\n" + j + "\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
writer.close();
|
||||||
|
}
|
||||||
|
catch (Exception e) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getFilledBoxes() {
|
||||||
|
return this.filled_boxes;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getNbMirrors() {
|
||||||
|
return this.nb_mirors;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int[][] getGrid() {
|
||||||
|
return this.grid;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int[][] copyGrid() {
|
||||||
|
int [][] newGrid = new int[this.height][this.width];
|
||||||
|
|
||||||
|
for (int i = 0; i < this.height; i++) {
|
||||||
|
for (int j = 0; j < this.width; j++) {
|
||||||
|
newGrid[i][j] = this.grid[i][j];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return newGrid;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getWidth() {
|
||||||
|
return this.width;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getHeight() {
|
||||||
|
return this.height;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int[] getStartCoords() {
|
||||||
|
int [] tab = new int[2];
|
||||||
|
tab[0] = this.start_i;
|
||||||
|
tab[1] = this.start_j;
|
||||||
|
return tab;
|
||||||
|
}
|
||||||
|
}
|
291
userInterface/Grid.java
Normal file
|
@ -0,0 +1,291 @@
|
||||||
|
package userInterface;
|
||||||
|
|
||||||
|
import javax.swing.JButton;
|
||||||
|
import javax.swing.JFrame;
|
||||||
|
import javax.swing.JPanel;
|
||||||
|
|
||||||
|
import java.awt.Dimension;
|
||||||
|
import java.awt.Color;
|
||||||
|
import java.awt.GridBagConstraints;
|
||||||
|
import java.awt.GridLayout;
|
||||||
|
import java.awt.Insets;
|
||||||
|
|
||||||
|
import javax.swing.*;
|
||||||
|
import java.awt.event.*;
|
||||||
|
import java.awt.*;
|
||||||
|
import java.awt.event.ActionEvent;
|
||||||
|
import java.awt.event.ActionListener;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.File;
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import java.net.URL;
|
||||||
|
|
||||||
|
import universe.Universe;
|
||||||
|
import universe.Stack;
|
||||||
|
import universe.Situation;
|
||||||
|
|
||||||
|
import java.time.Instant;
|
||||||
|
|
||||||
|
public class Grid extends JPanel {
|
||||||
|
private int width;
|
||||||
|
private int height;
|
||||||
|
private JButton[][] mat;
|
||||||
|
private int selected;
|
||||||
|
private Universe universe;
|
||||||
|
private int button_width, button_height;
|
||||||
|
private int refreshRate;
|
||||||
|
private boolean solving;
|
||||||
|
private int display;
|
||||||
|
|
||||||
|
public Grid(int width, int height, Universe universe, int refreshRate, int display) {
|
||||||
|
super(new GridLayout(height, width));
|
||||||
|
this.width = width;
|
||||||
|
this.height = height;
|
||||||
|
this.selected = 0;
|
||||||
|
this.universe = universe;
|
||||||
|
this.button_width = 600 / this.height;
|
||||||
|
this.button_height = button_width;
|
||||||
|
this.refreshRate = refreshRate;
|
||||||
|
this.solving = false;
|
||||||
|
this.display = display;
|
||||||
|
|
||||||
|
this.mat = new JButton[height][width];
|
||||||
|
|
||||||
|
for (int i = 0; i < this.height; i++) {
|
||||||
|
for (int j = 0; j < this.width; j++) {
|
||||||
|
this.mat[i][j] = new JButton();
|
||||||
|
|
||||||
|
this.mat[i][j].setPreferredSize(new Dimension(this.button_width, this.button_height));
|
||||||
|
|
||||||
|
final int coord_i = i;
|
||||||
|
final int coord_j = j;
|
||||||
|
|
||||||
|
this.mat[i][j].addActionListener(e -> {
|
||||||
|
if (solving) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.universe.resetUniverse();
|
||||||
|
|
||||||
|
switch (this.universe.getGrid()[coord_i + 1][coord_j + 1]) {
|
||||||
|
case 0:
|
||||||
|
if (this.selected == 1) {
|
||||||
|
this.universe.changeUniverseStart(coord_i + 1, coord_j + 1, 10);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.universe.addObstacle(coord_i + 1, coord_j + 1);
|
||||||
|
break;
|
||||||
|
case -1:
|
||||||
|
this.universe.removeObstacle(coord_i + 1, coord_j + 1);
|
||||||
|
break;
|
||||||
|
case 10:
|
||||||
|
if (this.selected == 1) {
|
||||||
|
this.universe.changeUniverseStart(coord_i + 1, coord_j + 1, 11);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 11:
|
||||||
|
if (this.selected == 1) {
|
||||||
|
this.universe.changeUniverseStart(coord_i + 1, coord_j + 1, 12);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 12:
|
||||||
|
if (this.selected == 1) {
|
||||||
|
this.universe.changeUniverseStart(coord_i + 1, coord_j + 1, 13);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 13:
|
||||||
|
if (this.selected == 1) {
|
||||||
|
this.universe.changeUniverseStart(coord_i + 1, coord_j + 1, 10);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.printUniverseGrid(this.universe.getGrid());
|
||||||
|
});
|
||||||
|
|
||||||
|
super.add(this.mat[i][j]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.printUniverseGrid(this.universe.getGrid());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setSelected(int selected) {
|
||||||
|
this.selected = selected;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRefreshRate(int refreshRate) {
|
||||||
|
this.refreshRate = refreshRate;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setSolving(boolean solving) {
|
||||||
|
this.solving = solving;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDisplay(int display) {
|
||||||
|
this.display = display;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void printUniverseGrid(int [][] universeGrid) {
|
||||||
|
for (int i = 0; i < this.height; i++) {
|
||||||
|
for (int j = 0; j < this.width; j ++) {
|
||||||
|
Image photo;
|
||||||
|
switch (universeGrid[i + 1][j + 1]) {
|
||||||
|
case -1:
|
||||||
|
this.changeButtonState(i, j, "../images/wall.png");
|
||||||
|
break;
|
||||||
|
case 0:
|
||||||
|
this.changeButtonState(i, j, null);
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
this.changeButtonState(i, j, "../images/verticalLaser.png");
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
this.changeButtonState(i, j, "../images/horizontalLaser.png");
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
this.changeButtonState(i, j, "../images/crossLaser.png");
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
this.changeButtonState(i, j, "../images/miror1.png");
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
this.changeButtonState(i, j, "../images/miror2.png");
|
||||||
|
break;
|
||||||
|
case 6:
|
||||||
|
this.changeButtonState(i, j, "../images/miror3.png");
|
||||||
|
break;
|
||||||
|
case 7:
|
||||||
|
this.changeButtonState(i, j, "../images/miror4.png");
|
||||||
|
break;
|
||||||
|
case 10:
|
||||||
|
this.changeButtonState(i, j, "../images/startUp.png");
|
||||||
|
break;
|
||||||
|
case 11:
|
||||||
|
this.changeButtonState(i, j, "../images/startBot.png");
|
||||||
|
break;
|
||||||
|
case 12:
|
||||||
|
this.changeButtonState(i, j, "../images/startRight.png");
|
||||||
|
break;
|
||||||
|
case 13:
|
||||||
|
this.changeButtonState(i, j, "../images/startLeft.png");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void changeButtonState(int coord_i, int coord_j, String url) {
|
||||||
|
if (url == null) {
|
||||||
|
Thread t = new Thread(new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
mat[coord_i][coord_j].setBackground(Color.WHITE);
|
||||||
|
mat[coord_i][coord_j].setIcon(null);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
t.start();
|
||||||
|
} else {
|
||||||
|
Thread t = new Thread(new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
Image image = new ImageIcon(getClass().getResource(url)).getImage().getScaledInstance(button_width, button_height, Image.SCALE_SMOOTH);
|
||||||
|
mat[coord_i][coord_j].setIcon(new ImageIcon(image));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
t.start();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void reset() {
|
||||||
|
this.universe.resetUniverse();
|
||||||
|
this.printUniverseGrid(this.universe.getGrid());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void alert(String message) {
|
||||||
|
JOptionPane.showMessageDialog(this, message);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void solve() {
|
||||||
|
this.universe.resetUniverse();
|
||||||
|
final Universe universe = this.universe;
|
||||||
|
|
||||||
|
this.solving = true;
|
||||||
|
|
||||||
|
Thread computeThread = new Thread(new Runnable() {
|
||||||
|
int [][] bestGrid;
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
int [] startCoords = universe.getStartCoords();
|
||||||
|
|
||||||
|
int firstState_i = startCoords[0];
|
||||||
|
int firstState_j = startCoords[1];
|
||||||
|
int start_dir = universe.getGrid()[startCoords[0]][startCoords[1]];
|
||||||
|
|
||||||
|
if (start_dir == 10) firstState_i = firstState_i - 1;
|
||||||
|
else if (start_dir == 11) firstState_i = firstState_i + 1;
|
||||||
|
else if (start_dir == 12) firstState_j = firstState_j + 1;
|
||||||
|
else if (start_dir == 13) firstState_j = firstState_j - 1;
|
||||||
|
|
||||||
|
Stack <Situation> stack = new Stack <Situation>();
|
||||||
|
Situation currentState = new Situation(firstState_i, firstState_j, start_dir, 0);
|
||||||
|
|
||||||
|
this.bestGrid = universe.copyGrid();
|
||||||
|
int best_filled_boxes = 0;
|
||||||
|
int best_nb_mirrors = 0;
|
||||||
|
|
||||||
|
long start = Instant.now().toEpochMilli();
|
||||||
|
long lastRefresh = start;
|
||||||
|
|
||||||
|
do {
|
||||||
|
if (universe.canEvolve(currentState)) {
|
||||||
|
stack.push(currentState.copy(universe.possibleChoices(currentState)));
|
||||||
|
currentState = universe.evolve(currentState);
|
||||||
|
|
||||||
|
if (display == 1 && Instant.now().toEpochMilli() - lastRefresh > refreshRate) {
|
||||||
|
lastRefresh = Instant.now().toEpochMilli();
|
||||||
|
printUniverseGrid(universe.getGrid());
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((universe.getFilledBoxes() > best_filled_boxes) || (universe.getFilledBoxes() == best_filled_boxes && universe.getNbMirrors() < best_nb_mirrors)) {
|
||||||
|
this.bestGrid = universe.copyGrid();
|
||||||
|
best_filled_boxes = universe.getFilledBoxes();
|
||||||
|
best_nb_mirrors = universe.getNbMirrors();
|
||||||
|
|
||||||
|
if (display == 2 && Instant.now().toEpochMilli() - lastRefresh > refreshRate) {
|
||||||
|
lastRefresh = Instant.now().toEpochMilli();
|
||||||
|
printUniverseGrid(this.bestGrid);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (stack.size() > 0) {
|
||||||
|
currentState = stack.pop();
|
||||||
|
universe.reset(currentState);
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (display == 0 && Instant.now().toEpochMilli() - lastRefresh > refreshRate) {
|
||||||
|
lastRefresh = Instant.now().toEpochMilli();
|
||||||
|
printUniverseGrid(universe.getGrid());
|
||||||
|
}
|
||||||
|
} while (stack.size() != 0 && solving == true);
|
||||||
|
|
||||||
|
printUniverseGrid(bestGrid);
|
||||||
|
|
||||||
|
solving = false;
|
||||||
|
String message = "Solved in " + ((Instant.now().toEpochMilli() - start)/1000) + "s and " + ((Instant.now().toEpochMilli() - start)%1000) + "ms \nMirrors : " + best_nb_mirrors + "\nLaser length : " + best_filled_boxes;
|
||||||
|
alert(message);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
computeThread.start();
|
||||||
|
}
|
||||||
|
}
|
14
userInterface/UserInterface.java
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
package userInterface;
|
||||||
|
|
||||||
|
import universe.*;
|
||||||
|
|
||||||
|
public class UserInterface extends Thread {
|
||||||
|
private Window window;
|
||||||
|
|
||||||
|
public UserInterface(Universe universe) {
|
||||||
|
window = new Window(universe);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void run() {
|
||||||
|
}
|
||||||
|
}
|
275
userInterface/Window.java
Normal file
|
@ -0,0 +1,275 @@
|
||||||
|
package userInterface;
|
||||||
|
|
||||||
|
import java.awt.Dimension;
|
||||||
|
import java.awt.Color;
|
||||||
|
import java.awt.GridBagConstraints;
|
||||||
|
import java.awt.GridLayout;
|
||||||
|
import java.awt.Insets;
|
||||||
|
|
||||||
|
import java.io.FileReader;
|
||||||
|
import java.io.BufferedReader;
|
||||||
|
import java.io.File;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.stream.Stream;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
import javax.swing.*;
|
||||||
|
import java.awt.event.*;
|
||||||
|
import java.awt.*;
|
||||||
|
import java.awt.event.ActionEvent;
|
||||||
|
import java.awt.event.ActionListener;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.File;
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import java.net.URL;
|
||||||
|
|
||||||
|
import universe.Universe;
|
||||||
|
|
||||||
|
public class Window extends JFrame {
|
||||||
|
|
||||||
|
private JPanel panel;
|
||||||
|
private JMenuBar menuBar;
|
||||||
|
private Grid grid;
|
||||||
|
private Universe universe;
|
||||||
|
|
||||||
|
public Window(Universe universe) {
|
||||||
|
super("Laser Finder");
|
||||||
|
|
||||||
|
this.universe = universe;
|
||||||
|
|
||||||
|
panel = new JPanel();
|
||||||
|
panel.setPreferredSize(new Dimension(1000,800));
|
||||||
|
panel.setBackground(Color.decode("#EBEBD3"));
|
||||||
|
|
||||||
|
menuBar = new JMenuBar();
|
||||||
|
|
||||||
|
JMenu fichierMenu = new JMenu("File");
|
||||||
|
JMenu aideMenu = new JMenu("Help");
|
||||||
|
JMenu toolsMenu = new JMenu("Tools");
|
||||||
|
JMenu solveMenu = new JMenu("Solve");
|
||||||
|
JMenu displayMenu = new JMenu("Display");
|
||||||
|
JMenu refreshRate = new JMenu("Refresh Rate");
|
||||||
|
|
||||||
|
URL newUrl = getClass().getResource("../images/new.png");
|
||||||
|
URL openUrl = getClass().getResource("../images/open.png");
|
||||||
|
URL saveUrl = getClass().getResource("../images/save.png");
|
||||||
|
|
||||||
|
ImageIcon nouveauIcon = new ImageIcon(newUrl.getPath());
|
||||||
|
ImageIcon openIcon = new ImageIcon(openUrl.getPath());
|
||||||
|
ImageIcon saveIcon = new ImageIcon(saveUrl.getPath());
|
||||||
|
|
||||||
|
JMenuItem nouveauItem = new JMenuItem("New", nouveauIcon);
|
||||||
|
JMenuItem ouvrirItem = new JMenuItem("Open", openIcon);
|
||||||
|
JMenuItem enregistrerItem = new JMenuItem("Save", saveIcon);
|
||||||
|
|
||||||
|
JMenuItem apropos = new JMenuItem("About");
|
||||||
|
JMenuItem regles = new JMenuItem("Rules");
|
||||||
|
|
||||||
|
JRadioButtonMenuItem radioWall = new JRadioButtonMenuItem("Wall");
|
||||||
|
JRadioButtonMenuItem radioStart = new JRadioButtonMenuItem("Start");
|
||||||
|
|
||||||
|
radioWall.setSelected(true);
|
||||||
|
|
||||||
|
ButtonGroup buttonGroup = new ButtonGroup();
|
||||||
|
|
||||||
|
buttonGroup.add(radioWall);
|
||||||
|
buttonGroup.add(radioStart);
|
||||||
|
|
||||||
|
JMenuItem changeSize = new JMenuItem("Change Size");
|
||||||
|
JMenuItem reset = new JMenuItem("Reset");
|
||||||
|
|
||||||
|
JMenuItem solve = new JMenuItem("Start");
|
||||||
|
JMenuItem stop = new JMenuItem("Stop");
|
||||||
|
|
||||||
|
JRadioButtonMenuItem radio10ms = new JRadioButtonMenuItem("10ms");
|
||||||
|
JRadioButtonMenuItem radio200ms = new JRadioButtonMenuItem("200ms");
|
||||||
|
JRadioButtonMenuItem radio500ms = new JRadioButtonMenuItem("500ms");
|
||||||
|
JRadioButtonMenuItem radio1000ms = new JRadioButtonMenuItem("1000ms");
|
||||||
|
|
||||||
|
radio10ms.setSelected(true);
|
||||||
|
|
||||||
|
ButtonGroup refreshRates = new ButtonGroup();
|
||||||
|
|
||||||
|
refreshRates.add(radio10ms);
|
||||||
|
refreshRates.add(radio200ms);
|
||||||
|
refreshRates.add(radio500ms);
|
||||||
|
refreshRates.add(radio1000ms);
|
||||||
|
|
||||||
|
JMenuItem displayAll = new JMenuItem("Display progress and regress");
|
||||||
|
JMenuItem displayProgress = new JMenuItem("Display only progress");
|
||||||
|
JMenuItem displayBest = new JMenuItem("Display best grid");
|
||||||
|
|
||||||
|
fichierMenu.add(nouveauItem);
|
||||||
|
fichierMenu.add(ouvrirItem);
|
||||||
|
fichierMenu.add(enregistrerItem);
|
||||||
|
|
||||||
|
aideMenu.add(apropos);
|
||||||
|
aideMenu.add(regles);
|
||||||
|
|
||||||
|
toolsMenu.add(radioWall);
|
||||||
|
toolsMenu.add(radioStart);
|
||||||
|
toolsMenu.addSeparator();
|
||||||
|
toolsMenu.add(changeSize);
|
||||||
|
toolsMenu.addSeparator();
|
||||||
|
toolsMenu.add(reset);
|
||||||
|
|
||||||
|
solveMenu.add(solve);
|
||||||
|
solveMenu.add(stop);
|
||||||
|
|
||||||
|
refreshRate.add(radio10ms);
|
||||||
|
refreshRate.add(radio200ms);
|
||||||
|
refreshRate.add(radio500ms);
|
||||||
|
refreshRate.add(radio1000ms);
|
||||||
|
|
||||||
|
displayMenu.add(refreshRate);
|
||||||
|
displayMenu.addSeparator();
|
||||||
|
displayMenu.add(displayAll);
|
||||||
|
displayMenu.add(displayProgress);
|
||||||
|
displayMenu.add(displayBest);
|
||||||
|
|
||||||
|
menuBar.add(fichierMenu);
|
||||||
|
menuBar.add(aideMenu);
|
||||||
|
menuBar.add(toolsMenu);
|
||||||
|
menuBar.add(solveMenu);
|
||||||
|
menuBar.add(displayMenu);
|
||||||
|
|
||||||
|
nouveauItem.addActionListener(e -> {
|
||||||
|
this.universe.changeUniverseStart(1, 1, 11);
|
||||||
|
this.universe.changeUniverseDim(5, 5);
|
||||||
|
this.universe.resetUniverseObstacles();
|
||||||
|
this.panel.remove(this.grid);
|
||||||
|
this.grid = new Grid(3, 3, this.universe, 10, 0);
|
||||||
|
this.panel.add(this.grid);
|
||||||
|
super.pack();
|
||||||
|
super.repaint();
|
||||||
|
});
|
||||||
|
|
||||||
|
enregistrerItem.addActionListener(e -> {
|
||||||
|
String name = JOptionPane.showInputDialog("Choose the universe name");
|
||||||
|
this.universe.save(name);
|
||||||
|
});
|
||||||
|
|
||||||
|
ouvrirItem.addActionListener(e -> {
|
||||||
|
String message = "Choose the universe among those : ";
|
||||||
|
|
||||||
|
Set<String> files = Stream.of(new File("./saves").listFiles()).filter(file -> !file.isDirectory()).map(File::getName).collect(Collectors.toSet());
|
||||||
|
|
||||||
|
for (String element : files) {
|
||||||
|
message += "\n- " + element.replace(".txt", "");
|
||||||
|
}
|
||||||
|
|
||||||
|
String name = JOptionPane.showInputDialog(message);
|
||||||
|
|
||||||
|
try {
|
||||||
|
BufferedReader reader = new BufferedReader(new FileReader("./saves/" + name + ".txt"));
|
||||||
|
int universe_height = Integer.valueOf(reader.readLine());
|
||||||
|
int universe_width = Integer.valueOf(reader.readLine());
|
||||||
|
int start_dir = Integer.valueOf(reader.readLine());
|
||||||
|
int start_i = Integer.valueOf(reader.readLine());
|
||||||
|
int start_j = Integer.valueOf(reader.readLine());
|
||||||
|
|
||||||
|
|
||||||
|
this.universe.changeUniverseDim(universe_width + 2, universe_height + 2);
|
||||||
|
this.universe.changeUniverseStart(start_i, start_j, start_dir);
|
||||||
|
this.universe.resetUniverseObstacles();
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
try {
|
||||||
|
int pos1 = Integer.valueOf(reader.readLine());
|
||||||
|
int pos2 = Integer.valueOf(reader.readLine());
|
||||||
|
|
||||||
|
this.universe.addObstacle(pos1, pos2);
|
||||||
|
}
|
||||||
|
catch (Exception error) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.panel.remove(this.grid);
|
||||||
|
this.grid = new Grid(universe_width, universe_height, this.universe, 10, 0);
|
||||||
|
this.panel.add(this.grid);
|
||||||
|
super.pack();
|
||||||
|
super.repaint();
|
||||||
|
}
|
||||||
|
catch (Exception error) {}
|
||||||
|
});
|
||||||
|
|
||||||
|
regles.addActionListener(e -> {
|
||||||
|
JOptionPane.showMessageDialog(this, "Définissez la taille du plateau ainsi que l'orientation du laser, enfin ajoutez des obstacles et laissez le programme trouver le bon chemin !");
|
||||||
|
});
|
||||||
|
|
||||||
|
changeSize.addActionListener(e -> {
|
||||||
|
int width = Integer.valueOf(JOptionPane.showInputDialog("Choose the width"));
|
||||||
|
int height = Integer.valueOf(JOptionPane.showInputDialog("Choose the height"));
|
||||||
|
|
||||||
|
this.universe.changeUniverseDim(width + 2, height + 2);
|
||||||
|
this.panel.remove(this.grid);
|
||||||
|
this.grid = new Grid(width, height, this.universe, 10, 0);
|
||||||
|
this.panel.add(this.grid);
|
||||||
|
super.pack();
|
||||||
|
super.repaint();
|
||||||
|
});
|
||||||
|
|
||||||
|
radioWall.addActionListener(e -> {
|
||||||
|
this.grid.setSelected(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
radioStart.addActionListener(e -> {
|
||||||
|
this.grid.setSelected(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
solve.addActionListener(e -> {
|
||||||
|
this.grid.solve();
|
||||||
|
});
|
||||||
|
|
||||||
|
stop.addActionListener(e -> {
|
||||||
|
this.grid.setSolving(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
reset.addActionListener(e -> {
|
||||||
|
this.grid.reset();
|
||||||
|
});
|
||||||
|
|
||||||
|
radio10ms.addActionListener(e -> {
|
||||||
|
this.grid.setRefreshRate(10);
|
||||||
|
});
|
||||||
|
|
||||||
|
radio200ms.addActionListener(e -> {
|
||||||
|
this.grid.setRefreshRate(200);
|
||||||
|
});
|
||||||
|
|
||||||
|
radio500ms.addActionListener(e -> {
|
||||||
|
this.grid.setRefreshRate(500);
|
||||||
|
});
|
||||||
|
|
||||||
|
radio1000ms.addActionListener(e -> {
|
||||||
|
this.grid.setRefreshRate(1000);
|
||||||
|
});
|
||||||
|
|
||||||
|
displayAll.addActionListener(e -> {
|
||||||
|
this.grid.setDisplay(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
displayProgress.addActionListener(e -> {
|
||||||
|
this.grid.setDisplay(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
displayBest.addActionListener(e -> {
|
||||||
|
this.grid.setDisplay(2);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.grid = new Grid(this.universe.getHeight() - 2, this.universe.getWidth() - 2, this.universe, 10, 0);
|
||||||
|
this.panel.add(grid, BorderLayout.CENTER);
|
||||||
|
|
||||||
|
super.setJMenuBar(menuBar);
|
||||||
|
super.setContentPane(this.panel);
|
||||||
|
|
||||||
|
super.setLocationRelativeTo(null);
|
||||||
|
super.setLocation(1000, 400);
|
||||||
|
super.pack();
|
||||||
|
super.setVisible(true);
|
||||||
|
super.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
|
||||||
|
}
|
||||||
|
}
|