---
# System prepended metadata

title: CS50 Nuggets Project

---

# CS50 Nuggets Project
## Design Spec 

In this document we reference the Requirements Spec and focus on the implementation-independent design decisions. We focus on the: 

- User interface
- Inputs and outputs
- Functional decomposition into modules
- Pseudo code (plain English-like language) for logic/algorithmic flow
- Major data structures
- Testing plan


### User interface
## *client*

Described in the Requirements Spec, the Nuggets client will begin with the commandline; it will need three arguments. 

```
./client hostname port [playername]
```
The client program lets users join the game as players or spectators, with each commandline argument helping set the game up: 
`hostname`: *IP Adress where server runs.*
`port`: *Port number on which server receives messages* 
`playername`: *(optional): Determines if user will join as player or spectator. If provided, client will join as player and if not the client will join as spectator.*

*Gameplay*: 
* Players will use keystrokes to move within the game. 
* Spectators will be able to observe the game without being able to control anything.
    
*Display*:
* The game display is a grid which represents the game map. 
* The display has different symbols that represent the player, gold, areas, and boundaries. 

## *server* 
The Nuggets server's has no contact with the user and will start with the commandline; it will need two arguments.  
``` bash
$ ./server map.txt [seed]
```
The following arguments are for the server program: 
`map.txt`: The pathname for a map file that creates the game. It has information concerning the rooms, halls, and other map information. 
`seed`(optional): This is an optional seed for a random number generator. If seed is included it must be a positive integer. 





### Inputs and outputs
### *client*
**Input**: The client's inputs are received through the commandline arguments discussed above and user interactions in the game.  

User interactions depend on keystrokes which are responsible for action in the game. 
* Player Keystrokes: 
    * Q: Quit the game.
    * h: Move left
    * l: Move right
    * j: Move down
    * k: Move up
    * y: Move diagonally up and left
    * u: Move diagonally up and right
    * b: Move diagonally down and left
    * n: Move diagonally down and right
* Spectator Keystrokes: 
    * `Q`: Quit the game. 




**Output**: The client outputs information regarding the game and does not print anything to stdout other than what is required: 
* Display:
    * Game Status: The client will display a line at the top of the display concerning game status. For a player status line, the output will look like this:
        * Player A has 39 nuggets (211 nuggets unclaimed).
For a spectator, the output will look like:
        * Spectator: 211 nuggets unclaimed.
    * Game Grid: The client will display the game grid, or map, on lines in the display. The grid represents the map of the world and will display characters and nuggets. 
* Errors: The client is able to print error messages to stderr if the program encounters any errors during its execution.
* Logging: The program is able to log important information to a logfile that concerns game events, errors or other details. 

### *server*
**Input**: The server reads an address to a *map.txt* file. It can assume that the file is a text with NR lines and NR characters. The server also assumes that all map files submitted are already valid.

**Output**:The server does not print anything out that is not required for the game. Its outputs include: 
* Game Updates: Server updates the game based on client actions, showing any changes to all clients. Actions like movement, gold amount, and changes in game map. 
* Game-over Message: When all gold nuggets are found, the server creates a game-over summary. This message shows the player's name and amount of nuggets they collected. 
* Network Status: The server sends messages about the network to clients. Messages concerning the game grid, status updates, and error messages. 
* Logging: The server is able to log information to a logfile that could include warnings or errors. This can save details about client connection so that instead of going to stderr, it goes to a logfile. 
* Error Messages: When errors occur, like invalid commandline arguments, errors with files, network problems, the server is able to create error messages that will accurately inform the user about the issue. 


### Functional decomposition into modules

We anticipate the following modules or functions:

 1. *main*, which parses arguments and initializes other modules;
 2. *parse_input* will parse the input that each player sends, which will start with either `move` or `quit`
     - The player movement will be sent in the format:
`move [playerID] [direction]`
    - The player quitting the game will be sent in the format `quit [playerID]`, which will disconnect the client and remove the player from 
 4. *player_move* will move a given player in a given direction (if posible)
 5. *player_disconnect* will disconnect the given player
 6. *player_delete* will free all of the players allocated memory
 7. *game_end* will end the game and display the amount of nuggets colleted


And some helper modules that provide data structures:

 1. *grid* a module which is responsible for player movement within the map structure. It integrates the *visibility* module. 
 2. *visibility* a module which is in charge of implementing the visibility functionality referenced in the Requirements spec.  

### Pseudo code for logic/algorithmic flow

The Server will run as follows:

    (validation)
    parse the command line, validate parameters
    if error occurs
        print error messege
        exit non zero
    
    (assuming validation for map readability already done)
    load designated map into memory
       
    (initialization of the game) 
    Start game (by dropping at least GoldMinNumPiles at most GoldMaxNumPiles)
    initialize the network and announce the port number
    
    (enter the loop)
    while listening on the port
        
        (check for connections)
        if a new connection registered
            (check whether it`s a palyer or spectator)
            if new connection equals player
                add the player to the player set data structure
                add the player to the map 
            else
                (check if the spectator is empty since we need only one spectator/ might add this functionality somewhere else not here)
                add to the spectator set
                
        (handle other messeges)
        
        else 
            (handle non connection messeges)
            if a new messege command
                run functions related to that messege
                
            (check for the game terminating messege)
            if all gold collected 
                stop game
            
            (update the map)
            present the score table
        
            
    
The Client will run as follows: 
        
    (validation)
    parse the command line, validate parameters
    if error occurs
        print error messege
        exit non zero
        
    (determine how to join)    
    if playername provided
        join the game as a player
        
    else
        join as a spectator
        
    initialize the game
        
    (looping)
    
    while the game is running
        ensure the correct size of the grid
        
        (if user == player)
        if input registered
            send to server
        (handle data from the server)
        
        if quit messege
            send quit to server
            (the game terminates upon receiving confirmation)
            
    (if the game is over)
    print game over summary
        

    


### Major data structures

The major data structures in `nuggets` are `player_t` and `grid_t`.

#### player_t structure:
The `player_t` structure represents a player and contains the following fields:
1. `x`: The x-coordinate of the player's position.
2. `y`: The y-coordinate of the player's position.
3. `nuggets_collected`: The number of nuggets collected by the player.
4. `visited`: A 2D array (char**) representing the map tiles visited by the player.

The `player_t` structure stores information about a player, including their position, collected nuggets, and the visited map tiles.

#### grid_t structure:
The `grid_t` structure represents the game grid and contains the following fields:
1. `numRows`: The number of rows in the grid.
2. `numColumns`: The number of columns in the grid.
3. `data`: A 2D array (char**) representing the grid data.
4. `gridstring`: A string representation of the grid data.

The `grid_t` structure stores information about the game grid, including its size, the grid data itself, and a string representation of the grid.

These data structures provide the necessary information for managing player positions, collecting nuggets, and representing the game grid in the `grid.c` module
 

### Testing plan
1. *Unit Test*:
    * Create unit tests that will validate functionality of functions and modules in the client program. 
    * Test functions with different scenarios. 
    * Practice module grid to handle visibility, and other map calculations. 
2. *Integration Test*: 
    * Test the client program, and server program using Linux server in the Thayer collection. Clients will be run on `plank` and server programs on `babylon5`. 
    * Use given `miniclient` program that will give messages to server. This allows for the server to be tested on response to different messages. 
    * Use the given `client`, `server`, `padmap`, and `checkmap`  to test certain components of the `nuggets` program. They will be run with their respective pathnames, such as; 
```
~/cs50-dev/shared/nuggets/linux/server ...
~/cs50-dev/shared/nuggets/linux/client ...
```
1. We will test the `nuggets` program with various invalid arguments. 
* 2. No arguments provided
* 3. One argument provided
* 4. Two arguments provided
* 5. Invalid hostname (non-existent or unreachable server)
* 6. Invalid port (unavailable or blocked port)
* 7. Invalid playername (unsupported or invalid player name)



