您好,欢迎访问三七文档
当前位置:首页 > 商业/管理/HR > 信息化管理 > 嵌入式Linux大作业实现2048
2018-2019学年下学期《嵌入式Linux应用程序开发》期末大作业专业:软件工程班级:1603学号:201616040305姓名:赵亮任课教师:薛正元成绩:题目内容:在Linux下,用qt编程实现一个小游戏,2048.整体的代码结构如图1:图1完成后预览如图2:图2游戏主逻辑说明:1初始生成两个值,要么2,要么42移动(上下左右四个方向):首先,在行/列上找到当前行第一个为空的值,记录下该位置,再往后找到第一个不为空的值,最后将这两个位置交换。3合并:1:在2.移动中,边界值为空当交换后的位置与交换后的位置的前一个位置(简称前一个位置)的值相等,前一个位置值*2,删除要移动的值。2:在2.移动中,边界值不为空判断边界值是否与后面第一个不为空的值相等3:相等,边界值*2,删除第一个不为空的值4:不相等,不做任何操作4:游戏结束:如果出现2048,赢,游戏结束,当方格填满,没有合并项,失败,游戏结束1.注:要记录下该位置在同一回合中是否合并过,避免同一回合多次合并核心步骤:1设定背景样式:voidBGWidget::paintEvent(QPaintEvent*event){QStylePainterpainter(this);//用style画背景(会使用setstylesheet中的内容)QStyleOptionopt;opt.initFrom(this);opt.rect=rect();painter.drawPrimitive(QStyle::PE_Widget,opt);painter.setPen(QColor(204,192,180));painter.setBrush(QColor(204,192,180));//4*4的背景矩阵constintcolWidth=75;constintrowHeight=75;constintxOffset=10;constintyOffset=10;for(introw=0;row4;++row){for(intcol=0;col4;++col){//背景方框intx=col*colWidth+xOffset;inty=row*rowHeight+yOffset;painter.drawRoundRect(x,y,65,65,10,10);}}QWidget::paintEvent(event);}2Label类构造:MyLabel::MyLabel(inttext){this-setText(QString::number(text));this-setAlignment(Qt::Alignment(Qt::AlignCenter));this-setFont(QFont(Gadugi,20,QFont::Bold));//初始化样式intindex=log_2(text)-1;//计算背景数组索引值QStringfontColor=color:rgb(255,255,255);;if(index8){fontColor=color:rgb(119,110,101);;}QStringbgColor=QString(QLabel{background-color:%1;border-radius:5px;%2}).arg(digitBkg[index]).arg(fontColor);this-setStyleSheet(bgColor);//透明度QGraphicsOpacityEffect*m_pGraphicsOpacityEffect=newQGraphicsOpacityEffect(this);m_pGraphicsOpacityEffect-setOpacity(1);this-setGraphicsEffect(m_pGraphicsOpacityEffect);//动画让label慢慢出现QPropertyAnimation*animation=newQPropertyAnimation(m_pGraphicsOpacityEffect,opacity,this);animation-setEasingCurve(QEasingCurve::Linear);animation-setDuration(400);animation-setStartValue(0);animation-setEndValue(1);animation-start(QAbstractAnimation::KeepWhenStopped);}voidMyLabel::reSetText(inttext){this-setText(QString::number(text));intindex=log_2(text)-1;//计算背景数组索引值QStringfontColor=color:rgb(255,255,255);;if(index8){fontColor=color:rgb(119,110,101);;}QStringbgColor=QString(QLabel{background-color:%1;border-radius:5px;%2}).arg(digitBkg[index]).arg(fontColor);this-setStyleSheet(bgColor);this-show();this-repaint();}这里,ui就不贴出了,见源代码。3游戏主逻辑的设计与实现//初始化voidGameWidget::initGame(){//初始化分数为0m_score=0;m_highScore=0;//初始化for(introw=0;row4;++row){for(intcol=0;col4;++col){labels[row][col]=NULL;}}//读取文件,最高分设置//ReadOnly文件不存在,打开失败//WriteOnly文件不存在,会自动创建文件//ReadWrite文件不存在,会自动创建文件//Append文件不存在,会自动创建文件//Truncate文件不存在,打开失败//Text文件不存在,打开失败//Unbuffered文件不存在,打开失败QFile*file=newQFile(data.json);if(file-open(QIODevice::ReadOnly)){QByteArrayba=file-readAll();QJsonDocumentd=QJsonDocument::fromJson(ba);QJsonObjectjson=d.object();QJsonValuevalue=json.value(QString(m_highScore));QJsonValuescore=json.value(QString(m_score));//最高分数m_highScore=value.toVariant().toInt();this-ui-best_2-setText(QString::number(m_highScore));//当前分数m_score=score.toVariant().toInt();this-ui-score_3-setText(QString::number(m_score));//文件保存的进度QJsonValuelabelsArr=json.value(QString(labels));QJsonArrayarr=labelsArr.toArray();for(inti=0;iarr.size();i++){QJsonValuelabelValue=arr.at(i);QJsonArrayarr1=labelValue.toArray();for(intj=0;jarr1.size();j++){QJsonValuearrValue=arr1.at(j);intoldValue=arrValue.toVariant().toInt();if(oldValue!=0){MyLabel*label=newMyLabel(oldValue);intx=j*colWidth+xOffset;inty=i*rowHeight+yOffset;label-setGeometry(x,y,66,66);label-setParent(m_bgWidget);labels[i][j]=label;labels[i][j]-show();++m_labelCount;}}}file-close();//判断读取的文件是否游戏结束//这里可以不用判断,为了防止游戏在结束的时候程序意外关闭//gameOver();}else{//初始化两个标签for(inti=0;i2;i++){createLabel();}}}对游戏期间数字相碰的逻辑处理:boolGameWidget::merge(MyLabel*temp,introw,intcol){if(temp!=NULL){//判断两个值是否相等,是合并if(temp-text()==labels[row][col]-text()){intx=labels[row][col]-x();inty=row*rowHeight+yOffset;//y轴偏移//动画效果QPropertyAnimation*animation=newQPropertyAnimation(temp,geometry);animation-setStartValue(temp-geometry());animation-setEndValue(QRect(x,y,temp-width(),temp-height()));animation-setDuration(100);animation-setEasingCurve(QEasingCurve::Linear);animation-start(QAbstractAnimation::DeleteWhenStopped);intscore=2*labels[row][col]-text().toInt();labels[row][col]-reSetText(score);m_score+=score;emitScoreChange();--m_labelCount;returntrue;}}returnfalse;}boolGameWidget::isMerge(){for(introw=0;row4;++row){for(intcol=0;col4;++col){if(isMergeDown(row,col)||isMergeRight(row,col)){returntrue;}}}returnfalse;}游戏胜利或者失败的判断:boolGameWidget::gameOver(){boolflag=false;//如果格子全满(m_labelCount==16)if(m_labelCount==16){boolisWin=isMerge();if(!isWin){//没有可以合并的标签,显示失败QMessageBox::about(this,信息,失败!);flag=true;}}else{//最大数出现2048,则显示胜利for(introw=0;row4;++row){for(intcol=0;col4;++col){if(labels[row][col]!=NULL&&labels[row][col]-text()==2048){QMessageBox::about(this,信息,恭喜,你赢了!);flag=true;break;}}if(flag){break;}}}if(flag){//删除数组,从头开始releaseRes();m_labelCount=0;m_score=0;emitScoreChange();for(inti=0;i2;i++){createLabel();}}returnflag
本文标题:嵌入式Linux大作业实现2048
链接地址:https://www.777doc.com/doc-5867109 .html