Programmation Java - Mouvements d'échecs (de base, pas d'IA)


J'ai besoin d'aide pour concevoir un jeu d'échecs. J'ai déjà commencé mais je ne suis pas allé loin car je suis assez nouveau en Java, nouveau en programmation en fait.

Quoi qu'il en soit, j'ai ma pièce de classe abstraite et les différentes pièces en tant que sous-classes. J'ai une méthode movePiece, dans ma classe abstraite, que je veux définir pour toutes les sous-classes.

Tout ce qu'il fait actuellement est de déplacer la pièce d'un carré à un autre. J'ai une classe Carrée qui peut contenir un objet Pièce, le tableau se compose d'un 64x1 Matrice carrée.

Je sais comment les pièces se déplacent, mais comment faire la programmation? Je veux essayer d'appliquer le modèle MVC mais c'est vraiment la première fois que j'utiliserai des modèles.

Fondamentalement, je pensais utiliser Graphics2D pour créer une boîte pour chaque carré. Ensuite, lorsqu'un joueur clique sur une pièce, les cases qui sont disponibles comme destination après le déplacement seront décrites dans une couleur. Après que le joueur clique sur l'une de ces cases, le code que j'ai déjà dans mon meuble méthode d'exécution.

Ce que je veux faire, c'est remplacer ma méthode movePiece dans chaque sous-classe de Piece. La question est, comment le code pourrait-il ressembler à l'une de ces méthodes? prenez la sous-classe Pion par exemple.

Je ne demande pas de code à copier/coller, juste quelques pointeurs sur la façon de le faire, éventuellement un exemple de code.

Merci!

public class Game {


@SuppressWarnings("unused")
public static void main(String[] args){
    Board board = new Board();
} }

public class Board {

Square[] grid;

public Board(){
    grid = new Square[64];
}   
public Square getSquare(int i){
    return grid[i];
}   
public void setDefault(){

}   
public Boolean isMoveValid(){
    return null;    
} }

public class Square {

private Piece piece;

public void addPiece(Piece pieceType, String pieceColour, String pieceOwner) 
        throws ClassNotFoundException, InstantiationException, IllegalAccessException{

    PieceFactory factory = new PieceFactory();
    Piece piece = factory.createPiece(pieceType);

    piece.setColour(pieceColour);
    piece.setOwner(pieceOwner);

    this.piece = piece; 
}
public void addPiece(Piece pieceType){ 
    this.piece = pieceType; 
}
public void removePiece(){  
    piece = null;
}
public Piece getPiece(){
    return piece;       
}

class PieceFactory {     
     @SuppressWarnings("rawtypes")
     public Piece createPiece(Piece pieceType) 
            throws ClassNotFoundException, InstantiationException, IllegalAccessException{
         Class pieceClass = Class.forName(pieceType.toString());
         Piece piece = (Piece) pieceClass.newInstance();

         return piece;       
     } }

public void setColour(String colour){

} }

public abstract class Piece {

Board board;

public void setColour(String pieceColour) {
}

public void setOwner(String pieceOwner) {
}

public String getColour() {
    return "";
}

public String getOwner() {
    return "";      
}
public void movePiece(int oldIndex, int newIndex){
    board.getSquare(oldIndex).removePiece();
    board.getSquare(newIndex).addPiece(this);
}
public String toString(){
    return this.getClass().getSimpleName();
} }

Vous vouliez voir le code, très basique, je sais. Et je vais changer le [64] à [8][8]. J'essaie de ne pas le rendre plus difficile alors il doit être. Je peux probablement combiner la couleur et le propriétaire comme attribut et en faire une énumération (NOIR ou BLANC).

Désolé si le formatage n'est pas bon.

Author: Smooth Operator, 2011-01-06

6 answers

Lors de la conception d'un logiciel, je trouve utile de réfléchir à la façon dont j'utiliserais une méthode, puis d'écrire la signature de la méthode (et si vous faites du développement piloté par les tests, le test unitaire), et ensuite seulement de penser à la façon dont je l'implémenterais.

En faisant cela ici, je trouve que l'exigence

Puis quand un joueur clique sur une pièce, le carrés qui sont disponibles comme destination après un déménagement souligné dans une certaine couleur.

Est impossible à satisfaire avec un méthode comme

void move(Square destination);

Parce qu'il n'y a aucun moyen de découvrir les mouvements possibles sans les faire réellement. Pour mettre en évidence les carrés, il serait probablement préférable d'avoir une méthode comme

Collection<Square> getPossibleMoves();

Et alors nous pourrions implémenter

void move(Square destination) {
    if (!getPossibleMoves().contains(destination) {
        throw new IllegalMoveException();
    }

    this.location.occupyingPiece = null;
    this.location = destination;
    this.location.occupyingPiece = this;
}

Quant à la mise en œuvre de getPossibleMoves:

class Pawn extends Piece {
    @Override Collection<Square> getPossibleMoves() {
        List<Square> possibleMoves = new ArrayList<Square>();
        int dy = color == Color.white ? 1 : -1;
        Square ahead = location.neighbour(0, dy);
        if (ahead.occupyingPiece == null) {
            possibleMoves.add(ahead);
        }
        Square aheadLeft = location.neighbour(-1, dy);
        if (aheadLeft != null && aheadLeft.occupyingPiece != null && aheadLeft.occupyingPiece.color != color) {
            possibleMoves.add(aheadLeft);
        }
        Square aheadRight = location.neighbour(1, dy);
        if (aheadRight != null && aheadRight.occupyingPiece != null && aheadRight.occupyingPiece.color != color) {
            possibleMoves.add(aheadRight);
        }
        return possibleMoves;
    }
}

Modifier :

class Knight extends Piece {
    @Override Collection<Square> getPossibleMoves() {
        List<Square> possibleMoves = new ArrayList<Square>();
        int[][] offsets = {
            {-2, 1},
            {-1, 2},
            {1, 2},
            {2, 1},
            {2, -1},
            {1, -2},
            {-1, -2},
            {-2, -1}
        };
        for (int[] o : offsets) {
            Square candidate = location.neighbour(o[0], o[1]);
            if (candidate != null && (candidate.occupyingPiece == null || candidate.occupyingPiece.color != color)) {
                possibleMoves.add(candidate);
            }
        }
        return possibleMoves;
    }
}
 18
Author: meriton, 2011-01-09 19:46:21

La façon dont vous le décrivez, plus qu'une méthode movePiece, vous avez besoin d'une méthode getPossibleMoves qui vous donne tous les endroits où vous pouvez vous déplacer. Alternativement ou en plus une méthode moveAllowed pour une pièce qui vous indique s'il est permis pour une pièce de se déplacer à l'emplacement donné.

Au lieu d'utiliser des coordonnées brutes (x,y), vous pouvez créer une classe pour définir un Location dans le tableau. Cela pourrait vous fournir des méthodes pour traduire un emplacement en "coordonnées d'échecs" comme utilisé dans la littérature d'échecs. Un Emplacement serait construit comme new Location(x, y).

Aussi, je préfère aller avec une classe Board qui représente le tableau de cellules 8x8 et est le conteneur pour les pièces, et peut avoir une logique plus riche qu'un simple tableau (par exemple, pourrait vous donner un pathClear(from, to) qui vous indique s'il n'y a pas de pièces bloquant votre passage d'un endroit à un autre) etc.

 2
Author: Carles Barrobés, 2011-01-05 23:12:42

Je ferais une méthode abstraite isValidMove(Board boardState, int square), qui serait remplacée dans chaque pièce et appelée pour mettre en évidence les mouvements valides (dans chaque itération de dessin.) Cette même méthode serait appelée dans movePiece (int square) pour vérifier si le mouvement est valide et effectuer le mouvement s'il en est ainsi. En fait, la méthode movePiece appartiendrait à la Planche elle-même (et appellerait la Pièce.isValidMove(...) vérifier.)

IsValidMove de Pion serait quelque chose comme (notez que c'est un pseudo-code):

if ( boardState.getSquare(square).isFree() && square == this.square+ONE_FILE)
    return true;
else
    return false;
 1
Author: kaoD, 2011-01-05 23:04:12

Je créerais une méthode appelée getValidMoves() qui renvoie la liste de tous les mouvements possibles pour une pièce donnée. De cette façon, vous n'avez pas à boucler sur tout le tableau pour trouver les carrés à mettre en évidence. Je rendrais également la classe de base abstraite afin que les méthodes telles que celle-ci n'aient pas besoin d'une implémentation de base.

 1
Author: Zeki, 2011-01-05 23:15:46

Je termine juste mon propre jeu d'échecs. Voici quelques conseils / points pour vous que je veux partager.

Rappelez-vous, Java est un langage orienté objet, divisez le jeu en objets logiques et interagissez avec les méthodes.

Gardez les méthodes aussi simples que possible (comme toujours). Faire de l'homme un code lisible. Parfois! 8 différentes méthodes pour vérifier les pièces (Roi) les mouvements disponibles sont plus lisibles que certaines phrases cryptiques pour essayer de faire tout ce travail de calcul.

Vous vouliez postuler Modèle MVC, vous voudrez peut-être considérer votre interface graphique comme étant également votre contrôleur qui a une référence à votre carte réelle.

Pièce.Java liste protégée allowedSquares; public abstract void calculateAllowedSquares (échiquier échiquier); le vide public se déplace (échiquier échiquier, Carré fromSquare, Carré toSquare)

Dans la classe King, vous devrez peut-être remplacer la méthode move. Par exemple, dans le roque déplacement, vous devez déplacer la tour en même temps.

  • , Vous aurez besoin de savoir aussi d'où vous vous déplacez (vérifiez la règle pour passer move) aussi, vous devrez probablement effacer le "fromSquare" de votre mouvement puisque vous utilisez [][] board.

Deux problèmes majeurs dans l'ensemble du concept de jeu d'échecs sont: 1. Comment vous éliminez les mouvements qui expose votre propre roi à vérifier. Parfois, les pièces ne peuvent pas bouger du tout. 2. Comment vous permettez à une pièce de se déplacer uniquement pour protéger votre roi dans des situations de contrôle. Ce qui signifie si pour.l'ex évêque menace votre roi et vous pouvez en déplacer pièce pour bloquer cette menace mais nulle part ailleurs.

Et enfin je vous conseille de créer votre interface graphique main dans la main avec votre logique. Il est d'une grande aide lorsque vous cliquez sur votre morceau(ou carré où la pièce est) et vous pouvez immédiatement voir à l'écran ce sont les places disponibles. Il vous permet d'économiser des heures et des heures de débogage.

 0
Author: interfacesAreCool, 2011-01-27 22:30:46

Tu dois ralentir!

Tout d'abord, vous devez créer une classe pour chaque élément et ajouter des mouvements possibles pour chacun et également implémenter une méthode pour vérifier les mouvements possibles pendant le jeu , ensuite, utilisez l'interface graphique Netbeans et ajoutez des JLabels et changez leur couleur en blanc et noir, afin que vous puissiez avoir une bonne vue de l'ensemble du processus.

Commencez simplement , n'hésitez jamais à supprimer les anciens codes et à les changer avec de nouveaux meilleurs codes. voilà comment cela fonctionne mec.

Bonne chance.

 0
Author: Adib, 2013-11-24 08:42:47