程序员是值得尊敬的,程序员的双手是魔术师的双手,他们把枯燥无味的代码变成了丰富多彩的软件……
最近蛮无聊的,在实验室发现一个12864,哦哈哈,正好可以拿来写点小游戏玩,于是便萌生了用评估板写一些小游戏的想法,让我想想,神马贪吃蛇、拼图、坦克大战……,好多的说,昨天没事,就写了一个,虽然可能还有许多小问题,但是可以确定的是可以玩,…^-^
首先来一张硬件连接的照片,拿手机照的,效果不大好,话说我有一个无线模块的,没有用上,在实验室呢
下面再来一张游戏开始的画面
最后是游戏中的画面
下面是程序源码,因为时间短,也没有太多关心,所以程序并没有进行过优化,还有很大的改进余地,包括算法也不是精心设计的,程序健壮性可能还有些弱,至于12864的程序,可以参看相关的文档,都有相关的实例,那个很无聊。
12864使用的是串口,所以有些慢
/*****************************************************************************
* NewProject.c
*****************************************************************************/
#include
#include
#include
#include
#include
#include <12864.c>
struct SnakePoint
{
char Number;
char SnakeX;
char SnakeY;
char SnakeD;
};
char windows[64][128];
void initwindows(int *pRand);
int testkey(void);
int Forword(struct SnakePoint *pstart,int *pspeed,int rands);
void DrawWindows(int x);
void DrawInit12864(void);
void DrawTo12864(int flag,int x,int y);
char x,y,direction[2],x0,y0;
int dx,dy;
struct SnakePoint *pStart,*pEnd;
void main( void )
{
struct SnakePoint snake[100];
char flag;
int i,j,speed,rands;
rands=32657;
direction[0]=direction[1]=2;
speed=100000;
*pPORTFIO_DIR=0x001f;
ssync();
*pPORTFIO=0x0001; //拉高片选
Init12864();
for(i=0;i<300;i++)
{
snake[i].Number=i;
} //初始化
snake[0].SnakeD=2; //默认初始水平前进
pStart=&snake[0];
pEnd=&snake[0]; //为直线
x=25; //初始化位置
y=25;
x0=25;
y0=35;
*pPORTGIO_INEN=0x0F00;
initwindows(&rands); //按任意键继续界面
do //½øÈëÖ÷½çÃæ
{
flag=testkey();
if(flag!=0) //Óа´¼ü
{
rands=rands*rands+782;
rands=rands>>2; //取随机
if( ( (direction[0]+flag)!=5) && (direction[0]!=flag) ) //只能向左或者右
{
direction[0]=flag; //更新方向
pStart->SnakeX=x;
pStart->SnakeY=y;
pStart->SnakeD=flag; //记录拐点坐标和方向
pStart++;
if(pStart->Number==299)
{
pStart=&snake[0];
}
}
}
for(i=0;i>1;
}
else
{
dx=*pRand&0x0ff0ffff;
dx=(dx%64);
dy=*pRand&0x000fffff;
dy=(dy%128);
DrawWindows(1); //画游戏画面
break;
}
}
}
int testkey(void) //检测按键
{
int iotest=*pPORTGIO & 0x0f00;
if(iotest==0x0e00)
{
return 1;
}
if(iotest==0x0d00)
{
return 4;
}
if(iotest==0x0b00)
{
return 2;
}
if(iotest==0x0700)
{
return 3;
}
return 0;
}
int Forword(struct SnakePoint *pstart,int *pspeed,int rands) //前进一格
{
switch(direction[0])
{
case 1:
x=x-1;
break;
case 2:
y=y-1;
break;
case 3:
y=y+1;
break;
case 4:
x=x+1;
break;
} //更新头部坐标
////////////////////////
if(x<0 || x >63 || y<0 || y>127 ||(windows[x][y]!=0 && (x!=dx || y!=dy) ) ) //撞墙
{
DrawWindows(2);
while(testkey()!=0)
{
}
return 1;
}
windows[x][y]=0xff;
DrawTo12864(1,x,y);
/////////////////////////////////
if(x!=dx || y!=dy)
{ //没吃到
if(pStart==pEnd)
{ //直线
direction[1]=direction[0];
}
else
{
if(x0==pEnd->SnakeX && y0==pEnd->SnakeY)
{ //到达拐点
direction[1]=pEnd->SnakeD; //更新尾部方向
++pEnd; //指向下一拐点
if(pEnd->Number==299)
{
pEnd=pstart;
} //循环
}
}
/////////////////////////////
windows[x0][y0]=0; //清尾部
DrawTo12864(0,x0,y0);
switch(direction[1])
{ //计算下一尾部坐标
case 1:
--x0;
break;
case 2:
--y0;
break;
case 3:
++y0;
break;
case 4:
++x0;
break;
}
///////////////////
}
else
{ //吃到
dx=rands&0x0ff0ffff;
dx=(dx%64);
dy=rands&0x000fffff;
dy=(dy%128);
windows[dx][dy]=0xff; //设定新豆
DrawTo12864(1,dx,dy);
*pspeed=*pspeed-(*pspeed)/300; //加速
}
return 0;
}
void DrawWindows(int x) //画出画面
{
int i;
char a[15]={"按任意键继续"};
switch(x)
{
case 1: //画不同界面
for(i=25;i<35;i++)
{
windows[25][i]=0xff;
}
windows[dx][dy]=0xff;
DrawInit12864();
DrawTo12864(1,dx,dy);
break;
case 0:
Lcdwrite(0x01,0xf8);
Lcdwrite(0x91,0xf8);
for(i=0;i<12;i++)
{
Lcdwrite(a[i],0xfa);
}
break;
case 2:
Lcdwrite(0x34,0xf8);
break;
}
}
void DrawInit12864(void) //画初始化界面
{
Lcdwrite(0x01,0xf8);
Lcdwrite(0x36,0xf8);
Delay(50);
lcdclean();
Lcdwrite(0x99,0xf8);
Lcdwrite(0x81,0xf8); //25行25列,长度10
Lcdwrite(0x00,0xfa);
Lcdwrite(0xff,0xfa);
Lcdwrite(0xc0,0xfa);
}
void DrawTo12864(int flag,int x,int y) //将内存数据写入12864
{
int wx=x%32+0x80; //计算得到地址
int wy=y/16,i;
char tmp0,tmp1;
if(x>31)
{ //ÔÚÏ°ëÆÁ
wy=0x88+wy;
}
else
{
wy=0x80+wy;
} //计算的到地址
Lcdwrite(wx,0xf8);
Lcdwrite(wy,0xf8);
//写入地址
tmp0=(y/16)*16; //得到16的整数倍开始地址
tmp1=0;
for(i=0;i<8;i++)
{
tmp1=tmp1<<1;
if(windows[x][tmp0]==0)
{
tmp1=tmp1&0xfe;
}
else
{
tmp1=tmp1|0x01;
}
tmp0++;
}
Lcdwrite(tmp1,0xfa);
tmp1=0;
for(i=0;i<8;i++)
{
tmp1=tmp1<<1;
if(windows[x][tmp0]==0)
{
tmp1=tmp1&0xfe;
}
else
{
tmp1=tmp1|0x01;
}
tmp0++;
}
Lcdwrite(tmp1,0xfa);
}