引语:过年的时候闲着无聊,恰好也刚学了点51开发板的东西,所以就想写一个贪吃蛇的小程序。在网上总结了一些关于贪吃蛇的算法,于是就有了以下的程序。

先来说以一下算法的原理:将8*8LED看作是直角坐标系,将左上角定为坐标原点。定义两个数组  snake_x[],snake_y[]用来存储蛇的x,y轴坐标。因此,我们的核心算法就是小蛇惯性保持自己的运动姿态,产生食物,以及小蛇吃到食物后长度增加。

再来看一下我的开发板,我的开发板是德飞莱51开发板,这里不再讲解其8*8LED的工作原理,直接上代码

void Hc595SendByte()
{unsigned char a;SRCLK=0;RCLK=0;for(a=0;a<8;a++){SER=CHARCODE[p_now][a];
SRCLK=1;
_nop_();
_nop_();
SRCLK=0;
}RCLK=1;_nop_();_nop_();RCLK=0;
}
void Display()
{unsigned int tab;for(tab=0;tab<8;tab++) //扫描8列
{
Hc595SendByte_clean(0x00); //消隐
COMMONPORTS= TAB[tab]; //输出字码
Hc595SendByte(); //写入一个直字节数据
p_now++; //扫描下一行
if(p_now == 8) //扫描8行后归零
{
p_now = 0; //伪指针归零
}
}
}

这里定义了两个函数 Hc595SendByte ()和Display()两个函数,其中CHARCODE[x][y]数组是用来存放LED的状态值的。0x00代表灭,0x01代表亮。因此,在整个程序中,如果想将小蛇或食物显示在LED上,只需将相关点的坐标作为数组括号内的两个常量表达式,并将其赋值0x00或0x01即可。
 在void Auto_Move()函数中,

void Auto_Move()
{unsigned char i;if(Time==10) //蛇500ms移动一下
{ temp_x = snake_x[0]; //蛇尾坐标临时存储temp_y = snake_y[0];for(i=0;i<snake_long;i++) //除了蛇头蛇尾-身体其它部分不改变只需要移位{snake_x[i] = snake_x[i+1];snake_y[i] = snake_y[i+1];}snake_x[snake_long] = x; //蛇头坐标临时存储snake_y[snake_long] = y;switch(direction_flag){case 16:{//默认移动-向右即一开始适时,舍x++;temp_direction=direction_flag;break;}case 1:{//惯性制导-向上y--;temp_direction=direction_flag;break;}case 4{//惯性制导-向左                x--;temp_direction=direction_flag;break;}case 6:{//惯性制导-向右 x++;temp_direction=direction_flag;break;}case 9:{//惯性制导-向下y++;temp_direction=direction_flag;break;}default:{direction_flag=temp_direction;//按键按错时修正运动方向
switch(direction_flag){case 1:{y--;break; //修正-向上
}
case 4:{x--;break; //修正-向左
}
case 6:{x++;break; //修正-向右
}
case 9:{y++;break; //修正-向下
}
case 16:{x++;break; //修正-默认
}}
break;}}

Auto_move()函数是本程序的核心,关于他具体怎么实现小蛇的移动,程序的注释已经写的很清楚。

接下来就是定义产生食物的函数。这个函数内部运用了rand()随机函数,用来产生随机的食物位置。food_x和food_y是食物的横纵坐标。

void Food()
{if(food_flag>0){food_x=rand()%7; //伪随机数-食物横坐标(0-7之间)food_y=rand()%7; //伪随机数-食物纵坐标(0-7之间)CHARCODE[food_x][food_y]=0x01;//在地图中显示食物food_flag=-food_flag; //食物产生标志翻转
}
}

接下来是小蛇长度变长的函数

void Eating()
{if(food_flag<0&&snake_x[snake_long]==food_x&&snake_y[snake_long]==food_y)//小蛇的头部坐标如果等于食物的坐标,那么则说明小蛇吃到食物
{
snake_long++; //蛇身加长,即增加小蛇数组常量表达式的值
switch(direction_flag)
{case 1:{snake_x[snake_long]=food_x; //将惯性运动下一个坐标点亮增加蛇长
snake_y[snake_long]=food_y-1;break;}case 4:{snake_y[snake_long]=food_y; //将惯性运动下一个坐标点亮增加蛇长
snake_x[snake_long]=food_x-1;break;}case 6:{snake_y[snake_long]=food_y; //将惯性运动下一个坐标点亮增加蛇长
snake_x[snake_long]=food_x+1;break;}case 9:{snake_x[snake_long]=food_x; //将惯性运动下一个坐标点亮增加蛇长
snake_y[snake_long]=food_y+1;break;}}CHARCODE[food_x][food_y]=0x00;//清除食物food_flag=-food_flag; //产生新的食物}
} 

仅看注释已经可以明白该段程序。

下面是程序相关变量的定义以及函数的声明部分。

#ifndef _DEFINITION_H
#define _DEFINITION_H
#include<reg51.h> //库调用及宏
#include<intrins.h>
#include<stdlib.h>
#include<math.h>
#define COMMONPORTS P0 //LED位码IO口
#define GPIO_KEY P1 //矩阵键盘IO口sbit SRCLK=P3^6; //74HC595控制端口
sbit RCLK=P3^5;
sbit SER=P3^4;
int x=1,y=3; //蛇头初始坐标
int temp_x=0,temp_y=0; //蛇尾初始坐标
int food_x,food_y; //食物坐标
int food_flag=1; //食物产生标志
unsigned char temp_direction; //方向矫正
unsigned char snake_long=1; //蛇身长-初始为2
unsigned char Time=0; //用于定时累计
unsigned char p_now=0; //伪指针(点阵需横向扫描8次)
unsigned char KeyValue=16; //矩阵键盘键值存储
unsigned char direction_flag=16; //惯性移动方向标志unsigned char snake_x[10]={0,1}; //蛇的横坐标 蛇的最长长度为10
unsigned char snake_y[10]={3,3}; //蛇的纵坐标unsigned char code TAB[8] = {0x7f,0xbf,0xdf,0xef,0xf7,0xfb,0xfd,0xfe};//LED位码
unsigned char CHARCODE[8][8]= //地图
{
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}
};
#endif
#ifndef _FUNCTION_H
#define _FUNCTION_H
void Hc595SendByte();
void Hc595SendByte_clean(unsigned char);//消隐函数,SER=0x00
void Delay10ms();
void KeyDown();//按键扫描函数,上下左右四个方向键
void WALL();//小蛇撞到墙后,从另一边出来
void Direction();//上下左右四个方向键,对应四个direction_flag
void Auto_Move();
void Food();
void Eating();
void INIT();//定时器函数,用于扫描LED
void Display();
void Distory();//小蛇的头部坐标等于蛇身的某处坐标时,则触发bee()函数,并停止小蛇移动
void bee();//蜂鸣器函数
#endif

好了,现在你应该可以将剩下的代码完成了。

现在这个代码还有不够完善的地方,比如在实际运行的时候,小蛇的长度达到定义的长度以后就无法继续向下移动,或者是LED矩阵显示的是乱码。

基于51单片机开发板8*8LED矩阵的贪吃蛇程序相关推荐

  1. 巫妖王51单片机开发板配套视频课程-朱有鹏-专题视频课程

    巫妖王51单片机开发板配套视频课程-8368人已学习 课程介绍         本课程是巫妖王51单片机开发板的配套视频课程,本课程的目标是用少的时间带大家初级入门51单片机.配合巫妖王51单片机开发 ...

  2. 【网络收录】基于51单片机开发音乐播放器

    [网络收录]基于51单片机开发音乐播放器 本文作者:天析 作者邮箱:2200475850@qq.com 发布时间: Thu, 22 May 2014 18:14:00 +0800 特别声明:本资料来源 ...

  3. 基于51单片机的智能鱼缸设计。 有原理图,程序,原文,可代做实物。 才用STC12C5A60S2,最新款国产51单片机

    基于51单片机的智能鱼缸设计. 有原理图,程序,原文,可代做实物. 才用STC12C5A60S2,最新款国产51单片机. 本系统设计的主要是基于单片机为核心,设计一款集温度检测.恒温控制.步进电机控制 ...

  4. 单片机六位抢答器c语言程序,八路电子抢答器(基于51单片机的8路抢答器设计C语言程序)...

    哥,你还有AT89C51单片机8路抢答器的资料吗 哥,你还有AT89C51单片机8路抢答器的资料吗 AT89C51单片机8路抢答器的资料 源程序如下 #include #define uchar un ...

  5. 基于51单片机的数字电压表(ADC0832)(Proteus仿真+程序)

    编号:29 基于51单片机的数字电压表(ADC0832) 功能描述: 本设计由51单片机最小系统+ADC0832模块+两路模拟量输入模块+液晶1602显示模块 1.主控制器是AT89C82单片机 2. ...

  6. 基于51单片机轮胎胎压监测系统-压力传感器(仿真+程序+报告)

    本设计: 基于51单片机轮胎胎压监测系统-压力传感器(仿真+程序+报告) Proteus仿真版本:proteus7.8 程序编译器:keil 4 编程语言:C语言 编号C0018 ----本设计分享下 ...

  7. 基于51单片机的智能加湿器设计。 有仿真,程序,原理图,原文

    基于51单片机的智能加湿器设计. 有仿真,程序,原理图,原文. 可做实物. 通过DHT11实时监测环境温湿度,按键设定温湿度阈值,超限加湿器工作. 有水位检测电路,水位不足时候,报警提醒,防止干烧. ...

  8. 基于51单片机的数字电压表(PCF8591)(Proteus仿真+程序)

    编号:32 基于51单片机的数字电压表(PCF8591) 功能描述: 本设计由51单片机最小系统+PCF8591模块+四路模拟量输入模块+一路DA输出+液晶1602显示模块 1.主控制器是89C82单 ...

  9. 基于普中51单片机开发板的温控风扇

    自学单片机也不算很久,刚好遇上了这一门的课程设计,查找了好多的资料发现都不算合适,合适的又要收费,那么最后呢才找到了一个有关我使用的开发板的温控风扇程序,也就是普中单片机开发板,该程序来自--黑51论 ...

  10. 【STC12C5A60S2】TOF250(TTL)基于51系列开发板的运用

    目录 一.前言 二.硬件准备 二.软件准备 三.硬件接线图 四.例程源码 五.烧录说明 5.1 烧录接线示意图 5.2 烧录动态图 六.结果输出 一.前言 此片文章主要介绍如果通过51系列开发板来读取 ...

最新文章

  1. 【学习参考】Animate.css动画演示
  2. python与鸭子类型
  3. jquery 控制模板菜单样式
  4. tensorflow环境下的识别食物_在TensorFlow+Keras环境下使用RoI池化一步步实现注意力机制...
  5. cs文件中控制页面table的大小、title名称(.aspx)
  6. 类中匿名函数如何从 event 中去除
  7. LeetCode 1799. N 次操作后的最大分数和(回溯 / 状态压缩DP)
  8. hive内部表和外部表的区别_走近大数据之Hive进阶(四、Hive的表连接)
  9. DELPHI10.2的LINUX数据库开发环境配置
  10. echarts 中国地图+穿透
  11. Exchange Server 2016下载链接
  12. js 跨浏览器tab页通信
  13. 数据结构大作业——银行排队系统
  14. 【uni-app】uniapp项目优化方式及建议
  15. CSR867x — TWS模式的应用笔记【转载】
  16. 网易云音乐 ios android 通用,网易云游戏苹果和安卓不通用吗 | 手游网游页游攻略大全...
  17. [杨可桢]机械设计基础题库 机械设计基础习题 2022机械设计基础考试题答案 杨可桢《机械设计基础》(第7版)笔记和课后习题(含考研真题)详解
  18. 如何启用dhcp linux,怎么开启DHCP服务器啊
  19. $http请求之options
  20. Hibernate 一对一关系映射总结篇

热门文章

  1. 2021起重机作业 (Q)模拟考试题库及软件
  2. 人脸对齐—级联回归模型和深度学习模型
  3. 存储解决方案之——FC存储解决方案
  4. Android实现思维导图功能,Android实现思维导图
  5. 车型数据导入excel
  6. 3Dmax移动,旋转,缩放图标不显示
  7. HTTP协议-报文解析
  8. 给大家推荐几个查找芯片手册的网址,超级全建议收藏
  9. 2022年第五届中青杯赛题浅评
  10. USB C口5V输入,四节串联锂电池充电管理芯片,IC电路板PW4405芯片-22号电路板