Assignment 3: A Dungeon Crawl
Due: Monday, June 7
Implement a simple "dungeon crawl"--a program emulating what a viewer would see walking through a labyrinth.
Specifications:
- The lay-out of the labyrinth will be specified in the file dungeon.dat, which your program must read at start-up. Each line of the file consists of asterix ('*'), space, and dollar sign ('$') characters. The asterices indicate the positions of solid walls, the dollar signs indicate the presence of "treasure", and the space characters correspond to empty space (i.e., corridors). The first and last character in each line will be an asterix, the first and last lines of the file will consist completely of asterices, and each line of the file will have the same number of characters.
- If your program cannot load "dungeon.dat", it must print an appropriate error message before terminating.
- The simulated viewer should start in the lower right-hand corner of the labyrinth, facing 'north' (along the positive y axis). (This will actually be at a position offset by one up and to the left from the bottom rightmost corner of the dungeon.dat array, which is a '*', and therefore a wall.)
- The walls appear to be tall enough that the camera can not see their tops. The camera should not be able to see through the walls.
- There should be a simulated "floor" that the camera can not see through.
- The "treasure" should be represented by some kind of object, perhaps a simple cube, tetrahedron, etc.
- The user should be able to move the viewer via a keypad and the arrow keys: 8 and up-arrow will move the viewer forward one space, 4 (and left-arrow) and 6 (and right-arrow) will turn the viewer 90 degrees to the left and right (but not otherwise move the viewer), 2 (and the back-arrow) will move the viewer backward one space, but not change the viewer's orientation. If forward of backward movement would take the viewer into a wall, then the action should have no effect (this prevents the camera from ending up "inside" a wall). Moving into a space that contains a treasure should remove that treasure from the labyrinth.
- The 'q' or 'Q' key should terminate the program.
- The 'r' or 'R' key should reset the dungeon and the viewer to their original states/orientations.
- When the program terminates, output to the command line the number of treasures that the viewer "collected" since the program first began running, and since the most recent reset.
- When including glut.h into your program, use the following, so that your code will be portable:
#if defined(__APPLE__) || defined(MACOSX)
#include <GLUT/glut.h>
#else
#include <GL/glut.h>
#endif
Here is a sample dungeon.dat input file.
Additional Specifications for 561 Students:
- Movement should be smooth. I.e., animate the movement from one square to the next.
- Provide sound using an appropriate library, such as OpenAL or fmod.
Hints:
You can use any lighting model, so long as the viewer can appreciate his/her position in the labyrinth.
There is an on-line tutorial explaining a simple way to effect apparent "camera movement" over fixed terrain, by Antonio Ramires Fernandes (you may have to click on the "Moving the Camera" link in the navigation bar there). The technique relies on maintaining variables representing the camera's postition and orientation. The variables are altered via the keyboard. They are then applied via the gluLookAt function to obtain the desired view. Here is a link to a slightly modified version of the code Ramires provides on his page. There is another excellent discussion at the on-line RedBook, http://glprogramming.com/red/chapter05.html#name3. See the section labelled "Moving the Light".
One way to work on this is to generate a rectangular prism for each "space" of the dungeon. Some spaces are walls ('*' in the input file), and some are corridors/rooms (space characters in the input file). For the former, generate "tall prisms". For the latter, generate "short prisms". The "floor" that the user walks upon is actually the tops of the short prisms. To that end, you probably want a function/method something like:
generatePrism(int mazeX, int mazeY, boolean isFloor)
This function could make the necessary glPolygon calls to generate the appropriate prism. The mazeX and mazeY are coordinates into the character array comprised by the input file.
Submission:
Submit your source code to the dropbox.