An interactive Android game featuring a game board, different screens, game modes, and result handling. Built to practise Kotlin, declarative UI design, and Android app development.
An interactive Android game with multiple screens, game modes, and result handling.
Tic-Tac-Toe — Play and Have Fun is an interactive Android game developed with Kotlin and Jetpack Compose. The project was built as a hands-on exercise to practise modern Android development, declarative UI design, and game logic implementation. It features a clean game board, multiple screens, different game modes, and proper handling of game results.
Built entirely with Jetpack Compose, the app demonstrates a declarative approach to building Android UIs. State management drives the game flow—from the start screen through gameplay to the result screen—making the code predictable and easy to follow. The game supports both player-versus-player and other modes, with win, lose, and draw conditions handled cleanly.
Problem: A tic-tac-toe game requires the UI to update immediately every time a player makes a move. Without proper state management, the board can become inconsistent with the underlying game logic.
Solution: Used Jetpack Compose's state management to hold the board state as observable state. Each move updates the state, triggering automatic recomposition of the board UI. This keeps the displayed board perfectly in sync with the game logic.
Problem: Detecting a win or draw correctly requires checking all possible winning combinations (rows, columns, diagonals) after every move, while avoiding false positives and handling the draw condition.
Solution: Implemented a dedicated function that checks all eight winning lines after each move. If a line is fully occupied by the same player, a win is declared. If the board is full with no winner, a draw is declared. The result is then reflected in the UI.
Problem: The app has multiple screens (start, game, result), and moving between them while preserving or resetting game state can be tricky in a declarative UI framework.
Solution: Used Jetpack Compose Navigation to define routes for each screen. Game state is scoped appropriately so that starting a new game resets the board, while navigating back to the menu retains a clean starting point. This gives a smooth, intuitive flow.