diff --git a/src/all_moves_functions.cpp b/src/all_moves_functions.cpp index 000927f..34e0a2f 100644 --- a/src/all_moves_functions.cpp +++ b/src/all_moves_functions.cpp @@ -184,7 +184,7 @@ void _get_all_moves_king(int pos, std::vector *pns, std::array *pns, std::array dumb_move(int move, std::array board) std::array new_board; std::copy(std::begin(board), std::end(board), std::begin(new_board)); int en_passant_flag = get_en_pass_flag(move); + int castle_flag = get_castle_flag(move); int from = get_from_sq(move); int to = get_to_sq(move); PieceType piece = new_board[from]; @@ -210,7 +211,25 @@ std::array dumb_move(int move, std::array board) new_board[other_pawn_pos] = PieceType::NONE; new_board[to] = piece; new_board[from] = PieceType::NONE; - } else { + } else if(castle_flag == 1){ + int diff = to-from; + int rook_from_pos = 0; + int rook_to_pos = 0; + // If castling queenside + if (diff == -2){ + rook_from_pos = to-2; + rook_to_pos = from-1; + // If caslting kingside + } else if (diff == 2){ + rook_from_pos = to+1; + rook_to_pos = from+1; + } + PieceType rook_pt = new_board[rook_from_pos]; + new_board[rook_from_pos] = PieceType::NONE; + new_board[rook_to_pos] = rook_pt; + new_board[from] = PieceType::NONE; + new_board[to] = piece; + } else { new_board[to] = piece; new_board[from] = PieceType::NONE; } diff --git a/tests/main.cpp b/tests/main.cpp index 70ea985..a358a75 100644 --- a/tests/main.cpp +++ b/tests/main.cpp @@ -153,6 +153,11 @@ TEST_CASE("Test for castling moves.", "[get_all_moves]"){ auto bcast_checked_moves = get_all_moves(BCASTLING_POS, CASTLING_CHECK_BOARD, true, 0, 0xF); CHECK(get_to_squares(bcast_checked_moves) == BCASTLING_CHECK_MOVES); CHECK(get_castle_flags(bcast_checked_moves) == checked_cast_flags); + // Check that castling moves are not allowed when the rook is blocked. + auto blocked_castling_moves = get_all_moves(CASTLE_BLOCKED_POS, CASTLE_BLOCKED_BOARD, true, 0, 0xF); + CHECK(get_to_squares(blocked_castling_moves) == CASTLE_BLOCKED_MOVES); + auto blocked_castling_qmoves = get_all_moves(CASTLE_BLOCKED_QPOS, CASTLE_BLOCKED_QBOARD, true, 0, 0xF); + CHECK(get_to_squares(blocked_castling_qmoves) == CASTLE_BLOCKED_QMOVES); } TEST_CASE("Test that en passant moves are properly handled by dumb_move", "dumb_move"){ @@ -161,3 +166,10 @@ TEST_CASE("Test that en passant moves are properly handled by dumb_move", "dumb_ CHECK(dumb_move(make_move(EN_PASSANT_CHECK_POS2, EN_PASSANT_EN_PASSANT_SQUARE2, PieceType::B_PAWN, PieceType::NONE, 1), EN_PASSANT_CHECK_BOARD2) == EN_PASSANT_CHECK_MOVED_BOARD2); CHECK(dumb_move(make_move(EN_PASSANT_CHECK_POS3, EN_PASSANT_EN_PASSANT_SQUARE3, PieceType::B_PAWN, PieceType::NONE, 1), EN_PASSANT_CHECK_BOARD3) == EN_PASSANT_CHECK_MOVED_BOARD3); } + +TEST_CASE("Test that castle moves are poperly handled by dumb_mobe", "[dumb_move]"){ + CHECK(dumb_move(make_move(CASTLE_FROM_POS, CASTLE_TO_POS, PieceType::NONE, PieceType::NONE, 0, 0, 1), CASTLE_BOARD) == CASTLE_BOARD_WK); + CHECK(dumb_move(make_move(CASTLE_FROM_QPOS, CASTLE_TO_QPOS, PieceType::NONE, PieceType::NONE, 0, 0, 1), CASTLE_BOARD) == CASTLE_BOARD_WQ); + CHECK(dumb_move(make_move(BCASTLE_FROM_POS, BCASTLE_TO_POS, PieceType::NONE, PieceType::NONE, 0, 0, 1), CASTLE_BOARD) == CASTLE_BOARD_BK); + CHECK(dumb_move(make_move(BCASTLE_FROM_QPOS, BCASTLE_TO_QPOS, PieceType::NONE, PieceType::NONE, 0, 0, 1), CASTLE_BOARD) == CASTLE_BOARD_BQ); +} diff --git a/tests/valid_moves.h b/tests/valid_moves.h index 0fe497c..32c970c 100644 --- a/tests/valid_moves.h +++ b/tests/valid_moves.h @@ -311,6 +311,128 @@ const int BLACK_CHECK_POS2 = F8; const std::vector BCASTLING_CHECK_MOVES = { D7, E7, F7 }; +// Check that the dumb_move function actually moves the rook and the king to the right squares. +const int CASTLE_FROM_POS = E1; +const int CASTLE_TO_POS = G1; +const int BCASTLE_FROM_POS = E8; +const int BCASTLE_TO_POS = G8; + +const int CASTLE_FROM_QPOS = E1; +const int CASTLE_TO_QPOS = C1; +const int BCASTLE_FROM_QPOS = E8; +const int BCASTLE_TO_QPOS = C8; + +const std::array CASTLE_BOARD = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, NONE, NONE, NONE, B_KING, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, NONE, NONE, NONE, W_KING, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::array CASTLE_BOARD_WK = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, NONE, NONE, NONE, B_KING, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, NONE, NONE, NONE, NONE, W_ROOK, W_KING, NONE, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::array CASTLE_BOARD_BK = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, NONE, NONE, NONE, NONE, B_ROOK, B_KING, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, NONE, NONE, NONE, W_KING, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::array CASTLE_BOARD_WQ = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, NONE, NONE, NONE, B_KING, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, W_KING, W_ROOK, NONE, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::array CASTLE_BOARD_BQ = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, NONE, NONE, B_KING, B_ROOK, NONE, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, NONE, NONE, NONE, W_KING, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; + +// Check that castling is disallowed when there is a piece blocking the rook queenside. +const int CASTLE_BLOCKED_POS = E1; +const std::array CASTLE_BLOCKED_BOARD = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, NONE, NONE, NONE, B_KING, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, W_KNIGHT, NONE, NONE, W_KING, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::vector CASTLE_BLOCKED_MOVES = { + D2, E2, F2, + F1, D1, G1 +}; + +const int CASTLE_BLOCKED_QPOS = E8; +const std::array CASTLE_BLOCKED_QBOARD = { + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, B_ROOK, B_KNIGHT, NONE, NONE, B_KING, NONE, NONE, B_ROOK, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, NONE, NONE, NONE, NONE, NONE, NONE, NONE, NONE, INV, + INV, W_ROOK, W_KNIGHT, NONE, NONE, W_KING, NONE, NONE, W_ROOK, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV, + INV, INV, INV, INV, INV, INV, INV, INV, INV, INV +}; +const std::vector CASTLE_BLOCKED_QMOVES = { + D7, E7, F7, + F8, D8, G8 +}; // Check tests for king