C++ Pacman游戏
一个简单的控制台应用程序或快速的裁剪游戏,名为Pacman Game in C,用于娱乐。类似于贪吃蛇游戏,Pacman需要移动,以便在它擦除或被Pacman吃掉之前沿着预定义的蓝色路径行进。这个游戏很容易玩,并且在你前进时清除路径会奖励积分。在这里,您可以获得此项目的源代码和输出屏幕。
程序拆解
# include < iostream >
# include < stdio.h >
# include < windows.h >
# include < string >
# include < vector >
我们在我们的代码中包含了所有必需的文件。
char tmp_map [ 18 ] [ 32 ] ;
char map [ 18 ] [ 32 ] = {
" +#############################+ " ,
" | |",
" | | " ,
" | ## ########### ## ######### | " ,
" | | | " ,
" | | | ### | | | | " ,
"| | | | | ### | | | | " ,
"| | #####| | | ## | | " ,
" | | | ### | | | " ,
" | | ##### ### ## | " ,
" | ###### ####### ### | " ,
" | | " ,
" | # ### #### ### ####### | " ,
" | | " ,
" | | " ,
" | | " ,
" | | " ,
" + ############################# + " } ;
我们利用char类型的地图声明了游戏的结构。
void ShowMap ( )
{
for ( int i = 0 ; i < 18 ; I + + )
{
Printf ( " % s \ n " , map [ i ] ) ;
}
}
上述代码用于打印展示我们游戏的地图。
void gotoxy ( short x , short y )
{
HANDLE hStdout = GetStdHandle ( STD_OUTPUT_HANDLE ) ;
COORD position = { x , y } ;
SetConsoleCursorPosition ( hStdout , position ) ;
}
以上代码显示了“吃豆人”最初的位置。
class entity
{
public:
entity(int x, int y)
{
this->x = x;
this->y = y;
}
void move_x(int p)
{
if (map[y][x + p] == ' ')
x += p;
}
void move_y(int p)
{
if (map[y + p][x] == ' ')
y += p;
}
void move(int p, int q)
{
x += p;
y += q;
}
int get_x() { return x; }
int get_y() { return y; }
void draw(char p)
{
map[x][y] = p;
gotoxy(x, y);
printf("%c", p);
}
private :
int x ;
int y ;
} ;
struct walk
{
short walk_count ;
short x ;
short y ;
short back ;
} ;
struct target
{
short x ;
short y ;
} ;
上面的class实体用于使我们的吃豆人在地图上移动或行走。
void AddArray ( int x , int y , int wc , int back )
{
if ( tmp_map [ y ] [ x ] == ' ' || tmp_map [ y ] [ x ] == ' . ' )
{
tmp_map [ y ] [ x ] = ' # ' ;
walk tmp ;
tmp.x = x ;
tmp.y = y ;
tmp.walk_count = wc ;
tmp.back = back ;
BFSArray.push_back ( tmp ) ;
}
}
上述代码将显示Pacman在移动后的位置。
void FindPath ( int sx , int sy , int x , int y )
{
memcpy ( tmp_map , map , sizeof ( map ) ) ;
BFSArray . clear ( ) ;
walk tmp ;
tmp.x = sx ;
tmp.y = sy ;
tmp.walk_count = 0 ;
tmp.back = -1 ;
BFSArray.push_back ( tmp ) ;
int i = 0 ;
while ( i < BFSArray.size ( ) )
{
if ( BFSArray [ i ].x = = x & & BFSArray [ i ]. y = = y )
{
walk_queue.clear ( ) ;
target tmp2 ;
while ( BFSArray [ i ] . walk_count ! = 0 )
{
tmp2 . x = BFSArray [ i ] . x ;
tmp2 . y = BFSArray [ i ] . y ;
walk_queue . push_back ( tmp2 ) ;
i = BFSArray [ i ] . back ;
}
break ;
}
AddArray ( BFSArray [ i ] . x + 1 , BFSArray [ i ] . y , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x - 1 , BFSArray [ i ] . y , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x , BFSArray [ i ] . y + 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x , BFSArray [ i ] . y - 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
/*
AddArray ( BFSArray [ i ] . x + 1 , BFSArray [ i ] . y + 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x - 1 , BFSArray [ i ] . y + 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x + 1 , BFSArray [ i ] . y + 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray ( BFSArray [ i ] . x + 1 , BFSArray [ i ] . y - 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray( BFSArray [ i ] . x + 1 , BFSArray [ i ] . y - 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray( BFSArray [ i ] . x - 1 , BFSArray [ i ] . y - 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray( BFSArray [ i ] . x - 1 , BFSArray [ i ] . y + 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
AddArray( BFSArray [ i ] . x - 1 , BFSArray [ i ] . y - 1 , BFSArray [ i ] . walk_count + 1 , i ) ;
*/
i++ ;
}
BFSArray . clear ( ) ;
}
这个函数被 pacman 用来检测或查找路径。
int main ( )
{
bool running = true ;
int x = 15 ; // hero x
int y = 16 ; // hero y
int old_x ;
int old_y ;
int ex = 1 ;
int ey = 1 ;
int pts = 0 ;
printf ( " Instruction : \ n1. Arrow Keys to move your hero \ n2. Eat the dots produced by the Eater to gain poins \ n3. Don't get caught by the Eater \ n \ n");
printf ( " H -> Hard \ n N -> Normal \ n E -> Easy \ n \ n Input : " ) ;
在此驱动程序代码部分,用户将被提供指令,如箭头键来移动你的英雄,吃掉由吞食者产生的点以获得积分,并避免被吞食者捕捉。它还会询问困难、普通或容易级别。
char diffi ;
int speedmod = 3 ;
cin >> diffi ;
if ( diffi = = ' N ' )
{
speedmod = 2 ;
}
else if ( diffi = = ' H ' )
{
speedmod = 1 ;
}
system ( " cls " ) ;
ShowMap ( ) ;
gotoxy ( x , y ) ;
cout << " H " ;
int frame = 0 ;
FindPath ( ex , ey , x , y ) ;
while ( running )
{
gotoxy ( x , y ) ;
cout << " " ;
old_x = x ;
old_y = y ;
if ( GetAsyncKeyState ( VK_UP ) )
{
if ( map [ y - 1 ] [ x ] = = ' . ' )
{
y - - ;
pts + + ;
}
else if ( map [ y - 1 ] [ x ] = = ' ' )
y - - ;
}
if ( GetAsyncKeyState ( VK_DOWN ) )
{
if ( map [ y + 1 ] [ x ] = = ' . ' )
{
y + + ;
pts + + ;
}
else if ( map [ y + 1 ] [ x ] = = ' ' )
y + + ;
}
如果用户选择了H、N或E,则速度将相应增加。
用C++编写的Pacman游戏程序
#include <iostream>
#include <stdio.h>
#include <windows.h>
#include <string>
#include <vector>
using namespace std;
char tmp_map[18][32];
char map[18][32] = {
"+#############################+",
"| |",
"| |",
"|## ########### ## #########|",
"| | |",
"| | |### | | | |",
"| | | | |### | | | |",
"| | #####| | | ## | |",
"| | |### | | |",
"| |##### ### ## |",
"| ###### ####### ###|",
"| |",
"|# ### #### ### #######|",
"| |",
"| |",
"| |",
"| |",
"+#############################+"};
void ShowMap()
{
for (int i = 0; i < 18; i++)
{
printf("%s\n", map[i]);
}
}
void gotoxy(short x, short y)
{
HANDLE hStdout = GetStdHandle(STD_OUTPUT_HANDLE);
COORD position = {x, y};
SetConsoleCursorPosition(hStdout, position);
}
class entity
{
public:
entity(int x, int y)
{
this->x = x;
this->y = y;
}
void move_x(int p)
{
if (map[y][x + p] == ' ')
x += p;
}
void move_y(int p)
{
if (map[y + p][x] == ' ')
y += p;
}
void move(int p, int q)
{
x += p;
y += q;
}
int get_x() { return x; }
int get_y() { return y; }
void draw(char p)
{
map[x][y] = p;
gotoxy(x, y);
printf("%c", p);
}
private:
int x;
int y;
};
struct walk
{
short walk_count;
short x;
short y;
short back;
};
struct target
{
short x;
short y;
};
vector<target> walk_queue;
vector<walk> BFSArray;
void AddArray(int x, int y, int wc, int back)
{
if (tmp_map[y][x] == ' ' || tmp_map[y][x] == '.')
{
tmp_map[y][x] = '#';
walk tmp;
tmp.x = x;
tmp.y = y;
tmp.walk_count = wc;
tmp.back = back;
BFSArray.push_back(tmp);
}
}
void FindPath(int sx, int sy, int x, int y)
{
memcpy(tmp_map, map, sizeof(map));
BFSArray.clear();
walk tmp;
tmp.x = sx;
tmp.y = sy;
tmp.walk_count = 0;
tmp.back = -1;
BFSArray.push_back(tmp);
int i = 0;
while (i < BFSArray.size())
{
if (BFSArray[i].x == x && BFSArray[i].y == y)
{
walk_queue.clear();
target tmp2;
while (BFSArray[i].walk_count != 0)
{
tmp2.x = BFSArray[i].x;
tmp2.y = BFSArray[i].y;
walk_queue.push_back(tmp2);
i = BFSArray[i].back;
}
break;
}
AddArray(BFSArray[i].x + 1, BFSArray[i].y, BFSArray[i].walk_count + 1, i);
AddArray(BFSArray[i].x - 1, BFSArray[i].y, BFSArray[i].walk_count + 1, i);
AddArray(BFSArray[i].x, BFSArray[i].y + 1, BFSArray[i].walk_count + 1, i);
AddArray(BFSArray[i].x, BFSArray[i].y - 1, BFSArray[i].walk_count + 1, i);
/*
AddArray( BFSArray[i].x+1, BFSArray[i].y+1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x-1, BFSArray[i].y+1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x+1, BFSArray[i].y+1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x+1, BFSArray[i].y-1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x+1, BFSArray[i].y-1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x-1, BFSArray[i].y-1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x-1, BFSArray[i].y+1, BFSArray[i].walk_count+1, i );
AddArray( BFSArray[i].x-1, BFSArray[i].y-1, BFSArray[i].walk_count+1, i );
*/
i++;
}
BFSArray.clear();
}
int main()
{
bool running = true;
int x = 15; // hero x
int y = 16; // hero y
int old_x;
int old_y;
int ex = 1;
int ey = 1;
int pts = 0;
printf("Instruction:\n1. Arrow Keys to move your hero\n2. Eat the dots produced by the Eater to gain poins\n3. Don't get caught by the Eater\n\n");
printf("H -> Hard\nN -> Normal\nE -> Easy\n\nInput : ");
char diffi;
int speedmod = 3;
cin >> diffi;
if (diffi == 'N')
{
speedmod = 2;
}
else if (diffi == 'H')
{
speedmod = 1;
}
system("cls");
ShowMap();
gotoxy(x, y);
cout << "H";
int frame = 0;
FindPath(ex, ey, x, y);
while (running)
{
gotoxy(x, y);
cout << " ";
old_x = x;
old_y = y;
if (GetAsyncKeyState(VK_UP))
{
if (map[y - 1][x] == '.')
{
y--;
pts++;
}
else if (map[y - 1][x] == ' ')
y--;
}
if (GetAsyncKeyState(VK_DOWN))
{
if (map[y + 1][x] == '.')
{
y++;
pts++;
}
else if (map[y + 1][x] == ' ')
y++;
}
if (GetAsyncKeyState(VK_LEFT))
{
if (map[y][x - 1] == '.')
{
x--;
pts++;
}
else if (map[y][x - 1] == ' ')
x--;
}
if (GetAsyncKeyState(VK_RIGHT))
{
if (map[y][x + 1] == '.')
{
x++;
pts++;
}
else if (map[y][x + 1] == ' ')
x++;
}
if (old_x != x || old_y != y)
{
FindPath(ex, ey, x, y);
}
gotoxy(x, y);
cout << "H";
map[ey][ex] = '.';
gotoxy(ex, ey);
cout << ".";
if (frame % speedmod == 0 && walk_queue.size() != 0)
{
ex = walk_queue.back().x;
ey = walk_queue.back().y;
walk_queue.pop_back();
}
gotoxy(ex, ey);
cout << "E";
if (ex == x && ey == y)
{
break;
}
gotoxy(32, 18);
gotoxy(32, 1);
cout << pts;
Sleep(100);
frame++;
}
system("cls");
printf("You Lose and your score is : %i", pts);
cin.get();
cin.get();
cin.get();
cin.get();
cin.get();
cin.get();
cin.get();
cin.get();
return 0;
}
输出:
Instruction:
1. Arrow Keys to move your hero
2. Eat the dots produced by the Eater to gain poins
3. Don't get caught by the Eater
H -> Hard
N -> Normal
E -> Easy
Input : N
+#############################+
|... | 0
| . |
|##.########### ## #########|
| .| |
| |.|### | | | |
| |. | | |### | | | |
| |.#####| | | ## | |
| |...... |### | | |
| |#####.### ## |
| ..E ###### ####### ###|
| |
|# ### #### ### #######|
| |
| |
| |
| H |
+#############################+
You Lose and your score is : 0