nettoyage + lisibilité code + changement structure

This commit is contained in:
2026-01-26 06:39:49 -05:00
parent 25f8dcdc76
commit b97b9cef69
17 changed files with 794 additions and 396 deletions

View File

@@ -9,15 +9,44 @@ import fr.iut_fbleau.GameAPI.Result;
import java.util.ArrayDeque;
import java.util.Iterator;
/**
* La classe <code>AvalamBoard</code>
*
* Représente le plateau et les règles du jeu Avalam.
* Cette classe étend <code>AbstractBoard</code> (GameAPI) et fournit :
* - la génération des coups (iterator)
* - le test de légalité (isLegal)
* - lapplication dun coup (doPly)
* - la détection de fin de partie (isGameOver)
* - le calcul du résultat (getResult)
*/
public class AvalamBoard extends AbstractBoard {
//Attributs
/** Taille du plateau Avalam (9x9). */
public static final int SIZE = 9;
/** Hauteur maximale autorisée pour une tour après fusion. */
private static final int MAX_HEIGHT = 5;
/** Grille du plateau : chaque case contient une tour (Tower) ou null si vide. */
private final Tower[][] grid;
/** Indique si la partie est terminée (mémoïsation). */
private boolean gameOver = false;
/** Résultat de la partie si elle est terminée (mémoïsation). */
private Result result = null;
//Constructeur
/**
* Construit un plateau Avalam à partir dune grille initiale et dun joueur qui commence.
*
* @param initialGrid grille initiale (Tower ou null)
* @param startingPlayer joueur qui commence (PLAYER1 ou PLAYER2)
*/
public AvalamBoard(Tower[][] initialGrid, Player startingPlayer) {
super(startingPlayer, new ArrayDeque<>());
this.grid = new Tower[SIZE][SIZE];
@@ -27,10 +56,24 @@ public class AvalamBoard extends AbstractBoard {
this.grid[r][c] = initialGrid[r][c];
}
/**
* Construit un plateau Avalam à partir dune grille initiale.
* Par défaut, PLAYER1 commence.
*
* @param initialGrid grille initiale (Tower ou null)
*/
public AvalamBoard(Tower[][] initialGrid) {
this(initialGrid, Player.PLAYER1);
}
/**
* Constructeur interne utilisé par safeCopy().
*
* @param grid grille à réutiliser
* @param current joueur courant
* @param gameOver état “partie terminée”
* @param result résultat mémorisé
*/
private AvalamBoard(Tower[][] grid, Player current, boolean gameOver, Result result) {
super(current, new ArrayDeque<>());
this.grid = grid;
@@ -38,24 +81,61 @@ public class AvalamBoard extends AbstractBoard {
this.result = result;
}
//Méthodes
/**
* Retourne la tour située à la position (row, col), ou null si hors bornes ou vide.
*
* @param row ligne
* @param col colonne
* @return tour présente ou null
*/
public Tower getTowerAt(int row, int col) {
return inBounds(row, col) ? grid[row][col] : null;
}
/**
* Teste si une position est à lintérieur du plateau.
*
* @param r ligne
* @param c colonne
* @return true si (r,c) est dans [0..SIZE-1]
*/
private boolean inBounds(int r, int c) {
return r >= 0 && r < SIZE && c >= 0 && c < SIZE;
}
/**
* Teste si deux cases sont adjacentes (8-voisinage).
*
* @param r1 ligne source
* @param c1 colonne source
* @param r2 ligne destination
* @param c2 colonne destination
* @return true si les cases sont voisines et différentes
*/
private boolean areAdjacent(int r1, int c1, int r2, int c2) {
int dr = Math.abs(r1 - r2);
int dc = Math.abs(c1 - c2);
return (dr <= 1 && dc <= 1 && !(dr == 0 && dc == 0));
}
/**
* Associe un joueur GameAPI à une couleur Avalam.
*
* @param p joueur (PLAYER1/PLAYER2)
* @return couleur correspondante (YELLOW/RED)
*/
private Color colorForPlayer(Player p) {
return (p == Player.PLAYER1 ? Color.YELLOW : Color.RED);
}
/**
* Indique si la partie est terminée.
* Ici : fin lorsque litérateur de coups légaux ne produit plus aucun coup.
*
* @return true si aucun coup nest possible
*/
@Override
public boolean isGameOver() {
if (gameOver) return true;
@@ -67,6 +147,12 @@ public class AvalamBoard extends AbstractBoard {
return true;
}
/**
* Retourne le résultat si la partie est terminée.
* Règle utilisée ici : comparaison du nombre de tours contrôlées par chaque couleur.
*
* @return WIN / LOSS / DRAW ou null si partie non terminée
*/
@Override
public Result getResult() {
if (!isGameOver()) return null;
@@ -91,6 +177,19 @@ public class AvalamBoard extends AbstractBoard {
return result;
}
/**
* Teste si un coup est légal selon les règles implémentées :
* - coup de type AvalamPly
* - source/destination dans le plateau et différentes
* - source et destination non null
* - la tour source appartient au joueur courant (couleur du sommet)
* - cases adjacentes
* - couleurs différentes entre source et destination (règle de ce projet)
* - hauteur finale <= MAX_HEIGHT
*
* @param c coup à tester
* @return true si le coup est légal
*/
@Override
public boolean isLegal(AbstractPly c) {
if (!(c instanceof AvalamPly)) return false;
@@ -114,6 +213,14 @@ public class AvalamBoard extends AbstractBoard {
return true;
}
/**
* Applique un coup légal :
* - fusion de la tour source sur la destination
* - la case source devient vide
* - passage au joueur suivant via super.doPly
*
* @param c coup à jouer
*/
@Override
public void doPly(AbstractPly c) {
if (!isLegal(c)) throw new IllegalArgumentException("Coup illégal : " + c);
@@ -135,6 +242,12 @@ public class AvalamBoard extends AbstractBoard {
result = null;
}
/**
* Retourne un itérateur sur tous les coups légaux du joueur courant.
* Génération brute : pour chaque case et chaque voisin (8 directions), on teste isLegal().
*
* @return itérateur de coups possibles (AbstractPly)
*/
@Override
public Iterator<AbstractPly> iterator() {
java.util.List<AbstractPly> moves = new java.util.ArrayList<>();
@@ -159,6 +272,12 @@ public class AvalamBoard extends AbstractBoard {
return moves.iterator();
}
/**
* Retourne une copie “sûre” de létat du plateau.
* Ici, la grille est recopiée case par case (copie des références Tower).
*
* @return copie du plateau (IBoard)
*/
@Override
public IBoard safeCopy() {
Tower[][] newGrid = new Tower[SIZE][SIZE];