CISC 124 - Assignment 1 - Due Friday, January 30, 2004 Your assignment is to build a text-based adventure game, based on the classic "Rogue" game. Players appear in a 2D scene drawn as characters on your screen. You control one of the players and the computer controls the others, who are monsters that chase and attack you. Your object is to collect as much treasure as possible before the monsters get you. Here's what your game might look like on the screen: ----+----- | | + | --------+- # # # ## -------------+- |.............| #######+.....*.B.....| |.............| |..........@..| --------------- The scene consists of rooms and passages. Each room is rectangular, and rooms are connected by passages (#) at doorways (+). Objects and monsters appear in the rooms. Above is gold (*), a bat (B), and you (@). You and the monsters take turns moving. On your move, you type in a single character and press Enter. (In this assignment, you'll have to press Enter after each command. Later in the course, we'll see how this can be avoided, so that you just press the motion key itself.) Type j to go down, k to go up, h to go left, and l to go right. Then each of the monsters moves at most one space. When you move over a treasure, you pick it up automatically. When you are within one space of a monster and move toward it, you are attacking it. Similarly, when a monster is within one space of you and moves toward you, it is attacking you. The attacker damages the attackee, reducing the health of the attackee, who dies when the health reaches zero. Not all attacks are successful, and the damage inflicted can vary randomly. Most of the scene is hidden from you. When you are in a room, the room and its contents are visible. When you leave a room, the interior of the room and anything inside it become invisible, but the walls remain (as though you were building a map of the scene). When you move along a passage, only the passage within one space of you is visible. But once you have seen a part of a passage, it remains visible, even if you leave it. To see how the real game works, you can play it online at http://www.hexatron.com/rogue/oldrogue.html You don't have to provide all of the functionality of the real game, but playing it will give you some ideas for Part 4 below. What's provided to you ---------------------- Some skeleton code is provided at http://www.cs.queensu.ca/~jstewart/124/a1 That code provides a base Player class from which you should derive your Person class and at least two classes of monster (perhaps a Bat and an Orc). That code provides a Board class which stores a grid of cells: 24 rows and 80 columns. The Board class provides an input method, which allows you to define the scene in a text file, and to read it in when the game starts. A sample scene is also provided. That code provides a rudimentary Game class which has the main() procedure. You can run the code to see how the scene is read in and displayed. What you have to do ------------------- 1. Develop derived classes for a Person and two monsters. The derived classes should override methods from the base Player class as appropriate. In particular, the proposeMove() and giveDamage() must be provided, since they're abstract in the Player class. Your Person class should generate a proposed move by querying the Console for a single character (one of j,k,h,l) with a call to console.readChar(), after moving the cursor to the bottom left of the screen with a call to console.setCursor(25,1). (The console has 25 rows and 80 columns.) Your monster classes should compute a proposed move based on the characteristics of the monster: Bats might flit randomly, and only start chasing you once they become hungry. Bats probably don't inflict much damage, while Orcs would inflict a lot. Orcs might be able to detect you if you're within the same room, and would chase you immediately. It's your decision on how your monsters should behave, and what damage they can inflict. You'll likely have to add methods to the Board class which can provide information to a monster when the monster is calculating its proposed move. Note that the Player class has a random number generator. You can generate random numbers for damage and for moving using the Random class: rand.nextInt() and rand.nextGaussian() are useful, for example. 2. Augment the Cell class to store a set of Treasures. Provide methods that allow a person to pick up all of the Treasures in a Cell. 3. Augment the Game class with a nextMove() method, which lets each Player move once, causes your Person to pick up a treasure when your Person moves onto one, detects an attack of one Player upon another (monsters should only attack the Person, and not other monsters) and transfers damage from the attacker to the attackee, and removes a Player when the Player dies. The nextMove() method should call helper methods where appropriate, to keep all of the game logic from being concentrated in a single method. In particular, there should be a helper method for the action of one Player attacking another. That method should transfer the damage and show a small status message on the screen, like "The bat hit you", "You hit the bat", or "The bat missed". The message stays on the screen until your Person makes its next move. The main() procedure should loop around, each time calling nextMove() and redrawing the scene. When the Person dies, the loop should terminate and a message should be displayed to summarize the Person's success, or lack of success. 4. Add at least one novel feature to the game. You choose the feature. It should be interesting and should take about 25% of your total work on this assignment.