A production-quality, GUI-based multiplayer Tic Tac Toe game built in Java, demonstrating core Operating Systems concepts including multithreading, synchronization, TCP socket programming, and concurrent resource management.
This project implements a full client-server multiplayer game using Java Swing for the GUI and raw TCP sockets for networking. Multiple clients can connect simultaneously, enter a matchmaking queue, and play concurrent Tic Tac Toe matches — all while the server coordinates everything with thread-safe shared state.
| Feature | Description |
|---|---|
| 🌐 Client-Server | Full TCP socket architecture |
| 🔁 Matchmaking Queue | Thread-safe FIFO queue with live position updates |
| 🎭 Concurrent Sessions | Multiple matches run simultaneously |
| 💬 In-Game Chat | Real-time chat panel during gameplay |
| 📊 Session Stats | Win/Loss/Draw stats shown in the header |
| 🎨 Modern Dark UI | Polished Swing GUI with animations |
project/
├── server/
│ ├── GameServer.java ← Main entry point; accept loop
│ ├── ClientHandler.java ← Per-client thread (state machine)
│ ├── GameSession.java ← Manages one match (board, turns, chat)
│ ├── MatchmakingQueue.java ← Thread-safe queue (ReentrantLock)
│ └── ServerUtils.java ← Logging, LAN IP
│
├── client/
│ ├── GameClient.java ← Client entry point
│ ├── NetworkManager.java ← TCP socket I/O on background thread
│ ├── GameGUI.java ← Game board window (Swing)
│ └── QueueScreen.java ← Login + queue waiting screen (Swing)
│
├── common/
│ ├── Message.java ← Protocol POJO
│ ├── MessageType.java ← All protocol message type enums
│ └── Protocol.java ← JSON builders/parsers (Gson)
│
├── lib/
│ └── gson-2.10.1.jar ← JSON serialization library
│
├── build.bat ← Windows build script
├── run_server.bat ← Launch server
└── run_client.bat ← Launch one client instance
- One thread per client:
GameServer.acceptLoop()spawns a newThread(ClientHandler)for every connection. With 4 clients connected, 4 threads run concurrently. - One thread per game session:
MatchmakingQueue.tryCreateMatch()starts aThread(GameSession)for each match. Two simultaneous matches = two session threads. - Background I/O thread:
NetworkManager.startListening()runs a dedicated reader thread on the client, preventing the Swing EDT from ever blocking.
ReentrantLockinMatchmakingQueue: Guards all queue reads and writes. MultipleClientHandlerthreads calladdPlayer()concurrently; the fair lock ensures no thread starves.synchronizedinGameSession.processMove(): Prevents two threads from modifying the board simultaneously (e.g., both players sending a move packet at the same instant).synchronized sendMessage()inClientHandler: Ensures only one thread writes to a socket'sPrintWriterat a time (game session + heartbeat may call it concurrently).
- Server:
ServerSocket.accept()(blocking OS call) returns aSocketper client. - Client:
Socket(host, port)opens a TCP connection to the server. - Data flows as newline-delimited JSON strings over
PrintWriter/BufferedReader.
ConcurrentHashMap-backedSet<ClientHandler>tracks active connections safely.- Timer tasks in
GameSessionare cancelled on game end to prevent resource leaks.
MatchmakingQueueuses aLinkedList(FIFO) with position broadcast after every add/remove.- Queue positions are re-numbered and pushed to clients in real time.
- When 4 clients join, two
GameSessionthreads start simultaneously — each with its own independent board, turn state, and timer.
All messages are JSON objects sent as single newline-delimited lines:
{ "type": "LOGIN", "payload": { "name": "Alice" } }
{ "type": "JOIN_QUEUE", "payload": {} }
{ "type": "QUEUE_UPDATE", "payload": { "position": 2, "total": 3 } }
{ "type": "MATCH_FOUND", "payload": { "opponent": "Bob", "symbol": "X" } }
{ "type": "MOVE", "payload": { "position": 4 } }
{ "type": "BOARD_UPDATE", "payload": { "board": "X_O_X____", "turn": "O" } }
{ "type": "GAME_OVER", "payload": { "result": "WIN", "winner": "Alice" } }
{ "type": "CHAT", "payload": { "sender": "Alice", "text": "gg!" } }
{ "type": "STATS_UPDATE", "payload": { "wins": 3, "losses": 1, "draws": 0 } }- Java 11 or higher (
java -version) lib/gson-2.10.1.jar(included / downloaded by setup)
build.batCompiles all .java files into out/.
run_server.batThe server prints its LAN IP and port. Example output:
[23:18:32] ╔══════════════════════════════════════════╗
[23:18:32] ║ Tic Tac Toe Game Server [OS Lab] ║
[23:18:32] ║ LAN IP : 192.168.1.105 ║
[23:18:32] ║ Port : 5555 ║
[23:18:32] ╚══════════════════════════════════════════╝
Open multiple terminals and run:
run_client.bat- Enter the server's IP shown above.
- Enter a username and click Join Queue.
- After 2 players join, a match starts automatically.
Run run_client.bat 4 times simultaneously → 2 matches start concurrently.
Main Thread (Server)
└─ acceptLoop() → [Thread: Client-192.168.1.x] ← ClientHandler #1
→ [Thread: Client-192.168.1.y] ← ClientHandler #2
→ [Thread: Client-192.168.1.z] ← ClientHandler #3
→ [Thread: Client-192.168.1.w] ← ClientHandler #4
│
MatchmakingQueue (ReentrantLock)
│ tryCreateMatch()
▼
[Thread: Session-Alice-vs-Bob] ← GameSession #1
[Thread: Session-Carol-vs-Dave] ← GameSession #2
Client Side:
EDT (Swing) ← all GUI operations
[Thread: NetworkReader] ← reads from socket, dispatches to EDT
- Spectator mode (observe live matches)
- Leaderboard screen with top-10 players
- Server-side replay recording
- TLS encryption for socket communication
- Web-based GUI alternative (React/WebSocket bridge)
- Room-based matchmaking (create/join named rooms)
| Technology | Purpose |
|---|---|
| Java 11+ | Core language |
| Java Swing | GUI framework |
TCP Sockets (ServerSocket / Socket) |
Network transport |
ReentrantLock |
Queue synchronization |
synchronized |
Board / send mutual exclusion |
ConcurrentHashMap |
Thread-safe client registry |
| Gson 2.10.1 | JSON serialization |
Timer / TimerTask |
Inactivity timeout |
(Run the application and add screenshots to this folder)
Built for the Operating Systems Lab — demonstrating real-world OS concepts through a working multiplayer game.