diff --git a/lib/chex/game/inspect.ex b/lib/chex/game/inspect.ex new file mode 100644 index 0000000..abf6b4e --- /dev/null +++ b/lib/chex/game/inspect.ex @@ -0,0 +1,52 @@ +defimpl Inspect, for: Chex.Game do + @unicode_map %{ + {:white, :pawn} => "♙", + {:white, :rook} => "♖", + {:white, :knight} => "♘", + {:white, :bishop} => "♗", + {:white, :queen} => "♕", + {:white, :king} => "♔", + {:black, :pawn} => "♟", + {:black, :rook} => "♜", + {:black, :knight} => "♞", + {:black, :bishop} => "♝", + {:black, :queen} => "♛", + {:black, :king} => "♚", + nil => " " + } + + @ranks 8..1 + @files [:a, :b, :c, :d, :e, :f, :g, :h] + + @doc """ + Output a string in the unicode notation shown below. + + iex> Chex.Game.new + 8 [♜][♞][♝][♛][♚][♝][♞][♜] + 7 [♟][♟][♟][♟][♟][♟][♟][♟] + 6 [ ][ ][ ][ ][ ][ ][ ][ ] + 5 [ ][ ][ ][ ][ ][ ][ ][ ] + 4 [ ][ ][ ][ ][ ][ ][ ][ ] + 3 [ ][ ][ ][ ][ ][ ][ ][ ] + 2 [♙][♙][♙][♙][♙][♙][♙][♙] + 1 [♖][♘][♗][♕][♔][♗][♘][♖] + a b c d e f g h + """ + def inspect(game, opts) do + for rank <- @ranks, file <- @files do + piece = + case Map.get(game.board, {file, rank}) do + {material, color, _} -> {color, material} + _ -> nil + end + + unicode = Map.get(@unicode_map, piece) + "[#{unicode}]" + end + |> Enum.chunk_every(8) + |> Enum.with_index() + |> Enum.map(fn {row, rank} -> ["#{8 - rank} " | row] |> Enum.join("") end) + |> Enum.concat([" a b c d e f g h"]) + |> Enum.join("\n") + end +end diff --git a/test/chex/game/inspect_test.exs b/test/chex/game/inspect_test.exs new file mode 100644 index 0000000..6dafdf5 --- /dev/null +++ b/test/chex/game/inspect_test.exs @@ -0,0 +1,45 @@ +defmodule Chex.Game.InspectTest do + use ExUnit.Case, async: true + + describe "inspect game" do + test "new game" do + expected = + """ + 8 [♜][♞][♝][♛][♚][♝][♞][♜] + 7 [♟][♟][♟][♟][♟][♟][♟][♟] + 6 [ ][ ][ ][ ][ ][ ][ ][ ] + 5 [ ][ ][ ][ ][ ][ ][ ][ ] + 4 [ ][ ][ ][ ][ ][ ][ ][ ] + 3 [ ][ ][ ][ ][ ][ ][ ][ ] + 2 [♙][♙][♙][♙][♙][♙][♙][♙] + 1 [♖][♘][♗][♕][♔][♗][♘][♖] + a b c d e f g h + """ + |> String.trim() + + assert expected == inspect(Chex.new_game!()) + end + + test "promotion game" do + expected = + """ + 8 [ ][ ][ ][ ][ ][ ][ ][ ] + 7 [ ][ ][♚][ ][♙][ ][ ][ ] + 6 [ ][ ][ ][ ][ ][ ][ ][ ] + 5 [ ][ ][ ][ ][ ][ ][ ][ ] + 4 [ ][ ][ ][ ][ ][ ][ ][ ] + 3 [ ][ ][ ][ ][ ][ ][ ][ ] + 2 [ ][ ][♔][ ][ ][ ][ ][ ] + 1 [ ][ ][ ][ ][ ][ ][ ][ ] + a b c d e f g h + """ + |> String.trim() + + {:ok, game} = Chex.Game.new("8/2k1P3/8/8/8/8/2K5/8 w - - 0 1") + + IO.inspect(game) + + assert expected == inspect(game) + end + end +end diff --git a/test/chex/game_test.exs b/test/chex/game_test.exs index 153d368..6748e6f 100644 --- a/test/chex/game_test.exs +++ b/test/chex/game_test.exs @@ -1,6 +1,5 @@ defmodule Chex.GameTest do use ExUnit.Case, async: true - import AssertValue alias Chex.Game @@ -8,7 +7,7 @@ defmodule Chex.GameTest do test "returns new game state" do {:ok, game} = Game.new() - assert_value( + assert( game == %Game{ active_color: :white, board: %{