这是基于51单片机的贪吃蛇小游戏,用四个独立按键控制上下左右,用8*8点阵作为显示
程序如下:
#include
#include
#include
#define SNAKE 20
unsigned char x[SNAKE]; //存放蛇的X轴坐标
unsigned char y[SNAKE]; //存放蛇的Y轴坐标
unsigned char point_x; //存放果实的X轴坐标
unsigned char point_y; //存放果实的Y轴坐标
/*
//点阵模块接口定义
sbit LEDARRAY_LAT = P3^6;//储存寄存器是时钟
sbit LEDARRAY_CLK = P3^5;//移位寄存器时钟输入端
sbit LEDARRAY_DI = P3^4;//串行数据输入端
sbit up = P3^0;
sbit down = P3^1;
sbit left = P3^2;
sbit right = P3^3;
unsigned char num[8][8]={
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0
};//定义8*8数组作为清屏数据(有点走弯路,也就不改了自己有能力可以自己改)
unsigned char move_flag=0; //移动标志, 1 上,2 下,3 左,4 右;
unsigned char snake=3; //蛇身长度
unsigned int flag=1; //是否需要生成果实
//SPI通信函数 发送一个直接数据给点阵模块
void Send_Byte( unsigned char dat)
{
unsigned char i;//循环次数数变量
LEDARRAY_CLK = 0;//拉低移位时钟
_nop_();
LEDARRAY_LAT = 0;//拉低储存时钟
_nop_();
for( i = 0 ; i < 8 ; i++ ) //?循环8次写入一个字节数据
{
if( dat&0x01 )
{
LEDARRAY_DI = 1;
}
else
{
LEDARRAY_DI = 0;
}
LEDARRAY_CLK = 1; //上升沿发送数据
// _nop_();
LEDARRAY_CLK = 0;
// _nop_();
dat >>= 1;
}
}
void chang_num() //这个函数用来转码,把8*8数组中的‘0’,‘1’按列写成十六进制
{ int i,j;
for(j=0;j<8;j++)
{
for(i=7;i>=0;i--)
{
Dis_num[j]*=2;
Dis_num[j]+=num[i][j]&0x01;
}
}
}
void Display(unsigned char* Dis_dat,delay) //显示函数
{
unsigned char k, temp;
unsigned int i;
for(i = 0 ; i < delay ; i++)
{
temp = 0x7f;
for(k = 0 ; k < 8 ; k++) //一个字节8byte
{
Send_Byte(temp); //列选择
Send_Byte(Dis_dat[k]); //行数据
LEDARRAY_LAT =1; //锁存数据
_nop_();
LEDARRAY_LAT = 0;
_nop_();
temp = (temp>>1)|0x80;
}
}
}
void key()
{
if(move_flag!=2&&(!up))
{
move_flag=1;
}
if(move_flag!=1&&(!down))
{
move_flag=2;
}
if(move_flag!=4&&(!left))
{
move_flag=3;
}
if(move_flag!=3&&(!right))
{
move_flag=4;
}
}
void move() //这个函数是让蛇走起来的,如果蛇现在向上走就把蛇尾所在坐标改为0,把蛇头上方所在坐标改为1.其他同理
{
unsigned int i;
if(move_flag==1)
{
for(i=snake;i>0;i--)
{
x[i+1]=x[i];
y[i+1]=y[i];
}
x[1]=x[1]-1;
y[1]=y[1];
}
if(move_flag==2)
{
for(i=snake;i>0;i--)
{
x[i+1]=x[i];
y[i+1]=y[i];
}
x[1]=x[1]+1;
y[1]=y[1];
}
if(move_flag==3)
{
for(i=snake;i>0;i--)
{
x[i+1]=x[i];
y[i+1]=y[i];
}
x[1]=x[1];
y[1]=y[1]-1;
}
if(move_flag==4)
{
for(i=snake;i>0;i--)
{
x[i+1]=x[i];
y[i+1]=y[i];
}
x[1]=x[1];
y[1]=y[1]+1;
}
}
void bulid_point() //生成果实函数
{
unsigned int i;
if((x[1]==point_x)&&(y[1]==point_y)) //判断吃到果实
{
snake++; //蛇的长度加1
flag=1; //标志需要生成果实
}
while(flag) //生成果实
{
point_x=(unsigned char)(rand()%8);
point_y=(unsigned char)(rand()%8);
for(i=1;i7||y[1]>7)
{
while(1)
{
num[x[1]][y[1]]=0;
chang_num();
Display(Dis_num,200);
}
}
}
}
代码中都有解释应该可以看懂,如有问题请加Q群317635311进行询问。