C#基础视频教程7.3 如何编写简单游戏
前面我们大致实现了鸟的一圈轨迹(其实如果你不做这个,就用两个矩形块的碰撞检测代替也可以),跟所有前面的教程一样,草稿打完了就要设计封装成一个类。至少到目前为止我们已经知道了鸟的属性和方法,先不要管方法具体如何实现,也不管方法输入输出,我们先要设计大概有几个方法。
鸟的初始化方法-根据前面一节导入导出一些多边形点(这里初始化只需要导入一堆点就行了)
鸟的销毁方法-比如鸟撞到管子上或者地底下,整个游戏重新开始,那么鸟肯定也要重新开始
运行方法-比如你可以定义鸟的运行是受重力影响往下掉,也可以定义是不动,或者往前匀速运行
飞行方法-不同于前面的运行方法,飞行方法是玩家控制的,你按一下按钮他飞一下(有时间间隔,不会一直被触发)
你还可以定义很多额外的方法(大部分酷跑游戏对控制人物会有发射子弹,变大变小,无敌,暴走等等,其实都可以定义在这个类里面)

想一下初始化方法如何实现
传入的类型需要是什么:我把整个Form传递过去,至少可以得到整个Form的宽度和高度,这样如果游戏的界面发生变化,我初始化生成鸟的位置可以始终保持在比如屏幕的中间的位置
这个方法需要做什么:1 导入一堆轨迹点,并生成到Point数组中,让主窗口随时准备绘制 2 设置初始的缩放和平移位置
这个方法还需要做什么:不管如何控制鸟的运动(Transform_X和Transform_Y),要刷新真正的轨迹点位置(一起跟着变)

尤其要注意导入的点都是固定的死点,随着鸟的运动,这些点都应该随之改变。所以不管是Fly方法还是RUN方法,或者为了测试方便的手动修改位置MoveX和MoveY方法,都应该刷新PolygonListAfterMoving这个Point数组。为了验证每次刷新的点确实是我们需要的,最好在主程序中把这个轨迹用不同的颜色描绘出来(这也是编程提高效率的一个重要方法,想一些方法把你要验证的东西可视化)

因为FlapperBird的游戏跟酷跑很像,比较科学的方法是场景不断的产生管子(宽度和高度都随机),并且管子不断的从屏幕一端跑到另一端,鸟看起来一直在往前飞,其实鸟是前后不动的。如果不控制鸟,则鸟会一直往下掉,如果让鸟飞一下,则可以往上走一点。那么这个往下掉的方法就很简单可以实现了,注意我们是单独放在一个线程里执行,每次给他的TransForm_Y累加一定距离(前面用try catch是一个比较偷懒的方法,第一次运行,则线程还没有实例化无法终止,如果已经在运行了则线程可以终止,不管是不是初次运行,直接终止掉重来最为简单暴力)

飞行方法就稍微复杂一点了,要分几个小块去分析。
首先要想清楚如何防止重复触发飞行方法,我们定义一个变量IfFlying,只要正在执行飞行则这个变量为TRUE,执行完成设置为FALSE,如果多次触发,则先看是不是TRUE,是TRUE就不往下执行了。当然在飞行的过程中也要判断是否游戏结束,如果游戏结束也不能再飞了(比如撞到东西了,如何定义游戏结束小鸟这个类不该管,他就应该是标准的方法,只需要通过几个变量告诉他该做什么,小鸟不是裁判,不负责具体游戏规则)
其次要想清楚如何飞行,假定每次飞行给1秒或者2秒,这个时间段内我们每隔20ms(也可以自己设定时间)修改一下Transform_Y的数值,这就不能像前面一样叠加一个固定值了,看起来太假,跟你跳高或者跑步一样,总归有一个加速-减速的过程。所以可以用一些抛物线,三角函数曲线来模拟(这些值都是测试出来了,为了游戏的动感,读者可以自行搜索非常逼真的函数来让鸟飞的更像真的)

鸟分析完了之后,再来看怎么做管子(我们已经暂时不考虑把管子做成多边形轨迹点了,只需要生成一个Rectangle),相比于鸟来说,这个矩形的类属性和方法有所不同,可以复制了之后照着改(我们重新定义了矩形的宽度,高度,X和Y的最大值最小值,是为了做碰撞检测使用,因为如果判断一个点是否在矩形内,只需要判断X坐标和Y坐标是否分别在XMin-XMax/YMin-YMax之间)

初始化管子的时候,宽度和高度都是随机值,但是一定是在屏幕的一侧开始生成的(为了测试先做几个按钮不断重复生成,看效果是否满意,然后调整随机值的参数)

其他方法是雷同的,矩形每次运行的时候都要刷新自己的边界点(跟多边形刷新所有Point数组一样),此外管子只有一个平移方法,没有Fly方法,这一点比鸟要简单

有了小鸟,管子,接下来就要定义一个裁判了。我做了一个额外的类叫做GameSense,他其实还干了画图的事情(应该额外做一个类来专门画图的),裁判最重要的就是判断是否撞了。注意我这里定义方法的输入输出,由于本游戏比较简单,碰撞之需要判断一个多边形实例跟一个矩形实例是否有碰撞,内部实现方法也很简单,遍历多边形实例的Point数组看他是否在矩形的四个边角点内即可。

测试不管移动哪个元素,只要两个区域有接触,碰撞状态确实响应了

我们再来看绘图的过程,Form1_Paint事件中,每次绘制完成一个东西都需要重置画笔(所谓的重置画笔是指你一旦使用了TranslateTransform,ScaleTransform,RotateTransform方法,你可以想想你本来拿着一支笔在屏幕的左上角X=0,Y=0的位置,每一次平移这个画笔都会移动到新的位置,每一次旋转你的画笔也会跟着旋转,这里的概念我们在应用教程中OPENGL仿真中也会讲到,需要一定的空间想象能力,更需要读者自己去验证绘图的整个流程,比如先绘制一个圆,然后再绘制跟他相切的一个圆怎么实现)

更多教学视频和资料下载,欢迎关注以下信息:
我的优酷空间:
http://i.youku.com/acetaohai123

我的在线论坛:
http://csrobot.gz01.bdysite.com/

问题交流:
QQ:910358960
C#基础视频教程7.3 如何编写简单游戏的更多相关文章
- C#基础视频教程7.5 如何编写简单游戏
有一些BUG需要处理,比如小鸟太高或者太低都应该报错(不然直接掉到窗口下面去了),这个方法跟前面的HitTest应该独立开来,而不是掺和在一起 测试确实可以检测是否超过边界(如果要非常精确,那么就 ...
- C#基础视频教程7.2 如何编写简单游戏
前面一小节我们实现了简单的碰撞检测,但是实际上游戏的对象并不是一个标准的矩形(小鸟是一个不规则的物体,其实碰撞的管道也是不规则物体),所以如果真的要做的比较完美,我们自己要写一个方法,能够导入一个图像 ...
- C#基础视频教程7.4 如何编写简单游戏
接下来我们实现整个的游戏流程,当点击开始游戏,则需要三个事情开始运行 1 小鸟初始化并往下掉(当然还是可以用按钮让他飞一下) 2 每隔一定时间从左侧产生一个管子(宽度和高度随机,产生周期2000ms左 ...
- C#基础视频教程7.1 如何编写简单游戏
要做一个FlappyBird,最核心的功能是创建几个区块,如果发生碰撞则游戏结束(小鸟撞到管子上,或者小鸟到地上),至于随机生成一些管子,小鸟如何跳跃,最后如何统计分数,都不难想通要怎么做. 首先 ...
- C#基础视频教程5.1 如何编写简单的超级热键
我们上一节介绍了编写简单计算器,实际上也是出于实用角度(这个计算器只要你肯改,肯定能做的比微软自带的计算器好用).这一节介绍做简单的超级热键(所谓的超级热键是指自定义快捷键的功能) 超级热键的最关键一 ...
- C#基础视频教程5.3 如何编写简单的超级热键
跟前面一章讲解计算器一样,到最后一小节,我们总是要把代码规整好,让整个程序显得非常简洁,先做个文件夹把我们自定义的类库都放进去 然后我们开始整理Form1里面的代码,为了实现超级热键的功能,我们应 ...
- C#基础视频教程5.2 如何编写简单的超级热键
我们前面已经理解了如何使用官方的代码实现鼠标键盘的监控,其实还差一点,因为他的代码只能捕捉单个的按键,而其实我们要的是组合键.什么是组合键呢?比如我想定义同时按下WIN+C是去执行屏幕截图.这只要理解 ...
- C#基础视频教程4.3 如何编写简单的计算器
我们接着往下改,为了让这个计算器更加实用,我们要像官方的计算器一样可以接着计算(你算出来一笔数据之后,可以接着累加累减,我们暂时不考虑加括号,优先级之类的,因为绝大部分情况下我们打开计算器就是为了进行 ...
- C#基础视频教程4.2 如何编写简单的计算器
用过VB6或者早期代码的人都应该能感觉到,C#目前也没看出来有什么特别之处,所谓的面向对象也没有什么体现.所以我们需要在原有基础上重写一份代码,然后比较两种做法的优缺点.我们在项目上右击添加一个Fun ...
随机推荐
- Redis学习篇(十)之排序
SORT 按照键值从小到大或者从大到小的顺序进行排序 对数字进行排序 语法:SORT key [DESC] 默认情况下,是升序排序,可以指定DESC进行降序排序 对字母进行排序 语法:SORT key ...
- ARGB 8888 内存大小
韩梦飞沙 韩亚飞 313134555@qq.com yue31313 han_meng_fei_sha 4字节 argb 各占8个bit
- 斐波那契数列(Java实现)
描述 一个斐波那契序列,F(0) = 0, F(1) = 1, F(n) = F(n-1) + F(n-2) (n>=2),根据n的值,计算斐波那契数F(n),其中0≤n≤1000. 输入 输入 ...
- 11.m进制转十进制
Strlen是字符串有多长就是多长,包括所有的元素和\0这个结束符 题目描述 Description 将m进制数n转化成一个十进制数 m<=16 题目保证转换后的十进制数<=100 输入描 ...
- python开发_os.path
在python中,os.path模块在处理路径的时候非常有用 下面是我做的demo 运行效果: ========================================= 代码部分: ==== ...
- ServiceStack.OrmLite破解
在 ServiceStack.OrmLite下的 OrmLiteConfigExtensions 第199行把这句注释掉就可以了 //LicenseUtils.AssertValidUsage(Lic ...
- HTTP协议返回状态码说明
http://1632004.blog.163.com/blog/static/29991497201231811231120/ 如果向您的服务器发出了某项请求要求显示您网站上的某个网页(例如,当用户 ...
- web前端开发必备压缩工具整理
影响网站打开时间有两个因素,一个是网页加载速度,另一个是网站页面的大小.网站加载速度与用户所处的网络环境及主机性能有关,而网站页面的大小则由网站开发者决定,最主要的就是web前端开发工程师的工作.本文 ...
- HDU 4611 Balls Rearrangement(2013多校2 1001题)
Balls Rearrangement Time Limit: 9000/3000 MS (Java/Others) Memory Limit: 65535/32768 K (Java/Othe ...
- CentOS6.5使用yum命令方便快捷安装Nginx与卸载
原文:https://my.oschina.net/ramboo/blog/223408 当然,首先要求是可以联网的CentOS系统,因为yum安装需要互联网连接. 卸载命令:yum remove n ...