//MAKEFILE # To use this Makefile, just type make. That's it. CC = gcc LDLIBS = -L /usr/X11R6/lib -lGL -lGLU -lglut -lXmu -lX11 -lXi -lm INCLUDE = -I /usr/X11R6/include -I /usr/X11R6/include/GL executable: $(CC) -g $(INCLUDE) -o $I maze $I maze.c $(LDLIBS) -Wall ------------------------------------------------------------------------- //maze.h /*menu definitions*/ #define MENU_START_OVER 0 #define MENU_QUIT 1 #define MENU_FAST 2 #define MENU_LIGHTING 3 #define MENU_TEXTURE 4 /*room type and list definitions*/ #define ROOM_SEW 2 #define ROOM_SEW_TEX 3 #define ROOM_SEW_FAST 4 #define ROOM_EW 5 #define ROOM_EW_TEX 6 #define ROOM_EW_FAST 7 #define ROOM_NS 8 #define ROOM_NS_TEX 9 #define ROOM_NS_FAST 10 #define ROOM_N 11 #define ROOM_N_TEX 12 #define ROOM_N_FAST 13 #define ROOM_SW 14 #define ROOM_SW_TEX 15 #define ROOM_SW_FAST 16 #define ROOM_SE 17 #define ROOM_SE_TEX 18 #define ROOM_SE_FAST 19 #define ROOM_S 20 #define ROOM_S_TEX 21 #define ROOM_S_FAST 22 #define ROOM_NW 23 #define ROOM_NW_TEX 24 #define ROOM_NW_FAST 25 #define ROOM_NE 26 #define ROOM_NE_TEX 27 #define ROOM_NE_FAST 28 #define ROOM_W 29 #define ROOM_W_TEX 30 #define ROOM_W_FAST 31 #define ROOM_E 32 #define ROOM_E_TEX 33 #define ROOM_E_FAST 34 /*wall list definitions*/ #define WALL_N_FAST 35 #define WALL_S_FAST 36 #define WALL_E_FAST 37 #define WALL_W_FAST 38 #define WALL_N_TEX 39 #define WALL_S_TEX 40 #define WALL_E_TEX 41 #define WALL_W_TEX 42 #define WALL_N 43 #define WALL_S 44 #define WALL_E 45 #define WALL_W 46 /*ceiling and floor tiles*/ #define FLOOR_CEILING 47 #define FLOOR_CEILING_FAST 48 #define FLOOR_CEILING_TEX 49 /*size definitions*/ #define ROOMSIZE 20 #define ROOMSIZE2 10 /*game states*/ #define FAST 0 #define TEXTURE 1 #define LIGHTING 2 struct room { int xMin, zMin; int roomType; int inRoom; }; /*type definitions*/ typedef GLfloat xyPoint[2]; typedef GLfloat color3f[3]; typedef GLfloat color4f[4]; ------------------------------------------------------------------------- //maze.c /* This program is a 3D maze using lighting and textures. The user starts deep * in the maze and the goal of the game is to successfully traverse the maze*/ #include #include #include #include #include #include #include #include "maze.h" /*structures to hold room information*/ struct room roomArray[7][7]; /*texture array*/ GLubyte texture[64][64][GL_RGB]; /*light position*/ GLfloat lightPosition[] = {-2.0,1.0,5.0, 1.0}; GLfloat lightAmbient[] = {0.0,0.0,0.0, 1.0}; GLfloat lightDiffuse[] = {1.0,1.0,1.0, 1.0}; GLfloat lightSpecular[] = {0.0,0.0,0.0, 1.0}; /*floor material gray*/ GLfloat materialAmbient[] = {0.1,0.1,0.1, 1.0}; GLfloat materialDiffuse[] = {0.5,0.5,0.5, 1.0}; GLfloat materialSpecular[] = {0.5,0.5,0.5, 1.0}; GLfloat materialEmission[] = {0.0,0.0,0.0, 1.0}; GLfloat materialShininess[] = {0.0,0.0,0.0, 1.0}; /*floor material blue*/ GLfloat materialAmbient2[] = {0.1,0.0,0.0, 1.0}; GLfloat materialDiffuse2[] = {0.0,0.0,0.5, 1.0}; GLfloat materialSpecular2[] = {0.0,0.5,0.0, 1.0}; GLfloat materialEmission2[] = {0.0,0.0,0.0, 1.0}; GLfloat materialShininess2[] = {0.0,0.0,0.0, 1.0}; /*wall material green*/ GLfloat materialAmbient3[] = {0.0,0.1,0.0, 1.0}; GLfloat materialDiffuse3[] = {0.0,0.5,0.0, 1.0}; GLfloat materialSpecular3[] = {0.0,0.5,0.0, 1.0}; GLfloat materialEmission3[] = {0.0,0.0,0.0, 1.0}; GLfloat materialShininess3[] = {0.0,0.0,0.0, 1.0}; /*positional information*/ int xPos = 5; int zRot = 0; int zPos = 65; /*buffers for textures*/ GLubyte *walls; /*texture variables*/ int brick_H, brick_W; /*initialization functions*/ void setWindowVals(xyPoint size, xyPoint pos, char * name); void initSystem(color4f winColor, color3f drawColor, xyPoint startDisp, xyPoint endDisp, float ptSize); void initRooms(); void defineMenu(); void defineLists(); void loadTextures(); GLubyte * glmReadPPM(char* filename, int* width, int* height); /*menu handling function*/ void menuFunction(int ID); /*event handling functions*/ void keyboardReader(unsigned char key, int x, int y); void display(); /*movement handler*/ int moveOK(int x, int z); /*game state*/ int gameState = FAST; /*int main(int argc, char **argv) * This function initializes the maze, glut, the window, the GL system, * the menu, the lists, and then calls the glutMainLoop*/ int main(int argc, char **argv){ xyPoint startDisplay = {0.0,0.0};//location to start the display at xyPoint endDisplay = {500.0,500.0};//location to finish the display at color4f winBGColor = {0.0, 0.0, 0.0, 1.0};//window background color color3f drawColor = {1.0, 1.0, 1.0};//color we are drawing in xyPoint windowSize = {500, 500};//size of the window xyPoint windowLoc = {0, 0};//location on screen of the window float ptsize = 0.5;//the point size char * windowName = "Maze";//name of the window /*initiate interaction with the local window system*/ glutInit(&argc, argv); /*initialize the window variables*/ setWindowVals(windowSize, windowLoc, windowName); /*initialize the system*/ initSystem(winBGColor, drawColor, startDisplay, endDisplay, ptsize); /*setup the system*/ loadTextures(); initRooms(); defineMenu(); defineLists(); glutMainLoop(); return 1; } /*setWindowVals(xyPoint size, xyPoint pos, char * name) * * Set the variables for the window*/ void setWindowVals(xyPoint size, xyPoint pos, char * name){ /*set number and type of buffers*/ glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); /*set the window size*/ glutInitWindowSize(size[0], size[1]); /*position the window*/ glutInitWindowPosition(pos[0], pos[1]); /*actually create the window*/ glutCreateWindow(name); } /* initSystem(color4f winColor, color3f drawColor, xyPoint startDisp, xyPoint endDisp, float ptSize) * This function initializes all of display variables*/ void initSystem(color4f winColor, color3f drawColor, xyPoint startDisp, xyPoint endDisp, float ptSize){ /*set the background color*/ glClearColor(winColor[0], winColor[1], winColor[2], winColor[3]); /*clear the window*/ glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); /*set the drawing color*/ glColor3f(drawColor[0], drawColor[1], drawColor[2]); glMatrixMode(GL_PROJECTION); glLoadIdentity(); /*set the portion of the world to display*/ gluOrtho2D(-50.0, 50.0, -50.0, 50.0); glMatrixMode(GL_MODELVIEW); /*set the point size*/ glPointSize(ptSize); /*set the callback functions*/ glutDisplayFunc(display); glutKeyboardFunc(keyboardReader); } /* void initRooms() * This function initializes the 7x7 array of rooms*/ void initRooms(){ int xCounter, zCounter; struct room *ptr; /*run through the entire array of rooms*/ for (zCounter = 0; zCounter < 7; zCounter++){ for(xCounter = 0; xCounter < 7; xCounter++){ ptr = &roomArray[zCounter][xCounter]; /*set the room type*/ if(zCounter == 0){ if((xCounter == 0) || (xCounter == 5)){ ptr->roomType = ROOM_SW; } if((xCounter == 1) || (xCounter == 2) || (xCounter == 3)){ ptr->roomType = ROOM_EW; } if(xCounter == 6){ ptr->roomType = ROOM_NW; } if(xCounter == 4){ ptr->roomType = ROOM_W; } } if(zCounter == 1){ if(xCounter == 0){ ptr->roomType = ROOM_NS; } if((xCounter == 2) || (xCounter == 3) || (xCounter == 5)){ ptr->roomType = ROOM_E; } if((xCounter == 4) || (xCounter == 6)){ ptr->roomType = ROOM_N; } } if(zCounter == 2){ if((xCounter == 0) || (xCounter == 4)){ ptr->roomType = ROOM_NS; } if(xCounter == 6){ ptr->roomType = ROOM_N; } } if(zCounter == 3){ if(xCounter == 0){ ptr->roomType = ROOM_SEW; } if((xCounter == 1) || (xCounter == 2) || (xCounter == 3)){ ptr->roomType = ROOM_EW; } if(xCounter == 5){ ptr->roomType = ROOM_NE; } if(xCounter == 6){ ptr->roomType = ROOM_N; } } if(zCounter == 4){ if((xCounter == 0) || (xCounter == 2)){ ptr->roomType = ROOM_S; } if((xCounter == 1) || (xCounter == 3) || (xCounter == 4)){ ptr->roomType = ROOM_E; } if(xCounter == 5){ ptr->roomType = ROOM_NS; } if(xCounter == 6){ ptr->roomType = ROOM_N; } } if(zCounter == 5){ if(xCounter == 0){ ptr->roomType = ROOM_SE; } if((xCounter == 1) || (xCounter == 2)){ ptr->roomType = ROOM_E; } if(xCounter == 5){ ptr->roomType = ROOM_NS; } if(xCounter == 6){ ptr->roomType = ROOM_N; } } if(zCounter == 6){ if(xCounter == 0){ ptr->roomType = ROOM_S; } if((xCounter == 2) || (xCounter == 1) || (xCounter == 5)){ ptr->roomType = ROOM_E; } if((xCounter == 3) || (xCounter == 6) || (xCounter == 4)){ ptr->roomType = ROOM_NE; } } ptr->inRoom = 0; /*set the room location*/ ptr->xMin = xCounter * ROOMSIZE; ptr->zMin = zCounter * ROOMSIZE; } } } /*Function defineMenu() * This function defines the main menu for the program and attaches * values to each of the choices*/ void defineMenu(){ glutCreateMenu(menuFunction); glutAddMenuEntry("Start Over", MENU_START_OVER); glutAddMenuEntry("Quit", MENU_QUIT); glutAddMenuEntry("Fast Mode", MENU_FAST); glutAddMenuEntry("Texture Mode", MENU_TEXTURE); glutAddMenuEntry("Lighting Mode", MENU_LIGHTING); glutAttachMenu(GLUT_RIGHT_BUTTON); } /* void defineLists() * This function defines lists for the program. First it defines the * north, south, east, and west walls. There are three types of each * it then defines the rooms that are used. Also three types*/ void defineLists(){ /*default walls*/ glNewList(WALL_N_FAST, GL_COMPILE); glColor3f(0.7,0.7,0.7); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, 0); glVertex3f(ROOMSIZE, 15.01,0); glVertex3f(ROOMSIZE, 15.01,ROOMSIZE); glVertex3f(ROOMSIZE, 0.01,ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_S_FAST, GL_COMPILE); glColor3f(0.3,0.3,0.3); glBegin(GL_POLYGON); glVertex3f(0, 0.01, 0); glVertex3f(0, 15.01,0); glVertex3f(0, 15.01,ROOMSIZE); glVertex3f(0, 0.01,ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_E_FAST, GL_COMPILE); glColor3f(0.5,0.5,0.5); glBegin(GL_POLYGON); glVertex3f(0, 0.01, ROOMSIZE); glVertex3f(0, 15.01, ROOMSIZE); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_W_FAST, GL_COMPILE); glColor3f(0.9,0.9,0.9); glBegin(GL_POLYGON); glVertex3f(0, 0.01, 0); glVertex3f(0, 15.01, 0); glVertex3f(ROOMSIZE, 15.01, 0); glVertex3f(ROOMSIZE, 0.01, 0); glEnd(); glEndList(); /*Textured walls*/ glNewList(WALL_N_TEX, GL_COMPILE); glBegin(GL_POLYGON); /*set the polygon coordinates and the texture coordinates*/ glTexCoord2f(0.0,0.0); glVertex3f(ROOMSIZE, 0.01, 0); glTexCoord2f(1.0,0.0); glVertex3f(ROOMSIZE, 15.01,0); glTexCoord2f(1.0,1.0); glVertex3f(ROOMSIZE, 15.01,ROOMSIZE); glTexCoord2f(0.0,1.0); glVertex3f(ROOMSIZE, 0.01,ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_S_TEX, GL_COMPILE); glBegin(GL_POLYGON); /*set the polygon coordinates and the texture coordinates*/ glTexCoord2f(0.0,0.0); glVertex3f(0, 0.01, 0); glTexCoord2f(1.0,0.0); glVertex3f(0, 15.01,0); glTexCoord2f(1.0,1.0); glVertex3f(0, 15.01,ROOMSIZE); glTexCoord2f(0.0,1.0); glVertex3f(0, 0.01,ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_E_TEX, GL_COMPILE); glBegin(GL_POLYGON); /*set the polygon coordinates and the texture coordinates*/ glTexCoord2f(0.0,0.0); glVertex3f(0, 0.01, ROOMSIZE); glTexCoord2f(0.0,1.0); glVertex3f(0, 15.01, ROOMSIZE); glTexCoord2f(1.0,1.0); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE); glTexCoord2f(1.0,0.0); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_W_TEX, GL_COMPILE); glBegin(GL_POLYGON); /*set the polygon coordinates and the texture coordinates*/ glTexCoord2f(0.0,0.0); glVertex3f(0, 0.01, 0); glTexCoord2f(0.0,1.0); glVertex3f(0, 15.01, 0); glTexCoord2f(1.0,1.0); glVertex3f(ROOMSIZE, 15.01, 0); glTexCoord2f(1.0,0.0); glVertex3f(ROOMSIZE, 0.01, 0); glEnd(); glEndList(); /*material walls used in lighting mode*/ glNewList(WALL_N, GL_COMPILE); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient3); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse3); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular3); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission3); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess3); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE2); glVertex3f(ROOMSIZE, 7.51, 0); glVertex3f(ROOMSIZE, 15.01,ROOMSIZE2); glVertex3f(ROOMSIZE, 7.51,ROOMSIZE); glEnd(); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, 0); glVertex3f(ROOMSIZE, 7.51, 0); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 15.01, 0); glVertex3f(ROOMSIZE, 7.51, 0); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE); glVertex3f(ROOMSIZE, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE); glVertex3f(ROOMSIZE, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE2); glEnd(); glEndList(); glNewList(WALL_S, GL_COMPILE); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient3); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse3); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular3); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission3); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess3); glBegin(GL_POLYGON); glVertex3f(0, 0.01, ROOMSIZE2); glVertex3f(0, 7.51, 0); glVertex3f(0, 15.01,ROOMSIZE2); glVertex3f(0, 7.51,ROOMSIZE); glEnd(); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess); glBegin(GL_POLYGON); glVertex3f(0, 0.01, 0); glVertex3f(0, 7.51, 0); glVertex3f(0, 0.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(0, 15.01, 0); glVertex3f(0, 7.51, 0); glVertex3f(0, 15.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(0, 0.01, ROOMSIZE); glVertex3f(0, 7.51, ROOMSIZE); glVertex3f(0, 0.01, ROOMSIZE2); glEnd(); glBegin(GL_POLYGON); glVertex3f(0, 15.01, ROOMSIZE); glVertex3f(0, 7.51, ROOMSIZE); glVertex3f(0, 15.01, ROOMSIZE2); glEnd(); glEndList(); glNewList(WALL_E, GL_COMPILE); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient3); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse3); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular3); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission3); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess3); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE2, 0.01, ROOMSIZE); glVertex3f(0, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE2, 15.01, ROOMSIZE); glVertex3f(ROOMSIZE, 7.51, ROOMSIZE); glEnd(); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess); glBegin(GL_POLYGON); glVertex3f(0, 0.01, ROOMSIZE); glVertex3f(0, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE2, 0.01, ROOMSIZE); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, ROOMSIZE); glVertex3f(ROOMSIZE, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE2, 0.01, ROOMSIZE); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 15.01, ROOMSIZE); glVertex3f(ROOMSIZE, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE2, 15.01, ROOMSIZE); glEnd(); glBegin(GL_POLYGON); glVertex3f(0, 15.01, ROOMSIZE); glVertex3f(0, 7.51, ROOMSIZE); glVertex3f(ROOMSIZE2, 15.01, ROOMSIZE); glEnd(); glEndList(); glNewList(WALL_W, GL_COMPILE); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient3); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse3); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular3); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission3); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess3); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE2, 0.01, 0); glVertex3f(0, 7.51, 0); glVertex3f(ROOMSIZE2, 15.01, 0); glVertex3f(ROOMSIZE, 7.51, 0); glEnd(); /*set material type*/ glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, materialAmbient); glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, materialDiffuse); glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, materialSpecular); glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, materialEmission); glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, materialShininess); glBegin(GL_POLYGON); glVertex3f(0, 0.01, 0); glVertex3f(0, 7.51, 0); glVertex3f(ROOMSIZE2, 0.01, 0); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 0.01, 0); glVertex3f(ROOMSIZE, 7.51, 0); glVertex3f(ROOMSIZE2, 0.01, 0); glEnd(); glBegin(GL_POLYGON); glVertex3f(ROOMSIZE, 15.01, 0); glVertex3f(ROOMSIZE, 7.51, 0); glVertex3f(ROOMSIZE2, 15.01, 0); glEnd(); glBegin(GL_POLYGON); glVertex3f(0, 15.01, 0); glVertex3f(0, 7.51, 0); glVertex3f(ROOMSIZE2, 15.01, 0); glEnd(); glEndList(); /*the floor and ceiling for lighting mode*/ glNewList(FLOOR_CEILING, GL_COMPILE); /*set material type*/ glMaterialfv(GL_FRONT, GL_AMBIENT, materialAmbient); glMaterialfv(GL_FRONT, GL_DIFFUSE, materialDiffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, materialSpecular); glMaterialfv(GL_FRONT, GL_EMISSION, materialEmission); glMaterialfv(GL_FRONT, GL_SHININESS, materialShininess); glBegin(GL_POLYGON); glVertex3f(0, 0, 0); glVertex3f(10, 0, 0); glVertex3f(10, 0, 10); glVertex3f(0, 0, 10); glEnd(); glBegin(GL_POLYGON); glVertex3f(10, 0, 10); glVertex3f(20, 0, 10); glVertex3f(20, 0, 20); glVertex3f(10, 0, 20); glEnd(); /*set material type*/ glMaterialfv(GL_FRONT, GL_AMBIENT, materialAmbient2); glMaterialfv(GL_FRONT, GL_DIFFUSE, materialDiffuse2); glMaterialfv(GL_FRONT, GL_SPECULAR, materialSpecular2); glMaterialfv(GL_FRONT, GL_EMISSION, materialEmission2); glMaterialfv(GL_FRONT, GL_SHININESS, materialShininess2); glBegin(GL_POLYGON); glVertex3f(0, 0, 10); glVertex3f(0, 0, 20); glVertex3f(10, 0, 20); glVertex3f(10, 0, 10); glEnd(); glBegin(GL_POLYGON); glVertex3f(10, 0, 0); glVertex3f(20, 0, 0); glVertex3f(20, 0, 10); glVertex3f(10, 0, 10); glEnd(); glEndList(); /*the floor and ceiling for textured mode*/ /*it's just plain polygons, no textures*/ glNewList(FLOOR_CEILING_TEX, GL_COMPILE); glColor3f(0,0,0); glBegin(GL_POLYGON); glVertex3f(0, 0, 10); glVertex3f(0, 0, 20); glVertex3f(10, 0, 20); glVertex3f(10, 0, 10); glEnd(); glBegin(GL_POLYGON); glVertex3f(10, 0, 0); glVertex3f(20, 0, 0); glVertex3f(20, 0, 10); glVertex3f(10, 0, 10); glEnd(); glColor3f(0.3,0.3,0.3); glBegin(GL_POLYGON); glVertex3f(0, 0, 0); glVertex3f(10, 0, 0); glVertex3f(10, 0, 10); glVertex3f(0, 0, 10); glEnd(); glBegin(GL_POLYGON); glVertex3f(10, 0, 10); glVertex3f(20, 0, 10); glVertex3f(20, 0, 20); glVertex3f(10, 0, 20); glEnd(); glEndList(); /*the floor and ceiling for default mode*/ glNewList(FLOOR_CEILING_FAST, GL_COMPILE); glColor3f(0,0,0); glBegin(GL_POLYGON); glVertex3f(0,0,0); glVertex3f(20,0,0); glVertex3f(20,0,20); glVertex3f(0,0,20); glEnd(); glEndList(); /*a room with only a west wall : lightning, textured, default*/ glNewList(ROOM_W, GL_COMPILE); glCallList(WALL_W); glEndList(); glNewList(ROOM_W_TEX, GL_COMPILE); glCallList(WALL_W_TEX); glEndList(); glNewList(ROOM_W_FAST, GL_COMPILE); glCallList(WALL_W_FAST); glEndList(); /*a room with only an east wall*/ glNewList(ROOM_E, GL_COMPILE); glCallList(WALL_E); glEndList(); glNewList(ROOM_E_TEX, GL_COMPILE); glCallList(WALL_E_TEX); glEndList(); glNewList(ROOM_E_FAST, GL_COMPILE); glCallList(WALL_E_FAST); glEndList(); /*a room without a south wall*/ glNewList(ROOM_S, GL_COMPILE); glCallList(WALL_S); glEndList(); glNewList(ROOM_S_TEX, GL_COMPILE); glCallList(WALL_S_TEX); glEndList(); glNewList(ROOM_S_FAST, GL_COMPILE); glCallList(WALL_S_FAST); glEndList(); /*a room with only a north wall*/ glNewList(ROOM_N, GL_COMPILE); glCallList(WALL_N); glEndList(); glNewList(ROOM_N_TEX, GL_COMPILE); glCallList(WALL_N_TEX); glEndList(); glNewList(ROOM_N_FAST, GL_COMPILE); glCallList(WALL_N_FAST); glEndList(); /*a room with only a north and east wall*/ glNewList(ROOM_NE, GL_COMPILE); glCallList(WALL_N); glCallList(WALL_E); glEndList(); glNewList(ROOM_NE_TEX, GL_COMPILE); glCallList(WALL_N_TEX); glCallList(WALL_E_TEX); glEndList(); glNewList(ROOM_NE_FAST, GL_COMPILE); glCallList(WALL_N_FAST); glCallList(WALL_E_FAST); glEndList(); /*a room with only a north and west wall*/ glNewList(ROOM_NW, GL_COMPILE); glCallList(WALL_W); glCallList(WALL_N); glNewList(ROOM_NW_TEX, GL_COMPILE); glCallList(WALL_W_TEX); glCallList(WALL_N_TEX); glEndList(); glNewList(ROOM_NW_FAST, GL_COMPILE); glCallList(WALL_W_FAST); glCallList(WALL_N_FAST); glEndList(); /*a room with only south and east walls*/ glNewList(ROOM_SE, GL_COMPILE); glCallList(WALL_S); glCallList(WALL_E); glEndList(); glNewList(ROOM_SE_TEX, GL_COMPILE); glCallList(WALL_S_TEX); glCallList(WALL_E_TEX); glEndList(); glNewList(ROOM_SE_FAST, GL_COMPILE); glCallList(WALL_S_FAST); glCallList(WALL_E_FAST); glEndList(); /*a room with only south and west walls*/ glNewList(ROOM_SW, GL_COMPILE); glCallList(WALL_S); glCallList(WALL_W); glEndList(); glNewList(ROOM_SW_TEX, GL_COMPILE); glCallList(WALL_S_TEX); glCallList(WALL_W_TEX); glEndList(); glNewList(ROOM_SW_FAST, GL_COMPILE); glCallList(WALL_S_FAST); glCallList(WALL_W_FAST); glEndList(); /*a room with only a south wall*/ glNewList(ROOM_NS, GL_COMPILE); glCallList(WALL_N); glCallList(WALL_S); glEndList(); glNewList(ROOM_NS_TEX, GL_COMPILE); glCallList(WALL_N_TEX); glCallList(WALL_S_TEX); glEndList(); glNewList(ROOM_NS_FAST, GL_COMPILE); glCallList(WALL_N_FAST); glCallList(WALL_S_FAST); glEndList(); /*a room with east and west walls*/ glNewList(ROOM_EW, GL_COMPILE); glCallList(WALL_E); glCallList(WALL_W); glEndList(); glNewList(ROOM_EW_TEX, GL_COMPILE); glCallList(WALL_E_TEX); glCallList(WALL_W_TEX); glEndList(); glNewList(ROOM_EW_FAST, GL_COMPILE); glCallList(WALL_E_FAST); glCallList(WALL_W_FAST); glEndList(); /*a room without a north wall*/ glNewList(ROOM_SEW, GL_COMPILE); glCallList(WALL_S); glCallList(WALL_E); glCallList(WALL_W); glEndList(); glNewList(ROOM_SEW_FAST, GL_COMPILE); glCallList(WALL_S_FAST); glCallList(WALL_E_FAST); glCallList(WALL_W_FAST); glEndList(); glNewList(ROOM_SEW_TEX, GL_COMPILE); glCallList(WALL_S_TEX); glCallList(WALL_E_TEX); glCallList(WALL_W_TEX); glEndList(); } /*Function menu_function(int ID) * This is the callback function for the menu. It handles all menu * interaction*/ void menuFunction(int ID){ switch(ID){ case MENU_QUIT: { /*exit the game*/ exit(1); } case MENU_FAST: { gameState = FAST; break; } case MENU_LIGHTING: { gameState = LIGHTING; break; } case MENU_TEXTURE: { gameState = TEXTURE; break; } case MENU_START_OVER: { /*reset the important variables*/ initRooms(); xPos = 5; zPos = 65; zRot = 0; break; } } } /*void keyboardReader(unsigned char key, int x, int y) * this function handles all keyboard interaction*/ void keyboardReader(unsigned char key, int x, int y){ if ((key == 'Q') || (key == 'q')){ exit(1); } /*turn left*/ if ((key == 'H') || (key == 'h')){ zRot = zRot + 3; display(); } /*turn right*/ if ((key == 'K') || (key == 'k')){ zRot++; display(); } /*move camera back*/ if ((key == 'U') || (key == 'u')){ if(fmod(zRot, 4) == 0){ if(moveOK(1,0)){ xPos++; display(); } }else if(fmod(zRot, 4) == 1){ if(moveOK(0,1)){ zPos++; display(); } }else if(fmod(zRot, 4) == 2){ if(moveOK(-1,0)){ xPos--; display(); } }else if(fmod(zRot, 4) == 3){ if(moveOK(0,-1)){ zPos--; display(); } } } /*move camera forward*/ if ((key == 'J') || (key == 'j')){ if(fmod(zRot, 4) == 0){ if(moveOK(-1,0)){ xPos--; display(); } }else if(fmod(zRot, 4) == 1){ if(moveOK(0,-1)){ zPos--; display(); } }else if(fmod(zRot, 4) == 2){ if(moveOK(1,0)){ xPos++; display(); } }else if(fmod(zRot, 4) == 3){ if(moveOK(0,1)){ zPos++; display(); } } } } /* int moveOK(int x, int z) * This function checks to see if movement is ok. if it is, the move is made*/ int moveOK(int x, int z){ int newX, newZ; newX = xPos + x; newZ = zPos + z; /*don't allow crossing of the borders*/ if(newX <= 1){ return 0; }else if(newX >= 139){ return 0; }else if(newZ <= 1){ return 0; }else if((newZ >= 139) && (newX > 19) && (newX < 139)){ return 0; } /*the first north-south wall*/ if((newZ > 19) && (newZ < 21)){//1,2,3 - which walls are blocked if((newX > 19) && (newX < 81)){ return 0; } } /*the second north-south wall*/ else if((newZ > 39) && (newZ < 41)){//2,3,5 if(((newX > 39) && (newX < 81)) || ((newX > 99) && (newX < 121))){ return 0; } } /*the third north-south wall*/ else if((newZ > 59) && (newZ < 61)){//0,1,2,3 if(newX < 81){ return 0; } } /*the fourth north-south wall*/ else if((newZ > 79) && (newZ < 81)){//0,1,2,3,5 if((newX < 81) || ((newX > 99) && (newX < 121))){ return 0; } } /*fifth north-south wall*/ else if((newZ > 99) && (newZ < 101)){//1,3,4 if(((newX > 19) && (newX < 41)) || ((newX > 59) && (newX < 101))){ return 0; } } /*sixth north-south wall*/ else if((newZ > 119) && (newZ < 121)){//0,1,2 if(newX < 61){ return 0; } } /*first east-west-wall*/ if((newX > 19) && (newX < 21)){//1,2 if((newZ > 19) && (newZ < 61)){ return 0; } } /*second east-west-wall*/ else if((newX > 39) && (newX < 41)){//4 if((newZ > 79) && (newZ < 101)){ return 0; } } /*fourth east-west-wall*/ else if((newX > 79) && (newX < 81)){//2,6 if(((newZ > 39) && (newZ < 61)) || ((newZ > 119) && (newZ < 141))){ return 0; } } /*fifth east-west-wall*/ else if((newX > 99) && (newX < 101)){//0,1,2,4,5,6 if((newZ < 61) || ((newZ > 79) && (newZ < 141))){ return 0; } } /*sixth east-west-wall*/ else if((newX > 119) && (newX < 121)){//3,4,5 if((newZ > 59) && (newZ < 121)){ return 0; } } return 1; } /*void display() * This is the display function. It handles all drawing to the screen*/ void display(){ int xFloor, zFloor; int xCounter, zCounter; struct room *ptr; glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glMatrixMode(GL_PROJECTION); glEnable(GL_DEPTH_TEST); /*set the variables for lighting mode. disable others*/ if(gameState == LIGHTING){ glDisable(GL_TEXTURE_2D); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); } /*set the variables for texture mode. disable others*/ else if(gameState == TEXTURE){ glDisable(GL_LIGHTING); glDisable(GL_LIGHT0); glEnable(GL_TEXTURE_2D); gluBuild2DMipmaps(GL_TEXTURE_2D, 3, brick_W, brick_H, GL_RGB, GL_UNSIGNED_BYTE, walls); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); } /*disable all flags. regular mode*/ else { glDisable(GL_TEXTURE_2D); glDisable(GL_LIGHTING); glDisable(GL_LIGHT0); } glLoadIdentity(); /*set the portion of the world to display*/ gluPerspective(90, 1, 0.1, 140); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); /*set the camera position*/ gluLookAt(0,10,0,100,0,0,0,1,0); glRotatef(90 * zRot, 0, 1, 0); glTranslatef(-xPos, 0, -zPos); /*if we're doing lighting, set the light position*/ if(gameState == LIGHTING){ lightPosition[0] = xPos + 5; lightPosition[2] = zPos + 65; glLightfv(GL_LIGHT0, GL_POSITION, lightPosition); glLightfv(GL_LIGHT0, GL_AMBIENT, lightAmbient); glLightfv(GL_LIGHT0, GL_DIFFUSE, lightDiffuse); glLightfv(GL_LIGHT0, GL_SPECULAR, lightSpecular); } /*draw the floor and ceiling*/ glPushAttrib(GL_ALL_ATTRIB_BITS); for(zFloor = 0; zFloor < 7; zFloor++){ for(xFloor = 0; xFloor < 7; xFloor++){ /*translate down for floor*/ glTranslatef(xFloor * 20, -0.02, zFloor * 20); if(gameState == LIGHTING){ glCallList(FLOOR_CEILING); }else if(gameState == TEXTURE){ glCallList(FLOOR_CEILING_TEX); }else{ glCallList(FLOOR_CEILING_FAST); } /*translate up for ceiling*/ glTranslatef(0, 15.02, 0); if(gameState == LIGHTING){ glCallList(FLOOR_CEILING); }else if(gameState == TEXTURE){ glCallList(FLOOR_CEILING_TEX); }else{ glCallList(FLOOR_CEILING_FAST); } /*translate back to starting point*/ glTranslatef(-xFloor * 20, -15.00, -zFloor * 20); } } glPopAttrib(); /*draw all of the rooms*/ glPushAttrib(GL_ALL_ATTRIB_BITS); for (zCounter = 0; zCounter < 7; zCounter++){ for(xCounter = 0; xCounter < 7; xCounter++){ ptr = &roomArray[zCounter][xCounter]; glTranslatef(ptr->xMin, 0, ptr->zMin); switch(ptr->roomType){ case ROOM_SEW : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_SEW); }else if(gameState == FAST){ glCallList(ROOM_SEW_FAST); }else{ glCallList(ROOM_SEW_TEX); } break; } case ROOM_EW : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_EW); }else if(gameState == FAST){ glCallList(ROOM_EW_FAST); }else{ glCallList(ROOM_EW_TEX); } break; } case ROOM_NS : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_NS); }else if(gameState == FAST){ glCallList(ROOM_NS_FAST); }else{ glCallList(ROOM_NS_TEX); } break; } case ROOM_N : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_N); }else if(gameState == FAST){ glCallList(ROOM_N_FAST); }else{ glCallList(ROOM_N_TEX); } break; } case ROOM_SW : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_SW); }else if(gameState == FAST){ glCallList(ROOM_SW_FAST); }else{ glCallList(ROOM_SW_TEX); } break; } case ROOM_SE : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_SE); }else if(gameState == FAST){ glCallList(ROOM_SE_FAST); }else{ glCallList(ROOM_SE_TEX); } break; } case ROOM_S : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_S); }else if(gameState == FAST){ glCallList(ROOM_S_FAST); }else{ glCallList(ROOM_S_TEX); } break; } case ROOM_NW : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_NW); }else if(gameState == FAST){ glCallList(ROOM_NW_FAST); }else{ glCallList(ROOM_NW_TEX); } break; } case ROOM_NE : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_NE); }else if(gameState == FAST){ glCallList(ROOM_NE_FAST); }else{ glCallList(ROOM_NE_TEX); } break; } case ROOM_E : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_E); } else if(gameState == FAST){ glCallList(ROOM_E_FAST); }else{ glCallList(ROOM_E_TEX); } break; } case ROOM_W : { /*draw different rooms. dependent on mode*/ if(gameState == LIGHTING){ glCallList(ROOM_W); }else if(gameState == FAST){ glCallList(ROOM_W_FAST); }else{ glCallList(ROOM_W_TEX); } break; } } /*back to original position*/ glTranslatef(-ptr->xMin, 0, -ptr->zMin); } } glPopAttrib(); glutSwapBuffers(); } /* void loadTextures() * This function loads the textures. It is taken and modified from * the one in hte book. p149. "OpenGL, a Primer"*/ void loadTextures(){ walls = glmReadPPM("brick.ppm", &brick_W, &brick_H); } /* GLubyte * glmReadPPM(char* filename, int* width, int* height) * Taken from http://www.pobox.com/~nate*/ GLubyte * glmReadPPM(char* filename, int* width, int* height) { FILE* fp; int i, w, h, d; unsigned char* image; char head[70]; /* max line <= 70 in PPM (per spec). */ fp = fopen(filename, "rb"); if (!fp) { perror(filename); return NULL; } /* grab first two chars of the file and make sure that it has the * correct magic cookie for a raw PPM file. */ fgets(head, 70, fp); printf(head); if (strncmp(head, "P6", 2)) { fprintf(stderr, "%s: Not a raw PPM file\n", filename); return NULL; } /* grab the three elements in the header (width, height, maxval). */ i = 0; while(i < 3) { fgets(head, 70, fp); if (head[0] == '#') /* skip comments. */ continue; if (i == 0) i += sscanf(head, "%d %d %d", &w, &h, &d); else if (i == 1) i += sscanf(head, "%d %d", &h, &d); else if (i == 2) i += sscanf(head, "%d", &d); } /* grab all the image data in one fell swoop. */ image = (unsigned char*)malloc(sizeof(unsigned char)*w*h*3); fread(image, sizeof(unsigned char), w*h*3, fp); fclose(fp); *width = w; *height = h; return image; }