shon98 commited on
Commit
11d1573
ยท
1 Parent(s): d37ddd2

add readme

Browse files
Files changed (2) hide show
  1. LICENSE.txt +1 -0
  2. readme.md +194 -334
LICENSE.txt CHANGED
@@ -1,4 +1,5 @@
1
  Copyright (c) 2017 Josef Waller
 
2
 
3
  Permission is hereby granted, free of charge, to any person obtaining a copy
4
  of this software and associated documentation files (the "Software"), to deal
 
1
  Copyright (c) 2017 Josef Waller
2
+ Copyright (c) 2025 levinshon-98
3
 
4
  Permission is hereby granted, free of charge, to any person obtaining a copy
5
  of this software and associated documentation files (the "Software"), to deal
readme.md CHANGED
@@ -1,396 +1,256 @@
1
- # DEPRECATED: PyCatan has moved to this respository: https://github.com/josefwaller/PyCatan2
2
- # PyCatan
3
 
4
- A Library for simulating a game of *The Settlers of Catan*
5
 
6
- ## Run
7
 
8
- ### Download from pip3
9
- pip3 install pycatan
10
 
11
- ### Run tests from source
 
 
 
 
 
 
12
 
13
- #### Easy way
14
- Run the bash file test.sh
15
- `.test.sh'
16
 
17
- #### Hard Way
18
- * Install [virtualenv](https://virtualenv.pypa.io/en/stable/) and [virtualenvwrapper](https://virtualenvwrapper.readthedocs.io/en/latest/)
19
- * Create a new virtual environment (`mkvirtualenv test`)
20
- * Install [pytest](https://docs.pytest.org/en/latest/)
21
- * Run (from root directory) `python -m pytest tests`
22
-
23
- ## Contents
24
- * Documentation
25
- * `CatanGame`
26
- * `CatanBoard`
27
- * `CatanPlayer`
28
- * Etc
29
- * Example game
30
- * Something
31
-
32
- ## Documentation
33
-
34
- ### `CatanGame` module
35
-
36
- Represents a game of Catan
37
-
38
- #### Atttributes
39
-
40
- * `board`
41
- * The `CatanBoard` in the game
42
- * `players`
43
- * An array of `CatanPlayer`s (representing the players)
44
- * `longest\_road\_owner`
45
- * The index of the player who has the longest road
46
-
47
- #### Functions
48
-
49
- ##### `CatanGame.__init__(self, num_of_players=3, on_win=None, starting_board=False)`
50
-
51
- Creates a new `CatanGame`
52
- * `num_of_players`: The number of players playing the game
53
- * `on_win`: Optional function to run when the game is won
54
- * `starting_board`: Whether or not to use the beginner's board
55
-
56
-
57
-
58
- ##### `CatanGame.add_settlement(self, player, r, i, is_starting=False)`
59
-
60
- Builds a new settlement
61
-
62
- * `player`: The index of the player who is building the settlement
63
- * `r`: The row at which to build the settlement
64
- * `i`: The index at which to build the settlement
65
- * `is_starting`: Whether or not the settlement is being build during the building phase, and thus should be build for free
66
-
67
- Returns a `CatanStatus` value.
68
-
69
-
70
-
71
- ##### `CatanGame.add_road(self, player, start, end, is_starting=False)`
72
-
73
- Builds a new road
74
-
75
- * `player`: The index of the player building the road
76
- * `start`: An array with the coordinate of one the the road's points (given `[row, index]`)
77
- * `end`: An array with the coordinate of the road's other point (given `[row, index]`)
78
- * `is_starting`: Whether or not the road is being built during the building phase and thus should be build for free
79
-
80
- Returns a `CatanStatus` value
81
-
82
- ##### `CatanGame.add_city(self, r, i, player)`
83
-
84
- Builds a city on top of a settlement
85
-
86
- * `r`: The row at which to build the city
87
- * `i`: The index at which to build the city
88
- * `player`: The index of the player who is building the city
89
-
90
- Returns a `CatanStatus` value
91
-
92
- ##### `CatanGame.build_dev(self, player)`
93
-
94
- Builds a new developement card
95
-
96
- * `player`: The player who is building the developement card
97
-
98
- Returns a `CatanStatus` value
99
-
100
- ##### `CatanGame.use_dev_card(self, player, card, args)`
101
-
102
- Uses a developement card
103
-
104
- * `player`: The player who is using the card
105
- * `card`: The `CatanCard` value representing the type of card
106
- * `args`: Variable arguments in a dictionary depending on which type of developement card is played
107
- * `CatanCards.DEV_ROAD`: `args` contains `'road_one'` and `'road_two'` values, both of which are arrays of arrays coresponding to the point which the roads should be built
108
- * `road_one`: An array representing the first road in arrays representing points
109
- * Ex: `[[0, 0], [0, 1]]` would represent a road going from `0, 0` to `0, 1`
110
- * `road_two`: Same as `road_one`, but for the other road
111
- * `CatanCards.DEV_KNIGHT`: `args` contains `'robber_pos'` and `'victim'` values.
112
- * `robber_pos`: The position for the robber to be placed as an array, given as `[row, index]`
113
- * `victim`: The index of the player to take the card from. Can be `None` if the player playing the knight card doesn't want to take a card from anybody.
114
- * `CatanCards.DEV_MONOPOLY`: `args` contains a `'card_type'` value.
115
- * `card_type`: The `CatanCards` value representing the card the player wants to take
116
- * `CatanCards.DEV_YOP`: `args` contains `'card_one'` and `'card_two'` values.
117
- * `card_one`: The `CatanCards` value of the first card the player wants to take
118
- * `card_two`: The `CatanCards` value of the second card
119
- * `CatanCards.DEV_VP`: Do not call `CatanGame.use_dev_card` on `CatanCards.DEV_VP`, as players do not play VP cards, but keep them until the end of the game.
120
-
121
- ##### `CatanGame.add_yield_for_roll(self, roll)`
122
-
123
- Distributes cards based on a dice roll
124
-
125
- * `roll`: The dice roll
126
-
127
- Returns nothing
128
-
129
- ##### `CatanGame.get_roll(self)`
130
-
131
- Optional. Simulates 2 dice rolls added together.
132
-
133
- Returns a number
134
-
135
- ##### `CatanGame.trade(self, player_one, player_two, cards_one, cards_two)`
136
-
137
- Trades cards between players
138
- * `player_one`: The first player in the trade
139
- * `player_two`: The second player in the trade
140
- * `cards_one`: The cards the first player is giving
141
- * `cards_two`: The cards the second player is giving
142
-
143
- Returns a `CatanStatus` value
144
-
145
- ##### `CatanGame.trade_to_bank(self, player, cards, request)`
146
-
147
- Trades 4 cards to the bank for 1 card.
148
- Also will trade only 2 cards if the player is connected to the right harbor
149
-
150
- * `player`: The player who is trading the cards
151
- * `cards`: An array of numbers (`CatanCard` values) to trade from the player to the bank
152
- * `request`: The `CatanCard` value the player will receive
153
-
154
- Returns a `CatanStatus` value
155
-
156
-
157
- ### `CatanBoard`
158
-
159
- Represents a Catan game board.
160
-
161
- #### Static values
162
-
163
- * `CatanBoard.HEX_FOREST`
164
- * Represents a forest hex
165
- * `CatanBoard.HEX_Hills`
166
- * Represents a hills hex
167
- * `CatanBoard.HEX_MOUNTAINS`
168
- * Represents a mountains hex
169
- * `CatanBoard.HEX_PASTURE`
170
- * Represents a pasture hex
171
- * `CatanBoard.HEX_FIELDS`
172
- * Represents a fields hex
173
- * `CatanBoard.HEX_DESERT`
174
- * Represents a desert hex
175
-
176
- #### Attributes
177
-
178
- * `hexes`
179
- * An array representing the hexes on the board
180
- * `hex_nums`
181
- * An array representing the number tokens on the board
182
- * `points`
183
- * An array representing the intersections between hexes (where settlements are placed)
184
- * `roads`
185
- * An array of `CatanBuildings` representing all the roads in the game
186
- * `harbors`
187
- * An array of `CatanHarbors` representing all the harbors on the board
188
- * `robber`
189
- * An array representing the robber's position (given as `[row, index]`)
190
-
191
- #### Functions
192
-
193
- ##### `CatanBoard.get_card_from_hex(hex)`
194
- Gets a `CatanCards` value for a corresponding `CatanBoard` Hex value
195
- * `hex`: The `CatanBoard` hex value to get the card for
196
-
197
- Ex: `CatanBoard.get_card_from_hex(CatanBoard.HEX_HILLS)` would return `CatanCards.CARD_BRICK`
198
-
199
- Returns a `CatanCards` value
200
-
201
- ### `CatanBuilding`
202
-
203
- Represents a Catan Building
204
-
205
- #### Static Values
206
-
207
- ##### `CatanBuilding.BUILDING_ROAD`
208
-
209
- Represents a road
210
-
211
- ##### `CatanBuilding.BUILDING_SETTLEMENT`
212
-
213
- Represents a settlement
214
-
215
- ##### `CatanBuilding.BUILDING_CITY`
216
-
217
- Represents a city
218
-
219
- ### `CatanCards`
220
-
221
- Contains values representing different resource and developement cards
222
-
223
- #### Static Values
224
-
225
- ##### `CatanCards.CARD_WOOD`
226
-
227
- Represents a wood resource card.
228
-
229
- ##### `CatanCards.CARD_BRICK`
230
-
231
- Represents a brick resource card.
232
-
233
- ##### `CatanCards.CARD_SHEEP`
234
-
235
- Represents a sheep resource card.
236
-
237
- ##### `CatanCards.CARD_ORE`
238
-
239
- Represents a ore resource card.
240
-
241
- ##### `CatanCards.CARD_WHEAT`
242
-
243
- Represents a wheat resource card.
244
-
245
- ##### `CatanCards.DEV_ROAD`
246
-
247
- Represents a road building developement card.
248
-
249
- ##### `CatanCards.DEV_VP`
250
-
251
- Represents a victory point developement card.
252
-
253
- ##### `CatanCards.DEV_MONOPOLY`
254
-
255
- Represents a monopoly developement card.
256
-
257
- ##### `CatanCards.DEV_YOP`
258
-
259
- Represents a year of plenty developement card.
260
-
261
- ##### `CatanCards.DEV_KNIGHT`
262
-
263
- Represents a knight developement card.
264
-
265
- ### `CatanHarbor`
266
-
267
- Represents a harbor.
268
-
269
- #### Static values
270
-
271
- ##### `CatanHarbor.TYPE_WOOD`
272
-
273
- Represents a 2:1 Wood harbor
274
-
275
- ##### `CatanHarbor.TYPE_BRICK`
276
-
277
- Represents a 2:1 Brick harbor
278
-
279
- ##### `CatanHarbor.TYPE_WHEAT`
280
-
281
- Represents a 2:1 Wheat harbor
282
-
283
- ##### `CatanHarbor.TYPE_ORE`
284
 
285
- Represents a 2:1 Ore harbor
 
 
 
286
 
287
- ##### `CatanHarbor.TYPE_SHEEP`
288
 
289
- Represents a 2:1 Sheep harbor
 
 
290
 
291
- #### Functions
 
 
 
292
 
293
- ##### `CatanHarbor.get_type(self)`
 
 
294
 
295
- Returns a string representation of the harbor's type
 
296
 
297
- ### `CatanPlayer`
 
298
 
299
- Represents a player in the game.
 
 
300
 
301
- #### Functions
 
 
302
 
303
- ##### `CatanPlayer.get_VP(self, include_dev=False)`
 
 
304
 
305
- Returns the number of victory points the player has.
 
 
 
 
 
306
 
307
- * `include_dev`: Whether to include victory points from developement cards, which are only counted if the player wins and should be hidden otherwise.
 
308
 
309
- ### `CatanStatuses`
 
 
310
 
311
- Interger representation of different statuses returned by functions.
 
 
312
 
313
- #### Static values
314
 
315
- ##### `CatanStatuses.ALL_GOOD`
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
316
 
317
- The function ran successfully
318
 
319
- ##### `CatanStatuses.ERR_CARDS`
 
 
 
 
 
 
 
 
320
 
321
- The player trying to perform an action lacks the necessary cards.
322
 
323
- ##### `CatanStatuses.ERR_BLOCKED`
 
 
 
324
 
325
- A building is blocking the action.
 
326
 
327
- ##### `CatanStatuses.ERR_BAD_POINT`
 
 
328
 
329
- The point being used does not exist.
 
 
 
330
 
331
- ##### `CatanStatuses.ERR_NOT_CON`
 
 
332
 
333
- The player is trying to build a building which is not connected to any of their roads.
 
 
334
 
335
- ##### `CatanStatuses.ERR_HARBOR`
 
336
 
337
- The player is trying to use a harbor which they are not connected to
 
 
 
 
 
338
 
339
- ##### `CatanStatuses.ERR_NOT_EXIST`
340
 
341
- The player is trying to use a building which does not exist
342
 
343
- ##### `CatanStatuses.ERR_BAD_OWNER`
 
344
 
345
- The player is trying to use a building which belongs to another player
346
 
347
- ##### `CatanStatuses.ERR_UPGRADE_CITY`
 
 
 
 
 
 
 
 
 
348
 
349
- The player is trying to build a city on an invalid location
350
 
351
- ##### `CatanStatuses.ERR_DECK`
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
352
 
353
- There are not enough cards in the deck to perform this action
354
 
355
- ##### `CatanStatuses.ERR_INPUT`
 
 
356
 
357
- The input given is missing mandatory information
 
358
 
359
- ##### `CatanStatuses.ERR_TEST`
 
 
360
 
361
- When running the test module, an error was encountered
362
 
 
363
 
 
 
364
 
365
- ## Example game
 
366
 
367
- We're going to make an example text-game of Catan using *PyCatan*
 
368
 
369
- First, create a new file.
 
 
370
 
 
 
 
 
 
371
 
372
- `game.py`
373
 
374
- ```
375
- def main():
376
- print("Playing Catan!")
377
 
378
- if __name__ == "__main__":
379
- main()
380
- ```
381
 
 
382
 
383
- Now let's set up a new game of Catan
 
 
 
384
 
385
- `game.py`
386
 
387
- ```
388
- from PyCatan import CatanGame
389
 
390
- def main():
391
 
392
- num_of_players = int(input("How many players are playing? "))
 
393
 
394
- game = CatanGame(num_of_players)
395
 
396
- ```
 
1
+ # ๐ŸŽฒ PyCatan AI
 
2
 
3
+ A Python library for simulating and playing **The Settlers of Catan** with support for multiple interfaces and AI players.
4
 
5
+ > ๐Ÿš€ **Active Development**: This project extends the original [PyCatan](https://github.com/josefwaller/PyCatan) with a complete simulation framework including GameManager, AI players, and multiple visualization interfaces.
6
 
7
+ ## โœจ Features
 
8
 
9
+ - **Complete Game Logic** - Full implementation of Settlers of Catan rules
10
+ - **Multiple Interfaces**:
11
+ - ๐Ÿ–ฅ๏ธ Console/Terminal interface with colored output
12
+ - ๐ŸŒ Web browser interface with interactive board
13
+ - **Game Management** - Turn management, phases, and game flow control
14
+ - **Extensible Architecture** - Easy to add AI players and custom visualizations
15
+ - **Human & AI Players** - Support for multiple player types
16
 
17
+ ## ๐Ÿ“ฆ Installation
 
 
18
 
19
+ ### From Source
20
+ ```bash
21
+ git clone https://github.com/levinshon-98/PyCatan_AI.git
22
+ cd PyCatan_AI
23
+ pip install -e .
24
+ ```
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
25
 
26
+ ### Dependencies
27
+ ```bash
28
+ pip install flask # For web visualization
29
+ ```
30
 
31
+ ## ๐Ÿš€ Quick Start
32
 
33
+ ### Play a Full Game
34
+ ```python
35
+ from pycatan import RealGame
36
 
37
+ # Start an interactive game with console and web interfaces
38
+ game = RealGame()
39
+ game.run()
40
+ ```
41
 
42
+ ### Basic Game Setup
43
+ ```python
44
+ from pycatan import Game, Statuses
45
 
46
+ # Create a new game with 3 players
47
+ game = Game(num_of_players=3)
48
 
49
+ # Access the board
50
+ board = game.board
51
 
52
+ # Build a settlement (during setup phase)
53
+ point = board.points[0][0]
54
+ result = game.add_settlement(player=0, point=point, is_starting=True)
55
 
56
+ if result == Statuses.ALL_GOOD:
57
+ print("Settlement built successfully!")
58
+ ```
59
 
60
+ ### Using the Game Manager
61
+ ```python
62
+ from pycatan import GameManager, HumanUser, ConsoleVisualization
63
 
64
+ # Create players
65
+ users = [
66
+ HumanUser("Alice", player_num=0),
67
+ HumanUser("Bob", player_num=1),
68
+ HumanUser("Charlie", player_num=2)
69
+ ]
70
 
71
+ # Create game manager
72
+ game_manager = GameManager(users)
73
 
74
+ # Add visualization
75
+ console_viz = ConsoleVisualization()
76
+ game_manager.visualization_manager.add_visualization(console_viz)
77
 
78
+ # Start the game loop
79
+ game_manager.start_game()
80
+ ```
81
 
82
+ ## ๐Ÿ—๏ธ Architecture
83
 
84
+ ```
85
+ โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
86
+ โ”‚ GameManager โ”‚ โ† Manages turns and flow
87
+ โ”œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ค
88
+ โ”‚ โ€ข game_loop() โ”‚
89
+ โ”‚ โ€ข handle_turn_rules() โ”‚
90
+ โ”‚ โ€ข coordinate_interactions() โ”‚
91
+ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
92
+ โ”‚
93
+ โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ผโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
94
+ โ”‚ โ”‚ โ”‚
95
+ โ–ผ โ–ผ โ–ผ
96
+ โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ” โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ” โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
97
+ โ”‚ Game โ”‚ โ”‚ Users โ”‚ โ”‚Visualizationsโ”‚
98
+ โ”‚ (Core) โ”‚ โ”‚(Players)โ”‚ โ”‚ (Display) โ”‚
99
+ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
100
+ ```
101
 
102
+ ### Core Components
103
 
104
+ | Component | Description |
105
+ |-----------|-------------|
106
+ | `Game` | Core game logic - rules, validation, state management |
107
+ | `GameManager` | Turn management, game flow, user coordination |
108
+ | `User` | Abstract base class for players (Human/AI) |
109
+ | `HumanUser` | Human player with CLI input |
110
+ | `Visualization` | Base class for display interfaces |
111
+ | `ConsoleVisualization` | Terminal-based game display |
112
+ | `WebVisualization` | Browser-based interactive board |
113
 
114
+ ## ๐Ÿ“– Game Actions
115
 
116
+ ### Building
117
+ ```python
118
+ # Build settlement
119
+ game.add_settlement(player=0, point=point, is_starting=False)
120
 
121
+ # Build road
122
+ game.add_road(player=0, start=point1, end=point2, is_starting=False)
123
 
124
+ # Build city (upgrade settlement)
125
+ game.add_city(player=0, point=point)
126
+ ```
127
 
128
+ ### Trading
129
+ ```python
130
+ # Trade with bank (4:1)
131
+ game.trade_to_bank(player=0, give=ResCard.Wood, get=ResCard.Brick)
132
 
133
+ # Trade with harbor (3:1 or 2:1)
134
+ game.trade_to_bank(player=0, give=ResCard.Wheat, get=ResCard.Ore)
135
+ ```
136
 
137
+ ### Development Cards
138
+ ```python
139
+ from pycatan import DevCard
140
 
141
+ # Buy development card
142
+ game.build_dev(player=0)
143
 
144
+ # Use Knight card
145
+ game.use_dev_card(player=0, card=DevCard.Knight, args={
146
+ 'robber_pos': [2, 1],
147
+ 'victim': 1
148
+ })
149
+ ```
150
 
151
+ ## ๐ŸŽฎ Status-Based Error Handling
152
 
153
+ All game actions return `Statuses` enum values instead of exceptions:
154
 
155
+ ```python
156
+ from pycatan import Statuses
157
 
158
+ result = game.add_settlement(player=0, point=point)
159
 
160
+ match result:
161
+ case Statuses.ALL_GOOD:
162
+ print("Success!")
163
+ case Statuses.ERR_BLOCKED:
164
+ print("Location blocked by another building")
165
+ case Statuses.ERR_NOT_ENOUGH_RES:
166
+ print("Not enough resources")
167
+ case Statuses.ERR_BAD_LOCATION:
168
+ print("Invalid building location")
169
+ ```
170
 
171
+ ## ๐Ÿ—‚๏ธ Project Structure
172
 
173
+ ```
174
+ pycatan/
175
+ โ”œโ”€โ”€ game.py # Core game logic
176
+ โ”œโ”€โ”€ game_manager.py # Turn and flow management
177
+ โ”œโ”€โ”€ board.py # Board base class
178
+ โ”œโ”€โ”€ default_board.py # Standard Catan board
179
+ โ”œโ”€โ”€ player.py # Player state management
180
+ โ”œโ”€โ”€ card.py # Resource and development cards
181
+ โ”œโ”€โ”€ actions.py # Action types and results
182
+ โ”œโ”€โ”€ user.py # User base class
183
+ โ”œโ”€โ”€ human_user.py # Human player implementation
184
+ โ”œโ”€โ”€ visualization.py # Visualization base class
185
+ โ”œโ”€โ”€ console_visualization.py # Console display
186
+ โ”œโ”€โ”€ web_visualization.py # Web interface
187
+ โ”œโ”€โ”€ real_game.py # Complete game orchestration
188
+ โ””โ”€โ”€ statuses.py # Status codes for actions
189
+
190
+ tests/ # Unit tests
191
+ examples/ # Usage examples
192
+ ```
193
 
194
+ ## ๐Ÿงช Running Tests
195
 
196
+ ```bash
197
+ # Run all tests
198
+ python -m pytest tests/
199
 
200
+ # Run specific test file
201
+ python -m pytest tests/test_game.py
202
 
203
+ # Run with verbose output
204
+ python -m pytest tests/ -v
205
+ ```
206
 
207
+ ## ๐ŸŒ Web Visualization
208
 
209
+ The web visualization provides an interactive board in your browser:
210
 
211
+ ```python
212
+ from pycatan import WebVisualization, create_web_visualization
213
 
214
+ # Create web visualization
215
+ web_viz = create_web_visualization(port=5000)
216
 
217
+ # Start server (opens browser automatically)
218
+ web_viz.start()
219
 
220
+ # Update with game state
221
+ web_viz.update_full_state(game_state)
222
+ ```
223
 
224
+ **Features:**
225
+ - ๐Ÿ—บ๏ธ Interactive hexagonal board
226
+ - ๐Ÿ”„ Real-time updates via Server-Sent Events
227
+ - ๐Ÿ“Š Player info panel with resources and points
228
+ - ๐Ÿ“œ Action log with timestamped events
229
 
230
+ ## ๐Ÿ“š Documentation
231
 
232
+ - [Architecture Overview](.github/instructions/ARCHITECTURE.md) - Project design and components
233
+ - [Build Plan](.github/instructions/BUILD_PLAN.md) - Development roadmap and progress
234
+ - [Coding Instructions](.github/copilot-instructions.md) - Development guidelines
235
 
236
+ ## ๐Ÿค Contributing
 
 
237
 
238
+ Contributions are welcome! Please:
239
 
240
+ 1. Fork the repository
241
+ 2. Create a feature branch
242
+ 3. Write tests for new functionality
243
+ 4. Submit a pull request
244
 
245
+ ## ๐Ÿ“„ License
246
 
247
+ This project is licensed under the MIT License - see the [LICENSE.txt](LICENSE.txt) file for details.
 
248
 
249
+ ## ๐Ÿ™ Acknowledgments
250
 
251
+ - Original [PyCatan](https://github.com/josefwaller/PyCatan) by Josef Waller
252
+ - The Settlers of Catanยฎ is a trademark of Catan GmbH
253
 
254
+ ---
255
 
256
+ **Made with โค๏ธ for Catan enthusiasts and AI developers**