亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Qt實現(xiàn)Flappy Bird游戲

 更新時間:2018年12月24日 10:21:54   作者:https://blog.csdn.net/ly305750665/article/details/79006378  
這篇文章主要為大家詳細介紹了Qt實現(xiàn)Flappy Bird游戲,具有一定的參考價值,感興趣的小伙伴們可以參考一下

簡述

最近瀏覽網(wǎng)站的時候,忘記在哪里看的這個FlappyBird了,這個小游戲在之前小火了一段時間。今天用QT簡單的實現(xiàn)了一把,然后在網(wǎng)上找了一些相關(guān)的切圖,便進行了制作。難度不是很大,只是通過寫這篇博客,能有點啟發(fā)以及大家共同學(xué)習(xí)。

效果圖

代碼

主界面控制

MainWindow::MainWindow(QWidget *parent)
 : BasicWindow(parent)
 , m_startGame(false)
{
 ui.setupUi(this);
 setAttribute(Qt::WA_TranslucentBackground);
 initControl();
}

void MainWindow::initControl()
{
 loadStyleSheet("MainWindow");
 m_scene = new MainGraphicsScene(this, rect());
 QGraphicsView* view = new QGraphicsView(m_scene, this);

 view->setScene(m_scene);
 view->setStyleSheet("border:none; background:transparent;");
 view->setCacheMode(QGraphicsView::CacheBackground);
 startWelcome();
}

void MainWindow::startWelcome()
{
 //道路
 GraphicsRoadItem *roadItem = new GraphicsRoadItem(m_scene);

 //小鳥
 m_bird = new FlappyBird(m_scene);

 //管道
 GraphicsPipeitem *pipeItem = new GraphicsPipeitem(m_scene);

 //游戲狀態(tài)檢測,開啟定時器,50ms檢測一次
 m_checkGameStatus = new QTimer(this);
 connect(m_checkGameStatus, SIGNAL(timeout()), this, SLOT(onCheckGameStatus()));

 //flappybird字母
 static const int nLetters = 10;
 static struct {
  char const *pix;
  qreal initX, initY;
  qreal destX, destY;
 } letterData[nLetters] = {
  { "F", -1000, -1000, 150, 100 },
  { "L", -800, -1000, 200, 100 },
  { "A", -600, -1000, 250, 100 },
  { "P", -400, -1000, 300, 100 },
  { "P", 1000, 2000, 350, 100 },
  { "Y", 800, 2000, 400, 100 },
  { "B", 600, 2000, 260, 160 },
  { "I", 400, 2000, 310, 160 },
  { "R", 200, 2000, 360, 160 },
  { "D", 0, 2000, 410, 160 } };

 QSequentialAnimationGroup * lettersGroupMoving = new QSequentialAnimationGroup(this);
 m_lettersGroupFading = new QParallelAnimationGroup(this);

 for (int i = 0; i < nLetters; ++i) {
  QString& htmlText = QString("<span style=\"font-family:'Berlin Sans FB';font-size:48px;font-weight:600;color:#194819;\">%1</span>").arg(letterData[i].pix);
  QGraphicsTextItem *letter = new QGraphicsTextItem();
  letter->setHtml(htmlText);
  letter->setPos(letterData[i].initX, letterData[i].initY);

  QPropertyAnimation *moveAnim = new QPropertyAnimation(letter, "pos", lettersGroupMoving);
  moveAnim->setEndValue(QPointF(letterData[i].destX, letterData[i].destY));
  moveAnim->setDuration(200);
  moveAnim->setEasingCurve(QEasingCurve::OutElastic);
  lettersGroupMoving->addPause(50);

  QPropertyAnimation *fadeAnim = new QPropertyAnimation(letter, "opacity", m_lettersGroupFading);
  fadeAnim->setDuration(1000);
  fadeAnim->setEndValue(0);
  fadeAnim->setEasingCurve(QEasingCurve::OutQuad);

  m_scene->addItem(letter);
 }
 lettersGroupMoving->start(QAbstractAnimation::DeleteWhenStopped);

 //游戲開始按鈕
 QPixmap&& pix = QPixmap(":/FlappyBird/Resources/texture/startButton.png").scaled(QSize(160, 48), Qt::IgnoreAspectRatio, Qt::SmoothTransformation);
 GraphicsButtonItem* btnItem = new GraphicsButtonItem(pix, m_scene);
 btnItem->setPos(QPointF(220, 340));
 QPropertyAnimation *fadeAnim = new QPropertyAnimation(btnItem, "opacity", m_lettersGroupFading);
 fadeAnim->setDuration(600);
 fadeAnim->setEndValue(0);
 fadeAnim->setEasingCurve(QEasingCurve::OutQuad);
 connect(btnItem, SIGNAL(clicked()), this, SLOT(onStartBtnClicked()));
 connect(fadeAnim, &QPropertyAnimation::finished, [this](){
  m_startGame = true;
  m_checkGameStatus->start(50);
  m_bird->flyLandfallAnimation();
 });
}

void MainWindow::onCheckGameStatus()
{
 //檢測小鳥是否與地面和管道發(fā)生碰撞
 if (m_bird->checkIsCollided())
 {
  GameOver();
 }
}

void MainWindow::GameOver()
{
 static const int nLetters = 8;
 static struct {
  char const *pix;
  qreal initX, initY;
  qreal destX, destY;
 } letterData[nLetters] = {
  { "G", -1000, -1000, 150, 100 },
  { "A", -800, -1000, 200, 100 },
  { "M", -600, -1000, 250, 100 },
  { "E", -400, -1000, 300, 100 },
  { "O", 600, 2000, 260, 160 },
  { "V", 400, 2000, 310, 160 },
  { "E", 200, 2000, 360, 160 },
  { "R", 0, 2000, 410, 160 } };

 QParallelAnimationGroup * lettersGroupMoving = new QParallelAnimationGroup(this);

 for (int i = 0; i < nLetters; ++i) {
  QString& htmlText = QString("<span style=\"font-family:'Berlin Sans FB';font-size:48px;font-weight:600;color:#194819;\">%1</span>").arg(letterData[i].pix);
  QGraphicsTextItem *letter = new QGraphicsTextItem();
  letter->setHtml(htmlText);
  letter->setPos(letterData[i].initX, letterData[i].initY);

  QPropertyAnimation *moveAnim = new QPropertyAnimation(letter, "pos", lettersGroupMoving);
  moveAnim->setEndValue(QPointF(letterData[i].destX, letterData[i].destY));
  moveAnim->setDuration(200);
  moveAnim->setEasingCurve(QEasingCurve::OutElastic);
  m_scene->addItem(letter);
 }
 lettersGroupMoving->start(QAbstractAnimation::DeleteWhenStopped);

 m_scene->removeItem(m_bird);
}

void MainWindow::onStartBtnClicked()
{
 m_lettersGroupFading->start(QAbstractAnimation::DeleteWhenStopped);
}

void MainWindow::keyPressEvent(QKeyEvent *event)
{
 if (m_startGame)
 {
  m_bird->keyPressEvent(event);
 }
}

小鳥組件繪制

FlappyBird::FlappyBird(QGraphicsScene *scene): m_curflyStatus(0)
   , m_IsLandFall(true)
   , m_IsRaise(true)
{
 scene->addItem(this);
 m_scene = scene;
 m_birdRefreashTime = new QTimer(this);
 connect(m_birdRefreashTime, SIGNAL(timeout()), this, SLOT(onRefreashBird()));
 m_birdRefreashTime->start(12);

 m_flyAnimation = new QPropertyAnimation(this, "pos");
}

void FlappyBird::onRefreashBird()
{
 update();
}

QRectF FlappyBird::boundingRect() const
{
 return QRectF(60, FLY_BIRD_SIZE * 5 , FLY_BIRD_SIZE, FLY_BIRD_SIZE);
}

void FlappyBird::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *)
{
 painter->save();
 if (m_curflyStatus < 10)
 {
  m_curflyStatus++;
  painter->drawImage(boundingRect(), QImage(":/FlappyBird/Resources/texture/bird1.png"));
 }
 else if (m_curflyStatus < 20)
 {
  m_curflyStatus++;
  painter->drawImage(boundingRect(), QImage(":/FlappyBird/Resources/texture/bird2.png"));
 }
 else if ( m_curflyStatus < 30)
 {
  m_curflyStatus++;
  painter->drawImage(boundingRect(), QImage(":/FlappyBird/Resources/texture/bird3.png"));
 }
 else
 {
  m_curflyStatus = 0;
 }
 painter->restore();
}

void FlappyBird::flyRaiseAnimation()
{
 if (m_IsRaise)
 {
  m_IsLandFall = false;
  m_IsRaise = false;
  m_flyAnimation->stop();

  if (pos().y() > -180)
  {
   m_flyAnimation->setDuration(300);
   m_flyAnimation->setEndValue(QPoint(pos().x(), pos().y() - FLY_BIRD_SIZE));
  }
  else
  {
   m_flyAnimation->setDuration(300);
   m_flyAnimation->setEndValue(pos());
  }
  m_flyAnimation->setEasingCurve(QEasingCurve::OutQuad);
  m_flyAnimation->start();
  connect(m_flyAnimation, SIGNAL(finished()), this, SLOT(onFlyRaiseAnimationFinished()));
 }
}

void FlappyBird::onFlyRaiseAnimationFinished()
{
 m_flyAnimation->disconnect(SIGNAL(finished()));
 m_IsRaise = true;
 m_IsLandFall = true;
 flyLandfallAnimation();
}

void FlappyBird::flyLandfallAnimation()
{
 if (m_birdRefreashTime->isActive())
 {
  m_birdRefreashTime->stop();
 }

 if (m_IsLandFall)
 {
  m_flyAnimation->stop();
  int fallHeight = m_scene->height() - pos().y();
  int time = 1000 * fallHeight / m_scene->height();
  m_flyAnimation->setDuration(time);
  m_flyAnimation->setEndValue(QPoint(pos().x(), pos().y() + fallHeight));
  m_flyAnimation->setEasingCurve(QEasingCurve::InQuad);
  m_flyAnimation->start();
  m_IsLandFall = false;
 }
}

bool FlappyBird::checkIsCollided()
{
 if (!collidingItems().isEmpty())
  return true;
 else
  return false;
}

void FlappyBird::keyPressEvent(QKeyEvent *event)
{
 if (event->key() == Qt::Key_Space)
 {
  flyRaiseAnimation();
 }
}

游戲開始按鈕

GraphicsButtonItem::GraphicsButtonItem(const QPixmap &pixmap, QGraphicsScene *scene) : pix(pixmap)
{
 scene->addItem(this);
 setCursor(QCursor(Qt::PointingHandCursor));
}

void GraphicsButtonItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
{
 if (event->button() == Qt::LeftButton)
 {
  emit clicked();
 }
 __super::mousePressEvent(event);
}

QSizeF GraphicsButtonItem::size() const
{
 return pix.size();
}

QRectF GraphicsButtonItem::boundingRect() const
{
 return QRectF(QPointF(0, 0), pix.size());
}

void GraphicsButtonItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *)
{
 painter->drawPixmap(0, 0, pix);
}

管道組件繪制

#define PIPE_WIDTH 60

GraphicsPipeitem::GraphicsPipeitem(QGraphicsScene *scene)
{
 m_scene = scene;
 m_scene->addItem(this);

 createPipeHeight();
 startMove();
}
void GraphicsPipeitem::createPipeHeight()
{
 m_upPipeHeight = qrand() % 100 + 80;
 m_downPipeHeight = m_scene->height() - m_upPipeHeight - 178;
}

QRectF GraphicsPipeitem::boundingRect() const
{
 return QRectF(m_scene->width(), 0, PIPE_WIDTH, m_scene->height());
}

QPainterPath GraphicsPipeitem::shape() const
{
 QPainterPath path;
 path.addRect(QRectF(m_scene->width(), 0, PIPE_WIDTH, m_upPipeHeight));
 path.addRect(QRectF(m_scene->width(), m_upPipeHeight + 140, PIPE_WIDTH, m_downPipeHeight));
 return path;
}


void GraphicsPipeitem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{
 painter->save();
 painter->drawImage(QRectF(m_scene->width(), 0, PIPE_WIDTH, m_upPipeHeight), QImage(":/FlappyBird/Resources/texture/tubeup.png").scaled(PIPE_WIDTH, m_upPipeHeight));
 painter->drawImage(QRectF(m_scene->width(), m_upPipeHeight + 140, PIPE_WIDTH, m_downPipeHeight), QImage(":/FlappyBird/Resources/texture/tubedown.png").scaled(PIPE_WIDTH, m_downPipeHeight));
 painter->restore();
}

void GraphicsPipeitem::startMove()
{
 QPropertyAnimation* moveAnimation = new QPropertyAnimation(this, "pos");
 moveAnimation->setLoopCount(-1);
 moveAnimation->setDuration(3000);
 moveAnimation->setStartValue(QPoint(0, pos().y()));
 moveAnimation->setEndValue(QPoint(-1 * m_scene->width() - PIPE_WIDTH, pos().y()));
 moveAnimation->start();
 connect(moveAnimation, &QPropertyAnimation::currentLoopChanged, [this](int loopCount){
  createPipeHeight();
 });
}

地面繪制

#define ROAD_ITEM_HEIGHT 38

GraphicsRoadItem::GraphicsRoadItem(QGraphicsScene *scene) :m_scene(scene)
{
 scene->addItem(this);
 startMove();
}

QRectF GraphicsRoadItem::boundingRect() const
{
 return QRectF(0, m_scene->height() - ROAD_ITEM_HEIGHT, m_scene->width() * 2, ROAD_ITEM_HEIGHT);
}

void GraphicsRoadItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *)
{
 painter->drawImage(QRectF(0, m_scene->height() - ROAD_ITEM_HEIGHT, m_scene->width(), ROAD_ITEM_HEIGHT), QImage(":/FlappyBird/Resources/texture/road.png"));
 painter->drawImage(QRectF(m_scene->width(), m_scene->height() - ROAD_ITEM_HEIGHT, m_scene->width(), ROAD_ITEM_HEIGHT), QImage(":/FlappyBird/Resources/texture/road.png"));
}

void GraphicsRoadItem::startMove()
{
 QPropertyAnimation* moveAnimation = new QPropertyAnimation(this, "pos");
 moveAnimation->setLoopCount(-1);
 moveAnimation->setDuration(6000);
 moveAnimation->setStartValue(QPoint(0, pos().y()));
 moveAnimation->setEndValue(QPoint(0 - m_scene->width(), pos().y()));
 moveAnimation->setEasingCurve(QEasingCurve::Linear);
 moveAnimation->start();
}

結(jié)尾

全部代碼,都在上面了,希望對大伙有所點啟發(fā)和幫助,只為記錄,只為分享! 愿所寫能對你有所幫助。

以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • windows?使用ffmpeg?.a靜態(tài)庫讀取Wav音頻并保存PCM的方法

    windows?使用ffmpeg?.a靜態(tài)庫讀取Wav音頻并保存PCM的方法

    這篇文章主要介紹了windows?使用ffmpeg?.a靜態(tài)庫讀取Wav音頻并保存PCM,本文給大家介紹的非常詳細,對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2024-02-02
  • 利用上下文屬性將?C++?對象嵌入?QML?里

    利用上下文屬性將?C++?對象嵌入?QML?里

    這篇文章主要介紹了利用上下文屬性將?C++?對象嵌入?QML里,將?QML?對象加載到?C++?應(yīng)用程序中時,直接嵌入一些可在?QML?代碼中使用的?C++?數(shù)據(jù)會很有用。例如,這使得在嵌入對象上調(diào)用?C++?方法或使用?C++?對象實例作為?QML?視圖的數(shù)據(jù)模型成為可能,下面一起來學(xué)習(xí)該內(nèi)容吧
    2021-12-12
  • C語言安全編碼數(shù)組記法的一致性

    C語言安全編碼數(shù)組記法的一致性

    這篇文章主要介紹了C語言安全編碼數(shù)組記法的一致性,需要的朋友可以參考下
    2014-07-07
  • 關(guān)于C語言除0引發(fā)的思考

    關(guān)于C語言除0引發(fā)的思考

    很多 C 庫都提供了一組函數(shù)用來判斷一個浮點數(shù)是否是無窮大或 NaN。int _isnan(double x) 函數(shù)用來判斷一個浮點數(shù)是否是 NaN,而 int _finite(double x) 用以判斷一個浮點數(shù)是否是無窮大
    2013-08-08
  • C語言與C++項目實現(xiàn)相互調(diào)用

    C語言與C++項目實現(xiàn)相互調(diào)用

    extern?“c”的作用可以實現(xiàn)c語言和c++相互調(diào)用,本文就詳細的介紹一下C語言與C++項目實現(xiàn)相互調(diào)用,感興趣的可以了解一下
    2022-01-01
  • C++11 上下文關(guān)鍵字的具體實踐

    C++11 上下文關(guān)鍵字的具體實踐

    本文主要介紹了C++11 上下文關(guān)鍵字的具體實踐,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2023-06-06
  • strcat 函數(shù)的使用指南

    strcat 函數(shù)的使用指南

    strcat是連接字符串的函數(shù)。函數(shù)返回指針,兩個參數(shù)都是指針,第一個參數(shù)所指向的內(nèi)存的地址必須能容納兩個字符串連接后的大小。
    2015-09-09
  • Qt+Quick實現(xiàn)播放音樂和視頻的開發(fā)

    Qt+Quick實現(xiàn)播放音樂和視頻的開發(fā)

    這篇文章主要為大家詳細介紹了如何利用Qt+Quick實現(xiàn)播放音樂和視頻的開發(fā),文中的示例代碼講解詳細,感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下
    2023-03-03
  • 淺談C++虛重載操作符 virtual operator= 的使用方法

    淺談C++虛重載操作符 virtual operator= 的使用方法

    下面小編就為大家?guī)硪黄獪\談C++虛重載操作符 virtual operator= 的使用方法。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-01-01
  • c/c++基礎(chǔ)簡單易懂的快速排序算法

    c/c++基礎(chǔ)簡單易懂的快速排序算法

    這篇文章主要為大家介紹了c/c++基礎(chǔ)非常簡單易懂的快速排序算法,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2021-11-11

最新評論