一个很粗糙的贪吃蛇游戏
今天我随便写了一个贪吃蛇游戏,代码是随便写的,有许多问题。
用Qt写的。
#ifndef SNAKEWIDGET_H #define SNAKEWIDGET_H #define private public #include <QWidget> #include <QVector> #include <QQueue> #include <QTimer> class SnakeWidget : public QWidget { Q_OBJECT public: explicit SnakeWidget(QWidget *parent = 0); ~SnakeWidget(); void replay(); void makeFail(); signals: public slots: void timeout(); protected: void paintEvent(QPaintEvent * event); void keyPressEvent(QKeyEvent *event); private: void genFood(); QTimer timer; enum Dot { Empty, Snake, Food, Wall }; Dot * *snakeMap; enum Dir { Left = 0, Down = 1, Right = 2, Up = 3 }; Dir dir; QQueue<QPoint> snakeQueue; int cntWidth; int cntHeight; int cntFoods; int lenInitSnake; }; #endif // SNAKEWIDGET_H
#include "snakewidget.h" #include <QPainter> #include <QPaintEvent> #include <QMessageBox> #include <QtAlgorithms> SnakeWidget::SnakeWidget(QWidget *parent) : QWidget(parent), cntFoods(100), lenInitSnake(10), cntWidth(100), cntHeight(100) { // init map snakeMap = new Dot *[cntWidth]; for (int i = 0; i < cntWidth; i++) { snakeMap[i] = new Dot[cntHeight]; } connect(&timer, SIGNAL(timeout()), this, SLOT(timeout())); setFocusPolicy(Qt::StrongFocus); replay(); } SnakeWidget::~SnakeWidget() { for (int i = 0; i < 100; i++) { delete snakeMap[i]; } delete snakeMap; } void SnakeWidget::replay() { for (int i = 0; i < cntWidth; i++) { for (int j = 0; j < cntHeight; j++) { snakeMap[i][j] = Empty; } } for (int i = 10; i < 90; i++) { snakeMap[50][i] = Wall; snakeMap[70][i] = Wall; } while (!snakeQueue.empty()) { snakeQueue.pop_back(); } for (int i = 0; i < lenInitSnake; i++) { snakeQueue.push_back(QPoint(1, 1)); } for (int i = 0; i < cntFoods; i++) { genFood(); } dir = Down; timer.start(100); } void SnakeWidget::makeFail() { QMessageBox::information(this, "haha!!!", "You failed!"); replay(); } void SnakeWidget::genFood() { while (true) { int x = qrand() % cntWidth; int y = qrand() % cntHeight; if (snakeMap[x][y] == Empty) { snakeMap[x][y] = Food; break; } } } void SnakeWidget::timeout() { static int dx[] = { -1, 0, 1, 0 }; static int dy[] = { 0, 1, 0, -1 }; QPoint cur = snakeQueue.back(); int x = cur.x() + dx[dir]; int y = cur.y() + dy[dir]; x = (x + cntWidth) % cntWidth; y = (y + cntHeight) % cntHeight; if (x < 0 || x > cntWidth || y < 0 || y > cntWidth) { return; } if (snakeMap[x][y] == Snake || snakeMap[x][y] == Wall) { makeFail(); return; } QPoint npt(x, y); snakeQueue.push_back(npt); if (snakeMap[x][y] != Food) { QPoint last = snakeQueue.front(); snakeMap[last.x()][last.y()] = Empty; snakeQueue.pop_front(); } else { genFood(); } snakeMap[x][y] = Snake; update(); } void SnakeWidget::keyPressEvent(QKeyEvent *event) { switch (event->key()) { case Qt::Key_Down: if (dir == Up) break; dir = Down; break; case Qt::Key_Up: if (dir == Down) break; dir = Up; break; case Qt::Key_Left: if (dir == Right) break; dir = Left; break; case Qt::Key_Right: if (dir == Left) break; dir = Right; break; case Qt::Key_R: replay(); break; default: break; } } void SnakeWidget::paintEvent(QPaintEvent *event) { int dw = width() / cntWidth; int dh = height() / cntHeight; dw = dh = qMin(dw, dh); QPainter painter; painter.begin(this); for (int i = 0; i < cntWidth; i++) { for (int j = 0; j < cntHeight; j++) { if (snakeMap[i][j] == Empty) { painter.drawRect(dw * i, dh * j, dw, dh); } else if (snakeMap[i][j] == Snake) { painter.fillRect(dw * i, dh * j, dw, dh, QBrush(Qt::blue)); } else if (snakeMap[i][j] == Food) { painter.fillRect(dw * i, dh * j, dw, dh, QBrush(Qt::red)); } else if (snakeMap[i][j] == Wall) { painter.fillRect(dw * i, dh * j, dw, dh, QBrush(Qt::black)); } } } }