Skip to content

Commit

Permalink
Merge pull request #31 from nwagu/dev
Browse files Browse the repository at this point in the history
Dev
  • Loading branch information
nwagu authored Jul 24, 2021
2 parents 11a5857 + 9514228 commit 86dadf7
Show file tree
Hide file tree
Showing 56 changed files with 254 additions and 166 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ fun HistoryView(
.verticalScroll(rememberScrollState())
) {

for (gamePgn in gamesHistory.asReversed()) {
for (gamePgn in gamesHistory) {
PreviousGameView(modifier = Modifier.fillMaxWidth(), gamePgn) {
context.gameAnalysisViewModel.pgn = gamePgn
navHostController.navigate(Screen.GameAnalysis.route)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ fun PlayViewPortrait(
verticalArrangement = Arrangement.Center
) {
PlayerDisplay(modifier = Modifier, viewModel, viewModel.game.colorOnUserSideOfBoard.opposite())
ChessBoardView(modifier = Modifier.fillMaxWidth(), navHostController, viewModel)
ChessBoardView(modifier = Modifier.fillMaxWidth(), viewModel)
PlayerDisplay(modifier = Modifier, viewModel, viewModel.game.colorOnUserSideOfBoard)
Row(modifier = Modifier
.fillMaxWidth()
Expand Down Expand Up @@ -227,7 +227,6 @@ fun PlayViewLandscape(
) {
ChessBoardView(
modifier = Modifier.width((screenConfig.screenWidthDp - 64).dp),
navHostController,
viewModel
)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,6 @@ import kotlinx.serialization.json.*
@Composable
fun ChessBoardView(
modifier: Modifier = Modifier,
navHostController: NavHostController,
viewModel: PlayViewModel
) {

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -126,9 +126,6 @@ fun PreviousGameView(
val whitePlayer = getHeaderValueFromPgn(PGN_HEADER_WHITE_PLAYER, pgn)
val blackPlayer = getHeaderValueFromPgn(PGN_HEADER_BLACK_PLAYER, pgn)

val board = Board()
board.importMovesFromPGN(pgn)

Card(
modifier = modifier.padding(8.dp),
onClick = {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import com.nwagu.chess.gamelogic.moves.*

fun Board.validateMoveDoesNotLeaveKingExposed(move: Move): Boolean {
move(move, false)
val kingNotExposed = !isOnCheck(getSquareOccupant(move.destination).chessPieceColor)
val kingNotExposed = !isOnCheck(getSquareOccupantAsChessPiece(move.destination).chessPieceColor)
undoMove()
return kingNotExposed
}
Expand Down
26 changes: 11 additions & 15 deletions chess/src/commonMain/kotlin/com/nwagu/chess/gamelogic/Move.kt
Original file line number Diff line number Diff line change
Expand Up @@ -7,19 +7,17 @@ import com.nwagu.chess.gamelogic.moves.*
fun Board.move(move: Move, attachSan: Boolean = true): Boolean {

val movingPiece = try {
getSquareOccupant(move.source)
getSquareOccupantAsChessPiece(move.source)
} catch (e: Exception) {
return false
}

when(move) {
is RegularMove -> {
movingPiece.numberOfMovesMade++
squaresMap[move.destination].let { captive ->
if (captive is ChessPiece) {
move.isCapture = true
captives.add(captive)
}
getSquareOccupantAsChessPieceOrNull(move.destination)?.let { captive ->
move.isCapture = true
captives.add(captive)
}
setSquareOccupant(move.source, EmptySquare)
setSquareOccupant(move.destination, movingPiece)
Expand All @@ -32,11 +30,9 @@ fun Board.move(move: Move, attachSan: Boolean = true): Boolean {
startingRow = movingPiece.startingRow,
startingColumn = movingPiece.startingColumn
)
squaresMap[move.destination].let { captive ->
if (captive is ChessPiece) {
move.isCapture = true
captives.add(captive)
}
getSquareOccupantAsChessPieceOrNull(move.destination)?.let { captive ->
move.isCapture = true
captives.add(captive)
}
setSquareOccupant(move.source, EmptySquare)
setSquareOccupant(move.destination, promotionPiece)
Expand All @@ -45,7 +41,7 @@ fun Board.move(move: Move, attachSan: Boolean = true): Boolean {
val captivePosition = square(row(move.source), column(move.destination))
move.isCapture = true
movingPiece.numberOfMovesMade++
captives.add(getSquareOccupant(captivePosition))
captives.add(getSquareOccupantAsChessPiece(captivePosition))
setSquareOccupant(move.source, EmptySquare)
setSquareOccupant(move.destination, movingPiece)
setSquareOccupant(captivePosition, EmptySquare)
Expand All @@ -55,7 +51,7 @@ fun Board.move(move: Move, attachSan: Boolean = true): Boolean {
val rookSource = getCastlePartnerSourceForKingMove(move.source, move.destination)
val rookDestination = getCastlePartnerDestinationForKingMove(move.source, move.destination)

val rook = getSquareOccupant(rookSource)
val rook = getSquareOccupantAsChessPiece(rookSource)

movingPiece.numberOfMovesMade++
rook.numberOfMovesMade++
Expand Down Expand Up @@ -87,7 +83,7 @@ fun Board.undoMove(): Move? {
val move = movesHistory.removeLastOrNull() ?: return null

val movingPiece = try {
getSquareOccupant(move.destination)
getSquareOccupantAsChessPiece(move.destination)
} catch (e: Exception) {
return null
}
Expand Down Expand Up @@ -128,7 +124,7 @@ fun Board.undoMove(): Move? {
val rookSource = getCastlePartnerSourceForKingMove(move.source, move.destination)
val rookDestination = getCastlePartnerDestinationForKingMove(move.source, move.destination)

val rook = getSquareOccupant(rookDestination)
val rook = getSquareOccupantAsChessPiece(rookDestination)

movingPiece.numberOfMovesMade--
rook.numberOfMovesMade--
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,22 +4,22 @@ import com.nwagu.chess.model.*

fun Board.squareEmpty(square: Square) = squaresMap[square] is EmptySquare

fun Board.squareContainsOccupantColored(square: Square, color: ChessPieceColor): Boolean {
return getSquareOccupantOrNull(square)?.chessPieceColor == color
fun Board.squareContainsChessPieceColored(square: Square, color: ChessPieceColor): Boolean {
return getSquareOccupantAsChessPieceOrNull(square)?.chessPieceColor == color
}

fun Board.squareOccupantHasNotMoved(square: Square): Boolean {
if (squareEmpty(square))
return false

return getSquareOccupant(square).numberOfMovesMade == 0
return getSquareOccupantAsChessPiece(square).numberOfMovesMade == 0
}

fun Board.destinationIsEmptyOrHasEnemy(destination: Square, color: ChessPieceColor): Boolean {
return if (squareEmpty(destination))
true
else
getSquareOccupant(destination).chessPieceColor != color
getSquareOccupantAsChessPiece(destination).chessPieceColor != color
}

fun Board.destinationContainsAnEnemy(destination: Square, color: ChessPieceColor): Boolean {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ val Board.turn: ChessPieceColor
get() {
try {
val lastMove = movesHistory.lastOrNull() ?: return ChessPieceColor.WHITE
return getSquareOccupant(lastMove.destination).chessPieceColor.opposite()
return getSquareOccupantAsChessPiece(lastMove.destination).chessPieceColor.opposite()
} catch (e: Exception) {
e.printStackTrace()
TODO()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ fun Board.getPossibleMovesFrom(source: Square): List<Move> {
if (squareEmpty(source))
return emptyList()

val possibleMoves = when (getSquareOccupant(source).chessPieceType) {
val possibleMoves = when (getSquareOccupantAsChessPiece(source).chessPieceType) {
ChessPieceType.QUEEN -> {
getQueenMovesFrom(source)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ import com.nwagu.chess.model.*

fun Board.getBishopMovesFrom(source: Square): List<Move> {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.BISHOP)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.BISHOP)
throw IllegalStateException("Type must be BISHOP!")

return this.squaresMap.keys.filter { destination ->
canBishopMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(destination, getSquareOccupant(source).chessPieceColor)
destinationIsEmptyOrHasEnemy(destination, getSquareOccupantAsChessPiece(source).chessPieceColor)
}.map { destination ->
RegularMove(source, destination)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import com.nwagu.chess.model.Board

val Board.isWhiteQueenSideCastlingAvailable: Boolean
get() {
return (getSquareOccupant(whiteKingPosition).numberOfMovesMade == 0) &&
return (getSquareOccupantAsChessPiece(whiteKingPosition).numberOfMovesMade == 0) &&
run {
val queenSideCastlingRookSquare = square(row(whiteKingPosition), column(whiteKingPosition) - 4)
squareOccupantHasNotMoved(queenSideCastlingRookSquare)
Expand All @@ -18,7 +18,7 @@ val Board.isWhiteQueenSideCastlingAvailable: Boolean

val Board.isWhiteKingSideCastlingAvailable: Boolean
get() {
return (getSquareOccupant(whiteKingPosition).numberOfMovesMade == 0) &&
return (getSquareOccupantAsChessPiece(whiteKingPosition).numberOfMovesMade == 0) &&
run {
val kingSideCastlingRookSquare = square(row(whiteKingPosition), column(whiteKingPosition) + 3)
squareOccupantHasNotMoved(kingSideCastlingRookSquare)
Expand All @@ -27,7 +27,7 @@ val Board.isWhiteKingSideCastlingAvailable: Boolean

val Board.isBlackQueenSideCastlingAvailable: Boolean
get() {
return (getSquareOccupant(blackKingPosition).numberOfMovesMade == 0) &&
return (getSquareOccupantAsChessPiece(blackKingPosition).numberOfMovesMade == 0) &&
run {
val queenSideCastlingRookSquare = square(row(blackKingPosition), column(blackKingPosition) - 4)
squareOccupantHasNotMoved(queenSideCastlingRookSquare)
Expand All @@ -36,7 +36,7 @@ val Board.isBlackQueenSideCastlingAvailable: Boolean

val Board.isBlackKingSideCastlingAvailable: Boolean
get() {
return (getSquareOccupant(blackKingPosition).numberOfMovesMade == 0) &&
return (getSquareOccupantAsChessPiece(blackKingPosition).numberOfMovesMade == 0) &&
run {
val kingSideCastlingRookSquare = square(row(blackKingPosition), column(blackKingPosition) + 3)
squareOccupantHasNotMoved(kingSideCastlingRookSquare)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ import kotlin.math.abs

fun Board.getKingMovesFrom(source: Square): List<Move> {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.KING)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.KING)
throw IllegalStateException("Type must be KING!")

return this.squaresMap.keys.filter { destination ->
canKingMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(destination, getSquareOccupant(source).chessPieceColor)
destinationIsEmptyOrHasEnemy(destination, getSquareOccupantAsChessPiece(source).chessPieceColor)
}.map { destination ->
if (abs(column(source) - column(destination)) == 2)
Castling(source, destination)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ import kotlin.math.abs

fun Board.getKnightMovesFrom(source: Square): List<Move> {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.KNIGHT)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.KNIGHT)
throw IllegalStateException("Type must be KNIGHT!")

return this.squaresMap.keys.filter { destination ->
canKnightMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(destination, getSquareOccupant(source).chessPieceColor)
destinationIsEmptyOrHasEnemy(destination, getSquareOccupantAsChessPiece(source).chessPieceColor)
}.map { destination ->
RegularMove(source, destination)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,14 @@ fun Board.getPawnMovesFrom(source: Square): List<Move> {

try {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.PAWN)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.PAWN)
throw IllegalStateException("Type must be PAWN!")

return this.squaresMap.keys.filter { destination ->
canPawnMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(
destination,
getSquareOccupant(source).chessPieceColor
getSquareOccupantAsChessPiece(source).chessPieceColor
)
}.map { destination ->
if (column(destination) != column(source) && squareEmpty(destination))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,12 @@ import com.nwagu.chess.model.*

fun Board.getQueenMovesFrom(source: Square): List<Move> {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.QUEEN)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.QUEEN)
throw IllegalStateException("Type must be QUEEN!")

return this.squaresMap.keys.filter { destination ->
canQueenMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(destination, getSquareOccupant(source).chessPieceColor)
destinationIsEmptyOrHasEnemy(destination, getSquareOccupantAsChessPiece(source).chessPieceColor)
}.map { destination ->
RegularMove(source, destination)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,12 @@ import com.nwagu.chess.model.*

fun Board.getRookMovesFrom(source: Square): List<Move> {

if (getSquareOccupant(source).chessPieceType != ChessPieceType.ROOK)
if (getSquareOccupantAsChessPiece(source).chessPieceType != ChessPieceType.ROOK)
throw IllegalStateException("Type must be ROOK!")

return this.squaresMap.keys.filter { destination ->
canRookMoveFrom(source, destination) &&
destinationIsEmptyOrHasEnemy(destination, getSquareOccupant(source).chessPieceColor)
destinationIsEmptyOrHasEnemy(destination, getSquareOccupantAsChessPiece(source).chessPieceColor)
}.map { destination ->
RegularMove(source, destination)
}
Expand Down
14 changes: 10 additions & 4 deletions chess/src/commonMain/kotlin/com/nwagu/chess/model/Board.kt
Original file line number Diff line number Diff line change
Expand Up @@ -15,22 +15,28 @@ class Board(
var whiteKingPosition: Int = 0

init {
reset()
clear()
}

fun reset() {
fun clear() {
movesHistory.clear()
captives.clear()
repeat(numberOfColumns * numberOfRows) { index ->
squaresMap[index] = EmptySquare
}
}

fun getSquareOccupant(square: Square): ChessPiece {
/*
* Throws an exception if square is empty
* */
fun getSquareOccupantAsChessPiece(square: Square): ChessPiece {
return squaresMap[square] as ChessPiece
}

fun getSquareOccupantOrNull(square: Square): ChessPiece? {
/*
* Returns null if square is empty
* */
fun getSquareOccupantAsChessPieceOrNull(square: Square): ChessPiece? {
return if (squareEmpty(square)) null else squaresMap[square] as ChessPiece
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,7 @@ data class ChessPiece(
var numberOfMovesMade: Int,
val startingRow: Int,
val startingColumn: Int
): SquareOccupant()
): SquareOccupant()

val ChessPiece.id: String
get() = "${chessPieceType.fenSymbol}_${startingRow}_${startingColumn}"
8 changes: 7 additions & 1 deletion chess/src/commonMain/kotlin/com/nwagu/chess/model/Game.kt
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,16 @@ import com.benasher44.uuid.uuid4
import com.nwagu.chess.representation.loadStandardStartingPosition

class Game(
val id: String = uuid4().toString(),
val id: String,
val whitePlayer: Player,
val blackPlayer: Player
) {
// Using a second constructor (instead of default arguments)
// in order to support initialization in swift
constructor(
whitePlayer: Player,
blackPlayer: Player
): this(uuid4().toString(), whitePlayer, blackPlayer)

var title = "${whitePlayer.name} (W) vs ${blackPlayer.name} (B)"

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ fun Board.loadStandardStartingPosition() {
* */
fun Board.loadPositionFromFen(fen: String) {

reset()
clear()

val pieceArrangement = fen.takeWhile { it != ' ' }

Expand Down Expand Up @@ -80,7 +80,7 @@ fun Board.getFen(): String {
return@repeat
}

val piece = getSquareOccupant(square)
val piece = getSquareOccupantAsChessPiece(square)

if (emptySquaresCount > 0) {
fen.append(emptySquaresCount)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ fun getHeaderValueFromPgn(name: String, pgn: String): String? {

fun Board.importMovesFromPGN(pgn: String) {

reset()
clear()
loadStandardStartingPosition()

val lines = pgn.split("\n")
Expand Down
Loading

0 comments on commit 86dadf7

Please sign in to comment.