学习Qt有一个月了,想要实现一个推箱子的游戏来检验一下自己。今天先设计一下将要完成的具体表现,因为是第一次做,所以设计的稍微简单点,以后逐渐修改。首先要创建菜单栏,分为三个主菜单:
①游戏
②选择关卡
③关于
(1)游戏主菜单下分为:
①开始游戏
②重新开始
③结束游戏
(2)选择关卡分为
①前一关卡
②后一关卡
③选择关卡,
(3)关于则弹出游戏的信息
主要使用以下几个类:
1、QPainter绘制地图
2、QMenu、QAction制作菜单栏
3、QKeyEvent接收键盘事件 控制人物行走及推箱子
①界面设计
QpushBox::QpushBox(QWidget *parent)
: QMainWindow(parent)
{
//ui.setupUi(this);
createMenu();
createAction();
widget=new QWidget;
setCentralWidget(widget);
levelLabel=new QLabel(QStringLiteral("当前关卡"));
stepLabel=new QLabel(QStringLiteral("当前步数"));
levelLCD=new QLCDNumber;
stepLCD=new QLCDNumber;
restartButton=new QPushButton(QStringLiteral("重新开始"));
connect(restartButton,SIGNAL(clicked()),this,SLOT(restartGameSlot()));
restartButton->setEnabled(false);
QVBoxLayout *rightLayout=new QVBoxLayout;
rightLayout->addWidget(levelLabel);
rightLayout->addWidget(levelLCD);
rightLayout->addWidget(stepLabel);
rightLayout->addWidget(stepLCD);
rightLayout->addWidget(restartButton);
rightLayout->addSpacing(210);
mainmap=new mappaint;
QHBoxLayout *mainLayout=new QHBoxLayout;
mainLayout->addWidget(mainmap);
mainLayout->addLayout(rightLayout);
widget->setLayout(mainLayout);
mainmap->levelNow=0;
mainmap->stepNow=0;
mainmap->man_x=0;
mainmap->man_y=0;
mainmap->BeginOrEnd=1;
mainmap->update();
boxNum=0;
levelLCD->display(mainmap->levelNow);
stepLCD->display(mainmap->stepNow);
createMap();
//**************程序整体设定****************
setWindowTitle(QStringLiteral("推箱子小游戏----Dpt设计"));
widget->setFocus();
statusBar()->showMessage(QStringLiteral("欢迎进入推箱子小游戏。"));
}
QpushBox::~QpushBox()
{
}
void QpushBox::createMenu()
{
startGameAction = new QAction(QStringLiteral("开始游戏"),this);
startGameAction->setShortcut(QKeySequence("Ctrl+S"));
startGameAction->setStatusTip(QStringLiteral("开始一场新游戏."));
connect(startGameAction,SIGNAL(triggered()),this,SLOT(startGameSlot()));
restartGameAction = new QAction(QStringLiteral("重新开始"),this);
restartGameAction->setShortcut(QKeySequence("Ctrl+R"));
restartGameAction->setStatusTip(QStringLiteral("重新开始本局."));
restartGameAction->setEnabled(false);
connect(restartGameAction,SIGNAL(triggered()),this,SLOT(restartGameSlot()));
endGameAction = new QAction(QStringLiteral("结束游戏"),this);
endGameAction->setShortcut(QKeySequence("Ctrl+E"));
endGameAction->setStatusTip(QStringLiteral("结束当前游戏."));
endGameAction->setEnabled(false);
connect(endGameAction,SIGNAL(triggered()),this,SLOT(endGameSlot()));
previousGatesAction = new QAction(QStringLiteral("前一关卡"),this);
previousGatesAction->setShortcut(QKeySequence("Ctrl+P"));
previousGatesAction->setStatusTip("选择前一关卡");
previousGatesAction->setEnabled(false);
connect(previousGatesAction,SIGNAL(triggered()),this,SLOT(previousSlot()));
nextGatesAction = new QAction(QStringLiteral("后一关卡"),this);
nextGatesAction->setShortcut(QKeySequence("Ctrl+N"));
nextGatesAction->setStatusTip(QStringLiteral("选择后一关卡"));
nextGatesAction->setEnabled(false);
connect(nextGatesAction,SIGNAL(triggered()),this,SLOT(nextGatesSlot()));
customGatesAction = new QAction(QStringLiteral("选择关卡"),this);
customGatesAction->setShortcut(QKeySequence("Ctrl+C"));
customGatesAction->setStatusTip(QStringLiteral("选择任意关卡"));
connect(customGatesAction,SIGNAL(triggered()),this,SLOT(customGatesSlot()));
aboutAction = new QAction(QStringLiteral("关于"),this);
aboutAction->setShortcut(QKeySequence("Ctrl+A"));
aboutAction->setStatusTip(QStringLiteral("本游戏信息"));
connect(aboutAction,SIGNAL(triggered),this,SLOT(aboutSlot()));
}
void QpushBox::createAction()
{
gameMenu = menuBar()->addMenu(QStringLiteral("游戏"));
gameMenu->addAction(startGameAction);
gameMenu->addAction(restartGameAction);
gameMenu->addAction(endGameAction);
gatesMenu = menuBar()->addMenu(QStringLiteral("选择关卡"));
gatesMenu->addAction(previousGatesAction);
gatesMenu->addAction(nextGatesAction);
gatesMenu->addAction(customGatesAction);
helpMenu = menuBar()->addMenu(QStringLiteral("帮助"));
helpMenu->addAction(aboutAction);
}
void QpushBox::createMap()//建立地图信息,因为第一次写,只设置了三关
{
int i,j;
//***********第一关*****************
man[1][0]=8;man[1][1]=7;
box[1]=3;
for(i=0;i<12;i++)
for(j=0;j<12;j++)
map[1][i][j]=GROUND;
map[1][7][7]=BOX; map[1][7][8]=BOX;
map[1][8][6]=BOX; map[1][5][7]=GOAL;
map[1][8][5]=GOAL;map[1][7][10]=GOAL;
map[1][4][4]=WALL;map[1][8][4]=WALL;
map[1][8][8]=WALL;map[1][4][8]=WALL;
//***************第二关***************
man[2][0]=6;man[2][1]=9;
box[2]=3;
for(i=0;i<12;i++)
for(j=0;j<12;j++)
map[2][i][j]=GROUND;
map[2][4][10]=WALL;map[2][4][11]=WALL;
map[2][5][5]=WALL; map[2][5][6]=WALL;
map[2][6][5]=WALL; map[2][6][6]=WALL;
map[2][6][7]=WALL;
map[2][6][10]=WALL; map[2][7][7]=WALL;
map[2][7][5]=WALL; map[2][7][6]=WALL;
map[2][8][7]=WALL; map[2][9][6]=WALL;
map[2][9][7]=WALL; map[2][10][6]=WALL;
map[2][10][7]=GOAL; map[2][10][9]=GOAL;
map[2][10][8]=GOAL; map[2][6][8]=BOX;
map[2][5][9]=BOX; map[2][5][10]=BOX;
//********************第三关*********************************
man[3][0]=5;man[3][1]=8;
box[3]=4;
for(i=0;i<12;i++)
for(j=0;j<12;j++)
map[3][i][j]=GROUND;
map[3][4][7]=WALL;map[3][4][8]=WALL;
map[3][6][8]=WALL;map[3][5][10]=WALL;
map[3][8][10]=WALL;map[3][9][6]=WALL;
map[3][9][8]=WALL;map[3][10][6]=WALL;
map[3][9][9]=WALL;map[3][7][8]=BOX;
map[3][9][7]=BOX;map[3][5][9]=BOX;
map[3][10][8]=BOX;map[3][6][7]=GOAL;
map[3][5][6]=GOAL;map[3][5][7]=GOAL;
map[3][6][6]=GOAL;
}
mappaint::mappaint(QWidget *parent) :
QWidget(parent)
{
map_x=360;
map_y=360;
setMinimumSize(map_x,map_y);
paint[0]=new QPixmap("./man.png");
paint[1]=new QPixmap("./ground.png");
paint[2]=new QPixmap("./wall.png");
paint[3]=new QPixmap("./box.png");
paint[4]=new QPixmap("./goal.png");
paint[5]=new QPixmap("./start.png");
}
void mappaint::paintEvent(QPaintEvent *event)
{
QPainter p(this);
//p.translate(0,map_y);
if(BeginOrEnd==1)
{
QPixmap l=*paint[5];
p.drawPixmap(0,0,l);
}
else
{
for(int i=0;i<12;i++)
for(int j=0;j<12;j++)
{
QPixmap l=*paint[mapNow[i][j]];
p.drawPixmap(i*30,j*30,l);
}
QPixmap l1=*paint[0];
p.drawPixmap(man_x*30,man_y*30,l1);
}
}
移动策略
void QpushBox::keyPressEvent(QKeyEvent *e)
{
if(!(mainmap->levelNow==0))
{
switch(e->key())
{
case Qt::Key_Up:keyUp();break;
case Qt::Key_Left:keyLeft();break;
case Qt::Key_Right:keyRight();break;
case Qt::Key_Down:keyDown();break;
case Qt::Key_W:keyUp();break;
case Qt::Key_A:keyLeft();break;
case Qt::Key_D:keyRight();break;
case Qt::Key_S:keyDown();break;
default:break;
}
}
}
void QpushBox::keyUp()
{
int manx=mainmap->man_x;
int many=mainmap->man_y;
if(many-1<0||mainmap->mapNow[manx][many-1]==2)
return;
if(mainmap->mapNow[manx][many-1]==1||mainmap->mapNow[manx][many-1]==4)
{
mainmap->man_y--;
if(map[mainmap->levelNow][manx][many]==3)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
}
if(mainmap->mapNow[manx][many-1]==3)
{
if(many-2<0||mainmap->mapNow[manx][many-2]==3||mainmap->mapNow[manx][many-2]==2)
return;
if(mainmap->mapNow[manx][many-2]==1)
{
if(map[mainmap->levelNow][manx][many-1]==4)
boxNum--;
mainmap->mapNow[manx][many-2]=3;
if(map[mainmap->levelNow][manx][many-1]!=3)
mainmap->mapNow[manx][many-1]=map[mainmap->levelNow][manx][many-1];
else
mainmap->mapNow[manx][many-1]=1;
mainmap->man_y--;
}
if(mainmap->mapNow[manx][many-2]==4)
{
if(map[mainmap->levelNow][manx][many-1]!=4)
{
boxNum++;
}
if(map[mainmap->levelNow][manx][many]==3||map[mainmap->levelNow][manx][many]==0)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
mainmap->mapNow[manx][many-2]=3;
if(map[mainmap->levelNow][manx][many-1]==3)
mainmap->mapNow[manx][many-1]=1;
else
mainmap->mapNow[manx][many-1]=map[mainmap->levelNow][manx][many-1];
mainmap->man_y--;
}
}
mainmap->stepNow++;
stepLCDShow();
mainmap->update();
boxNumCheck();
}
void QpushBox::keyLeft()
{
int manx=mainmap->man_x;
int many=mainmap->man_y;
if(manx-1<0||mainmap->mapNow[manx-1][many]==2)
return;
if(mainmap->mapNow[manx-1][many]==1||mainmap->mapNow[manx-1][many]==4)
{
mainmap->man_x--;
if(map[mainmap->levelNow][manx][many]==3)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
}
if(mainmap->mapNow[manx-1][many]==3)
{
if(manx-2<0||mainmap->mapNow[manx-2][many]==3||mainmap->mapNow[manx-2][many]==2)
return;
if(mainmap->mapNow[manx-2][many]==1)
{
if(map[mainmap->levelNow][manx-1][many]==4)
boxNum--;
mainmap->mapNow[manx-2][many]=3;
if(map[mainmap->levelNow][manx-1][many]!=3)
mainmap->mapNow[manx-1][many]=map[mainmap->levelNow][manx-1][many];
else
mainmap->mapNow[manx-1][many]=1;
mainmap->man_x--;
}
if(mainmap->mapNow[manx-2][many]==4)
{
if(map[mainmap->levelNow][manx-1][many]!=4)
{
boxNum++;
}
if(map[mainmap->levelNow][manx][many]==3||map[mainmap->levelNow][manx][many]==0)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
mainmap->mapNow[manx-2][many]=3;
if(map[mainmap->levelNow][manx-1][many]==3)
mainmap->mapNow[manx-1][many]=1;
else
mainmap->mapNow[manx-1][many]=map[mainmap->levelNow][manx-1][many];
mainmap->man_x--;
}
}qDebug()<
stepLCDShow();
mainmap->update();
boxNumCheck();
}
void QpushBox::keyRight()
{
int manx=mainmap->man_x;
int many=mainmap->man_y;
if(manx+1>=12||mainmap->mapNow[manx+1][many]==2)
return;
if(mainmap->mapNow[manx+1][many]==1||mainmap->mapNow[manx+1][many]==4)
{
mainmap->man_x++;
if(map[mainmap->levelNow][manx][many]==3)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
}
if(mainmap->mapNow[manx+1][many]==3)
{
if(manx+2>=12||mainmap->mapNow[manx+2][many]==3||mainmap->mapNow[manx+2][many]==2)
return;
if(mainmap->mapNow[manx+2][many]==1)
{
if(map[mainmap->levelNow][manx+1][many]==4)
boxNum--;
mainmap->mapNow[manx+2][many]=3;
if(map[mainmap->levelNow][manx+1][many]!=3)
mainmap->mapNow[manx+1][many]=map[mainmap->levelNow][manx+1][many];
else
mainmap->mapNow[manx+1][many]=1;
mainmap->man_x++;
}
if(mainmap->mapNow[manx+2][many]==4)
{
if(map[mainmap->levelNow][manx+1][many]!=4)
{
boxNum++;
}
if(map[mainmap->levelNow][manx][many]==3||map[mainmap->levelNow][manx][many]==0)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
mainmap->mapNow[manx+2][many]=3;
if(map[mainmap->levelNow][manx+1][many]==3)
mainmap->mapNow[manx+1][many]=1;
else
mainmap->mapNow[manx+1][many]=map[mainmap->levelNow][manx+1][many];
mainmap->man_x++;
}
}
mainmap->stepNow++;
stepLCDShow();
mainmap->update();
boxNumCheck();
}
void QpushBox::keyDown()
{
int manx=mainmap->man_x;
int many=mainmap->man_y;
if(many+1>=12||mainmap->mapNow[manx][many+1]==2)
return;
if(mainmap->mapNow[manx][many+1]==1||mainmap->mapNow[manx][many+1]==4)
{
mainmap->man_y++;
if(map[mainmap->levelNow][manx][many]==3)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
}
if(mainmap->mapNow[manx][many+1]==3)
{
if(many+2>=12||mainmap->mapNow[manx][many+2]==3||mainmap->mapNow[manx][many+2]==2)
return;
if(mainmap->mapNow[manx][many+2]==1)
{
if(map[mainmap->levelNow][manx][many+1]==4)
boxNum--;
mainmap->mapNow[manx][many+2]=3;
if(map[mainmap->levelNow][manx][many+1]!=3)
mainmap->mapNow[manx][many+1]=map[mainmap->levelNow][manx][many+1];
else
mainmap->mapNow[manx][many+1]=1;
mainmap->man_y++;
}
if(mainmap->mapNow[manx][many+2]==4)
{
if(map[mainmap->levelNow][manx][many+1]!=4)
{
boxNum++;
}
if(map[mainmap->levelNow][manx][many]==3||map[mainmap->levelNow][manx][many]==0)
mainmap->mapNow[manx][many]=1;
else
mainmap->mapNow[manx][many]=map[mainmap->levelNow][manx][many];
mainmap->mapNow[manx][many+2]=3;
if(map[mainmap->levelNow][manx][many+1]==3)
mainmap->mapNow[manx][many+1]=1;
else
mainmap->mapNow[manx][many+1]=map[mainmap->levelNow][manx][many+1];
mainmap->man_y++;
}
}
mainmap->stepNow++;
stepLCDShow();
mainmap->update();
boxNumCheck();
}
void QpushBox::boxNumCheck()
{
qDebug()<
if(boxNum==box[mainmap->levelNow])
{
endGameAction->setEnabled(false);
restartGameAction->setEnabled(false);
restartButton->setEnabled(false);
if(mainmap->levelNow==3)
{
QMessageBox::information(this,QStringLiteral("恭喜通关"),QStringLiteral("恭喜你已通关!"),QMessageBox::Ok);
mainmap->levelNow=0;
mainmap->stepNow=0;
boxNum=0;
levelLCDShow();
stepLCDShow();
mainmap->BeginOrEnd=1;
mainmap->update();
}
else
{
QMessageBox::information(this,QStringLiteral("恭喜过关"),QStringLiteral("恭喜你完成本关!进入下一关"),QMessageBox::Ok);
startGame(mainmap->levelNow+1);
}
}
}
PS:用了一天的时间,总算完成了,第一次做这种,不喜勿喷,另外是用vs2012+QT5.2做的
程序下载地址:http://pan.baidu.com/s/1sj7OfoD 提取密码:d5ae
源码下载地址:http://download.csdn.net/detail/q5512049/8963595