设计游戏(c语言篇) 一.该游戏中所用到的头文件可调用的函数
标题二.写贪吃蛇具体步骤(精华必看)
标题三.将各步骤编译到一块即得到完整代码(调试检错)
标题四.对游戏进行优化和改良
一.
贪吃蛇算c中一个较为简单的游戏,其中要用到的函数较少且较为简单
1.1
在c语言里#include<Windows.h>是调用函数的头文件。
用到的函数有如下这些:
Sleep函数:
功 能: 执行挂起一段时间
用 法: unsigned sleep(unsigned seconds);
注意:
1.在VC中使用带上头文件#include <windows.h>,在Linux下,gcc编译器中,使用的头文件因gcc版本的不同而不同#include <unistd.h>
2.在VC中,Sleep中的第一个英文字符为大写的"S" ,在linux下不要大写,在标准C中是sleep, 不要大写,简单的说VC用Sleep, 别的一律使用sleep。
3.在VC中,Sleep()里面的单位,是以毫秒为单位,所以如果想让函数滞留1秒的话,应该是Sleep(1000); 在Linux下,sleep()里面的单位是秒,而不是毫秒。
试例:
#include<stdio.h>
#include <windows.h>
int main()
{
int a=100;
Sleep(3000);
printf("%d",a);
return 0;
}
gotoxy函数,x,y 分别代表当前控制台窗口的 坐标。以左上为原点,X往右为正半轴,Y轴往下为正半轴,gotoxy 实现光标的移动。#include<windows.h>
GetStdHandle 函数,检索指定标准设备的句柄(标准输入、标准输出或标准错误)。#include<windows.h>
句柄(Handle)是一个是用来标识对象或者项目的标识符,可以用来描述窗体、文件等,值得注意的是句柄不能是常量,应该明白的是,句柄是一个标识符,是用来标识对象或者项目的。从数据类型上来看它只是一个16位的无符号整数。应用程序几乎总是通过调用一个Windows函数来获得一个句柄,之后其他的Windows函数就可以使用该句柄,以引用相应的对象。在 Windows编程中会用到大量的句柄。
1.2
void startup()是使画面初始化
void show()是呈现画面
试例:
void startup()
{
int i,j;
for(i=0;i<High;i++)
{
canvas[i][0] = -1;
canvas[i][Width-1]=-1;
}
for(j=0;j<Width;j++)
{canvas[0][j]=-1;
canvas[High-1][j]=-1;
}
canvas[High/2][Width/2]=1;
for(i=1;i<=4;i++)
canvas[High/2][Width/2-i]=i+1;
moveDirecation=4;
food_x=rand()%(High-5)+2;
food_y=rand()%(Width-5)+2;
canvas[food_x][food_y]=-2;
}
void show()
{gotoxy(0,0);
int i,j;
for(i=0;i<High;i++)
{
for(j=0;j<Width;j++)
{
if(canvas[i][j]==0)
printf(" ");
else if(canvas[i][j]==-1)
printf("#");
else if(canvas[i][j]==1)
printf("@");
else if(canvas[i][j]>1)
printf("*");
else if(canvas[i][j]==-2)
printf("F");
include<stdlib.h>
rand()函数是Excel中产生随机数的一个随机函数。返回的随机数是大于等于 0 及小于 1 的均匀分布随机实数,rand()函数每次计算工作表时都将返回一个新的随机实数。
注意
rand()函数可以用来产生随机数,但是这不是真真意义上的随机数,是一个伪随机数,是根据一个数,我们可以称它为种了,为基准以某个递推公式推算出来的一系数,
当这系列数很大的时候,就符合正态公布,从而相当于产生了随机数,但这不是真正的随机数,当计算机正常开机后,这个种子的值是定了的,除非你破坏了系统,为了改变这个种子的值,C提供了 srand()函数,它的原形是void srand( int a) ,
功能是初始化随机产生器既rand()函数的初始值,即使把种子的值改成a; 从这你可以看到通过sand()函数,可以产生可以预见的随机序列。
1.3
这里canvas函数是构图函数(因为这里主讲游戏的编译,就不去为大家普及关于cancas函数的详细用法了)
二.
2.1
构造小蛇:
#include<stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<windows.h>
#define High 20
#define Width 30 //游戏画面尺寸
int canvas[High][Width]={0}; //二维数组存储游戏画布中对应的元素
void gotoxy(int x,int y) //光标的位置
{
HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);
COORD pos;
pos.X=x;
pos.Y=y;
SetConsoleCursorPosition(handle,pos);
}void startup() //数据初始化
{
int i,j; //初始化边框
for(i=0;i<High;i++)
{
canvas[i][0] = -1;
canvas[i][Width-1]=-1;
}
for(j=0;j<Width;j++)
{canvas[0][j]=-1;
canvas[High-1][j]=-1;
}
// 蛇头位置初始化
canvas[High/2][Width/2]=1;
for(i=1;i<=4;i++)
canvas[High/2][Width/2-i]=i+1;
moveDirecation=4;
food_x=rand()%(High-5)+2;
food_y=rand()%(Width-5)+2;
canvas[food_x][food_y]=-2;
}
void show() //展示画面
{gotoxy(0,0);
int i,j;
for(i=0;i<High;i++)
{
for(j=0;j<Width;j++)
{
if(canvas[i][j]==0)
printf(" ");
else if(canvas[i][j]==-1)
printf("#"); //边框符号
else if(canvas[i][j]==1)
printf("@");
else if(canvas[i][j]>1)
printf("*");
小蛇移动
#include<stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<windows.h>
#define High 20
#define Width 30
int canvas[High][Width]={0};
int food_x,food_y;
int moveDirecation;
void gotoxy(int x,int y)
{
HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);
COORD pos;
pos.X=x;
pos.Y=y;
SetConsoleCursorPosition(handle,pos);
}
void moveSnakeByDirection()
{
int i,j;
for(i=1;i<High-1;i++)
for(j=1;j<Width-1;j++)
if(canvas[i][j]>0)
canvas[i][j]++;
int oldTail_i,oldTail_j,oldHead_i,oldHead_j;
int max=0;
for(i=1;i<High-1;i++)
for(j=1;j<Width-1;j++)
if(canvas[i][j]>0)
{
if(max<canvas[i][j])
{
max=canvas[i][j];
oldTail_i=i;
oldTail_j=j;
}
if(canvas[i][j]==2)
{
oldHead_i=i;
oldHead_j=j;
}
}
int newHead_i,newHead_j;
if(moveDirecation==1)
{
newHead_i=oldHead_i-1;
newHead_j=oldHead_j;
}
if(moveDirecation==2)
{
newHead_i=oldHead_i+1;
newHead_j=oldHead_j;
}
if(moveDirecation==3)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j-1;
}
if(moveDirecation==4)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j+1;
}
}
控制小蛇移动
{
moveSnakeByDirection;
}
void updateWithInput()
{
char input;
if(kbhit())
{
input=getch();
if(input=='a')
{
moveDirecation=3;
moveSnakeByDirection();
}
else if(input=='d')
{moveDirecation=4;
moveSnakeByDirection();
}
else if(input=='w')
{moveDirecation=1;
moveSnakeByDirection();
}
else if(input=='s')
{moveDirecation=2;
moveSnakeByDirection();
}
}
}
判断游戏失败
int newHead_i,newHead_j;
if(moveDirecation==1)
{
newHead_i=oldHead_i-1;
newHead_j=oldHead_j;
}
if(moveDirecation==2)
{
newHead_i=oldHead_i+1;
newHead_j=oldHead_j;
}
if(moveDirecation==3)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j-1;
}
if(moveDirecation==4)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j+1;
}
if(canvas[newHead_i][newHead_j]==-2)
{
canvas[food_x][food_y]=0;
food_x=rand()%(High-5)+2;
food_y=rand()%(High-5)+2;
canvas[food_x][food_y]=-2;
}
else
canvas[oldTail_i][oldTail_j]=0;
if(canvas[newHead_i][newHead_j]>0||canvas[newHead_i][newHead_j]==-1)
{
printf("游戏结束!\n");
Sleep(2000);
system("pause");
exit(0);
}
else
canvas[newHead_i][newHead_j]=1;
}
这里canvas函数是构图函数(因为这里主讲游戏的编译,就不去为大家普及关于cancas函数的详细用法了)
三.
将每个步骤的代码码到一个文件里:
#include<stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<windows.h>
#define High 20
#define Width 30
int canvas[High][Width]={0};
int food_x,food_y;
int moveDirecation;
void gotoxy(int x,int y)
{
HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);
COORD pos;
pos.X=x;
pos.Y=y;
SetConsoleCursorPosition(handle,pos);
}
void moveSnakeByDirection()
{
int i,j;
for(i=1;i<High-1;i++)
for(j=1;j<Width-1;j++)
if(canvas[i][j]>0)
canvas[i][j]++;
int oldTail_i,oldTail_j,oldHead_i,oldHead_j;
int max=0;
for(i=1;i<High-1;i++)
for(j=1;j<Width-1;j++)
if(canvas[i][j]>0)
{
if(max<canvas[i][j])
{
max=canvas[i][j];
oldTail_i=i;
oldTail_j=j;
}
if(canvas[i][j]==2)
{
oldHead_i=i;
oldHead_j=j;
}
}
int newHead_i,newHead_j;
if(moveDirecation==1)
{
newHead_i=oldHead_i-1;
newHead_j=oldHead_j;
}
if(moveDirecation==2)
{
newHead_i=oldHead_i+1;
newHead_j=oldHead_j;
}
if(moveDirecation==3)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j-1;
}
if(moveDirecation==4)
{
newHead_i=oldHead_i;
newHead_j=oldHead_j+1;
}
if(canvas[newHead_i][newHead_j]==-2)
{
canvas[food_x][food_y]=0;
food_x=rand()%(High-5)+2;
food_y=rand()%(High-5)+2;
canvas[food_x][food_y]=-2;
}
else
canvas[oldTail_i][oldTail_j]=0;
if(canvas[newHead_i][newHead_j]>0||canvas[newHead_i][newHead_j]==-1)
{
printf("游戏结束!\n");
Sleep(2000);
system("pause");
exit(0);
}
else
canvas[newHead_i][newHead_j]=1;
}
void startup()
{
int i,j;
for(i=0;i<High;i++)
{
canvas[i][0] = -1;
canvas[i][Width-1]=-1;
}
for(j=0;j<Width;j++)
{canvas[0][j]=-1;
canvas[High-1][j]=-1;
}
canvas[High/2][Width/2]=1;
for(i=1;i<=4;i++)
canvas[High/2][Width/2-i]=i+1;
moveDirecation=4;
food_x=rand()%(High-5)+2;
food_y=rand()%(Width-5)+2;
canvas[food_x][food_y]=-2;
}
void show()
{gotoxy(0,0);
int i,j;
for(i=0;i<High;i++)
{
for(j=0;j<Width;j++)
{
if(canvas[i][j]==0)
printf(" ");
else if(canvas[i][j]==-1)
printf("#");
else if(canvas[i][j]==1)
printf("@");
else if(canvas[i][j]>1)
printf("*");
else if(canvas[i][j]==-2)
printf("F");
}
printf("\n");
}
Sleep(100);
}
void updateWithoutInput()
{
moveSnakeByDirection;
}
void updateWithInput()
{
char input;
if(kbhit())
{
input=getch();
if(input=='a')
{
moveDirecation=3;
moveSnakeByDirection();
}
else if(input=='d')
{moveDirecation=4;
moveSnakeByDirection();
}
else if(input=='w')
{moveDirecation=1;
moveSnakeByDirection();
}
else if(input=='s')
{moveDirecation=2;
moveSnakeByDirection();
}
}
}
int main()
{CONSOLE_CURSOR_INFO cci;
cci.bVisible = FALSE;
cci.dwSize = sizeof(cci);
SetConsoleCursorInfo(GetStdHandle(STD_OUTPUT_HANDLE), &cci);//作用:使光标消失不见
startup();
while(1)
{show();
updateWithoutInput();
updateWithInput();
}
return 0;
}
四.
4.1:升级程序
我这里的贪吃蛇是一个较为初级的贪吃蛇,接下来大家试着想一下如何能将其升级一下?
这里我给出以下建议:
**1.**将贪吃蛇改为自动移动且速度可以根据模式的快慢而进行改变
**2.**试着给出一些模式如:
困难 速度(超快)
中等 速度(快)
简单 速度(一般)
**3.**试着将贪吃蛇和食物的外貌进行修改,增加游戏的可玩性,使用户有更佳的体验感!
制作不易,未经许可不得转载