gjhk001 发表于 2020-9-7 16:25:22

基于stm32和LCD12864的贪吃蛇游戏制作,游戏分析(提供源码)


http://gg.eefocus.com/www/delivery/lg.php?bannerid=0&campaignid=0&zoneid=462&loc=http%3A%2F%2Fwww.stmcu.org.cn%2Fmodule%2Fforum%2Fforum.php%3Fmod%3Dviewthread%26tid%3D583680%26extra%3Dpage%253D16%2526filter%253Dreply%2526orderby%253Dreplies&cb=307b476a0c

http://www.stmcu.org.cn/module/forum/data/attachment/forum/201404/21/4e56dea5ea1d328d42fc7cfd59e59f0d.jpg
看到网上有人用单片机做俄罗斯方块、贪吃蛇游戏后,自己也想做个。。。说干就干,先是分析游戏内容,然后设计程序结构,最后调试硬件,写代码,花了一两天时间搞定了,在此分享下成果,做的过程中,没有参考任何游戏资料,所以应该是100%原创吧。。。:lol

游戏分析:

贪吃蛇游戏很简单,不用多说,就是按键控制蛇的移动方向,使之吃到食物增加自身长度,当蛇碰到边界或自身后游戏结束

所以开发这个游戏有一下几个事情要做

1、游戏界面:

采用LCD12864液晶屏,不是市场上常见的大屏,而是小屏,显示内容和大屏一样,外接字库芯片。

因为单个像素点太小,所以采用4*4像素作为一个最小显示单元,这样一来整屏就划分成了32*64的游戏区域,

在此方面控制程序主有两个,一个画点函数,一个擦点函数,用于在屏幕任意坐标添加或删除一个黑点,作为游戏显示操作

2、蛇身的建立

这一步将整个蛇显示到屏幕上,因为蛇身是一个点连接一个点,所以之前有想到用建立链表的方式去表示蛇,但后来发现有处理起来有点繁琐,就舍弃了。

转而第二种方式,采用数组方式,因为屏幕最大内容是32*64=2K个点,所以建立了一个2048 x 16bit的数组,虽然有点大,但是对于stm32拥有64K RAM来说就有点小巫见大巫了。。。:L

建立数组后,每个数据表示蛇在屏幕上的坐标,高八位表示行坐标,低八位表示列坐标,数组起始为头部坐标,根据蛇的长度决定尾部坐标。这样一来就解决了蛇身的问题

此外还建立了一个64*32bit的屏幕缓存,用以表示屏幕上任意坐标(x,y)处是否存在蛇身。

3、蛇的移动

当蛇要移动时,先提取头部坐标,如(x,y),根据当前的移动方向,计算下一个坐标,如果方向为左(以屏幕左上角为(0,0)水平向右为x轴,向下为y轴)则下一坐标为(x-1,y)向右(x+1,y)向下(x,y+1)向上(x,y-1)

然后再一次将蛇身坐标(数组内容)依次往后挪一个,长度为蛇身坐标。如果下一坐标为食物,则在尾坐标后再添加一个位置,复制尾坐标,长度+1,否者删除尾坐标。再将新坐标复制到数组0的地方作为新的蛇头,此过程中,及时根据坐标的改变(添加新坐标或删除坐标),在屏幕缓存相应位置画点和擦点,标记蛇身。

4、游戏的规则,按照3计算新坐标后,判断该店缓存是否为1(1表示存在蛇身或其他物体,0表示空白单元),如果为1,则表明蛇遇到物体了,如果该物体是食物,则进行游戏添加食物动作,如果不为食物则表明蛇撞自己了,即游戏失败,此外还要判断该坐标是否超出边界。

5、动作控制,4个按键,采用中断方式,代表4个方向。按下一个键,改变当前的移动方向,在这里要注意,方向改变之前要判断当前方向必须不为反向,如转变至左方向时,当前方向不能是右,防止蛇回头,撞到自身,这是游戏中不允许的。

6、食物的出现,随机出现,有两种办法,一是利用单片机的系统随机误差产生坐标,如ADC模块,随机读取ADC数据模块,分别对64和32取余。当然前提是误差最大有64的摆幅,这是一种不够精确地随机数。

二是采用C语言rand()随机函数,也是分别对64和32取余,比前者要科学,但前提是每次游戏运行前要给一个随机种子,进行随机函数种子初始化srand(seed),否者每次游戏运行出现的随机序列(食物的坐标)都是一样的,这一步就必须借助外部环境了,游戏中我采用的是这一方式获得食物,这里通过记录游戏开始后第一次按下键盘的时间作为随机数种子,开了一个72M不分频的定时器,因为技术频率快,从游戏开始到第一次按键的时间几乎是随机的。当然也可以采用ADC模块的随机误差数据。

然后就在游戏开始随机产生一个食物,当游戏开始后,在计算下一坐标后,如果该点为食物,则吃掉它,并产生一个食物,通过对屏幕缓存的判断,直到新的食物坐标是一个空白单元。

7、游戏进程控制:

开了一个定时器,周期决定蛇的移动速度。进入定时器后,根据当前的移动方向,进入不同的状态机,计算下一坐标,判断,(吃食物或者移动),移动蛇身将坐标往数组后面挪,如果游戏失败,将游戏标志位置位,主函数则实时判断游戏是否失败,如果失败,则关闭定时器,清屏,显示游戏分数(蛇身长度),并进入死循环或等待系统软复位。

http://www.stmcu.org.cn/module/forum/data/attachment/forum/201404/21/bf8d49b2358cadd89e8559414ae84d3a.jpg
**** Hidden Message *****


http://www.stmcu.org.cn/module/forum/data/attachment/forum/201404/21/bbdccc24baea6a4a94db7de71237e5b2.jpg


http://www.stmcu.org.cn/module/forum/data/attachment/forum/201404/21/536647df965cc4ab4f6fa0f2a2379f4f.jpg


kunchen 发表于 2020-9-7 18:26:00

谢谢分享

harry26 发表于 2020-9-17 13:59:33

谢谢分享

⭐️ 发表于 2021-6-13 17:59:10

谢谢

張皓鈞 发表于 2021-11-16 13:47:30

学习学习...........................

花海_361a11 发表于 2021-11-16 18:22:19

嗯嗯

eefocus_4067991 发表于 3 天前

好高级啊啊啊啊啊啊啊啊啊
页: [1]
查看完整版本: 基于stm32和LCD12864的贪吃蛇游戏制作,游戏分析(提供源码)