用Dev C++实现NOKIA经典游戏贪吃蛇

前期准备

头文件:

#include<bits/stdc++.h>
#include<stdio.h>
#include<conio.h>
#include<windows.h>

控制界面配置:

void color(int x)
{
	SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), x);
}//设置不同颜色
void Hide ()
{
	HANDLE hOut;
	CONSOLE_CURSOR_INFO curInfo;
	hOut=GetStdHandle (STD_OUTPUT_HANDLE);
	curInfo.bVisible=0;
	curInfo.dwSize=1;
	SetConsoleCursorInfo(hOut,&curInfo);
}//隐藏光标
void gotoxy(HANDLE hout,int x,int y)
{
    COORD pos;
    pos.X=x;
    pos.Y=y;
    SetConsoleCursorPosition(hout,pos);
}//光标直接移动至x,y

定义框架常量: 

#define framex 30
#define framey 5
#define wide 12
#define high 16

定义蛇与食物 :

struct  Snake
{
    int x[100];
    int y[100];
    int speed;
    int length;
    int count;
};
struct Food
{
    int x;
    int y;
};

我们为蛇开了100*100个空间,用于存储100节身体的x,y坐标。同时,我们定义了速度speed,长度length(方便我们计算蛇身)、分数。对于食物,设定了x,y,代表坐标。  

以上的内容,直接照搬进程序中就行。 

程序框架

void makeframe(){}
//打印边框
void infor(HANDLE hout,struct Snake* snake){}
//打印分数
void initsnake(struct Snake *snake){}
//初始化蛇
void printsnake(HANDLE hout ,struct Snake *snake){}
//打印蛇
void movesnake(HANDLE hout,struct Snake *snake){}
//蛇身的移动
void printfood (HANDLE hout,struct Snake *snake,struct Food* food){}
//打印食物
void eatfood(HANDLE hout,struct Snake * snake,struct Food *food){}
//蛇与食物的交互
int ifdead(struct Snake* snake){}
//判定蛇死亡
void Gaming (struct Snake* snake,struct Food *food){}
//操控蛇,上下左右等
void Gameover (){}
//打印游戏结束
int main(){}
//主程序

下面,我们详细对每个模块的实现进行阐述。 

打印边框

void makeframe()
{
    HANDLE hout=GetStdHandle(STD_OUTPUT_HANDLE);
    gotoxy(hout,framex+wide*2+5,framey);
    for(i=0;i<high;i++)
	{
        gotoxy(hout,framex,framey+i);
        printf("#");
    }
//打印左边框
    for(i=0;i<high;i++)
	{
        gotoxy(hout,framex+wide*2+2,framey+i);
        printf("#");
    }
//打印右边框
    for(i=0;i<wide*2+3;i++)
	{
        gotoxy(hout,framex+i,framey-1);
        printf("#");
    }
//打印上边框
    for(i=0;i<wide*2+3;i++)
	{
        gotoxy(hout,framex+i,framey+high);
        printf("#");
    }
//打印下边框
}

运行以上程序,我们会得到一个从坐标点(framex,framey-1)开始打印的宽为wide*2+2,高为high+2的边框。(如果觉得这数字丑,也可以重新调整一下)

打印分数

void infor(HANDLE hout,struct Snake* snake)
{
    gotoxy(hout,framex+wide+1,framey);
    printf("%d",snake->count);
}

运行这个模块,将会在上框架中心输出分数。 

初始化蛇

void initsnake(struct Snake *snake)
{
    snake->x[0]=framex+16;
    snake->y[0]=framey+6;
    snake->count=0;
    snake->length=3;
    snake->speed=200;
    for(i=1;i<snake->length;i++)
	{
        snake->x[i]=snake->x[i-1]+2;
        snake->y[i]=snake->y[i-1];
    }
}

让蛇出现在框架大概右侧的位置,头朝向为向左,长度为3,还原了NOKIA中的贪吃蛇初始状态。 

打印蛇

void printsnake(HANDLE hout ,struct Snake *snake)
{
  	color(6);
    for(i=0;i<snake->length;i++)
	{
		char z=111;
        gotoxy(hout,snake->x[i],snake->y[i]);
        if(i==snake->length-1) 
            printf ("%c",z);
        else if(i==0)
            printf("*");
        else 
            printf("*"); 
    }
	color(7);
}

打印一条黄色的*蛇(蛇头为o),这是因为用c++还原蛇的动画还要做另外的处理,这里懒得贴图了。

蛇身的移动

这是极其关键的一部分。关系到蛇是否能够越变越长。

void movesnake(HANDLE hout,struct Snake *snake)
{
    gotoxy(hout,snake->x[0],snake->y[0]);
    printf("  ");
    for(i=1;i<snake->length;i++)
	{
        snake->x[i-1]=snake->x[i];
        snake->y[i-1]=snake->y[i];
    }
}

打印食物

void printfood (HANDLE hout,struct Snake *snake,struct Food* food)
{
    srand((unsigned)time(NULL));
    while(1)
	{
        food->x=rand()%(wide-2)+1;
        food->y=rand()%(high-2)+1;
        if(food->x==0&&food->y==0)
            continue;
        food->x=2*food->x+framex;
        food->y+=framey;
        for(i=0;i<snake->length;i++)
		{
            if(food->x==snake->x[i]&&food->y==snake->y[i])
            break;
        }
        if(i==snake->length)
		{
			k+=1;
            gotoxy(hout,food->x,food->y);
            if (k==3)
            {
            	k=0;
				c[0]=food->x;
				c[1]=food->y;
  				color(4);
            	printf ("@");
  				color(7);
  				z=2;
			}
			else
			{
				d[0]=food->x;
				d[1]=food->y;
           		printf("Φ");
            	break;
			}
        }
    }
}

创设随机数,使得食物(Φ)随机出现在边框内部,同时规定每3个食物输出一个大食物(@)。 

蛇与食物的交互

void eatfood(HANDLE hout,struct Snake * snake,struct Food *food)
{
    if (snake->x[snake->length-1]==d[0]&&snake->y[snake->length-1]==d[1])
	{
        snake->length++;
        for(i=snake->length-1;i>0;i--)
		{
            snake->x[i]=snake->x[i-1];
            snake->y[i]=snake->y[i-1];
        }
        snake->x[0]=a[0];
        snake->y[0]=a[1];
        printfood(hout,snake,food);
        snake->count++;
    }
    if (snake->x[snake->length-1]==c[0]&&snake->y[snake->length-1]==c[1])
	{
		c[0]=0;
		c[1]=0;
        snake->length++;
        for(i=snake->length-1;i>0;i--)
		{
            snake->x[i]=snake->x[i-1];
            snake->y[i]=snake->y[i-1];
        }
        snake->x[0]=a[0];
        snake->y[0]=a[1];
        snake->count+=tim*3;
        z=0;
    }
}

判定蛇的死亡

int ifdead(struct Snake* snake)
{
    for(i=0; i<snake->length-1; i++) 
        if( snake->x[snake->length-1]==snake->x[i] && snake->y[snake->length-1]==snake->y[i] ) 
            return 0;
    return 1;
}

游戏交互核心

void Gaming (struct Snake* snake,struct Food *food)
{
    HANDLE hout = GetStdHandle(STD_OUTPUT_HANDLE);
    unsigned char ch ='d';
    int q2=0;
    clock_t start ;
	while(1)
	{
        infor(hout,snake);
        a[0]=snake->x[0];
        a[1]=snake->y[0];
        j=0;
        if(kbhit())
            ch=getch();
        switch(ch)
		{
            case 'w':
			{
				if (q!=3)
				{
                	movesnake(hout,snake);
                	snake->y[snake->length-1]-=1;
                	if (snake->y[snake->length-1]==framey-1)
                		snake->y[snake->length-1]=framey+high-1;
                	q=1;
               		break;
				}
				else 
				{
					movesnake(hout,snake);
					snake->y[snake->length-1]+=1;
					if (snake->y[snake->length-1]==framey+high)
                		snake->y[snake->length-1]=framey;
               		break;
				}
            }
            case 's':
			{
				if (q!=1)
				{
                	movesnake(hout,snake);
                	snake->y[snake->length-1]+=1;
					if (snake->y[snake->length-1]==framey+high)
                		snake->y[snake->length-1]=framey;
                	q=3;
               		break;
				}
				else 
				{
					movesnake(hout,snake);
					snake->y[snake->length-1]-=1;
                	if (snake->y[snake->length-1]==framey-1)
                		snake->y[snake->length-1]=framey+high-1;
               		break;
				}
            }
            case 'a':
			{
				if (q!=0)
				{
                	movesnake(hout,snake);
                	snake->x[snake->length-1]-=2;
                	if (snake->x[snake->length-1]==framex)
                		snake->x[snake->length-1]=framex+wide*2;
                	q=2;
               		break;
				}
				else 
				{
					movesnake(hout,snake);
					snake->x[snake->length-1]+=2;
                	if (snake->x[snake->length-1]==framex+wide*2+2)
                		snake->x[snake->length-1]=framex+2;
               		break;
				}
            }
            case 'd':
            {
            	if (q!=2)
				{
                	movesnake(hout,snake);
                	snake->x[snake->length-1]+=2;
                	if (snake->x[snake->length-1]==framex+wide*2+2)
                		snake->x[snake->length-1]=framex+2;
                	q=0;
               		break;
				}
				else 
				{
					movesnake(hout,snake);
					snake->x[snake->length-1]-=2;
                	if (snake->x[snake->length-1]==framex)
                		snake->x[snake->length-1]=framex+wide*2;
               		break;
				}
            }
            default:
            	q=5;
            	q2=0;
            
        }
        if(ifdead(snake)==0||ch==27)
            break;
        if (q!=5 && q2==1)
		{
			gotoxy(hout,framex+9,framey+4);
			printf("          ");
			gotoxy(hout,framex+10,framey+5);
    		printf("        ");
   			gotoxy(hout,framex+9,framey+6);
   			printf("          ");
   			q2=0;
		}
        eatfood(hout,snake,food);
        printsnake(hout,snake);
        if (q==5 && q2==0)
        {
        	start=clock(); 
        	q2=1;
            gotoxy(hout,framex+9,framey+4);
			printf("——————————");
			gotoxy(hout,framex+10,framey+5);
    		printf("游戏暂停");
   			gotoxy(hout,framex+9,framey+6);
   			printf("——————————");
		}
		if (z==2 && q!=5 && q2!=1)
		{
			z=1;
			start = clock(); 
			timeprint (hout,start);
		}
		else if (z==1 && q!=5 && q2!=1)
		{
			timeprint (hout,start);
		}
		else if (z==0 && q!=5 && q2!=1)
		{
			gotoxy (hout,c[0],c[1]);
			printf (" ");
			c[0]=0;
			c[1]=0;
		}
		infor(hout,snake);
        Sleep(snake->speed);
    }
}

打印游戏结束

void Gameover ()
{
    HANDLE hout = GetStdHandle(STD_OUTPUT_HANDLE);
	gotoxy(hout,framex+9,framey+4);
	printf("——————————");
	gotoxy(hout,framex+10,framey+5);
    printf("游戏结束");
    gotoxy(hout,framex+9,framey+6);
    printf("——————————");
    Sleep(1000);
    gotoxy(hout,0,framey+20);
}

主程序

int main()
{
	
    HANDLE hout = GetStdHandle(STD_OUTPUT_HANDLE);
    struct Snake s, *snake=&s;
    struct Food  f, *food=&f;
	Hide ();
    makeframe();
    int b=CoverChoose ();
    if (b==framey+1)
    {
    	makeframe();
    	initsnake(snake);
   	 	printfood(hout,snake,food);
    	Sleep(500);
   	 	Gaming (snake,food);
    	Gameover ();
	}
    return 0;
}

  • 14
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
好的,我可以为您提供一些基础代码,您可以在Dev-C++中进行修改和调试。 ```c++ #include <stdio.h> #include <stdlib.h> #include <conio.h> #include <windows.h> #define MAX_X 50 // 地图的宽度 #define MAX_Y 20 // 地图的高度 // 定义一个结构体表示的每个节点 struct Node { int x; // 节点的横坐标 int y; // 节点的纵坐标 struct Node *next; // 指向下一个节点的指针 }; // 定义一个结构体表示食物 struct Food { int x; // 食物的横坐标 int y; // 食物的纵坐标 }; // 定义一个枚举类型表示的运动方向 enum Direct { UP, DOWN, LEFT, RIGHT }; int length = 3; // 的长度 struct Node *head; // 头指针 struct Node *tail; // 尾指针 struct Food food; // 食物 enum Direct direct; // 的运动方向 int score = 0; // 分数 // 初始化地图 void init() { // 隐藏光标 CONSOLE_CURSOR_INFO cursor_info = { 1, 0 }; SetConsoleCursorInfo(GetStdHandle(STD_OUTPUT_HANDLE), &cursor_info); // 随机生成食物的位置 srand((unsigned int)time(NULL)); food.x = rand() % MAX_X; food.y = rand() % MAX_Y; // 初始化的位置 head = (struct Node *)malloc(sizeof(struct Node)); head->x = MAX_X / 2; head->y = MAX_Y / 2; head->next = NULL; tail = head; for (int i = 1; i < length; i++) { struct Node *node = (struct Node *)malloc(sizeof(struct Node)); node->x = head->x + i; node->y = head->y; node->next = NULL; tail->next = node; tail = node; } // 初始化的运动方向 direct = RIGHT; } // 在屏幕上画出地图 void drawMap() { system("cls"); // 清空屏幕 for (int i = 0; i <= MAX_X + 1; i++) { printf("#"); } printf("\n"); for (int i = 0; i < MAX_Y; i++) { printf("#"); for (int j = 0; j < MAX_X; j++) { if (i == head->y && j == head->x) { // 如果是头 printf("@"); } else if (i == food.y && j == food.x) { // 如果是食物 printf("*"); } else { bool flag = false; struct Node *p = head->next; while (p != NULL) { // 如果是身 if (p->x == j && p->y == i) { printf("#"); flag = true; break; } p = p->next; } if (!flag) { printf(" "); } } } printf("#"); printf("\n"); } for (int i = 0; i <= MAX_X + 1; i++) { printf("#"); } printf("\n"); printf("Score: %d\n", score); } // 判断是否吃到了食物 bool isEatFood() { return head->x == food.x && head->y == food.y; } // 在屏幕上画出食物 void drawFood() { food.x = rand() % MAX_X; food.y = rand() % MAX_Y; struct Node *p = head; while (p != NULL) { if (food.x == p->x && food.y == p->y) { // 如果食物与身重合,重新生成 food.x = rand() % MAX_X; food.y = rand() % MAX_Y; p = head; continue; } p = p->next; } gotoxy(food.x + 1, food.y + 1); printf("*"); } // 的运动 void move() { struct Node *newHead = (struct Node *)malloc(sizeof(struct Node)); newHead->x = head->x; newHead->y = head->y; switch (direct) { case UP: newHead->y--; break; case DOWN: newHead->y++; break; case LEFT: newHead->x--; break; case RIGHT: newHead->x++; break; } newHead->next = head; head = newHead; if (!isEatFood()) { struct Node *p = head; while (p->next->next != NULL) { p = p->next; } tail = p; free(p->next); p->next = NULL; } else { length++; score++; drawFood(); } } // 判断游戏是否结束 bool isGameOver() { if (head->x < 0 || head->x >= MAX_X || head->y < 0 || head->y >= MAX_Y) { // 是否撞墙 return true; } struct Node *p = head->next; while (p != NULL) { // 是否撞到自己的身体 if (head->x == p->x && head->y == p->y) { return true; } p = p->next; } return false; } // 控制的运动方向 void control() { if (_kbhit()) { char ch = _getch(); if (ch == 'w' || ch == 'W') { if (direct != DOWN) { direct = UP; } } else if (ch == 's' || ch == 'S') { if (direct != UP) { direct = DOWN; } } else if (ch == 'a' || ch == 'A') { if (direct != RIGHT) { direct = LEFT; } } else if (ch == 'd' || ch == 'D') { if (direct != LEFT) { direct = RIGHT; } } } } int main() { init(); // 初始化地图 drawMap(); // 画出地图 while (!isGameOver()) { control(); // 控制的运动方向 move(); // 的运动 drawMap(); // 画出地图 Sleep(100); // 控制的速度 } printf("Game Over!"); return 0; } ``` 这是一个基础版本的贪吃游戏,您可以根据自己的需求进行修改和扩展。祝您编写愉快!

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值