程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> 關於C語言 >> 貪食蛇游戲

貪食蛇游戲

編輯:關於C語言

#include <stdio.h>
#include <windows.h>
#include <conio.h>
#include <string.h>
 
#define UP 0
#define DOWN 1
#define LEFT 2
#define RIGHT 3//宏定義,定義四個方向--0 1 2 3分別代表上下左右
 
#define TURN_NUM 1000//可以保存的最多轉彎次數,一條蛇同時最多只能有1000次的彎曲
#define INIT_LENGTH 8
 
#define UP_EDGE 0
#define DOWN_EDGE 24
#define LEFT_EDGE 0
#define RIGHT_EDGE 79//定義上下左右四個邊界
 
#define X 0//初始狀態下蛇的身體坐標(LEFT_EDGE+X,UP_EDGE+Y)
#define Y 0//決定初始狀態下蛇的身體相對於游戲界面原點(LEFT_EDGE,UP_EDGE)的位置
 
/*定義全局變量*/
char buf[1000]="@*******";//決定初始的snake_length的值:必須與INIT_LENGTH保持同步
char *snake=buf;//蛇的身體,最長有1000個環節
char FOOD='$';//記錄食物的形狀
int food_num=0;//記錄已經吃下的食物數量
int score=0;//記錄當前的得分,由food_num決定
int snake_length=INIT_LENGTH;//initializer is not a constant:strlen(snake);
int cursor[2]={LEFT_EDGE+20+INIT_LENGTH,UP_EDGE+10};//記錄當前光標所指位置
int head[2]={LEFT_EDGE+20+INIT_LENGTH-1,UP_EDGE+10};//記錄頭部的坐標
int tail[2]={0,0};//記錄尾巴的坐標
int old_tail[2];//記錄上一步尾巴所在位置
int food[2]={0,0};//記錄食物的坐標
int init_position[2]={LEFT_EDGE+X,UP_EDGE+Y};//蛇的初始位置
int direction=RIGHT;//記錄當前蛇的頭部的運動方向
int turn_point[TURN_NUM][2];
int head_turn_num=0;//記錄頭部的轉彎次數
int tail_turn_num=0;//記錄尾巴的轉彎次數
int game_over=0;//判斷游戲是否結束
 
/*主方法*/
void main(){
 //函數聲名
 void gotoxy(int x,int y);//移動光標的位置
 void cur_state();//測試游戲的當前狀態參數
 void print_introduction();//打印游戲規則
 void init();//初始化游戲
 void control();//接收鍵盤控制命令
 void move();//控制身體的運動
 void move_up();//向上運動
 void move_down();//向下運動
 void move_left();//向左運動
 void move_right();//向右運動
 void update_tail_position();//更新尾巴的坐標
 void generate_food();//隨機產生食物
 void eat_food();//吃下食物
 
 char ch;
 
 while(!game_over){
  print_introduction();
  printf("\t\t按任意鍵開始游戲");
  getch();
  system("cls");
  //cur_state();
  init();
  control();
  system("cls");
  gotoxy(0,10);
  printf("\t\t您的當前得分是%d\n",score);
  printf("\t\t這條蛇共轉了%d次彎,它的身體長度是%d\n",head_turn_num,strlen(snake));
  printf("\t\t游戲結束,您要再玩一局嗎?(y/n)");
  scanf("%c",&ch);
  getchar();
  if(ch=='y'||ch=='Y'){
   continue;
  }else{
   system("cls");
   printf("\n\n\n\t\t\t謝謝您的使用,再見!");
   _sleep(3000);
   game_over=1;
  }
 }
}
 
/*打印游戲規則*/
void print_introduction(){
 int i=0;
 int rule_num;
 char *rule[4];
 rule[i++]="\n\n\t\t\t歡迎您來玩貪食蛇游戲\n";
 rule[i++]="\t\t游戲規則如下:\n";
 rule[i++]="\t\t1.按上下左右鍵控制蛇的運動方向\n";
 rule[i++]="\t\t2.按Ctrl+C結束當前游戲\n";
 rule_num=i;
 system("cls");
 for(i=0;i<rule_num;i++){
  puts(rule[i]);
 }
}
 
/*移動光標的位置*/
void gotoxy(int x,int y){
 COORD coord={x,y};
 SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE),coord);
}
 
/*測試游戲的當前狀態參數*/
void cur_state(){
 printf("游戲的當前狀態參數如下:\n");
 printf("snake=%s\n",snake);
 printf("snake_body_length=%d\n",strlen(snake));
 printf("head=(%d,%d)\n",head[0],head[1]);
 printf("tail=(%d,%d)\n",tail[0],tail[1]);
 printf("direction=%d\n",direction);
 printf("game_over=%d\n",game_over);
}
 
/*游戲進入初始狀態*/
void init(){
 int i;
 
 /*初始化游戲參數*/
 food_num=0;//記錄已經吃下的食物數量
 score=0;//記錄當前的得分,由food_num決定
 snake_length=INIT_LENGTH;
 cursor[0]=init_position[0]+INIT_LENGTH;
 cursor[1]=init_position[1];//記錄當前光標所指位置
 head[0]=init_position[0]+INIT_LENGTH-1;
 head[1]=init_position[1];//記錄頭部的坐標
 tail[0]=init_position[0];
 tail[1]=init_position[1];//記錄尾巴的坐標
 direction=RIGHT;//記錄當前蛇的頭部的運動方向
 head_turn_num=0;//記錄頭部的轉彎次數
 tail_turn_num=0;//記錄尾巴的轉彎次數
 game_over=0;//判斷游戲是否結束
 turn_point[0][0]=RIGHT_EDGE;
 turn_point[0][1]=0;
 /*游戲參數初始化完畢*/
 
 generate_food();//投下第一粒食物
 gotoxy(init_position[0],init_position[1]);//將光標移動到到初始化位置
 for(i=snake_length;i>0;i--){
  putchar(snake[i-1]);
 }
}
 
/*接收鍵盤控制命令*/
void control(){
 char command;//存放接收到命令
 while(1){
  command=getch();
  if(command==-32){
   //F11,F12:-123,-122
   command=getch();
   if(command=='H' && (direction==LEFT || direction==RIGHT)){//光標上移
    direction=UP;
    turn_point[head_turn_num%TURN_NUM][0]=head[0];
    turn_point[head_turn_num%TURN_NUM][1]=head[1];
    head_turn_num++;
   }else if(command=='P' && (direction==LEFT || direction==RIGHT)){//光標下移
    direction=DOWN;
    turn_point[head_turn_num%TURN_NUM][0]=head[0];
    turn_point[head_turn_num%TURN_NUM][1]=head[1];
    head_turn_num++;
   }else if(command=='K' && (direction==UP || direction==DOWN)){//光標左移
    direction=LEFT;
    turn_point[head_turn_num%TURN_NUM][0]=head[0];
    turn_point[head_turn_num%TURN_NUM][1]=head[1];
    head_turn_num++;
   }else if(command=='M' && (direction==UP || direction==DOWN)){//光標右移
    direction=RIGHT;
    turn_point[head_turn_num%TURN_NUM][0]=head[0];
    turn_point[head_turn_num%TURN_NUM][1]=head[1];
    head_turn_num++;
   }else if(command==-122 || command==-123);
   
  }else if(command==0){
   command=getch();//接收Fn的下一個字符
   //F1~F10:59~68
  }else if(command>=1&&command<=26){
   //Ctrl+a~z:1~26
   if(command==3){
    break;
   }
  }else{
   //do nothing!
  }
  move();
  if(head[0]==food[0] && head[1]==food[1]){
   eat_food();//吃掉一粒事物
   generate_food();//投下新食物
  }
 }
}
 
/*蛇的身體運動*/
void move(){
 if(direction==UP){
  //printf("Moving up!\n");
  move_up();
 }else if(direction==DOWN){
  //printf("Moving down!\n");
  move_down();
 }else if(direction==LEFT){
  //printf("Moving left!\n");
  move_left();
 }else if(direction==RIGHT){
  //printf("Moving right!\n");
  move_right();
 }
}
 
/*向上運動*/
void move_up(){
 if(cursor[1]>=UP_EDGE){
  gotoxy(head[0],head[1]);
  putchar('*');
  gotoxy(head[0],head[1]-1);
  putchar(snake[0]);
  gotoxy(tail[0],tail[1]);
  //_sleep(1000);//查看尾部光標
  putchar(0);
  update_tail_position();
  head[1]-=1;
  cursor[0]=head[0];
  cursor[1]=head[1]-1; 
  gotoxy(cursor[0],cursor[1]);
 }else{
  gotoxy(head[0],head[1]);
 }
}
 
/*向下運動*/
void move_down(){
 if(cursor[1]<=DOWN_EDGE){
  gotoxy(head[0],head[1]);
  putchar('*');
  gotoxy(head[0],head[1]+1);
  putchar(snake[0]);
  gotoxy(tail[0],tail[1]);
  //_sleep(1000);//查看尾部光標
  putchar(0);
  update_tail_position();
  head[1]+=1;
  cursor[0]=head[0];
  cursor[1]=head[1]+1;
  gotoxy(cursor[0],cursor[1]);
 }else{
  gotoxy(head[0],head[1]);
 }
}
 
/*向左運動*/
void move_left(){
 if(cursor[0]>=LEFT_EDGE){
  gotoxy(head[0],head[1]);
  putchar('*');
  gotoxy(head[0]-1,head[1]);
  putchar(snake[0]);
  gotoxy(tail[0],tail[1]);
  //_sleep(1000);//查看尾部光標
  putchar(0);
  update_tail_position();
  head[0]-=1;
  cursor[0]=head[0]-1;
  cursor[1]=head[1];
  gotoxy(cursor[0],cursor[1]);
 }else{
  gotoxy(head[0],head[1]);
 }
}
 
/*向右運動*/
void move_right(){
 if(cursor[0]<=RIGHT_EDGE){
  gotoxy(head[0],head[1]);
  putchar('*');
  putchar(snake[0]);
  gotoxy(tail[0],tail[1]);
  //_sleep(1000);//查看尾部光標
  putchar(0);
  update_tail_position();
  head[0]+=1;
  cursor[0]=head[0]+1;
  cursor[1]=head[1];
  gotoxy(cursor[0],cursor[1]);
 }else{
  gotoxy(head[0],head[1]);
 }
}
 
/*更新尾巴的坐標*/
void update_tail_position(){
 old_tail[0]=tail[0];
 old_tail[1]=tail[1];//保存上次尾巴的位置
 if(tail[0]==food[0] && tail[1]==food[1]){
  gotoxy(tail[0],tail[1]);
  putchar(FOOD);
 }
 if(tail_turn_num<head_turn_num){
  if(tail[0]<turn_point[tail_turn_num%TURN_NUM][0]){
   tail[0]+=1;
  }else if(tail[0]>turn_point[tail_turn_num%TURN_NUM][0]){
   tail[0]-=1;
  }else if(tail[1]<turn_point[tail_turn_num%TURN_NUM][1]){
   tail[1]+=1;
  }else if(tail[1]>turn_point[tail_turn_num%TURN_NUM][1]){
   tail[1]-=1;
  }else if(tail[0]==turn_point[(tail_turn_num-1)%TURN_NUM][0] && tail[1]==turn_point[(tail_turn_num-1)%TURN_NUM][1]){
   if(tail[0]<turn_point[tail_turn_num%TURN_NUM][0]){
    tail[0]+=1;
   }else if(tail[0]>turn_point[tail_turn_num%TURN_NUM][0]){
    tail[0]-=1;
   }else if(tail[1]<turn_point[tail_turn_num%TURN_NUM][1]){
    tail[1]+=1;
   }else if(tail[1]>turn_point[tail_turn_num%TURN_NUM][1]){
    tail[1]-=1;
   }
  }
  if(tail[0]==turn_point[tail_turn_num%TURN_NUM][0] && tail[1]==turn_point[tail_turn_num%TURN_NUM][1]){
   tail_turn_num+=1;
  }
 }else if(tail_turn_num==head_turn_num){
  if(tail[0]<head[0]){
   tail[0]+=1;
  }else if(tail[0]>head[0]){
   tail[0]-=1;
  }else if(tail[1]<head[1]){
   tail[1]+=1;
  }else if(tail[1]>head[1]){
   tail[1]-=1;
  }
 }
}
 
void generate_food(){
 int i=0,j=0;
 do{
  i=rand()%DOWN_EDGE;
 }while(i<UP_EDGE || i>DOWN_EDGE);
 
 do{
  j=rand()%DOWN_EDGE;
 }while(j<LEFT_EDGE || j>RIGHT_EDGE);
 food[0]=i;
 food[1]=j;
 gotoxy(food[0],food[1]);//抵達食物投放點
 putchar(FOOD);//放置食物
 gotoxy(cursor[0],cursor[1]);//返回光標當前位置
}
 
void eat_food(){
 if(tail[0]==turn_point[(tail_turn_num-1)%TURN_NUM][0] && tail[1]==turn_point[(tail_turn_num-1)%TURN_NUM][1]){
  tail_turn_num-=1;
 }
 snake[snake_length++]=snake[1];
 tail[0]=old_tail[0];
 tail[1]=old_tail[1];//將尾巴回退到上一步所在的位置
 gotoxy(tail[0],tail[1]);
 putchar(snake[1]);
 food_num++;
 score=food_num;
 gotoxy(cursor[0],cursor[1]);
}


作者“sxmalinhu”

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved