arret de jeu lors de la mise en echec

This commit is contained in:
bensefia 2025-05-13 14:11:10 +02:00
parent 6b85a0b6e0
commit e3b4b0c3d4
2 changed files with 201 additions and 30 deletions

View File

@ -15,48 +15,160 @@ public class AutoPlayer {
int px = p.getX(); int px = p.getX();
int py = p.getY(); int py = p.getY();
for (int dx = -1; dx <= 1; dx++) { ArrayList<int[]> candidateMoves = generatePossibleMoves(p, board);
for (int dy = -1; dy <= 1; dy++) { for (int[] move : candidateMoves) {
if (dx == 0 && dy == 0) continue; int nx = move[0];
int nx = px + dx; int ny = move[1];
int ny = py + dy; Piece target = board.getPieceAt(nx, ny);
if (nx >= 0 && ny >= 0 && nx < board.getWidth() && ny < board.getHeight()) { Board simulated = new Board(board);
Piece target = getPieceAt(pieces, nx, ny); simulated.playMove(new Move(p, px, py, nx, ny, target));
if (target == null || target.isWhite() != aiColor) {
int score = (target != null) ? pieceValue(target) : 0; int score = evaluateBoard(simulated, aiColor);
if (score > bestScore) { if (score > bestScore) {
bestScore = score; bestScore = score;
bestMove = new Move(p, px, py, nx, ny, target); bestMove = new Move(p, px, py, nx, ny, target);
}
}
}
} }
} }
} }
} }
return bestMove; return bestMove;
} }
private ArrayList<int[]> generatePossibleMoves(Piece piece, Board board) {
ArrayList<int[]> moves = new ArrayList<>();
int x = piece.getX();
int y = piece.getY();
boolean isWhite = piece.isWhite();
switch (piece.getType()) {
case Pawn:
int dir = isWhite ? -1 : 1;
int oneStepY = y + dir;
int twoStepY = y + 2 * dir;
if (inBounds(x, oneStepY, board) && board.getPieceAt(x, oneStepY) == null) {
moves.add(new int[] { x, oneStepY });
if ((isWhite && y == 6) || (!isWhite && y == 1)) {
if (board.getPieceAt(x, twoStepY) == null) {
moves.add(new int[] { x, twoStepY });
}
}
}
for (int dx = -1; dx <= 1; dx += 2) {
int nx = x + dx;
if (inBounds(nx, oneStepY, board)) {
Piece target = board.getPieceAt(nx, oneStepY);
if (target != null && target.isWhite() != isWhite) {
moves.add(new int[] { nx, oneStepY });
}
}
}
break;
case Knight:
int[][] knightMoves = { { 2, 1 }, { 1, 2 }, { -1, 2 }, { -2, 1 },
{ -2, -1 }, { -1, -2 }, { 1, -2 }, { 2, -1 } };
for (int[] d : knightMoves) {
int nx = x + d[0];
int ny = y + d[1];
if (inBounds(nx, ny, board)) {
Piece target = board.getPieceAt(nx, ny);
if (target == null || target.isWhite() != isWhite)
moves.add(new int[] { nx, ny });
}
}
break;
case Bishop:
addSlideMoves(moves, board, piece, 1, 1);
addSlideMoves(moves, board, piece, 1, -1);
addSlideMoves(moves, board, piece, -1, 1);
addSlideMoves(moves, board, piece, -1, -1);
break;
case Rook:
addSlideMoves(moves, board, piece, 1, 0);
addSlideMoves(moves, board, piece, -1, 0);
addSlideMoves(moves, board, piece, 0, 1);
addSlideMoves(moves, board, piece, 0, -1);
break;
case Queen:
for (int dx = -1; dx <= 1; dx++) {
for (int dy = -1; dy <= 1; dy++) {
if (dx != 0 || dy != 0) {
addSlideMoves(moves, board, piece, dx, dy);
}
}
}
break;
case King:
for (int dx = -1; dx <= 1; dx++) {
for (int dy = -1; dy <= 1; dy++) {
if (dx == 0 && dy == 0) continue;
int nx = x + dx;
int ny = y + dy;
if (inBounds(nx, ny, board)) {
Piece target = board.getPieceAt(nx, ny);
if (target == null || target.isWhite() != isWhite) {
moves.add(new int[] { nx, ny });
}
}
}
}
break;
}
return moves;
}
private void addSlideMoves(ArrayList<int[]> moves, Board board, Piece piece, int dx, int dy) {
int x = piece.getX();
int y = piece.getY();
boolean isWhite = piece.isWhite();
int nx = x + dx;
int ny = y + dy;
while (inBounds(nx, ny, board)) {
Piece p = board.getPieceAt(nx, ny);
if (p == null) {
moves.add(new int[] { nx, ny });
} else {
if (p.isWhite() != isWhite)
moves.add(new int[] { nx, ny });
break;
}
nx += dx;
ny += dy;
}
}
private boolean inBounds(int x, int y, Board board) {
return x >= 0 && y >= 0 && x < board.getWidth() && y < board.getHeight();
}
private int evaluateBoard(Board board, boolean aiColor) {
int score = 0;
for (Piece p : board.getPieces()) {
int value = pieceValue(p);
score += p.isWhite() == aiColor ? value : -value;
}
return score;
}
private int pieceValue(Piece piece) { private int pieceValue(Piece piece) {
switch (piece.getType()) { switch (piece.getType()) {
case Pawn: return 1; case Pawn: return 10;
case Knight: case Knight:
case Bishop: return 3; case Bishop: return 30;
case Rook: return 5; case Rook: return 50;
case Queen: return 9; case Queen: return 90;
case King: return 1000; case King: return 900;
default: return 0; default: return 0;
} }
} }
private Piece getPieceAt(ArrayList<Piece> list, int x, int y) {
for (Piece p : list) {
if (p.getX() == x && p.getY() == y) return p;
}
return null;
}
} }

View File

@ -10,6 +10,7 @@ public class Board {
private ArrayList<Piece> pieces; private ArrayList<Piece> pieces;
private int turnNumber = 0; private int turnNumber = 0;
private boolean turnIsWhite = true; private boolean turnIsWhite = true;
private boolean gameOver = false;
private Integer selectedX = null; private Integer selectedX = null;
private Integer selectedY = null; private Integer selectedY = null;
@ -39,6 +40,10 @@ public class Board {
return turnIsWhite; return turnIsWhite;
} }
public boolean isGameOver() {
return gameOver;
}
public void setPiece(boolean isWhite, PieceType type, int x, int y) { public void setPiece(boolean isWhite, PieceType type, int x, int y) {
pieces.removeIf(p -> p.getX() == x && p.getY() == y); pieces.removeIf(p -> p.getX() == x && p.getY() == y);
pieces.add(new Piece(isWhite, type, x, y)); pieces.add(new Piece(isWhite, type, x, y));
@ -73,6 +78,7 @@ public class Board {
selectedY = null; selectedY = null;
highlightedPositions.clear(); highlightedPositions.clear();
moveHistory.clear(); moveHistory.clear();
gameOver = false;
} }
public ArrayList<Piece> getPieces() { public ArrayList<Piece> getPieces() {
@ -80,6 +86,8 @@ public class Board {
} }
public void userTouch(int x, int y) { public void userTouch(int x, int y) {
if (gameOver) return;
Piece clickedPiece = getPieceAt(x, y); Piece clickedPiece = getPieceAt(x, y);
if (selectedX == null || selectedY == null) { if (selectedX == null || selectedY == null) {
if (clickedPiece != null && clickedPiece.isWhite() == turnIsWhite) { if (clickedPiece != null && clickedPiece.isWhite() == turnIsWhite) {
@ -104,6 +112,10 @@ public class Board {
moveHistory.push(move); moveHistory.push(move);
turnNumber++; turnNumber++;
turnIsWhite = !turnIsWhite; turnIsWhite = !turnIsWhite;
if (isCheckmate(!turnIsWhite)) {
gameOver = true;
}
} }
selectedX = null; selectedX = null;
selectedY = null; selectedY = null;
@ -129,9 +141,52 @@ public class Board {
selectedX = null; selectedX = null;
selectedY = null; selectedY = null;
highlightedPositions.clear(); highlightedPositions.clear();
gameOver = false;
} }
} }
public boolean isCheckmate(boolean forWhite) {
for (Piece piece : pieces) {
if (piece.isWhite() == forWhite) {
ArrayList<int[]> moves = getLegalMovesFor(piece);
for (int[] move : moves) {
Board copy = new Board(this);
Piece captured = copy.getPieceAt(move[0], move[1]);
copy.pieces.removeIf(p -> p.getX() == piece.getX() && p.getY() == piece.getY());
copy.pieces.removeIf(p -> p.getX() == move[0] && p.getY() == move[1]);
copy.pieces.add(new Piece(piece.isWhite(), piece.getType(), move[0], move[1]));
if (!copy.isKingInCheck(forWhite)) {
return false;
}
}
}
}
return isKingInCheck(forWhite);
}
public boolean isKingInCheck(boolean isWhite) {
Piece king = null;
for (Piece p : pieces) {
if (p.getType() == PieceType.King && p.isWhite() == isWhite) {
king = p;
break;
}
}
if (king == null) return true;
for (Piece enemy : pieces) {
if (enemy.isWhite() != isWhite) {
ArrayList<int[]> moves = getLegalMovesFor(enemy);
for (int[] pos : moves) {
if (pos[0] == king.getX() && pos[1] == king.getY()) {
return true;
}
}
}
}
return false;
}
public boolean isSelected(int x, int y) { public boolean isSelected(int x, int y) {
return selectedX != null && selectedY != null && selectedX == x && selectedY == y; return selectedX != null && selectedY != null && selectedX == x && selectedY == y;
} }
@ -265,7 +320,7 @@ public class Board {
return x >= 0 && y >= 0 && x < width && y < height; return x >= 0 && y >= 0 && x < width && y < height;
} }
private Piece getPieceAt(int x, int y) { public Piece getPieceAt(int x, int y) {
for (Piece p : pieces) { for (Piece p : pieces) {
if (p.getX() == x && p.getY() == y) return p; if (p.getX() == x && p.getY() == y) return p;
} }
@ -318,7 +373,7 @@ public class Board {
} }
public void playMove(Move move) { public void playMove(Move move) {
if (move == null) return; if (move == null || gameOver) return;
pieces.removeIf(p -> p.getX() == move.getToX() && p.getY() == move.getToY()); pieces.removeIf(p -> p.getX() == move.getToX() && p.getY() == move.getToY());
pieces.removeIf(p -> p.getX() == move.getFromX() && p.getY() == move.getFromY()); pieces.removeIf(p -> p.getX() == move.getFromX() && p.getY() == move.getFromY());
pieces.add(new Piece( pieces.add(new Piece(
@ -333,6 +388,10 @@ public class Board {
selectedX = null; selectedX = null;
selectedY = null; selectedY = null;
highlightedPositions.clear(); highlightedPositions.clear();
if (isCheckmate(!turnIsWhite)) {
gameOver = true;
}
} }
} }