From aa7f685521e0a2ed7f3088e163e1478ee5979584 Mon Sep 17 00:00:00 2001 From: Dan Barber Date: Sun, 18 Mar 2018 19:48:26 -0400 Subject: [PATCH] Check for attacks from pawns --- lib/chess/board.ex | 15 +++++++++++++++ lib/chess/moves/piece.ex | 27 ++++++++++++++++++++++----- test/chess/moves/piece_test.exs | 27 +++++++++++++++++++++++++++ 3 files changed, 64 insertions(+), 5 deletions(-) diff --git a/lib/chess/board.ex b/lib/chess/board.ex index 553d2de..1157ac2 100644 --- a/lib/chess/board.ex +++ b/lib/chess/board.ex @@ -9,6 +9,14 @@ defmodule Chess.Board do end) end + def search(board, %{"type" => type, "colour" => colour}) do + board + |> Enum.filter(fn({_index, piece}) -> + match?(%{"type" => ^type, "colour" => ^colour}, piece) + end) + |> Enum.map(fn({index, _piece}) -> index_to_tuple(index) end) + end + def piece(board, {file, rank}) do board["#{file},#{rank}"] end @@ -61,4 +69,11 @@ defmodule Chess.Board do "7,0" => %{"type" => "rook", "colour" => "white"} } end + + defp index_to_tuple(index) do + index + |> String.split(",") + |> Enum.map(&(String.to_integer(&1))) + |> List.to_tuple + end end diff --git a/lib/chess/moves/piece.ex b/lib/chess/moves/piece.ex index 635b1e1..fb8cc30 100644 --- a/lib/chess/moves/piece.ex +++ b/lib/chess/moves/piece.ex @@ -4,14 +4,13 @@ defmodule Chess.Moves.Piece do alias Chess.Board alias Chess.Moves.Generator alias Chess.Moves.Pieces.Knight - - def find(board, piece) do - end + alias Chess.Moves.Pieces.Pawn def attacked?(board, {file, rank}) do attacked_by_rook_or_queen?(board, {file, rank}) || attacked_by_bishop_or_queen?(board, {file, rank}) || - attacked_by_knight?(board, {file, rank}) + attacked_by_knight?(board, {file, rank}) || + attacked_by_pawn?(board, {file, rank}) end defp attacked_by_rook_or_queen?(board, {file, rank}) do @@ -32,6 +31,24 @@ defmodule Chess.Moves.Piece do _attacked?(board, {file, rank}, Knight.pattern, "knight") end + defp attacked_by_pawn?(board, {file, rank}) do + colour = + board + |> Board.piece({file, rank}) + |> Map.get("colour") + + board + |> _attacked_by_pawn?({file, rank}, Pawn.pattern(colour)) + end + + defp _attacked_by_pawn?(board, {file, rank}, pattern) do + moves = + board + |> Generator.moves({file, rank}, pattern) + + Enum.any?(moves, &(match_piece(board, &1, "pawn"))) + end + defp _attacked?(board, {file, rank}, {fv, rv}, pieces) do {file, rank} = board @@ -40,7 +57,7 @@ defmodule Chess.Moves.Piece do piece = board["#{file},#{rank}"] - Enum.any?(pieces, &(match?(%{"type" => &1}, piece))) + Enum.any?(pieces, &(match?(%{"type" => ^&1}, piece))) end defp _attacked?(board, {file, rank}, pattern, piece_type) do diff --git a/test/chess/moves/piece_test.exs b/test/chess/moves/piece_test.exs index c861f31..8b20e4d 100644 --- a/test/chess/moves/piece_test.exs +++ b/test/chess/moves/piece_test.exs @@ -12,6 +12,15 @@ defmodule Chess.Moves.PieceTest do refute Piece.attacked?(board, {4, 5}) end + test "piece is not being attacked by piece of its own colour" do + board = %{ + "4,5" => %{"type" => "king", "colour" => "white"}, + "2,5" => %{"type" => "rook", "colour" => "white"}, + } + + refute Piece.attacked?(board, {4, 5}) + end + test "piece can be attacked by a rook" do board = %{ "4,5" => %{"type" => "king", "colour" => "white"}, @@ -56,4 +65,22 @@ defmodule Chess.Moves.PieceTest do assert Piece.attacked?(board, {4, 5}) end + + test "piece can be attacked by a pawn" do + board = %{ + "4,5" => %{"type" => "king", "colour" => "white"}, + "5,6" => %{"type" => "pawn", "colour" => "black"}, + } + + assert Piece.attacked?(board, {4, 5}) + end + + test "piece is not attacked by a pawn directly in front" do + board = %{ + "4,5" => %{"type" => "king", "colour" => "white"}, + "4,6" => %{"type" => "pawn", "colour" => "black"}, + } + + refute Piece.attacked?(board, {4, 5}) + end end