/// <summary> /// GetWalks - Получить прогулки /// Get availables walks /// Получить доступные прогулки /// </summary> /// <param name="moves"> /// Walk moves will be added to the collection /// Ходовые ходы будут добавлены в коллекцию /// </param> /// <param name="board"> /// the board state /// состояние правления /// </param> /// <param name="player"> /// the player /// игрок /// </param> private static void GetWalks(ICollection <Move> moves, IBoard board, Player player) { for (int pos = 1; pos <= BoardConstants.LightSquareCount; pos++) { Piece piece = board[pos]; Location location = Location.FromPosition(pos); int row = location.Row; int col = location.Col; if (BoardUtilities.IsOwner(player, piece)) { int forwardDirection = (BoardUtilities.IsBlack(piece)) ? 1 : -1; int backwardDirection = (!BoardUtilities.IsKing(piece)) ? 0 : (BoardUtilities.IsBlack(piece)) ? -1 : 1; GetWalks(moves, board, row, col, forwardDirection, -1); GetWalks(moves, board, row, col, forwardDirection, 1); if (backwardDirection != 0) { GetWalks(moves, board, row, col, backwardDirection, -1); GetWalks(moves, board, row, col, backwardDirection, 1); } } } }
/// <summary>Is the move legal. This move doesn't check multiple jumps.</summary> /// <param name="board">the board state</param> /// <param name="startRow">the start row</param> /// <param name="startCol">the start col</param> /// <param name="endRow">the end row</param> /// <param name="endCol">the end col</param> /// <param name="player">the player with the turn</param> /// <returns>LEGAL if the move is legal. Illegal if the move is not legal. INCOMPLETE if the move results in a jump.</returns> private static MoveStatus IsMoveLegal(IBoard board, int startRow, int startCol, int endRow, int endCol, Player player) { if (!InBounds(startRow, startCol, board) || !InBounds(endRow, endCol, board)) { // out of board bounds return(MoveStatus.Illegal); } Piece startPosition = board[startRow, startCol]; Piece endPosition = board[endRow, endCol]; if ((player == Player.Black && !BoardUtilities.IsBlack(startPosition)) || (player == Player.White && !BoardUtilities.IsWhite(startPosition))) { // wrong player attempting to make a move return(MoveStatus.Illegal); } else if (!BoardUtilities.IsEmpty(endPosition)) {// destination is not empty return(MoveStatus.Illegal); } int forwardDirection = (BoardUtilities.IsBlack(startPosition)) ? 1 : -1; int backwardDirection = (!BoardUtilities.IsKing(startPosition)) ? 0 : (BoardUtilities.IsBlack(startPosition)) ? -1 : 1; // check for single step along vertical axis if (Math.Abs(endRow - startRow) == 1) {//possible walk made // check if we took a walk when a jump was available if (CanJump(board, player)) { return(MoveStatus.Illegal); } // one step along the horizontal axis and proper vertical direction movement // men can't go backwards but kings can if ((Math.Abs(endCol - startCol) == 1) && (startRow + forwardDirection == endRow || startRow + backwardDirection == endRow)) { return(MoveStatus.Legal); } } else if (Math.Abs(endRow - startRow) == 2) {// possible jump made int jumpedRow = (endRow + startRow) / 2; int jumpedCol = (endCol + startCol) / 2; if (BoardUtilities.IsOpponentPiece(player, board[jumpedRow, jumpedCol])) { // one step along the horizontal axis and proper vertical direction movement // men can't go backwards but kings can if ((Math.Abs(endCol - startCol) == 2) && (startRow + forwardDirection * 2 == endRow || startRow + backwardDirection * 2 == endRow)) { return(MoveStatus.Incomplete); } } } return(MoveStatus.Illegal); }
/// <summary> /// GetCaptures - Получить захваты /// Generate captures list for the piece at the given location /// Создать список снимков для произведения в заданном месте /// </summary> /// <param name="moves"> /// stores the list of moves generated /// сохраняет список сгенерированных ходов /// </param> /// <param name="locations"> /// list of parent locations /// список родительских локаций /// </param> /// <param name="board"> /// the board state /// состояние правления /// </param> /// <param name="piece"> /// the piece /// кусок /// </param> /// <param name="row"> /// the row of the piece /// строка произведения /// </param> /// <param name="col"> /// the column of the piece /// столбец произведения /// </param> /// <param name="dx"> /// the horizontal direction /// горизонтальное направление /// </param> /// <param name="dy"> /// the vertical direction /// вертикальное направление /// </param> /// <returns><c>true</c> /// if capture available /// если захват доступен /// </returns> private static bool GetCaptures(ICollection <Move> moves, IList <Location> locations, IBoard board, Piece piece, int row, int col, int dx, int dy) { int endRow = row + dy * 2; int endCol = col + dx * 2; int jumpRow = row + dy; int jumpCol = col + dx; // jump available // прыжок доступен if (InBounds(endRow, endCol, board) && BoardUtilities.AreOpponents(piece, board[jumpRow, jumpCol]) && BoardUtilities.IsEmpty(board[endRow, endCol])) { locations.Add(new Location(endRow, endCol)); board[row, col] = Piece.None; board[jumpRow, jumpCol] = Piece.None; board[endRow, endCol] = piece; bool captureAvailable = false; int[] DIRECTIONS = { -1, 1 }; // {down/right, up/left} // {вниз / вправо, вверх / влево} int Y_START_INDEX = (BoardUtilities.IsKing(piece) || BoardUtilities.IsWhite(piece)) ? 0 : 1; int Y_END_INDEX = (BoardUtilities.IsKing(piece) || BoardUtilities.IsBlack(piece)) ? 1 : 0; for (int idxY = Y_START_INDEX; idxY <= Y_END_INDEX; idxY++) { for (int idxX = 0; idxX < DIRECTIONS.Length; idxX++) { bool result = GetCaptures( moves, new List <Location>(locations), board.Copy(), piece, endRow, endCol, DIRECTIONS[idxX], DIRECTIONS[idxY] ); captureAvailable = captureAvailable || result; } } if ((!captureAvailable) && (locations.Count > 1)) { Move move = new Move(); foreach (Location location in locations) { move.AddMoves(location); } moves.Add(move); } return(true); } else { return(false); } }
/// <summary>Generate captures list for the piece at the given location</summary> /// <param name="moves">stores the list of moves generated</param> /// <param name="locations">list of parent locations</param> /// <param name="board">the board state</param> /// <param name="piece">the piece</param> /// <param name="row">the row of the piece</param> /// <param name="col">the column of the piece</param> /// <param name="dx">the horizontal direction</param> /// <param name="dy">the vertical direction</param> /// <returns><c>true</c> if capture available</returns> private static bool GetCaptures(ICollection <Move> moves, IList <Location> locations, IBoard board, Piece piece, int row, int col, int dx, int dy) { int endRow = row + dy * 2; int endCol = col + dx * 2; int jumpRow = row + dy; int jumpCol = col + dx; // jump available if (InBounds(endRow, endCol, board) && BoardUtilities.AreOpponents(piece, board[jumpRow, jumpCol]) && BoardUtilities.IsEmpty(board[endRow, endCol])) { locations.Add(new Location(endRow, endCol)); board[row, col] = Piece.None; board[jumpRow, jumpCol] = Piece.None; board[endRow, endCol] = piece; bool captureAvailable = false; int[] directions = { -1, 1 }; // {down/right, up/left} int yStartIndex = (BoardUtilities.IsKing(piece) || BoardUtilities.IsWhite(piece)) ? 0 : 1; int yEndIndex = (BoardUtilities.IsKing(piece) || BoardUtilities.IsBlack(piece)) ? 1 : 0; for (int idxY = yStartIndex; idxY <= yEndIndex; idxY++) { foreach (int t in directions) { bool result = GetCaptures( moves, new List <Location>(locations), board.Copy(), piece, endRow, endCol, t, directions[idxY] ); captureAvailable = captureAvailable || result; } } if ((!captureAvailable) && (locations.Count > 1)) { Move move = new Move(); foreach (Location location in locations) { move.AddMoves(location); } moves.Add(move); } return(true); } else { return(false); } }
/// <summary>Generate captures list for the piece at the given location</summary> /// <param name="moves">capture moves will be added to the collection</param> /// <param name="board">the board state</param> /// <param name="row">the row of the piece</param> /// <param name="col">the column of the piece</param> private static void GetCaptures(ICollection <Move> moves, IBoard board, int row, int col) { Piece piece = board[row, col]; IList <Location> locations = new List <Location>(); locations.Add(new Location(row, col)); if (BoardUtilities.IsKing(piece) || BoardUtilities.IsBlack(piece)) { // go up GetCaptures(moves, new List <Location>(locations), board.Copy(), piece, row, col, -1, 1); // right GetCaptures(moves, new List <Location>(locations), board.Copy(), piece, row, col, 1, 1); // left } if (BoardUtilities.IsKing(piece) || BoardUtilities.IsWhite(piece)) { // go down GetCaptures(moves, new List <Location>(locations), board.Copy(), piece, row, col, -1, -1); // right GetCaptures(moves, new List <Location>(locations), board, piece, row, col, 1, -1); // left } }
/// <summary> /// CanJump - Может прыгать /// Check if piece at position can jump /// Проверьте, может ли кусок в положении прыгать /// </summary> /// <param name="board"> /// the board state /// состояние правления /// </param> /// <param name="row"> /// the row the piece is on /// строка, на которой стоит произведение /// </param> /// <param name="col"> /// the column the piece is on /// колонка, на которой находится произведение /// </param> /// <returns><code>true</code> /// if the piece can jump /// если кусок может прыгать /// </returns> static bool CanJump(IBoard board, int row, int col) { Piece piece = board[row, col]; if (!BoardUtilities.IsPiece(piece)) { return(false); } int forwardDirection = (BoardUtilities.IsBlack(piece)) ? 1 : -1; int backwardDirection = (!BoardUtilities.IsKing(piece)) ? 0 : (BoardUtilities.IsBlack(piece)) ? -1 : 1; return(CanJump(board, row, col, forwardDirection, -1) || CanJump(board, row, col, forwardDirection, 1) || (backwardDirection != 0 && ( CanJump(board, row, col, backwardDirection, -1) || CanJump(board, row, col, backwardDirection, 1) ) )); }
/// <summary> /// IsMoveLegal - Это законно /// Is the move legal. This move doesn't check multiple jumps. /// Это законный ход. Этот ход не проверяет несколько прыжков. /// </summary> /// <param name="board"> /// the board state /// состояние правления /// </param> /// <param name="startRow"> /// the start row /// начальный ряд /// </param> /// <param name="startCol"> /// the start col /// начальный столб /// </param> /// <param name="endRow"> /// the end row /// конец строки /// </param> /// <param name="endCol"> /// the end col /// конец колонки /// </param> /// <param name="player"> /// the player with the turn /// игрок с поворотом /// </param> /// <returns> /// LEGAL if the move is legal. Illegal if the move is not legal. INCOMPLETE if the move results in a jump. /// ЗАКОННЫЙ, если движение законно. Незаконный, если движение не законно. НЕПОЛНЫЙ, если движение приводит к скачку. /// </returns> private static MoveStatus IsMoveLegal(IBoard board, int startRow, int startCol, int endRow, int endCol, Player player) { if (!InBounds(startRow, startCol, board) || !InBounds(endRow, endCol, board)) { // out of board bounds //из границ правления return(MoveStatus.Illegal); } Piece startPosition = board[startRow, startCol]; Piece endPosition = board[endRow, endCol]; if ((player == Player.Black && !BoardUtilities.IsBlack(startPosition)) || (player == Player.White && !BoardUtilities.IsWhite(startPosition))) { // wrong player attempting to make a move //неправильный игрок, пытающийся сделать движение return(MoveStatus.Illegal); } else if (!BoardUtilities.IsEmpty(endPosition)) {// destination is not empty //место назначения не пусто return(MoveStatus.Illegal); } int forwardDirection = (BoardUtilities.IsBlack(startPosition)) ? 1 : -1; int backwardDirection = (!BoardUtilities.IsKing(startPosition)) ? 0 : (BoardUtilities.IsBlack(startPosition)) ? -1 : 1; // check for single step along vertical axis //проверьте на единственный шаг вдоль вертикальной оси if (Math.Abs(endRow - startRow) == 1) {//possible walk made //возможная ходьба сделана // check if we took a walk when a jump was available //проверьте, прогулялись ли мы, когда скачок был доступен if (CanJump(board, player)) { return(MoveStatus.Illegal); } // one step along the horizontal axis and proper vertical direction movement // один шаг по горизонтальной оси и правильное вертикальное движение // men can't go backwards but kings can // люди не могут идти назад, но короли могут if ((Math.Abs(endCol - startCol) == 1) && (startRow + forwardDirection == endRow || startRow + backwardDirection == endRow)) { return(MoveStatus.Legal); } } else if (Math.Abs(endRow - startRow) == 2) {// possible jump made // возможный прыжок сделан int jumpedRow = (endRow + startRow) / 2; int jumpedCol = (endCol + startCol) / 2; if (BoardUtilities.IsOpponentPiece(player, board[jumpedRow, jumpedCol])) { // one step along the horizontal axis and proper vertical direction movement // один шаг по горизонтальной оси и правильное вертикальное движение // men can't go backwards but kings can // люди не могут идти назад, но короли могут if ((Math.Abs(endCol - startCol) == 2) && (startRow + forwardDirection * 2 == endRow || startRow + backwardDirection * 2 == endRow)) { return(MoveStatus.Incomplete); } } } return(MoveStatus.Illegal); }