diff --git a/fr/iut_fbleau/Avalam/ArenaWindow.java b/fr/iut_fbleau/Avalam/ArenaWindow.java
index f6d0580..2a604ad 100644
--- a/fr/iut_fbleau/Avalam/ArenaWindow.java
+++ b/fr/iut_fbleau/Avalam/ArenaWindow.java
@@ -14,11 +14,14 @@ import java.util.ArrayList;
import java.util.List;
/**
- * Fenêtre pour le mode Arène.
- * Permet de sélectionner trois bots (Idiot, Alpha-Beta, Divin), de configurer la profondeur
- * de recherche pour les bots intelligents, de choisir le nombre de parties, et d'afficher les résultats.
- *
- * @version 1.0
+ * Fenêtre pour le mode Arène (bots vs bots).
+ *
+ * Elle permet :
+ * - de sélectionner deux bots parmi Idiot, Alpha-Beta et Divin ;
+ * - de configurer la profondeur de recherche pour les bots intelligents ;
+ * - de choisir le nombre de parties à jouer ;
+ * - d’afficher, dans un tableau, le résultat de chaque partie (gagnant ou erreur) ;
+ * - de revenir au menu principal ou de quitter entièrement le jeu.
*/
public class ArenaWindow extends JFrame {
@@ -55,14 +58,19 @@ public class ArenaWindow extends JFrame {
JButton startButton = new JButton("Lancer les parties");
startButton.addActionListener(e -> showConfigDialog());
buttonPanel.add(startButton);
-
+
JButton backButton = new JButton("Retour au menu");
backButton.addActionListener(e -> {
dispose(); // Ferme la fenêtre Arène
Main.showModeSelection(); // Affiche le menu principal
});
buttonPanel.add(backButton);
-
+
+ // Nouveau bouton pour quitter entièrement le jeu
+ JButton quitButton = new JButton("Quitter");
+ quitButton.addActionListener(e -> System.exit(0));
+ buttonPanel.add(quitButton);
+
add(buttonPanel, BorderLayout.SOUTH);
pack();
@@ -226,13 +234,22 @@ public class ArenaWindow extends JFrame {
}
}
- // Afficher un message de fin
- JOptionPane.showMessageDialog(
+ // Afficher un message de fin avec possibilité de quitter directement
+ Object[] options = {"OK", "Quitter le jeu"};
+ int choice = JOptionPane.showOptionDialog(
this,
"Toutes les parties sont terminées !",
"Arène terminée",
- JOptionPane.INFORMATION_MESSAGE
+ JOptionPane.DEFAULT_OPTION,
+ JOptionPane.INFORMATION_MESSAGE,
+ null,
+ options,
+ options[0]
);
+
+ if (choice == 1) {
+ System.exit(0);
+ }
}
/**
diff --git a/fr/iut_fbleau/Avalam/AvalamWindow.java b/fr/iut_fbleau/Avalam/AvalamWindow.java
index 1497478..5594021 100644
--- a/fr/iut_fbleau/Avalam/AvalamWindow.java
+++ b/fr/iut_fbleau/Avalam/AvalamWindow.java
@@ -1,7 +1,6 @@
package fr.iut_fbleau.Avalam;
import fr.iut_fbleau.Bot.AlphaBetaBot;
-// A FAIRE PLUS TARD (PVGOD)
import fr.iut_fbleau.Bot.DivineBot;
import fr.iut_fbleau.Bot.IdiotBot;
import fr.iut_fbleau.GameAPI.AbstractPly;
@@ -14,22 +13,25 @@ import java.awt.*;
/**
* La classe AvalamWindow
*
- * Fenêtre principale (interface graphique) du jeu Avalam.
- * Elle contient :
- * - le plateau (BoardView)
- * - l’affichage du score (ScoreView)
- * - l’affichage du joueur courant (TurnView)
- *
- * Elle pilote un objet AvalamBoard (moteur du jeu).
- * Elle peut fonctionner en mode :
- * - joueur vs joueur
- * - joueur vs bot idiot (aléatoire)
- * - joueur vs bot alpha (cut-off)
+ * Fenêtre principale (interface graphique) du jeu Avalam pour tous les modes
+ * hors Arène :
+ * - joueur vs joueur (PVP)
+ * - joueur vs bot idiot (PVBOT)
+ * - joueur vs bot alpha (PVALPHA)
* - joueur vs bot divin (PVGOD)
*
- * @version 1.0
- * Date :
- * Licence :
+ * Elle contient :
+ * - le plateau (BoardView)
+ * - l’affichage du score (ScoreView)
+ * - l’affichage du joueur courant (TurnView)
+ *
+ * Elle pilote un objet AvalamBoard (moteur du jeu) et,
+ * en fonction du {@link GameMode}, instancie le bot approprié
+ * (idiot, alpha-bêta ou divin).
+ *
+ * En fin de partie, elle ouvre une fenêtre de fin (EndGameDialog)
+ * affichant le gagnant, les scores et proposant les actions :
+ * « Rejouer », « Menu principal » ou « Quitter le jeu ».
*/
public class AvalamWindow extends JFrame {
@@ -50,6 +52,9 @@ public class AvalamWindow extends JFrame {
/** Mode de jeu sélectionné. */
private final GameMode mode;
+ /** Profondeur de recherche utilisée (utile pour les modes avec bot intelligent et pour rejouer). */
+ private final int searchDepth;
+
/** Joueur contrôlé par le bot (si actif). */
private final Player botPlayer = Player.PLAYER2;
@@ -59,18 +64,9 @@ public class AvalamWindow extends JFrame {
/** Bot Alpha-Beta (utilisé si mode PVALPHA). */
private final AlphaBetaBot alphaBot;
+ /** Bot Divin (utilisé si mode PVGOD). */
private final DivineBot divineBot;
- // A FAIRE PLUS TARD (PVGOD)
- // /** Bot Divin (utilisé si mode PVGOD). */
- // private final DivineBot divineBot;
-
- /**
- * A FAIRE PLUS TARD (PVGOD)
- * On garde l'attribut à null pour ne pas casser la compilation,
- * mais toute la logique PVGOD est désactivée/commentée.
- */
-
/** Indique si une animation de tour de bot est en cours. */
private boolean botAnimating = false;
@@ -87,7 +83,7 @@ public class AvalamWindow extends JFrame {
* Construit la fenêtre en fonction du mode choisi.
* Pour PVALPHA/PVGOD, la profondeur par défaut est 4.
*
- * @param mode mode de jeu
+ * @param mode mode de jeu (PVP, PVBOT, PVALPHA ou PVGOD)
*/
public AvalamWindow(GameMode mode) {
this(mode, 4);
@@ -95,22 +91,23 @@ public class AvalamWindow extends JFrame {
/**
* Construit la fenêtre en fonction du mode choisi.
- * Si le mode est PVALPHA ou PVGOD, la profondeur est utilisée comme cut-off.
+ * Si le mode est PVALPHA ou PVGOD, la profondeur est utilisée comme cut-off
+ * pour les bots Alpha-Beta et Divin.
*
- * @param mode mode de jeu
+ * @param mode mode de jeu
* @param alphaDepth profondeur de recherche pour Alpha-Beta / Bot Divin
*/
public AvalamWindow(GameMode mode, int alphaDepth) {
super("Avalam");
this.mode = mode;
+ this.searchDepth = Math.max(1, alphaDepth);
this.idiotBot = (mode == GameMode.PVBOT) ? new IdiotBot(botPlayer) : null;
- int depth = Math.max(1, alphaDepth);
+ int depth = this.searchDepth;
this.alphaBot = (mode == GameMode.PVALPHA) ? new AlphaBetaBot(botPlayer, depth) : null;
- // A FAIRE PLUS TARD (PVGOD)
this.divineBot = (mode == GameMode.PVGOD) ? new DivineBot(botPlayer, depth) : null;
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
@@ -169,28 +166,30 @@ public class AvalamWindow extends JFrame {
if (board.isGameOver()) {
Result res = board.getResult();
- String msg;
- switch (res) {
- case WIN:
- msg = "Le joueur jaune a gagné !";
- break;
- case LOSS:
- msg = "Le joueur rouge a gagné !";
- break;
- case DRAW:
- msg = "Égalité !";
- break;
- default:
- msg = "Fin de partie.";
- break;
- }
+ int scoreJaune = computeScore(Color.YELLOW);
+ int scoreRouge = computeScore(Color.RED);
- JOptionPane.showMessageDialog(
+ EndGameDialog dialog = new EndGameDialog(
this,
- msg,
- "Partie terminée",
- JOptionPane.INFORMATION_MESSAGE
+ res,
+ scoreJaune,
+ scoreRouge,
+ mode,
+ searchDepth,
+ // Rejouer : on ferme la fenêtre actuelle et on relance une nouvelle partie avec le même mode/profondeur
+ () -> SwingUtilities.invokeLater(() -> {
+ dispose();
+ new AvalamWindow(mode, searchDepth);
+ }),
+ // Menu principal : on ferme la fenêtre actuelle et on réaffiche le menu de mode de jeu
+ () -> SwingUtilities.invokeLater(() -> {
+ dispose();
+ Main.showModeSelection();
+ }),
+ // Quitter complètement l'application
+ () -> System.exit(0)
);
+ dialog.setVisible(true);
return;
}
@@ -220,12 +219,8 @@ public class AvalamWindow extends JFrame {
if (mode == GameMode.PVBOT && idiotBot == null) return;
if (mode == GameMode.PVALPHA && alphaBot == null) return;
- // A FAIRE PLUS TARD (PVGOD)
if (mode == GameMode.PVGOD && divineBot == null) return;
- // A FAIRE PLUS TARD (PVGOD)
- // Pour l'instant, si PVGOD est sélectionné, on ne joue pas de coup bot.
-
botAnimating = true;
// Désactiver les interactions du joueur pendant le tour du bot.
diff --git a/fr/iut_fbleau/Avalam/EndGameDialog.java b/fr/iut_fbleau/Avalam/EndGameDialog.java
new file mode 100644
index 0000000..dcbf32a
--- /dev/null
+++ b/fr/iut_fbleau/Avalam/EndGameDialog.java
@@ -0,0 +1,160 @@
+package fr.iut_fbleau.Avalam;
+
+import fr.iut_fbleau.GameAPI.Result;
+
+import javax.swing.*;
+import java.awt.*;
+
+/**
+ * Fenêtre de fin de partie.
+ *
+ * Elle est ouverte par {@link AvalamWindow} lorsque le moteur signale
+ * que la partie est terminée. Elle affiche :
+ * - le résultat (gagnant ou égalité) à partir du {@link Result} ;
+ * - le score détaillé (tours contrôlées par Jaune et Rouge) ;
+ * - le mode de jeu courant (PVP, PVBOT, PVALPHA, PVGOD, avec profondeur pour les bots intelligents).
+ *
+ * Elle propose également trois actions sous forme de boutons :
+ * - « Rejouer » : relancer une partie avec la même configuration ;
+ * - « Menu principal » : retourner au menu de sélection de mode ;
+ * - « Quitter » : fermer complètement l’application.
+ */
+public class EndGameDialog extends JDialog {
+
+ /**
+ * Construit la fenêtre de fin de partie.
+ *
+ * @param parent fenêtre principale (généralement une {@link AvalamWindow})
+ * @param result résultat de la partie (WIN / LOSS / DRAW du point de vue de PLAYER1 / Jaune)
+ * @param scoreJaune score du joueur jaune (nombre de tours contrôlées)
+ * @param scoreRouge score du joueur rouge (nombre de tours contrôlées)
+ * @param mode mode de jeu courant (pour l’information et le « Rejouer »)
+ * @param depth profondeur utilisée (pour les modes avec bot intelligent)
+ * @param onReplay action à exécuter lorsque l’utilisateur clique sur « Rejouer »
+ * @param onMenu action à exécuter lorsque l’utilisateur clique sur « Menu principal »
+ * @param onQuit action à exécuter lorsque l’utilisateur clique sur « Quitter »
+ */
+ public EndGameDialog(
+ JFrame parent,
+ Result result,
+ int scoreJaune,
+ int scoreRouge,
+ GameMode mode,
+ int depth,
+ Runnable onReplay,
+ Runnable onMenu,
+ Runnable onQuit
+ ) {
+ super(parent, "Fin de partie", true);
+
+ setLayout(new BorderLayout(10, 10));
+
+ // Panel principal d'information
+ JPanel infoPanel = new JPanel();
+ infoPanel.setLayout(new BoxLayout(infoPanel, BoxLayout.Y_AXIS));
+ infoPanel.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
+
+ JLabel titre = new JLabel("Partie terminée");
+ titre.setFont(titre.getFont().deriveFont(Font.BOLD, 18f));
+ titre.setAlignmentX(Component.CENTER_ALIGNMENT);
+
+ String gagnant;
+ switch (result) {
+ case WIN:
+ gagnant = "Le joueur JAUNE a gagné !";
+ break;
+ case LOSS:
+ gagnant = "Le joueur ROUGE a gagné !";
+ break;
+ case DRAW:
+ gagnant = "Égalité parfaite !";
+ break;
+ default:
+ gagnant = "Fin de partie.";
+ }
+
+ JLabel gagnantLabel = new JLabel(gagnant);
+ gagnantLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
+
+ JLabel scoreLabel = new JLabel(
+ "Score - Jaune : " + scoreJaune + " | Rouge : " + scoreRouge
+ );
+ scoreLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
+
+ JLabel modeLabel = new JLabel("Mode : " + modeToString(mode, depth));
+ modeLabel.setAlignmentX(Component.CENTER_ALIGNMENT);
+
+ infoPanel.add(titre);
+ infoPanel.add(Box.createVerticalStrut(10));
+ infoPanel.add(gagnantLabel);
+ infoPanel.add(Box.createVerticalStrut(5));
+ infoPanel.add(scoreLabel);
+ infoPanel.add(Box.createVerticalStrut(5));
+ infoPanel.add(modeLabel);
+
+ add(infoPanel, BorderLayout.CENTER);
+
+ // Panel des boutons d'action
+ JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.CENTER, 15, 10));
+
+ JButton replayButton = new JButton("Rejouer");
+ replayButton.addActionListener(e -> {
+ if (onReplay != null) {
+ onReplay.run();
+ }
+ dispose();
+ });
+
+ JButton menuButton = new JButton("Menu principal");
+ menuButton.addActionListener(e -> {
+ if (onMenu != null) {
+ onMenu.run();
+ }
+ dispose();
+ });
+
+ JButton quitButton = new JButton("Quitter");
+ quitButton.addActionListener(e -> {
+ if (onQuit != null) {
+ onQuit.run();
+ }
+ dispose();
+ });
+
+ buttonPanel.add(replayButton);
+ buttonPanel.add(menuButton);
+ buttonPanel.add(quitButton);
+
+ add(buttonPanel, BorderLayout.SOUTH);
+
+ pack();
+ setResizable(false);
+ setLocationRelativeTo(parent);
+ }
+
+ /**
+ * Retourne une description lisible du mode de jeu courant.
+ *
+ * @param mode mode de jeu
+ * @param depth profondeur (pour les bots intelligents)
+ * @return chaîne décrivant le mode
+ */
+ private String modeToString(GameMode mode, int depth) {
+ switch (mode) {
+ case PVP:
+ return "Joueur vs Joueur";
+ case PVBOT:
+ return "Joueur vs Bot idiot";
+ case PVALPHA:
+ return "Joueur vs Bot Alpha (profondeur " + depth + ")";
+ case PVGOD:
+ return "Joueur vs Bot Divin (profondeur " + depth + ")";
+ case ARENA:
+ return "Arène (bots)"; // normalement non utilisé ici
+ default:
+ return mode.name();
+ }
+ }
+}
+
+
diff --git a/fr/iut_fbleau/Avalam/Main.java b/fr/iut_fbleau/Avalam/Main.java
index 598e445..74457d6 100644
--- a/fr/iut_fbleau/Avalam/Main.java
+++ b/fr/iut_fbleau/Avalam/Main.java
@@ -22,7 +22,7 @@ public class Main {
"joueur vs joueur",
"joueur vs botidiot",
"joueur vs bot alpha",
- "joueur vs bot divin (NON IMPLEMENTE)",
+ "joueur vs bot divin",
"Arène"
};