💻 Exemplos: Capítulo 19: Projeto Integrador 1: Arquitetura Orientada a Objetos de um Motor de Xadrez em Console
Especialização em Sistemas com Java 21 LTS • Capítulo 19
🎯 Visão Geral dos Exemplos Práticos
Neste laboratório prático, implementaremos exemplos corporativos completos explorando:
- Modelagem de Tabuleiro e Peças com POO Pura: arquitetura de classes
Board,Piece,Rook,BishopeKing. - Cálculo Matricial Polimórfico de Movimentos Legais: varredura ortogonal e diagonal com detecção de obstáculos e capturas.
- Conversão de Notação Algébrica: tradução de coordenadas civis de xadrez (
a1ah8) para índices internos da matriz bidimensional[row][col].
💻 Exemplo 01 — Motor Funcional de Xadrez com Torre, Bispo e Rei
package com.empresa.xadrez;
/**
* Motor completo de xadrez em modo texto demonstrando herança, polimorfismo e validação matricial.
*/
public class SimuladorPartidaXadrez {
public enum Cor { BRANCO, PRETO }
public record Coordenada(int linha, int coluna) {}
public static class PosicaoXadrez {
private final char coluna;
private final int linha;
public PosicaoXadrez(char coluna, int linha) {
if (coluna < 'a' || coluna > 'h' || linha < 1 || linha > 8) {
throw new IllegalArgumentException("Posição de xadrez inválida: " + coluna + linha);
}
this.coluna = coluna;
this.linha = linha;
}
public Coordenada paraCoordenadaMatriz() {
return new Coordenada(8 - linha, coluna - 'a');
}
public static PosicaoXadrez deCoordenada(Coordenada coord) {
return new PosicaoXadrez((char) ('a' + coord.coluna()), 8 - coord.linha());
}
@Override
public String toString() { return "" + coluna + linha; }
}
public static abstract class Peca {
protected Coordenada posicao;
protected final Cor cor;
public Peca(Cor cor) { this.cor = cor; }
public abstract boolean[][] gerarMovimentosValidos(Peca[][] grade);
public Cor getCor() { return cor; }
public Coordenada getPosicao() { return posicao; }
public void setPosicao(Coordenada p) { this.posicao = p; }
}
public static class Torre extends Peca {
public Torre(Cor cor) { super(cor); }
@Override
public boolean[][] gerarMovimentosValidos(Peca[][] grade) {
boolean[][] mat = new boolean[8][8];
int r = posicao.linha();
int c = posicao.coluna();
// Cima
for (int i = r - 1; i >= 0; i--) {
if (grade[i][c] == null) mat[i][c] = true;
else { if (grade[i][c].getCor() != this.cor) mat[i][c] = true; break; }
}
// Baixo
for (int i = r + 1; i < 8; i++) {
if (grade[i][c] == null) mat[i][c] = true;
else { if (grade[i][c].getCor() != this.cor) mat[i][c] = true; break; }
}
// Esquerda
for (int j = c - 1; j >= 0; j--) {
if (grade[r][j] == null) mat[r][j] = true;
else { if (grade[r][j].getCor() != this.cor) mat[r][j] = true; break; }
}
// Direita
for (int j = c + 1; j < 8; j++) {
if (grade[r][j] == null) mat[r][j] = true;
else { if (grade[r][j].getCor() != this.cor) mat[r][j] = true; break; }
}
return mat;
}
@Override
public String toString() { return cor == Cor.BRANCO ? "T" : "t"; }
}
public static class Bispo extends Peca {
public Bispo(Cor cor) { super(cor); }
@Override
public boolean[][] gerarMovimentosValidos(Peca[][] grade) {
boolean[][] mat = new boolean[8][8];
int r = posicao.linha();
int c = posicao.coluna();
// Noroeste
for (int i = r - 1, j = c - 1; i >= 0 && j >= 0; i--, j--) {
if (grade[i][j] == null) mat[i][j] = true;
else { if (grade[i][j].getCor() != this.cor) mat[i][j] = true; break; }
}
// Nordeste
for (int i = r - 1, j = c + 1; i >= 0 && j < 8; i--, j++) {
if (grade[i][j] == null) mat[i][j] = true;
else { if (grade[i][j].getCor() != this.cor) mat[i][j] = true; break; }
}
// Sudoeste
for (int i = r + 1, j = c - 1; i < 8 && j >= 0; i++, j--) {
if (grade[i][j] == null) mat[i][j] = true;
else { if (grade[i][j].getCor() != this.cor) mat[i][j] = true; break; }
}
// Sudeste
for (int i = r + 1, j = c + 1; i < 8 && j < 8; i++, j++) {
if (grade[i][j] == null) mat[i][j] = true;
else { if (grade[i][j].getCor() != this.cor) mat[i][j] = true; break; }
}
return mat;
}
@Override
public String toString() { return cor == Cor.BRANCO ? "B" : "b"; }
}
public static class TabuleiroXadrez {
private final Peca[][] matriz = new Peca[8][8];
public void alocarPeca(Peca peca, PosicaoXadrez pos) {
Coordenada c = pos.paraCoordenadaMatriz();
matriz[c.linha()][c.coluna()] = peca;
peca.setPosicao(c);
}
public boolean mover(PosicaoXadrez origem, PosicaoXadrez destino) {
Coordenada cOrig = origem.paraCoordenadaMatriz();
Coordenada cDest = destino.paraCoordenadaMatriz();
Peca p = matriz[cOrig.linha()][cOrig.coluna()];
if (p == null) return false;
boolean[][] possiveis = p.gerarMovimentosValidos(matriz);
if (!possiveis[cDest.linha()][cDest.coluna()]) {
System.out.printf("❌ Movimento ilegal de %s para %s!%n", origem, destino);
return false;
}
// Realiza movimento
matriz[cDest.linha()][cDest.coluna()] = p;
matriz[cOrig.linha()][cOrig.coluna()] = null;
p.setPosicao(cDest);
System.out.printf("✅ Peça %s movimentada com êxito de %s para %s%n", p, origem, destino);
return true;
}
public void imprimir() {
System.out.println(" a b c d e f g h");
System.out.println(" +----------------");
for (int i = 0; i < 8; i++) {
System.out.print((8 - i) + " |");
for (int j = 0; j < 8; j++) {
Peca p = matriz[i][j];
System.out.print((p == null ? ". " : p + " "));
}
System.out.println("| " + (8 - i));
}
System.out.println(" +----------------");
System.out.println(" a b c d e f g h");
}
}
public static void main(String[] args) {
System.out.println("================================================================================");
System.out.println(" SIMULADOR DE MOTOR DE XADREZ CONSOLE (JAVA 21 LTS) ");
System.out.println("================================================================================");
TabuleiroXadrez jogo = new TabuleiroXadrez();
// Posicionamento de Peças em notação algébrica
jogo.alocarPeca(new Torre(Cor.BRANCO), new PosicaoXadrez('a', 1));
jogo.alocarPeca(new Bispo(Cor.BRANCO), new PosicaoXadrez('c', 1));
jogo.alocarPeca(new Torre(Cor.PRETO), new PosicaoXadrez('a', 8));
jogo.imprimir();
// Tentativa de Movimento Válido da Torre Branca: a1 -> a5
System.out.println("\n--- Movimento 1: Torre Branca a1 para a5 ---");
jogo.mover(new PosicaoXadrez('a', 1), new PosicaoXadrez('a', 5));
jogo.imprimir();
// Tentativa de Captura: a5 captura a8 (Torre Preta)
System.out.println("\n--- Movimento 2: Torre Branca a5 captura Torre Preta em a8 ---");
jogo.mover(new PosicaoXadrez('a', 5), new PosicaoXadrez('a', 8));
jogo.imprimir();
System.out.println("================================================================================");
}
}
📋 Resultado Esperado no Console
================================================================================
SIMULADOR DE MOTOR DE XADREZ CONSOLE (JAVA 21 LTS)
================================================================================
a b c d e f g h
+----------------
8 |t . . . . . . . | 8
7 |. . . . . . . . | 7
6 |. . . . . . . . | 6
5 |. . . . . . . . | 5
4 |. . . . . . . . | 4
3 |. . . . . . . . | 3
2 |. . . . . . . . | 2
1 |T . B . . . . . | 1
+----------------
a b c d e f g h
--- Movimento 1: Torre Branca a1 para a5 ---
✅ Peça T movimentada com êxito de a1 para a5
a b c d e f g h
+----------------
8 |t . . . . . . . | 8
7 |. . . . . . . . | 7
6 |. . . . . . . . | 6
5 |T . . . . . . . | 5
4 |. . . . . . . . | 4
3 |. . . . . . . . | 3
2 |. . . . . . . . | 2
1 |. . B . . . . . | 1
+----------------
a b c d e f g h
--- Movimento 2: Torre Branca a5 captura Torre Preta em a8 ---
✅ Peça T movimentada com êxito de a5 para a8
a b c d e f g h
+----------------
8 |T . . . . . . . | 8
7 |. . . . . . . . | 7
6 |. . . . . . . . | 6
5 |. . . . . . . . | 5
4 |. . . . . . . . | 4
3 |. . . . . . . . | 3
2 |. . . . . . . . | 2
1 |. . B . . . . . | 1
+----------------
a b c d e f g h
================================================================================