利用qt实现贪吃蛇小游戏,不明白为什么动不起来,以及怎么加背景图片。
感觉自己好像把这个程序写复杂了,看别的程序员的帖子好像寥寥几行就实现了
这是.h文件
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QKeyEvent>
#include <QTimer>
#include <QList>
#include <QRectF>
#include <QList>
QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE
//1.按键
//2.定时器
//3.画图
enum Direct{
DIR_LEFT,
DIR_RIGHT,
DIR_UP,
DIR_DOWN
};
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = nullptr);
~Widget();
protected:
void addTop();
void addDown();
void addRight();
void addLeft();
void addNewReward();
//按键
void keyPressEvent(QKeyEvent *event);
void timeout();
void paintEvent(QPaintEvent *event);
void deleteLast();
bool checkContact();
private:
Ui::Widget *ui;
int moveflag = DIR_UP;
bool blsRun;
bool blsOver;
//定时器
QTimer *timer;
int time = 100;
//snake
QList <QRectF> snake;
//reward
QRectF rewardNode;
int nodeWidth = 20;
int nodeHeight = 20;
};
#endif // WIDGET_H
这是.cpp文件
#include "widget.h"
#include "ui_widget.h"
#include <QPainter>
#include <QRectF>
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
,blsRun(false)
{
ui->setupUi(this);
//定时器
timer = new QTimer();
connect(timer,SIGNAL(timeout()),this,SLOT(timeout()));
resize(600,368);
setWindowTitle("贪吃蛇");
//初始化snake
QRectF rect(300,180,nodeWidth,nodeHeight);
snake.append(rect);
addTop();
addTop();
//初始化奖品
addNewReward();
}
Widget::~Widget()
{
delete ui;
}
//方向按键
void Widget::keyPressEvent(QKeyEvent *event)
{
switch(event -> key()){
case Qt::Key_Up:
if(moveflag != DIR_DOWN){
moveflag = DIR_UP;
}
break;
case Qt::Key_Down:
if(moveflag != DIR_UP){
moveflag = DIR_DOWN;
}
break;
case Qt::Key_Left:
if(moveflag != DIR_RIGHT){
moveflag = DIR_LEFT;
}
break;
case Qt::Key_Right:
if(moveflag != DIR_LEFT){
moveflag = DIR_RIGHT;
}
break;
case Qt::Key_Space:
if(!blsRun)
{
//begin
timer -> start(time);
}
else
{
blsRun = false;
timer -> stop();
}
break;
default:
break;
}
}
void Widget::timeout()
{
//吃到了吗
int flag = 1;
if(snake[0].intersects(rewardNode))
{
flag++;
addNewReward();
}
while(flag--)
{
switch(moveflag)
{
case DIR_UP:
addTop();
break;
case DIR_DOWN:
addDown();
break;
case DIR_RIGHT:
addRight();
break;
case DIR_LEFT:
addLeft();
break;
default:break;
}
}
deleteLast();
update();
}
void Widget::addTop()
{
QPointF leftTop;
QPointF rightBottom;
if(snake[0].y() - nodeHeight < 0)
{
leftTop = QPointF(snake[0].x(),this -> height() - nodeHeight);
rightBottom = QPointF(snake[0].x() + nodeWidth,this -> height());
}
else
{
leftTop = QPointF(snake[0].x(),snake[0].y()-nodeHeight);
rightBottom = snake[0].topRight();
}
snake.insert(0,QRectF(leftTop,rightBottom));
}
void Widget::addDown()
{
QPointF leftTop;
QPointF rightBottom;
if(snake[0].y() - nodeHeight * 2 > this -> height())
{
leftTop = QPointF(snake[0].x(),0);
rightBottom = QPointF(snake[0].x() + nodeWidth, nodeHeight);
}
else
{
leftTop = snake[0].bottomLeft();
rightBottom = snake[0].bottomRight() + QPointF(0,nodeHeight);
}
snake.insert(0,QRectF(leftTop,rightBottom));
}
void Widget::addLeft()
{
QPointF leftTop;
QPointF rightBottom;
if(snake[0].x() - nodeWidth < 0 )
{
leftTop = QPointF(this -> width() - nodeWidth,snake[0].y());
}
else
{
leftTop = snake[0].topLeft() - QPointF(nodeWidth,0);
}
rightBottom = leftTop + QPointF(nodeWidth,nodeHeight);
snake.insert(0,QRectF(leftTop,rightBottom));
}
void Widget::addRight()
{
QPointF leftTop;
QPointF rightBottom;
if(snake[0].x() + nodeWidth * 2 > this->width())
{
leftTop = QPointF(0,snake[0].y());
}
else
{
leftTop = snake[0].topRight();
}
rightBottom = leftTop + QPointF(nodeWidth,nodeHeight);
snake.insert(0,QRectF(leftTop,rightBottom));
}
//绘制
void Widget::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
QPen pen;
QBrush brush;
// QPixmap pix;
// pix.load("C:\Users\29737\Desktop\OIP-C.jpg");
// painter.drawPixmap(0,,0,600,368.pix);
//1.snake
pen.setColor(Qt::black);
brush.setColor(Qt::green);
brush.setStyle(Qt::SolidPattern);
painter.setPen(pen);
painter.setBrush(brush);
for(int i = 0;i < snake.length();i++)
{
painter.drawRect(snake[i]);
}
//2.reward
pen.setColor(Qt::black);
brush.setColor(Qt::red);
brush.setStyle(Qt::SolidPattern);
painter.setPen(pen);
painter.setBrush(brush);
painter.drawEllipse(rewardNode);
if(checkContact())
{
QFont font("黑体",30,QFont::ExtraLight,false);
painter.setFont(font);
painter.drawText(this->width()-300 / 2,
this->height()-30 / 2,
QString("GAME OVER"));
timer->stop();
}
QWidget::paintEvent(event);
}
void Widget::deleteLast()
{
snake.removeLast();
}
void Widget::addNewReward()
{
rewardNode = QRectF(
qrand()%(this->width()/20) * 20,
qrand()%(this->height()/20) * 20,
nodeWidth,
nodeHeight);
}
bool Widget::checkContact()
{
for(int j = 0;j < snake.length();j++)
{
for(int i = j+1;i < snake.length();i++)
{
if(snake[j] == snake[i])
{
return 1;
}
}
}
return 0;
}