Objectives To understand the design goal of reusability Introduction This project will give you an opportunity to reuse classes and methods you've already made to show how objects can work together beyond an individual assignment. You're back to card playing in this project, where you'll implement the card game Crazy Eights, which is the model for Uno, if you've ever played that. Unlike the last project, the goal here is to allow two or more users to play the game using a computer. Sorry: human players only. Take our AI course to learn about game-playing programs. The Game There are many variations of Crazy Eights, so here are the rules we'll be using. The game is played with a 104-card deck, so there are two instances of each card. At least two players are required, and each player is dealt seven cards from the shuffled deck. One card is placed face up for all to see. Each player plays a card that either matches the suit or value of the face-up card. So if the face- up card is a Jack of Clubs, the current player may play any Jack or any Club (including the other Jack of Clubs). Alternatively, the player may play any Eight, which acts as a wildcard. The player playing the Eight then announces the suit that the card will act as, which does not have to be the suit that is actually on the card. Play then goes to the next player, who must repeat the process. That is, she must play a card matching the suit or value of the new face-up card, play a card of the called suit if the previous player put down an Eight, or play an Eight herself. The winner is the first player to have no cards remaining. If a player has no playable cards in her hand, she must draw from the deck to find a playable card. A player can only pass if there are no cards remaining to draw. However, a player may choose to draw as many cards as she wants on her turn, even if she has a playable card in her hand. Your Mission Create a program that allows 2 or more humans to play Crazy Eights via keyboard input and System.out for output. Play may look something like this (the blue-green text is the user's input):
The game should announce when any player has exactly one card remaining (as a warning to the other players). The game will end when the computer announces a winner. The Details When first run, your program should ask the user for the number of players and then ask for the name of each player. You should also print instructions for how the user is to play the game. During each player's turn, the following should happen: 1. display the name of the person whose turn it is 2. display the player's hand 3. display the face-up card (including the suit that the card is acting as, if the card is an eight) 4. allow the user to input which card to play or else to indicate that the user wishes to draw a card. In the picture above, I let the user play a card by entering the number of the card in the displayed list. (The user could also have input "d" to draw.) You may choose a different route. For example, you may choose for the user to type in the value and suit of the card to be played. 5. if the user drew a card, add a card to the player's hand and go to step 2. If the user selected a card from her hand to play, but the card is an invalid play (not the right suit/value), tell the user so and go to step 2. If the selected card is valid, display it as the new face-up card and remove the card from the player's hand. If the card happened to be an eight, you'll also have to somehow let the user input the suit that it will act as. One way of doing this is in the picture above. 6. Once a card has been played, check to see if the player has any cards left. If not, you've got a winner. If just 1 card remains, announce that. Otherwise, this player's turn is over, and you can move on to the next player. Then go to step 1. You should reuse your Card and Deck classes from Project 2 in this project. Part of your job is to notice how easy or how difficult it is to incorporate these classes. Does a class work as-is? With minimal changes? With major changes? The best case is that a class works with no changes, but depending on how you built it in Project 2, that may or may not be possible. As this course goes on, we'll be talking a lot about how to make a class reusable, so that changes to the code are minimized despite changes to the context that may occur. For this project, you just need to document on a separate sheet of paper the changes you made to the Card and Deck classes (methods changed, instance variables added or removed, etc.) Turn this document in with your code. You'll also need the following classes. This time, I'm only telling you some of the methods and instance variables you'll need. You'll have to figure out the rest on your own. Hand This class represents the group of cards that a player is holding. instance variables: o the player who owns this hand o others? methods: o drawCard: a method to add a card from the deck to a hand o removeCard: a method to remove a card from a hand and return it. This method will need at least one parameter specifying the card to remove. You can do the specifying in many ways: as a Card object, as a suit and value, or as an int representing the number from the displayed list, to name a few. o seekCard: a method like removeCard in that it returns the Card specified in the parameter, but it doesn't remove it from the player's hand. o toString: a method that returns the hand as a printable string o others? CrazyEights This class contains everything specific to a game of Crazy Eights. This class should allow two or more players to play a game. instance variables: o You figure this out. What objects are absolutely necessary for a game of Crazy Eights to take place? methods: o Besides a constructor, only one method is really necessary: playGame. This method will play a game using the rules and skeletal algorithm described above. Remember to be modular. This is also the method where you'll be reading input from the user. How do you read from the console (also known as System.in)? Check out the docs for the Scanner class, especially the examples at the top of the document. It's pretty easy. Client A good rule of thumb is that your main method should be very short, since its only job is to create appropriate objects and then tell them to start running. Here, the only thing main needs to do is to create a CrazyEights object and tell it to run playGame. Remember to practice good programming skills: Comment before you write a method, not after. Use Javadoc format for all comments. Test each method individually. Private methods are your friends. Use them to modularize. Grading This project will be worth 50 points. It will be divided up this way: 20 points for a correctly working and thoroughly tested game. 15 points for the overall design of your code, including correct instance variables and methods. 10 points for modularity and understandability. Logic should be straightforward and complex only when necessary. Don't forget about named constants! 5 points for a good write-up of your changes. Remember to turn in both a paper and an electronic copy of your project. Don't forget the honor code affirmation. Having trouble? Don't wait until the last minute! Come see me and get your $80 worth. Gentle Reminder Programming assignments, like homework assignments, are individual projects. I encourage you to talk to others about the general nature of the project and ideas about how to pursue it. However, the technical work, the writing, and the inspiration behind these must be substantially your own. If any person besides you contributes in any way to the project, you must credit their work on your project. Similarly, if you include information that you have gleaned from other published sources, you must cite them as references. Looking at, and/or copying, other people's programs or written work is inappropriate, and will be considered cheating.