本文为原创文章,转载请注明出处。
以下为主要核心代码,想查看详细代码可下载源码。int main(int argc, char *argv[])
{
start:
system("cls");
Init();/*初始化*/
PrintNotice_XY("贪吃蛇",_CENTER_X(6),_CENTER_Y-2);
PrintNotice("Press Enter to start!");
int key;/*为获取按键*/
while(1)
{
if(kbhit())
{
key=getch();
break;
}
Sleep(1000);
}
if(key==0xA||key==0xD)/*Enter:0xA和0xD是为兼容不同系统*/
{
/*清字幕*/
PrintNotice_XY(" ",_CENTER_X(6),_CENTER_Y-2);
PrintNotice(" ");
StartGame();/*开始游戏*/
}
if(key==0x1b) /*Esc*/
{
exit(0);
}
goto start;
return 0;
}
/*初始化*/
void Init()
{
i_Point=0;//初始化分数
HideCursor();/*隐藏光标*/
PrintUI();/*打印背景*/
}
/*初始化蛇*/
void InitSnake()
{
snakeHead=(Node *)malloc(sizeof(Node));
snakeEnd=(Node *)malloc(sizeof(Node));
snakeHead->nodeX=_COL_NUM+_COL_START-(_SNAKE_INIT_LEN);
snakeHead->nodeY=_ROW_NUM/2+_ROW_START;
snakeHead->direction=_LEFT;/*向左移动*/
snakeEnd->nodeX=snakeHead->nodeX+2;
snakeEnd->nodeY=snakeHead->nodeY;
snakeEnd->direction=snakeHead->direction;
snakeHead->next=snakeEnd;
snakeEnd->next=NULL;
}
/*打印蛇*/
void PrintSnake(Node *node)
{
GotoXy(node->nodeX,node->nodeY);
printf(_Node_CHAR);
if(node->next!=NULL)
{
PrintSnake(node->next);
}
}
/*显示食物*/
void PrintFood()
{
food=(Food *)malloc(sizeof(Food));
srand(_SEED);/*设置随机种子*/
while(1)
{
/*用rand()生成范围(x,y)的随机数,公式:x+rand()%(y-x+1)*/
food->foodX=_COL_START+2+rand()%((_COL_NUM*2-2-2)-1);/*(_COL_NUM*2-2-2):偏移量+宽*2-右边框宽度-圆点宽度*/
food->foodY=_ROW_START+1+rand()%(_ROW_NUM-2);
if(food->foodX%2)/*此段代码是为防止食物X坐标是单数而加*/
{
if(food->foodX>_COL_NUM+_COL_START)/*在屏幕中心的右边,则-1,否则+1*/
{
food->foodX=food->foodX-1;
}
else
{
food->foodX=food->foodX+1;
}
}
int flag=IsOccupied(snakeHead,food->foodX,food->foodY);
if(flag==0)
{
GotoXy(food->foodX,food->foodY);
printf("●");
break;
}
}
}
/*指示坐标是否被蛇占用*/
int IsOccupied(Node *head,char x,char y)
{
if((head->nodeX==x && head->nodeY==y)||(head->nodeX+1==x && head->nodeY==y))
{
return 1;
}
if(head->next!=NULL)
{
IsOccupied(head->next,x,y);
}
else
{
return 0;
}
}
/*开始游戏*/
void StartGame()
{
InitSnake();/*初始化蛇参数*/
PrintSnake(snakeHead);/*打印蛇*/
PrintFood();/*打印食物*/
short speed=_INIT_SPEED;
int isSuccess=1;
char key;/*按键*/
while(1)
{
if(kbhit())
{
key=getch();
if(key==0x20)/*空格*/
{
PrintNotice(" PAUSE ");
getch();
PrintNotice(" ");
GotoXy(food->foodX,food->foodY);
printf("●");
}
if(key==0x1b) /*Esc*/
{
char ques[]=" Do you want to exit? ";
char ansYes[]=" [Y]:Yes ";
char ansNo[]=" [Any key]:No ";
short len=strlen(ques);
PrintNotice_XY(ques,_CENTER_X(len),_CENTER_Y-1);
len=strlen(ansYes);
PrintNotice_XY(ansYes,_CENTER_X(len),_CENTER_Y);
len=strlen(ansNo);
PrintNotice_XY(ansNo,_CENTER_X(len),_CENTER_Y+1);
key=getch();
if(key=='Y' || key=='y')
{
exit(0);
}
/*重新打印背景和食物*/
PrintUI();
GotoXy(food->foodX,food->foodY);
printf("●");
}
/*处理方向键和大写锁定*/
switch(key)
{
case 'W':
case 72:
key=_UP;
break;
case 'A':
case 75:
key=_LEFT;
break;
case 'D':
case 77:
key=_RIGHT;
break;
case 'S':
case 80:
key=_DOWN;
break;
}
/*避免蛇逆向移动*/
if(key==_UP||key==_LEFT||key==_DOWN||key==_RIGHT)
{
switch(snakeHead->direction)
{
case _UP:
case _DOWN:
if(key==_DOWN||key==_UP)
{
continue;
}
break;
case _LEFT:
case _RIGHT:
if(key==_LEFT||key==_RIGHT)
{
continue;
}
break;
}
snakeHead->direction=key;
}
}
GotoXy(_COL_START+(_COL_NUM*2)+1,_ROW_START+1);/*行1*/
printf("[蛇] X:%i Y:%i ",snakeHead->nodeX,snakeHead->nodeY);
GotoXy(_COL_START+(_COL_NUM*2)+1,_ROW_START+2);/*行2*/
printf("[食物] X:%i Y:%i ",food->foodX,food->foodY);
GotoXy(_COL_START+(_COL_NUM*2)+1,_ROW_START+3);/*行3*/
printf("[速度] %i ",speed);
GotoXy(_COL_START+(_COL_NUM*2)+1,_ROW_START+4);/*行4*/
printf("[得分] %i ",i_Point);
GotoXy(_COL_START+(_COL_NUM*2)+1,_ROW_START+5);/*行5*/
printf("SPACE 暂停");
isSuccess=MoveSnake();/*移动蛇*/
if(isSuccess==0)
{
char notice[] ="GAME OVER";
PrintNotice(notice);
break;
}
/*变速*/
speed=(_INIT_SPEED-i_Point*_SPEED_UP)<=1?1:(_INIT_SPEED-i_Point*_SPEED_UP);
Sleep(speed);
}
getch();
}
/*移动蛇*/
int MoveSnake()
{
int isPrintFood=0;
char emptyX=snakeEnd->nodeX;
char emptyY=snakeEnd->nodeY;
switch(snakeHead->direction)
{
case _UP:
if(IsBiteBody(snakeHead,snakeHead->nodeX,snakeHead->nodeY-1))
{
return 0;
}
if((snakeHead->nodeY-1)<=_ROW_START)
{
return 0;
}
if(food->foodX==snakeHead->nodeX&&food->foodY==snakeHead->nodeY-1)
{
/*将新的节点加到蛇尾巴*/
Node *newNode=(Node *)malloc(sizeof(Node));
newNode->next=NULL;
snakeEnd->next=newNode;
snakeEnd=newNode;
isPrintFood=1;
}
/*将头部数据往下更新*/
UpdataNode(snakeHead,snakeHead->nodeX,snakeHead->nodeY-1,snakeHead->direction);
break;
case _LEFT:
if(IsBiteBody(snakeHead,snakeHead->nodeX-2,snakeHead->nodeY))
{
return 0;
}
if(snakeHead->nodeX<=_COL_START+2)
{
return 0;
}
if(food->foodX==snakeHead->nodeX-2 && food->foodY==snakeHead->nodeY)
{
Node *newNode=(Node *)malloc(sizeof(Node));
newNode->next=NULL;
snakeEnd->next=newNode;
snakeEnd=newNode;
isPrintFood=1;
}
/*将头部数据往下更新*/
UpdataNode(snakeHead,snakeHead->nodeX-2,snakeHead->nodeY,snakeHead->direction);
break;
case _DOWN:
if(IsBiteBody(snakeHead,snakeHead->nodeX,snakeHead->nodeY+1))
{
return 0;
}
if(snakeHead->nodeY+2>=_ROW_START+_ROW_NUM)
{
return 0;
}
if(food->foodX==snakeHead->nodeX&&food->foodY==snakeHead->nodeY+1)
{
Node *newNode=(Node *)malloc(sizeof(Node));
newNode->next=NULL;
snakeEnd->next=newNode;
snakeEnd=newNode;
isPrintFood=1;
}
/*将头部数据往下更新*/
UpdataNode(snakeHead,snakeHead->nodeX,snakeHead->nodeY+1,snakeHead->direction);
break;
break;
case _RIGHT:
if(IsBiteBody(snakeHead,snakeHead->nodeX+2,snakeHead->nodeY))
{
return 0;
}
if(snakeHead->nodeX+2+2>=_COL_START+_COL_NUM*2)
{
return 0;
}
if(food->foodX==snakeHead->nodeX+2 && food->foodY==snakeHead->nodeY)
{
Node *newNode=(Node *)malloc(sizeof(Node));
newNode->next=NULL;
snakeEnd->next=newNode;
snakeEnd=newNode;
isPrintFood=1;
}
/*将头部数据往下更新*/
UpdataNode(snakeHead,snakeHead->nodeX+2,snakeHead->nodeY,snakeHead->direction);
break;
}
PrintSnake(snakeHead);
if(isPrintFood)
{
i_Point++;
emptyX=snakeEnd->nodeX;
emptyY=snakeEnd->nodeY;
PrintFood();
}
GotoXy(emptyX,emptyY);
printf(_EMPTY_CHAR);
return 1;
}
/*递归更新节点*/
void UpdataNode(Node *node,char x,char y,char dir)
{
char c_X=node->nodeX;
char c_Y=node->nodeY;
char c_Dir=node->direction;
node->nodeX=x;
node->nodeY=y;
node->direction=dir;
if(node->next!=NULL)
{
UpdataNode(node->next,c_X,c_Y,c_Dir);
}
}
/*判断是否咬到身体*/
int IsBiteBody(Node *node,char headX,char headY)
{
while (node->next!=NULL)
{
if(node->nodeX==headX && node->nodeY==headY)
{
return 1;
}
node=node->next;
}
return 0;
}
来源:时间去哪儿了博客(微信/QQ号:903918446),转载请保留出处和链接!