91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

利用Qt實現一個簡單的五子棋小游戲

發布時間:2020-11-06 17:07:39 來源:億速云 閱讀:955 作者:Leah 欄目:開發技術

這期內容當中小編將會給大家帶來有關利用Qt實現一個簡單的五子棋小游戲,文章內容豐富且以專業的角度為大家分析和敘述,閱讀完這篇文章希望大家可以有所收獲。

下圖為游戲主窗口頁面:

利用Qt實現一個簡單的五子棋小游戲

第一步:窗口繪圖的實現(QPaintEvent繪圖事件 和 QMouseEvent鼠標事件)

①鼠標事件(這里我的是mouseDoubleClickEvent()雙擊事件)

void GamePage::mouseDoubleClickEvent(QMouseEvent *event)//鼠標雙擊事件
{
 m_dx = event->x();
 m_dy = event->y();
 //避免亂點時存入坐標 需添加:標志符--》game狀態 坐標的界限(點)
 if(m_dx < POINT_X_MAX && m_dy < POINT_Y_MAX && m_bRunState == true)
 {
  //如果點在交叉點周圍則設置點在交叉點上(判斷點位置)
  QPointF newPoint(gainPointPosition(QPointF(m_dx,m_dy)));
 
  if(!m_VectorRedPoint.contains(newPoint) &&       
   !m_VectorBlackPoint.contains(newPoint))//判斷點是否已經存在
  {
   if(m_iFlagWho == 0)//紅棋
   {
    m_VectorRedPoint.append(newPoint);
    m_iFlagWho = 1;
   }
   else//黑棋
   {
    m_VectorBlackPoint.append(newPoint);
    m_iFlagWho = 0;
   }
  }
 
 }
}

在這里窗口網格圖是通過直接繪畫以及鼠標雙擊選擇坐標來存儲棋子和繪畫棋子,因此對點進行了一個設置位置函數以便處于兩線之間的交接處,代碼如下:

QPointF GamePage::gainPointPosition(QPointF srcPoint)//返回一個處于格子兩線交接處的坐標點
{
 QPointF tmp;
 for(int i = 0;i < 12;i++)
 {
  if(srcPoint.x() >= 50*i && srcPoint.x() <= (50*i+25))//X判斷
  {
   tmp.setX(50*i);//如果處于50*i ~ 50*i+25)之間則設置點坐標點為50*i
  }
  else if (srcPoint.x() >= (50*i + 25) && srcPoint.x() <= 50*(i+1))
  {
   tmp.setX(50*(i+1));//如果處于50*i+25 ~ 50*(i+1)之間則設置點坐標點為50*(i+1)
  }
  if(srcPoint.y() >= 50*i && srcPoint.y() <= (50*i+25))//Y判斷
  {
   tmp.setY(50*i);//同上
  }
  else if (srcPoint.y() >= (50*i + 25) && srcPoint.y() <= 50*(i+1))
  {
   tmp.setY(50*(i+1));//同上
  }
 
 }
 return tmp;
}

②繪圖事件( 主要是網格圖、黑棋、紅棋的繪畫 )

棋子坐標的存儲主要是通過QVector容器來實現,并對容器進行迭代循環繪圖,實現代碼如下:

void GamePage::paintEvent(QPaintEvent *event)//繪畫事件
{
 QPainter *pater = new QPainter(this);
 pater->begin(this);
 //網格圖
 pater->setPen(Qt::black);
 for(int i = 0;i <= 12;i++)
 {
  pater->drawLine(0,50*i,600,50*i);
  pater->drawLine(50*i,0,50*i,600);
 }
 
 //紅色棋繪畫
 QVector<QPointF>::iterator iter;
 for(iter = m_VectorRedPoint.begin();iter != m_VectorRedPoint.end();iter++)
 {
  pater->setBrush(QBrush(Qt::red, Qt::SolidPattern));
  pater->setPen(Qt::red);
  pater->drawEllipse(*iter,15,15);
 }
 //黑色棋繪畫
 QVector<QPointF>::iterator iter1;
 for(iter1 = m_VectorBlackPoint.begin();iter1 != m_VectorBlackPoint.end();iter1++)
 {
  pater->setBrush(QBrush(Qt::black, Qt::SolidPattern));
  pater->setPen(Qt::black);
  pater->drawEllipse(*iter1,15,15);
 }
 pater->end();
 update();
 
}

第二步:輸贏的計算

利用Qt實現一個簡單的五子棋小游戲

上圖列出了計算的關系規律,下面就用代碼分別實現三個不同方向的計算:

①橫向

bool GamePage::checkXPointF(QVector<QPointF> vector) //檢查X軸方向的
{
  int num_L= 1;
  int num_R = 1;
  QVector<QPointF>::iterator iter;
  QVector<QPointF>::iterator itertmp;
  for(iter = vector.begin();iter != vector.end();iter++)
  {
   QPointF tmp = *iter;
   for(int k = 1;k < 5;k++)//左方向的查找
   {
    for(itertmp = vector.begin();itertmp != vector.end();itertmp++)
    {
 
     qDebug()<<*itertmp<<"X compare"<<tmp;
     if((*itertmp).x() - tmp.x() == k*50)
     {
      num_L ++;
     }
    }
    //qDebug()<<"count:"<<num;
    if(num_L == k+1)//尋找過程中找到幾個點相連
    {
     if(num_L == 5)
     {
      return true;
     }
    }
    else
    {
     break;
    }
   }
 
   for(int k = 1;k < 5;k++)//右方向的查找
   {
    for(itertmp = vector.begin();itertmp != vector.end();itertmp++)
    {
     qDebug()<<*itertmp<<"X compare"<<tmp;
     if((*itertmp).x() - tmp.x() == -k*50)
     {
      num_R ++;
     }
   }
    //qDebug()<<"count:"<<num;
   if(num_R == k+1)//尋找過程中找到幾個點相連
   {
    if(num_R == 5)
    {
     return true;
    }
   }
   else
   {
    break;
   }
  }
  if(num_R + num_L == 5+1)//5+1 因為左右方向都是從1開始計算 重復了原點tmp坐標
  {
   return true;
  }
  else
  {
   num_R = 1;
   num_L = 1;
 
  }
 }
 return false;
}

②縱向(與橫向同理)

bool GamePage::checkYPointF(QVector<QPointF> vector)
{
  qDebug()<<"enter Y***************";
 int num_U = 1;
   int num_D = 1;
  QVector<QPointF>::iterator iter;
  QVector<QPointF>::iterator itertmp;
  for(iter = vector.begin();iter != vector.end();iter++)
  {
   QPointF tmp = *iter;
   for(int k = 1;k < 5;k++)//上
   {
    for(itertmp = vector.begin();itertmp != vector.end();itertmp++)
    {
 
     qDebug()<<*itertmp<<"Y compare"<<tmp;
     if((*itertmp).y() - tmp.y() == k*50)
     {
      num_U ++;
     }
    }
    qDebug()<<"num_U:"<<num_U;
    if(num_U == k+1)//尋找過程中找到幾個點相連
    {
     if(num_U == 5)
     {
      return true;
     }
    }else{break;}
   }
   for(int k = 1;k < 5;k++)//下
   {
    for(itertmp = vector.begin();itertmp != vector.end();itertmp++)
    {
     qDebug()<<*itertmp<<"Y compare"<<tmp;
     if((*itertmp).y() - tmp.y() == -k*50)
     {
      num_D ++;
     }
 
    }
   qDebug()<<"num_D:"<<num_D;
   if(num_D == k+1)//尋找過程中找到幾個點相連
   {
    if(num_D == 5)
    {
     return true;
    }
   }else{break;}
  }
  if(num_D + num_U == 5 + 1)//減去一個
  {
   return true;
  }
  else
  {
   num_D = 1;
   num_U= 1;
  }
 }
 
 return false;
}

③斜向(從上圖可知,以坐標系為例,分為四個象限的計算和計數來判斷是否達到要求)

int GamePage::findSeriesPointF(bool flag, QPointF tmp, QVector<QPointF> vector)
{
  bool flag_iter = false;
  int forward_count = 1;//一象限的數量
  int reverse_count = 1;
  int forward_count2 = 1;
  int reverse_count2 = 1;
  QVector<QPointF>::iterator iter= vector.begin();
 
  while(iter != vector.end())
  {
   qDebug()<<*iter<<"compare"<<tmp;
   switch(forward_count)//一象限
   {
    case 1:
     if((*iter).x() - tmp.x() == 50 && (*iter).y() - tmp.y() == -50)
     {
      forward_count ++;
 
      flag_iter = true;
     }
     break;
    case 2:
     if((*iter).x() - tmp.x() == 50*forward_count && (*iter).y() - tmp.y() == -50*forward_count)
     {
      forward_count++;
      flag_iter = true;
     }
     break;
    case 3:
     if((*iter).x() - tmp.x() == 50*forward_count && (*iter).y() - tmp.y() == -50*forward_count)
     {
      forward_count++;
      flag_iter = true;
     }
     break;
    case 4:
     if((*iter).x() - tmp.x() == 50*forward_count && (*iter).y() - tmp.y() == -50*forward_count)
     {
      forward_count++;
      flag_iter = true;
     }
     break;
 
   }
   switch(reverse_count)//三象限
   {
    case 1:
     if((*iter).x() - tmp.x() == -50 && (*iter).y() - tmp.y() == 50)
     {
      reverse_count=2;
      flag_iter = true;
     }
     break;
    case 2:
     if((*iter).x() - tmp.x() == -50*reverse_count && (*iter).y() - tmp.y() == 50*reverse_count)
     {
      reverse_count++;
      flag_iter = true;
     }
     break;
    case 3:
     if((*iter).x() - tmp.x() == -50*reverse_count && (*iter).y() - tmp.y() == 50*reverse_count)
     {
      reverse_count++;
      flag_iter = true;
     }
     break;
    case 4:
     if((*iter).x() - tmp.x() == -50*reverse_count && (*iter).y() - tmp.y() == 50*reverse_count)
     {
      reverse_count++;
      flag_iter = true;
     }
     break;
 
   }
   qDebug()<<forward_count<<"+"<<reverse_count;
   if(forward_count + reverse_count == 6)//未加上點本身
   {
    return 5;
 
   }
 
   switch(forward_count2)//2象限
   {
    case 1:
     if((*iter).x() - tmp.x() == -50 && (*iter).y() - tmp.y() == -50)
     {
      forward_count2++;
      flag_iter = true;
     }
     break;
    case 2:
     if((*iter).x() - tmp.x() == -50*forward_count2 && (*iter).y() - tmp.y() == -50*forward_count2)
     {
      forward_count2++;
      flag_iter = true;
     }
     break;
    case 3:
     if((*iter).x() - tmp.x() == -50*forward_count2 && (*iter).y() - tmp.y() == -50*forward_count2)
     {
      forward_count2++;
      flag_iter = true;
     }
     break;
    case 4:
     if((*iter).x() - tmp.x() == -50*forward_count2 && (*iter).y() - tmp.y() == -50*forward_count2)
     {
      forward_count2++;
      flag_iter = true;
     }
     break;
   }
 
   switch(reverse_count2)//4象限
   {
    case 1:
     if((*iter).x() - tmp.x() == 50 && (*iter).y() - tmp.y() == 50)
     {
      reverse_count2++;
      flag_iter = true;
     }
     break;
    case 2:
     if((*iter).x() - tmp.x() == 50*reverse_count2 && (*iter).y() - tmp.y() == 50*reverse_count2)
     {
      reverse_count2++;
      flag_iter = true;
     }
     break;
    case 3:
     if((*iter).x() - tmp.x() == 50*reverse_count2 && (*iter).y() - tmp.y() == 50*reverse_count2)
     {
      reverse_count2++;
      flag_iter = true;
     }
     break;
    case 4:
     if((*iter).x() - tmp.x() == 50*reverse_count2 && (*iter).y() - tmp.y() == 50*reverse_count2)
     {
      reverse_count2++;
      flag_iter = true;
     }
     break;
   }
   qDebug()<<forward_count2<<"+"<<reverse_count2;
   if(forward_count2 + reverse_count2 == 6)//未加上點本身
   {
    return 5;
   }
   if(flag_iter)
   {
     iter = vector.begin();//目的是返回首個點,重頭存貨在后 不錯過
     flag_iter = false;
   }
   else {
     iter++;
   }
 
  }
 
  return 0;
}

以上橫、縱、斜三個方向的運算都是通過最簡單的算法是實現,易于理解。

④定時器實現紅黑旗的定時檢查功能

void GamePage::slotCheckWhetherWin()//定時器檢查是否輸贏功能
{
  m_pVerVector.clear();
  m_pVerVectorB.clear();
  m_pHerVector.clear();
  m_pHerVectorB.clear();
 
  QVector<QPointF>::iterator iterRed;
  for(iterRed = m_VectorRedPoint.begin();iterRed != m_VectorRedPoint.end();iterRed++)
  {
   qDebug()<<*iterRed;
  }
  QVector<QPointF> tmpRed = m_VectorRedPoint;
  //紅棋判斷
  if(m_VectorRedPoint.size() >= 5)
  {
   for(iterRed = m_VectorRedPoint.begin();iterRed != m_VectorRedPoint.end();iterRed++)
   {
 
    QPointF tmp = *iterRed;//獲取第一個點
    qDebug()<<"tmp:"<<tmp;
    QVector<QPointF>::iterator itertmp;
    for(itertmp = tmpRed.begin();itertmp != tmpRed.end();itertmp++)
    {
     qDebug()<<"tmpRed:"<<*itertmp;
     //橫向連續5個點
     if((*itertmp).y() - tmp.y() >= -0.000001 && (*itertmp).y() - tmp.y() <= 0.000001)//先判斷y是同一坐標
     {
       m_pHerVector.append(*itertmp);
     }
     //縱向連續5個點
     if((*itertmp).x() - tmp.x() >= -0.000001 && (*itertmp).x() - tmp.x() <= 0.000001)//先判斷y是同一坐標
     {
       m_pVerVector.append(*itertmp);
     }
 
    }
    //對容器進行操作
    if(checkXPointF(m_pHerVector) || checkYPointF(m_pVerVector))
    {
     QMessageBox::warning(nullptr,"warning","紅方XY贏了!");
     m_ptimer->stop();
     return;
    }
    else
    {
     m_pHerVector.clear();//清空
     m_pVerVector.clear();//清空
     count = 0;
    }
 
    //其他都是斜向
    if(findSeriesPointF(true,tmp,m_VectorRedPoint) == 5)
    {
     QMessageBox::warning(nullptr,"warning","紅方斜線贏了!");
     m_ptimer->stop();
     return;
    }
   }
 
  }
  //黑棋判斷
  QVector<QPointF>::iterator iterBlack;
  QVector<QPointF> tmpBlack = m_VectorBlackPoint;
  if(m_VectorBlackPoint.size() >= 5)
  {
   for(iterBlack = m_VectorBlackPoint.begin();iterBlack != m_VectorBlackPoint.end();iterBlack++)
   {
 
    QPointF tmp = *iterBlack;//獲取第一個點
    qDebug()<<"tmp:"<<tmp;
    QVector<QPointF>::iterator itertmp;
    for(itertmp = tmpBlack.begin();itertmp != tmpBlack.end();itertmp++)//正向
    {
     qDebug()<<"tmpRed:"<<*itertmp;
     //橫向連續5個點
     if((*itertmp).y() - tmp.y() >= -0.000001 && (*itertmp).y() - tmp.y() <= 0.000001)//先判斷y是同一坐標
     {
       m_pHerVectorB.append(*itertmp);
     }
     //縱向連續5個點
     if((*itertmp).x() - tmp.x() >= -0.000001 && (*itertmp).x() - tmp.x() <= 0.000001)//先判斷y是同一坐標
     {
       m_pVerVectorB.append(*itertmp);
     }
 
    }
    //對容器進行操作
    if(checkXPointF(m_pHerVectorB) || checkYPointF(m_pVerVectorB))
    {
     QMessageBox::warning(nullptr,"warning","黑方XY贏了!");
     m_ptimer->stop();
     return;
    }
    else
    {
     m_pHerVectorB.clear();//清空
     m_pVerVectorB.clear();//清空
     count = 0;
    }
 
    //其他都是斜向
    if(findSeriesPointF(true,tmp,m_VectorBlackPoint) == 5)
    {
     QMessageBox::warning(nullptr,"warning","黑方斜線贏了!");
     m_ptimer->stop();
     return;
    }
   }
 
  }
 
}

上述就是小編為大家分享的利用Qt實現一個簡單的五子棋小游戲了,如果剛好有類似的疑惑,不妨參照上述分析進行理解。如果想知道更多相關知識,歡迎關注億速云行業資訊頻道。

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

肇东市| 湟中县| 泰州市| 安化县| 银川市| 庆城县| 永靖县| 凉城县| 洪泽县| 定襄县| 藁城市| 石阡县| 南通市| 新和县| 许昌县| 富锦市| 景洪市| 凌云县| 廊坊市| 安龙县| 伊金霍洛旗| 五华县| 和静县| 杭锦旗| 阳谷县| 聂拉木县| 多伦县| 化州市| 皋兰县| 驻马店市| 乐山市| 澄迈县| 临澧县| 万源市| 德昌县| 金堂县| 开封县| 扎赉特旗| 通化县| 金平| 耒阳市|