Sign in to follow this  
tnutty

Need help with Mr.Pacman

Recommended Posts

I have hoping to finish this pacman clone before I smash and burn my computer. The way I wanted to implement it, is by have and AxB array that keeps track of Mr.Pacman,Food,and enimies position, so it would be easier for say collision detection,or just to keep track . But I am having problem with this part. MY screen is 500x500. Here is some relevant code :
GameScreen::GameScreen()
{
	//Init Gamemap to none occupied map	
	//P = pacman
	//E = Enemy
	//* = Blank Space
	int Size = 35;
	//Initially set Size to 25x50
	GameMap.resize(Size,vector<char>(Size,'*'));


	 
}


I guess I would have to have some type of conversion because the screen width/height does not match my vector size. So I have a not implemented function that returns index. and this function :
void GameScreen::UpdateMap(float *PacManPos, float *EnemiesPos)
{
	unsigned int i(0),j(0);

	int posX = PacManPos[POS_X];
	int posY = PacManPos[POS_Y];

	//I Need some conversion here,I guess

	//Reset Board
	GameMap.resize(GameMap.size(),vector<char>(GameMap[0].size(),'*'));

	GameMap[posX][posY] = 'P';
	
	cout<<"\n\n\n"<<endl;

	for( i =0; i < GameMap.size(); i++)
	{
		for( j = 0; j<GameMap[i].size(); j++)
		{
		cout << GameMap[i][j];
		}
		printf("\n");
	}


}

I am not sure if I am going about this right. Any Help?

Share this post


Link to post
Share on other sites
A couple things...

1) Why are you storing the positions of Pacman and Enemies as arrays? I would assume structs with two variables (xPos and yPos) would be much simpler to use there, so you could then write

int posX = PacManPos.xPos;
int posY = PacManPos.yPos;

or something similar.


2) If I recall correctly, a 2d array works in the (y,x) orientation, so your array-printing function is going to be printing it out sideways. For instance, in a 5x5 array, the points at array[0][2] and array[4][1] would be

00x00 00000
00000 00000
00000 00000
00000 00000
00000 0x000

respectively.

Share this post


Link to post
Share on other sites
You know right now I am getting very frustrated with even displaying Food, via
glPoints. I tried debugging it but could not find any problem. Can you help.

Relevant code :

My Display List for food

void DisplayList::Render_Food(string *FoodCol, float Diameter)
{
cFood.dListIDFd[0] = glGenLists(3);

glNewList(cFood.dListIDFd[0],GL_COMPILE);

//Determine Color
if(FoodCol[0].compare("RED") == 0)
RED; else
if(FoodCol[0].compare("BLUE") == 0)
BLUE; else
if(FoodCol[0].compare("YELLOW") == 0)
YELLOW;

glPointSize(Diameter);

glBegin(GL_POINTS);
glVertex2f(0.0,0.0);
glEnd();

glEndList();

cFood.dListIDFd[1] = cFood.dListIDFd[0]+1;

glNewList(cFood.dListIDFd[1],GL_COMPILE);

//Determine Color
if(FoodCol[1].compare("RED") == 0)
RED; else
if(FoodCol[1].compare("BLUE") == 0)
BLUE; else
if(FoodCol[1].compare("YELLOW") == 0)
YELLOW;

glPointSize(Diameter);

glBegin(GL_POINTS);
glVertex2f(0.0,0.0);
glEnd();

glEndList();

cFood.dListIDFd[2] = cFood.dListIDFd[1]+1;

glNewList(cFood.dListIDFd[2],GL_COMPILE);

//Determine Color
if(FoodCol[2].compare("RED") == 0)
RED; else
if(FoodCol[2].compare("BLUE") == 0)
BLUE; else
if(FoodCol[2].compare("YELLOW") == 0)
YELLOW;

glPointSize(Diameter);

glBegin(GL_POINTS);
glVertex2f(10.0,-10.0);
glEnd();

glEndList();


}




This gets called in the constructor :

FOOD::FOOD()
{
//4 * Mr.Pacman Radius
Diameter = (SCREEN_W+SCREEN_H)/200;
//Set Food Color
FoodColor[0] = "RED";
FoodColor[1] = "BLUE";
FoodColor[2] = "YELLOW";

//Render Food Display List
cFood.Render_Food(FoodColor,Diameter);


}



Here is the Draw food Func:

void DrawFood(float PosX, float PosY,int colNum) {
glTranslatef(PosX,PosY,-1.0);
glCallList(dListIDFd[colNum]);

};



And

void LEVELS::DrawLevel1()
{
srand(0);
cLevel.DrawFood((rand()%SCREEN_W)-Line_width,rand()%SCREEN_H-Line_width,cLevel.dListIDFd[(rand()%3)]);
}



and in this func :

void StateFunc::GameState()
{
//Draw our blue borders
RED;
cScreen.DrawBorders(SCREEN_W,SCREEN_H);

glPushMatrix();

//Determine Level Number
switch(cLevel.GetLevel())
{
case 1: cLevel.DrawLevel1(); break;
default: cLevel.DrawLevel1();break;
}
glPopMatrix();

//Move Mr. Pacman
cPacman.Move_Pacman(cPacman.Direction,cPacman.vec2DPos,cPacman.Speed);
//Rotate Mr.pacman accordingly
glRotatef(cPacman.GetAngle(),0,0,1);
//Render Mr.Pacman by switching between D-lists
cPacman.Animate_Pacman(cPacman.AnimateChange);
//Handle Wall to pacman Collision
cHandle_collision.CheckWallToObjectCollision(cPacman.vec2DPos[POS_X],cPacman.vec2DPos[POS_Y],cPacman.vec2DPos,cPacman.Speed);

//cout<<"X : "<<cPacman.vec2DPos[POS_X]<<","<<"Y : "<< cPacman.vec2DPos[POS_Y]<<endl;


}






and
Its been a while since I first tried to fix this problem. So its not like
I did not try. I am at the point of starting all over, if that. And also this
level1 is just a test

Share this post


Link to post
Share on other sites
Pacman has some suprisingly tricky things to deal with for a first time project. Rather than trying to get everything working all at once, I suggest you focus on individual pieces first. Try taking it in a few steps like these (or whatever you think works best for you):

1. Get pacman on an empty screen.
1a. Move him around freely on the screen.

2 Use an array to define and draw a maze.
2a. Get pacman to appear and move around the maze (no wall collision checking).
2b. Add wall collision checking.

3. Add food.
3a. Add functionality so when everything has been eaten you move to next level.
3b. Add scoring.

4. Add enemies (no collision with pacman checking).
4a. Develop a simple enemy movement AI.
4b. Add pacman collision checking and death.
4c. Enhance enemy movement if desired.

I have some code on my website for a pacman clone that you could look at but it isn't openGL. It's also a bit buggy in places.

Share this post


Link to post
Share on other sites
QUOTE : 1. Get pacman on an empty screen.

Done...

QUOTE : 1a. Move him around freely on the screen.

Done...

QUOTE : 2 Use an array to define and draw a maze.

Not Done...

This was the OP question.

If it would help, I could zip my project to anyone willing to help.

Share this post


Link to post
Share on other sites
Use a couple of for loops to go through your array. If an element of the array indicates a wall, display the wall similarily as you would display a pacman (if not do nothing). As you go through the array, change the x,y destination of where the wall might be displayed on the screen. For example

for (y=0;y<MAZEYARRAYSIZE;y++)
{
for (x=0;x<MAZEXARRAYSIZE;x++)
{
if (TheMaze[x][y] == 1) //We have a wall.
{
PaintWall(x*TILEXSIZE,y*TILEYSIZE);
}
}
}




PaintWall() takes screen co-ordinates where you want the section of wall to be displayed.

Share this post


Link to post
Share on other sites
To represent a multi-dimensional array that is rectangular but not of known-ahead-of-time size, use boost::multi_array.

To compare std::string instances, don't bother with .compare() except for very specialized purposes (almost never applicable); instead, just use its operator== overload.

Don't hide code in macros like 'RED;'. Call a function. And don't repeat the colour-checking logic; do it inside the function. Actually, don't use strings for that purpose, either; use an enumeration to specify one of a finite, predetermined set of values.

It is possible in C++ to pass arrays by reference, which gives you a little better type-checking.

I suspect that you can't just call glGenLists once and use successive values after that. The function is doing more than giving you an integer handle; it's allocating memory behind the scenes.

And for heavens' sake, don't repeat code when you can use a simple looping construct.

So for example:


enum Colour { RED, BLUE, YELLOW };

// The parentheses around the '&' here cause the type to be interpreted as
// a reference to an array, instead of an array of references (which is
// illegal anyway; you'd think they'd have made it simpler... anyway)
void DisplayList::Render_Food(Colour (&) FoodCol[3], float Diameter) {
float coordinates[3][2] = {{0.0, 0.0}, {0.0, 0.0}, {10.0, -10.0}};
// Did you really mean for the first two to be the same?

for (int i = 0; i < 3; ++i) {
cFood.dListIDFd[i] = glGenLists(3);
glNewList(cFood.dListIDFd[i],GL_COMPILE);
doColorLogicFor(FoodCol[i]);
glPointSize(Diameter);
glBegin(GL_POINTS);
glVertex2f(coordinates[i][0], coordinates[i][1]);
glEnd();
glEndList();
}
}



Share this post


Link to post
Share on other sites
Quote:
Original post by Tom Sloper
Quote:
Original post by tnutty
I have hoping to finish this pacman clone before I smash and burn my computer.

So -- how much time is that? (^_^)
Sorry, couldn't resist.

ROFL!

Share this post


Link to post
Share on other sites
Instead of trying to everything at once. I just started over. Now I got
pacman running with food and collisions. All I need to do improve its speed
and make new levels. To me using an array to define a maze thats to be drawn
on screen seems harder than other parts. Well, at least the rendering the maze
relative to the screen Coordinates. And I got my head back together and
sorry, there is going to no smashing or burning my computer.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this