经典俄罗斯方块游戏

源码百度云链接

链接:https://pan.baidu.com/s/14frk2EuFoiRCzudol2Xgvg
提取码:syzk

GitHub

https://github.com/yocichenyx/Tetris-Game

开发者:yocichen

0引言

0.1背景和意义

一直以来,就有自己实现一个经典小游戏(比如贪吃蛇、俄罗斯方块等)的想法,但是从未实现过,这次课设正好有此机会并且本学期开设的图形学课程也可以派上用场。要求由自己独立设计(用面向对象方法)、完成一个游戏,就想到了俄罗斯方块这个经典又不失难度的小游戏。

用面向对象的方法来设计,可以培养自己的设计的能力,设计模式的运用又可以让自己熟悉常用的设计模式、体会其深邃的思想,独立开发也锻炼了自己的编码能力,这是一个较为全面的课程设计,对于我来说是一个不小的挑战。

0.2小组分工

任务分工

组员姓名

需求分析

yocichen

概要设计

yocichen

详细设计

yocichen

编码

yocichen

测试

yocichen

后期维护

NULL

1 工作计划

1.1主要工作阶段划分

阶段名称

时间安排

需求分析

12.21

概要设计

12.22

详细设计

12.22

编码

12.23-12.26

测试

12.21-12.26

1.2各阶段工作任务分解

阶段名称

任务名称

任务描述

负责人

需求分析

需求收集

收集需求,要求给出简要的需求说明

yocichen

用例图绘制

绘制用例图

概要设计

设计类图

根据需求说明和用例图,设计类图

yocichen

详细设计

Panel类设计

设计类属性和方法,给出实现思路

yocichen

Assembly类设计

Square类设计

编码

Panel类实现

按照详细设计,具体实现各个类,完成参数传递的协调,能达到游戏的基本要求

yocichen

Assembly类实现

Square类实现

测试

黑盒测试

测试游戏是否正常运行,各个功能是否实现

yocichen

白盒测试

进入代码内部,对逻辑进行推导和测试

2需求分析

2.1概述

收集需求,给出简要的需求说明,绘制用例图。

2.2用户分析

我是一个游戏玩家,我希望这个俄罗斯方块游戏是这样的:首先它的界面应该和经典的游戏界面风格保持一致,他的音效一定要好,有动感,让人在玩游戏时感受到快感。它还要能显示当前玩的累计时间,显示我已经消除的行数以及我的等级。在控制方面,我希望可以通过方向键控制同时WASD键也可以控制,这样会方便我操作。然后我希望我可以通过鼠标点击来控制开始和暂停游戏。

2.3 约束条件

成员和工作时间约束:小组只有一人,工作时间可从早上8:00持续到晚上11:30,其中要去掉休息时间。

用户约束:用户要求用最少的人员、最低的成本、最快的速度、最高的质量交付所需的软件,并且要求工作人员可以持续工作。

2.4功能需求

2.4.1 用例图

用例图

2.5用户界面需求

2.5.1 方块显示界面应该简约、像经典俄罗斯方块的界面,并且要有方格(辅助对齐)

方块界面

2.5.2 要能显示当前的分数、所消行数、累计时间、玩家等级

分数面板

2.5.3 开始和暂停按钮要做的醒目一些,容易点击

按钮图片

3设计与实现

3.1概述

经典俄罗斯方块游戏主要涉及游戏面板、组合块以及小方块三种显示元素,分别设计为三个类。其中,组合块由个数不同的小方块组成,所以组合块类与方块类相关联,面板类需要显示每一个组合块,因此面板类与组合块类相关联。

特别的,由于面板类对象只需要一个,它需要掌握大量对象的引用、占用较多资源并且要求能够公共访问,故将其设计为Singleton

3.2体系结构

3.2.1 类图

类图说明:主要包含四个类CTetrisView、Panel、Assembly、Square,其中CTetrisView由软件生成,Assembly类与Square类关联,Panel类与Assembly类关联,CTetrisView类与Panel关联。这样,Panel类对象就可以掌握所有Assembly对象,进而掌握所有Square类对象,这样在不断绘制、擦除、移动、重绘时就会非常方便。

类图

3.2.2 对象图:

对象图

说明:单件模式Panel类只有一个对象panel,它掌握多个Assembly对象,每个Assembly又掌握多个Square对象的引用,均属二元关联。

3.2.3 序列图

序列图

说明:在定时器中需要对当前的Assembly对象进行移动刷新,步骤是代码调用段发消息给焦点组合块对象p让其移动,p向自己掌握引用的方块对象发消息让其分别启动,下面是移动的序列图。(擦除和绘制机制与移动一致)

3.2.4 状态图

状态图

说明:运行程序时状态转入开始,鼠标点击开始按钮,进入组合块下落状态,每次到达底部进行判断,如果!isTop(),即未达到顶部,继续下落,如果接收到键盘方向键按下消息,进入移动/旋转状态,接收到释放键盘消息,则回到下落状态;如果此时点击暂停按钮,则静茹暂停状态,再点击开始按钮则继续下落。如果isTop()判断为真,则结束。

3.3 主要程序文件

主要文件

对应类

Panel.h

Panel

Assembly.h

Assembly

Square.h

Square

TetrisView.h

TetrisView

主要函数

功能

void drawSelf(CDC *pDC)

绘制(用于Panel/Assembly/Square)

void addAssembly(Assembly a)

Panel添加Assembly对象引用

void moveSelf(CDC *pDC,int x, int y)

移动对象

void wipeSelf(CDC *pDC)

擦出自己

void addSquare(Square s)

Assembly类对象添加Square类对象的引用

void delSquare(int y1, int y2)

Assembly类对象删除Square类对象的引用

void changeColor(CDC *pDC, COLORREF color)

改变对象颜色

void OnTimer(UINT_PTR nIDEvent)

定时器

int UpdateTopp(CDC *pDC)

更新panel的顶部值

BOOL PreTranslateMessage(MSG* pMsg)

键盘响应

bool isRightBoundary()

判断是否到达右边界

bool isLeftBoundary()

判断是否到达左边界

bool isUnderBoundary()

判断下方是否碰撞

void filledLineClear(CDC *pDC)

判断是否满行

int dropTopPart(int baseLine)

满行消除后,下移上方的部分

int rotatAssembly(CDC *pDC)

直接旋转对象

int playMusic(CString musicName)

用于播放背景音乐

int funcTop()

处理 上键/w键

int funcBottom()

处理下键/s键

int funcRight()

处理右键/d键

int funcLeft()

处理左键/a键

int updateMarkBoard(CDC *pDC)

更新得分板

static UINT gameOver(LPVOID pParam)

线程函数

int CreateAssembly(CDC *pDC)

产生新的组合对象,加入panel中

3.4开发环境以及部署环境要求

开发环境:Windows 10操作系统 & VS2017

部署环境:Windows 10操作系统

4 测试环境

4.1概述

对于本软件,主要采用黑盒测试方法。主要测试项目为,按钮工作状态、音效播放状态、方块下落状态、能否正常消行、方块是否会出界,是否会重叠、游戏结束判断状态、能否正常结束。 白盒测试,主要测试工作线程逻辑、定时器逻辑、消息响应逻辑等。

4.2 测试环境

机型:荣耀Magic Book

处理器:AMD Ryzen 5 2500U 2.00 GHz

内存(RAM):8.00 GB

系统类型:64位 基于x64处理器

操作系统:Windows 10 家庭中文版

4.3测试计划

测试项目编号

测试项目

负责人

1

按钮工作状态

yocichen

2

音效播放状态

yocichen

3

方块下落状态

yocichen

4

能否正常消行、

yocichen

5

游戏结束判断状态

yocichen

6

能否正常结束

yocichen

7

工作线程逻辑

yocichen

8

定时器逻辑

yocichen

9

消息响应逻辑

yocichen

4.4测试项目

测试项目

主要测试内容

按钮工作状态

游戏开始后,点击按钮是否会响应,响应有无异常

音效播放状态

游戏开始,音乐是否会响起

游戏暂停,音乐是否会停止

方块下落状态

方块是否会下落、下落频率,是否会出界,碰撞检测是否异常

能否正常消行、

当有满行时,是否会消除;

当连续有多行满时,消除是否异常

游戏结束判断状态

当组合块触及顶端时,是否会判断结束,就结束音效是否异常,提示信息是否正常

工作线程逻辑

逻辑是否会与用户线程冲突,主要测试音效的状态

定时器逻辑

定时器刷新频率是否合适,内部处理函数间是否会有冲突,是否会导致程序异常

消息响应逻辑

键盘响应函数逻辑

5、工作总结

5.1工作成果

成果

完成时间

用例图

12.21晚

类图

12.22整天

初步实现俄罗斯方块(方块能下落)

12.24早

初步实现碰撞检测、满行消除

12.24晚

添加分数面板,满行消除改善,加入键盘响应

12.25晚

音效调试

12.26

5.2过程分析

本次经典小游戏算是比较成功,这是我在课设中首次采用面向对象方法来设计,在开始时就采用了类关联的设计以及panel的单件设计。在具体的编码过程中采用“设计先行,及早测试”的思想,不断简化算法,以达到更强的鲁棒性。在具体算法的实现过程中,也遇到很多困难,比如结束判断异常,最终采用多线程方式(开一个工作线程不断测试)解决;在线程同步实现中,音效出现异常,最终采用更换设备(设备句柄)解决。另外,图形学的先导课程也对本游戏的开发起了很大的促进作用。

5.3经验教训及其分析

本次课设作品“经典俄罗斯方块游戏”确实存在一些不足,现罗列如下:

(1)      重新开始按钮未添加。在添加该按钮时,出现了程序逻辑很乱,无法顺利运行的情况,所以最终版本中取消了重新开始按钮。分析原因是,没有理清其中的逻辑顺序。

(2)      背景音乐无法循环播放。播放音乐采用的是Microsoft MCI接口,其中设置循环播放的参数,在VS2017中无法使用,经查找需要加入头文件,再加入头文件后程序出现崩溃,故最后放弃使用。

本次课设确实付出了很多,程序的主体是自己独立设计和实现的,只参考了多线程和MCI接口的资料。同时,在实现过程中,锻炼了我的面向对象思想和设计能力,提高了我的算法的实现和优化能力。最后,感谢教授概要设计课程的袁老师。


[MS1]人人有事做,事事有人做

MFC俄罗斯方块的更多相关文章

  1. 还是俄罗斯方块之android版

    前面的,口水话 请直接跳过. 虽然现在不比以前了 也没多少人气了,放到首页 都不到几百的点击量.也许博客园整体水平也是在往水的方向发展.不谈那些了,哥也曾经辉煌过 有过一天上千的点击量 ,哥也曾经有过 ...

  2. 带AI的俄罗斯方块源码

    好久没写俄罗斯方块的游戏了.从学习编程到现在,相继用Win32 API.MFC.C.C#.JS.iOS写过大约二十款左右的俄罗斯方块游戏.最近用Cocos2d-x写了一下,第一次完全将游戏逻辑与UI层 ...

  3. 【MFC三天一个游戏】之 局域网黑白棋

    欢迎加入我们的QQ群,无论你是否工作,学生,只要有c / vc / c++ 编程经验,就来吧!158427611 花了三天上班时间,妈的上班写就是不能静下心来,擦,要防BOSS巡山.... 以前也写过 ...

  4. vs2010静态链接MFC库报链接错误

    由于需要将MFC程序在其它电脑上运行,所以需要将动态链接的MFC改成静态链接,本以为很简单,没想到链接的时候出现下面的链接错误: uafxcw.lib(afxmem.obj) : error LNK2 ...

  5. MFC中成员变量的声明顺序与析构顺序

    第一次用博客,第一篇随笔,就写今天遇到的一个问题吧. 在VS2008的MFC对话框程序,窗口成员变量的声明顺序与其析构顺序相反,即,先声明的变量后析构,后声明的变量先析构.未在其他模式下测试. cla ...

  6. VC中的MFC到底是什么?

    1. 微软基础类库(英语:Microsoft Foundation Classes,简称MFC)是一个微软公司提供的类库(class libraries),以C++类的形式封装了Windows API ...

  7. MFC&Halcon之实时视频监控

    上一篇实现了在MFC的窗体内显示图片,本篇介绍如何在MFC窗体内实时显示摄像头的影像. 要实现的功能是点击一个“开始”按钮,可以显示影像,再点击“停止”按钮,可以停止显示. 因为实时显示影像需要在一个 ...

  8. x01.Tetris: 俄罗斯方块

    最强大脑有个小孩玩俄罗斯方块游戏神乎其技,那么,就写一个吧,玩玩而已. 由于逻辑简单,又作了一些简化,所以代码并不多. using System; using System.Collections.G ...

  9. MFC快速入门 - 菜单

    本文仅用于学习交流,商业用途请支持正版!转载请注明:http://www.cnblogs.com/mxbs/p/6231104.html 打开VS2010,依次打开File – New – Proje ...

随机推荐

  1. Java进阶篇设计模式之九----- 解释器模式和迭代器模式

    前言 在上一篇中我们学习了行为型模式的责任链模式(Chain of Responsibility Pattern)和命令模式(Command Pattern).本篇则来学习下行为型模式的两个模式, 解 ...

  2. 【转】大白话讲解Promise(一)

    原文地址:https://www.cnblogs.com/lvdabao/p/es6-promise-1.html ES6 Promise 先拉出来遛遛 复杂的概念先不讲,我们先简单粗暴地把Promi ...

  3. dart 如何优雅的避空

    前言 对于每一个程序员来说,空指针异常应该是基本都会遇到过的异常,而且这个异常出现的概率还比较大. 但是,空指针异常又是最容易解决的异常,因为只要加个非空判断就可以避免了. 本篇通过对比一般非空判断和 ...

  4. 微信小程序后端开发(Java语言)笔记

    前言: 因为是第一次真正接触后端开发,从编码到部署服务器到上线,所以做个笔记,也供和我一样的开发小白一些参考. 一.前期工作:开发环境与工具: 1. 编程语言:Java    #笔者还没学PHP,只想 ...

  5. AI应用开发实战 - 手写算式计算器

    扩展手写数字识别应用 识别并计算简单手写数学表达式 主要知识点 了解MNIST数据集 了解如何扩展数据集 实现手写算式计算器 简介 本文将介绍一例支持识别手写数学表达式并对其进行计算的人工智能应用的开 ...

  6. Linux 桌面玩家指南:01. 玩转 Linux 系统的方法论

    特别说明:要在我的随笔后写评论的小伙伴们请注意了,我的博客开启了 MathJax 数学公式支持,MathJax 使用$标记数学公式的开始和结束.如果某条评论中出现了两个$,MathJax 会将两个$之 ...

  7. 普通程序员如何转向AI方向(转)

    普通程序员如何转向AI方向   眼下,人工智能已经成为越来越火的一个方向.普通程序员,如何转向人工智能方向,是知乎上的一个问题.本文是我对此问题的一个回答的归档版.相比原回答有所内容增加. 一. 目的 ...

  8. 【原创开源】网络版二代双通道示波器开源发布,支持电脑,手机和Pad等各种OS平台访问

    前言感谢大家的支持,提前奉上今年的国庆福利. 一代示波器发布于3年前,去年年底的时候发布了二代示波器,软件性能已经比较强劲,但依然有值得升级改进的地方,经过今年这半年多努力,在二代示波器的基础上再推出 ...

  9. Java Main参数解析(Args4j)

    最近实现一个工具,Main函数会有很多参数,而且参数类型不同,为了统一解析,网上找到三方工具类Args4j,轻松搞定. 代码实例如下: 定义解析类: import java.io.File impor ...

  10. Java笔试题库之选题题篇【71-140题】

    71下面哪几个函数是public void method(){̷}的重载函数?() A.public void method( int m){̷} B.public int method(){̷} C ...