diff --git a/src/main/java/chess/Application.java b/src/main/java/chess/Application.java new file mode 100644 index 0000000000..9d756d4fd9 --- /dev/null +++ b/src/main/java/chess/Application.java @@ -0,0 +1,9 @@ +package chess; + +public class Application { + + public static void main(String[] args) { + Chess chess = new Chess(); + chess.play(); + } +} diff --git a/src/main/java/chess/Chess.java b/src/main/java/chess/Chess.java new file mode 100644 index 0000000000..971ce291d0 --- /dev/null +++ b/src/main/java/chess/Chess.java @@ -0,0 +1,73 @@ +package chess; + +import chess.piece.Piece; +import chess.piece.Queen; +import chess.piece.Rook; +import chess.view.OutputView; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.Objects; + +public class Chess { + + Map map; + + public void play() { + + map = new HashMap<>(); + + map.put(new Queen(Color.WHITE), new Position(Row.ONE, Column.E)); + map.put(new Rook(Color.BLACK), new Position(Row.ONE, Column.D)); + OutputView.displayBoard(map); + //사용자가 두 좌표를 입력 + Position beforePosition = new Position(Row.ONE, Column.E); + Position afterPosition = new Position(Row.TWO, Column.F); + + move(beforePosition, afterPosition); + OutputView.displayBoard(map); + } + + private void move(Position beforePosition, Position afterPosition) { + + Piece piece = map.entrySet().stream().filter(e -> e.getValue().equals(beforePosition)).map(e -> e.getKey()) + .findAny().get(); + + List movements = null; + if (piece.canMove(beforePosition, afterPosition)) { + movements = piece.getMovements(beforePosition, afterPosition); + } + + if (movements != null && piece.canMoveWithPieces( + checkRoute(beforePosition, movements))) { + Position position = beforePosition; + if (map.values().contains(afterPosition)) { + map.remove(map.entrySet().stream().filter(e -> e.getValue().equals(afterPosition)).map(e -> e.getKey()) + .findAny().get()); + } + for (Movement movement : Objects.requireNonNull(movements)) { + position= position.move(movement); + } + map.put(piece, position); + System.out.println("잘 이동됨"); + } + } + + private Map checkRoute(Position beforePosition, List movements) { + List positions = beforePosition.moveSimulRoute(movements); + Map m2 = new HashMap<>(); + List pieces = map.entrySet().stream().filter(e -> positions.contains(e.getValue())).map(e -> e.getKey()) + .toList(); + for (int i = 0; i < pieces.size(); i++) { + if (i == pieces.size() - 1) { + m2.put(pieces.get(i), true); + continue; + } + m2.put(pieces.get(i), false); + } + return m2; + } +} + +//TODO: 체스 좌표 두가지를 입력하면 해당 좌표로 이동한다. +// diff --git a/src/main/java/chess/Column.java b/src/main/java/chess/Column.java index b64b4dc77a..2341000912 100644 --- a/src/main/java/chess/Column.java +++ b/src/main/java/chess/Column.java @@ -2,14 +2,24 @@ public enum Column { - A, - B, - C, - D, - E, - F, - G, - H; + A(0), + B(1), + C(2), + D(3), + E(4), + F(5), + G(6), + H(7); + + private int number; + + Column(int number) { + this.number = number; + } + + public int getNumber() { + return number; + } public boolean isFarLeft() { return ordinal() == 0; diff --git a/src/main/java/chess/Position.java b/src/main/java/chess/Position.java index 3ebeb0ea18..389f93eecf 100644 --- a/src/main/java/chess/Position.java +++ b/src/main/java/chess/Position.java @@ -1,5 +1,9 @@ package chess; +import java.util.ArrayList; +import java.util.List; +import java.util.Objects; + public record Position( Column column, Row row @@ -167,4 +171,31 @@ public Position moveHorizontal(final int step) { } return this; } + + public Position moveSimul(Movement movement) { + Position position = new Position(this.row, this.column); + return position.move(movement); + } + + public List moveSimulRoute(List movements) { + List positions = new ArrayList<>(); + for (Movement movement : movements) { + positions.add(this.moveSimul(movement)); + } + return positions; + } + + @Override + public boolean equals(Object o) { + if (o == null || getClass() != o.getClass()) { + return false; + } + Position position = (Position) o; + return row == position.row && column == position.column; + } + + @Override + public int hashCode() { + return Objects.hash(column, row); + } } diff --git a/src/main/java/chess/Row.java b/src/main/java/chess/Row.java index 126ed048da..fa7e34f6ba 100644 --- a/src/main/java/chess/Row.java +++ b/src/main/java/chess/Row.java @@ -2,14 +2,20 @@ public enum Row { - EIGHT, - SEVEN, - SIX, - FIVE, - FOUR, - THREE, - TWO, - ONE; + EIGHT(7), + SEVEN(6), + SIX(5), + FIVE(4), + FOUR(3), + THREE(2), + TWO(1), + ONE(0); + + private int number; + + Row(int number) { + this.number = number; + } public boolean isTop() { return ordinal() == 0; @@ -50,4 +56,8 @@ public Row moveDown(final int step) { throw new IllegalStateException("움직일 수 없는 위치입니다."); } + + public int getNumber() { + return number; + } } diff --git a/src/main/java/chess/controller/Controller.java b/src/main/java/chess/controller/Controller.java new file mode 100644 index 0000000000..30c132cf03 --- /dev/null +++ b/src/main/java/chess/controller/Controller.java @@ -0,0 +1,9 @@ +package chess.controller; + +import chess.Chess; + +public class Controller { + + Chess chess = new Chess(); + +} diff --git a/src/main/java/chess/piece/Bishop.java b/src/main/java/chess/piece/Bishop.java index b14ab70f98..e00c94ede6 100644 --- a/src/main/java/chess/piece/Bishop.java +++ b/src/main/java/chess/piece/Bishop.java @@ -1,5 +1,71 @@ package chess.piece; -public class Bishop { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +public class Bishop extends Piece { + + public Bishop(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + if (Math.abs(afterPosition.row().getNumber() - beforePosition.row().getNumber()) == Math.abs( + afterPosition.column().getNumber() - beforePosition.column().getNumber())) { + return true; + } + return false; + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + int vertical = afterPosition.row().getNumber() - beforePosition.row().getNumber(); + int horizontal = afterPosition.column().getNumber() - beforePosition.column().getNumber(); + int count = Math.abs(vertical); + + List movements = new ArrayList<>(); + if (vertical > 0 && horizontal > 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT_UP); + } + } + if (vertical > 0 && horizontal < 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT_UP); + } + + } + if (vertical < 0 && horizontal > 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT_DOWN); + } + + } + if (vertical < 0 && horizontal < 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT_DOWN); + } + } + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + if (pieces.isEmpty()) { + return true; + } + Entry e = pieces.entrySet().stream().findFirst().get(); + if (pieces.size() == 1) { + if (e.getValue()) { + return e.getKey().getColor() != this.color; + } + } + return false; + } } diff --git a/src/main/java/chess/piece/King.java b/src/main/java/chess/piece/King.java index d64210cad1..3911bebfb8 100644 --- a/src/main/java/chess/piece/King.java +++ b/src/main/java/chess/piece/King.java @@ -1,5 +1,51 @@ package chess.piece; -public class King { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +public class King extends Piece { + + public King(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + List movements = List.of(Movement.LEFT, Movement.UP, Movement.RIGHT, Movement.DOWN, + Movement.LEFT_DOWN); + for (Movement movement : movements) { + if (beforePosition.canMove(movement)) { + return true; + } + } + return false; + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + List movements = new ArrayList<>(); + List kingMovements = List.of(Movement.LEFT, Movement.UP, Movement.RIGHT, Movement.DOWN, + Movement.LEFT_DOWN); + for (Movement movement : kingMovements) { + if (beforePosition.canMove(movement)) { + if (afterPosition.equals(beforePosition.moveSimul(movement))) { + movements.add(movement); + } + } + } + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + + if(pieces.size()==1){ + return pieces.entrySet().stream().findFirst().get().getKey().getColor()==(this.color); + } + return pieces.isEmpty(); + } } diff --git a/src/main/java/chess/piece/Knight.java b/src/main/java/chess/piece/Knight.java index 2ee7c47a3b..192a22837f 100644 --- a/src/main/java/chess/piece/Knight.java +++ b/src/main/java/chess/piece/Knight.java @@ -1,5 +1,57 @@ package chess.piece; -public class Knight { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +public class Knight extends Piece { + + public Knight(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + List movements = List.of(Movement.LEFT_LEFT_DOWN, Movement.LEFT_LEFT_UP, Movement.RIGHT_RIGHT_DOWN, + Movement.RIGHT_RIGHT_UP, Movement.DOWN_DOWN_LEFT, Movement.DOWN_DOWN_RIGHT, Movement.UP_UP_LEFT, + Movement.UP_UP_RIGHT); + for (Movement movement : movements) { + if (beforePosition.canMove(movement)) { + return true; + } + } + return false; + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + List movements = new ArrayList<>(); + List knightMovements = List.of(Movement.LEFT_LEFT_DOWN, Movement.LEFT_LEFT_UP, + Movement.RIGHT_RIGHT_DOWN, Movement.RIGHT_RIGHT_UP, Movement.DOWN_DOWN_LEFT, Movement.DOWN_DOWN_RIGHT, + Movement.UP_UP_LEFT, Movement.UP_UP_RIGHT); + for (Movement movement : knightMovements) { + if (beforePosition.canMove(movement)) { + if (afterPosition.equals(beforePosition.moveSimul(movement))) { + movements.add(movement); + } + } + } + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + if(pieces.isEmpty()){ + return true; + } + Entry e = pieces.entrySet().stream().findFirst().get(); + if (e.getValue() && e.getKey().getColor() == this.color) { + return false; + } + return true; + } } diff --git a/src/main/java/chess/piece/Pawn.java b/src/main/java/chess/piece/Pawn.java index c8b6cafa51..31dc1801c6 100644 --- a/src/main/java/chess/piece/Pawn.java +++ b/src/main/java/chess/piece/Pawn.java @@ -1,5 +1,82 @@ package chess.piece; -public class Pawn { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +public class Pawn extends Piece { + + public Pawn(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + int vertical = afterPosition.row().getNumber() - beforePosition.row().getNumber(); + int horizontal = afterPosition.column().getNumber() - beforePosition.column().getNumber(); + + if (color == Color.WHITE) { + if (vertical <= 0) { + return false; + } + if (vertical >= 2 || Math.abs(horizontal) >= 2) { + return false; + } + } + if (color == Color.BLACK) { + if (vertical >= 0) { + return false; + } + if (Math.abs(vertical) >= 2 || Math.abs(horizontal) >= 2) { + return false; + } + } + return true; + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + List movements = new ArrayList<>(); + int horizontal = afterPosition.column().getNumber() - beforePosition.column().getNumber(); + if (color == Color.WHITE) { + if (horizontal > 0) { + movements.add(Movement.RIGHT_UP); + } + if (horizontal < 0) { + movements.add(Movement.LEFT_UP); + } + movements.add(Movement.UP); + return movements; + } + if (color == Color.BLACK) { + if (horizontal > 0) { + movements.add(Movement.RIGHT_DOWN); + } + if (horizontal < 0) { + movements.add(Movement.LEFT_DOWN); + } + movements.add(Movement.DOWN); + return movements; + } + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + if (pieces.isEmpty()) { + + return true; + } + Entry e = pieces.entrySet().stream().findFirst().get(); + if (pieces.size() == 1) { + if (e.getValue()) { + return e.getKey().getColor() != this.color; + } + } + return false; + } } diff --git a/src/main/java/chess/piece/Piece.java b/src/main/java/chess/piece/Piece.java new file mode 100644 index 0000000000..456bb21bfd --- /dev/null +++ b/src/main/java/chess/piece/Piece.java @@ -0,0 +1,26 @@ +package chess.piece; + +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.List; +import java.util.Map; + +public abstract class Piece { + + Color color; + + public Piece(Color color) { + this.color = color; + } + + public abstract boolean canMove(Position beforePosition, Position afterPosition); + + public abstract List getMovements(Position beforePosition, Position afterPosition); + + public abstract boolean canMoveWithPieces(Map pieces); + + public Color getColor() { + return color; + } +} diff --git a/src/main/java/chess/piece/Queen.java b/src/main/java/chess/piece/Queen.java index 9b547261c4..7906cf4493 100644 --- a/src/main/java/chess/piece/Queen.java +++ b/src/main/java/chess/piece/Queen.java @@ -1,5 +1,101 @@ package chess.piece; -public class Queen { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +public class Queen extends Piece { + + public Queen(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + if (Math.abs(afterPosition.row().getNumber() - beforePosition.row().getNumber()) == Math.abs( + afterPosition.column().getNumber() - beforePosition.column().getNumber())) { + return true; + } + + if (afterPosition.row().equals(beforePosition.row()) || afterPosition.column() + .equals(beforePosition.column())) { + return true; + } + return false; + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + int vertical = afterPosition.row().getNumber() - beforePosition.row().getNumber(); + int horizontal = afterPosition.column().getNumber() - beforePosition.column().getNumber(); + int count = Math.abs(vertical); + + List movements = new ArrayList<>(); + if (vertical > 0 && horizontal > 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT_UP); + } + } + if (vertical > 0 && horizontal < 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT_UP); + } + + } + if (vertical < 0 && horizontal > 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT_DOWN); + } + + } + if (vertical < 0 && horizontal < 0) { + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT_DOWN); + } + } + if (vertical == 0 && horizontal < 0) { + count = Math.abs(horizontal); + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT); + } + } + if (vertical == 0 && horizontal > 0) { + count = Math.abs(horizontal); + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT); + } + } + if (vertical > 0 && horizontal == 0) { + count = Math.abs(vertical); + for (int i = 0; i < count; i++) { + movements.add(Movement.UP); + } + } + if (vertical < 0 && horizontal == 0) { + count = Math.abs(vertical); + for (int i = 0; i < count; i++) { + movements.add(Movement.DOWN); + } + } + + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + if (pieces.isEmpty()) { + return true; + } + Entry e = pieces.entrySet().stream().findFirst().get(); + if (pieces.size() == 1) { + if (e.getValue()) { + return e.getKey().getColor() != this.color; + } + } + return false; + } } diff --git a/src/main/java/chess/piece/Rook.java b/src/main/java/chess/piece/Rook.java index 7ed4d08bf0..343d59d347 100644 --- a/src/main/java/chess/piece/Rook.java +++ b/src/main/java/chess/piece/Rook.java @@ -1,5 +1,65 @@ package chess.piece; -public class Rook { +import chess.Color; +import chess.Movement; +import chess.Position; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +public class Rook extends Piece { + + public Rook(Color color) { + super(color); + } + + @Override + public boolean canMove(Position beforePosition, Position afterPosition) { + + return afterPosition.row().equals(beforePosition.row()) || afterPosition.column() + .equals(beforePosition.column()); + } + + @Override + public List getMovements(Position beforePosition, Position afterPosition) { + List movements = new ArrayList<>(); + int count; + if (afterPosition.row().equals(beforePosition.row())) { + count = Math.abs(afterPosition.column().getNumber() - beforePosition.column().getNumber()); + if (afterPosition.column().getNumber() > beforePosition.column().getNumber()) { + count = afterPosition.column().getNumber() - beforePosition.column().getNumber(); + for (int i = 0; i < count; i++) { + movements.add(Movement.RIGHT); + } + return movements; + } + for (int i = 0; i < count; i++) { + movements.add(Movement.LEFT); + } + } + count = afterPosition.row().getNumber() - beforePosition.row().getNumber(); + if (afterPosition.row().getNumber() > beforePosition.row().getNumber()) { + for (int i = 0; i < count; i++) { + movements.add(Movement.UP); + } + return movements; + } + for (int i = 0; i < count; i++) { + movements.add(Movement.DOWN); + } + return movements; + } + + @Override + public boolean canMoveWithPieces(Map pieces) { + if (pieces.size() == 1) { + Entry e = pieces.entrySet().stream().findFirst().get(); + if (e.getValue() && e.getKey().getColor() != this.getColor()) { + return true; + } + return false; + } + return false; + } } diff --git a/src/main/java/chess/view/InputView.java b/src/main/java/chess/view/InputView.java new file mode 100644 index 0000000000..12875bae51 --- /dev/null +++ b/src/main/java/chess/view/InputView.java @@ -0,0 +1,16 @@ +package chess.view; + +import java.util.Scanner; + +public class InputView { + + public static void getChessInput() { + Scanner scanner = new Scanner(System.in); + + System.out.println("하이 체스 게임임 방가"); + System.out.println("이동할 위치"); + scanner.nextLine(); + System.out.println("이동 후 위치"); + scanner.nextLine(); + } +} diff --git a/src/main/java/chess/view/OutputView.java b/src/main/java/chess/view/OutputView.java new file mode 100644 index 0000000000..a36f9a2c63 --- /dev/null +++ b/src/main/java/chess/view/OutputView.java @@ -0,0 +1,26 @@ +package chess.view; + +import chess.Position; +import chess.piece.Piece; +import java.util.Map; + +public class OutputView { + + public static void displayBoard(Map board) { + for (int i = 7; i >= 0; i--) { + for (int j = 7; j >= 0; j--) { + int i2 = i; + int j2 = j; + if (!board.entrySet().stream() + .filter(e -> e.getValue().row().getNumber() == i2 && e.getValue().column().getNumber() == j2) + .toList().isEmpty()) { + System.out.print("체"); + continue; + } + System.out.print("오"); + } + System.out.println(); + } + } + +}