贪吃蛇游戏(二)

贪吃蛇游戏(二)

转自大佬(…)

#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include<windows.h>    //光标设计API
#include<time.h>       //食物随机
#include<conio.h>      //按键监控

//音乐
#include<mmsystem.h>
#pragma comment(lib,"Winmm.lib")

//用户系统
//定义变量
char reg_name[30] = "", reg_pwd[10] = "";
char on_name[30], on_pwd[10];


//宏定义属性
//窗口属性
#define SNAKESIZE 100   //蛇的最大节数
#define MAPHEIGHT 40    //地图高度
#define MAPWIDTH  70    //地图宽度


void gotoxy(int x, int y);//1.辅助函数:光标移动
void drawMap();//2.画地图
void keyDown();//3.按键操作
void creatFood();//4.食物的产生
int  snakeStatus();//5.蛇的状态:判断是否结束游戏
void welcometogame();//6.开始界面
void gamecircle();//7.控制游戏
void endgame();//8.游戏结束界面
//9.背景音乐
void bgm1();//音乐1
void bgm2();//音乐2
void bgm3();//音乐3
void regist();//10.用户注册系统
void dl();//11.用户登录
void HideCursor();//12.隐藏光标


//1.辅助函数:光标移动
void gotoxy(int x, int y)
{
	//光标结构体
	COORD coord;
	//设置坐标
	coord.X = x;
	coord.Y = y;
	//同步到控制台/设置控制台光标位置
	SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), coord);
}
//食物结构体
struct
{
	int x;
	int y;
} food;
//蛇结构体
struct
{
	int speed;          //蛇的速度
	int len;            //蛇的长度
	//记录每一节蛇的坐标
	//一条蛇有多少节
	int x[SNAKESIZE];
	int y[SNAKESIZE];
} snake;

//全局变量
int i;
int key = 72;         //初始化移动方向,表示蛇移动的方向,72为按下“↑”所代表的数字
int changeFlag = 0;   //蛇变化标记,判断蛇是否吃掉了食物
int score = 0;        //记录玩家的得分
//2.画地图
void drawMap()
{
	//左右边框
	for (i = 1; i <= MAPHEIGHT; i++)
	{
		gotoxy(0, i);
		printf("■");
		gotoxy(MAPWIDTH, i);
		printf("■");
	}
	//上下边框
	for (i = 0; i <= MAPWIDTH; i += 2)
	{
		gotoxy(i, 0);
		printf("■");
		gotoxy(i, MAPHEIGHT);
		printf("■");
	}


	//食物刷新,画食物
	while (1)

	{
		srand((unsigned int)time(NULL));
		food.x = rand() % (MAPWIDTH - 4) + 2;
		food.y = rand() % (MAPHEIGHT - 2) + 1;
		if (food.x % 2 == 0) break;
	}

	//产生新的食物
	gotoxy(food.x, food.y);      //食物的光标
	printf("●");
	snake.len = 3;                //蛇初始长度
	snake.speed = 200;            //蛇初始速度
	snake.x[0] = MAPWIDTH / 2 + 1;
	snake.y[0] = MAPHEIGHT / 2;
	gotoxy(snake.x[0], snake.y[0]);
	printf("■");
	for (i = 1; i < snake.len; i++)
	{
		snake.x[i] = snake.x[i - 1] + 2;
		snake.y[i] = snake.y[i - 1];
		gotoxy(snake.x[i], snake.y[i]);
		printf("■");
	}
	gotoxy(MAPWIDTH - 2, 0);
	return;
}
//3.按键操作
void keyDown()
{
	//无按键操作,缓冲
	int pre_key = key;
	if (_kbhit())
	{
		//有按键接收
		fflush(stdin);
		key = _getch();
		key = _getch();
	}
	//擦除
	if (changeFlag == 0)
	{
		gotoxy(snake.x[snake.len - 1], snake.y[snake.len - 1]);
		printf("  ");
	}

	//后面蛇身的结束
	for (i = snake.len - 1; i > 0; i--)
	{
		snake.x[i] = snake.x[i - 1];
		snake.y[i] = snake.y[i - 1];
	}


	/*
	*控制台按键所代表的数字
	*“↑”:72
	*“↓”:80
	*“←”:75
	*“→”:77
	*/



	//移动方向处理
	if (pre_key == 72 && key == 80)
		key = 72;
	if (pre_key == 80 && key == 72)
		key = 80;
	if (pre_key == 75 && key == 77)
		key = 75;
	if (pre_key == 77 && key == 75)
		key = 77;
	switch (key)
	{
	case 75:
		snake.x[0] -= 2;
		break;
	case 77:
		snake.x[0] += 2;
		break;
	case 72:
		snake.y[0]--;
		break;
	case 80:
		snake.y[0]++;
		break;
	}
	gotoxy(snake.x[0], snake.y[0]);
	printf("■");
	gotoxy(MAPWIDTH - 2, 0);       //移动不能一直看着光标
	changeFlag = 0;
	return;

}
//4.食物的产生
void creatFood()
{
	//蛇把食物吃了
	if (snake.x[0] == food.x && snake.y[0] == food.y)
	{
		//产生的食物不能在蛇身上
		while (1)
		{
			int flag = 1;
			srand((unsigned int)time(NULL));
			food.x = rand() % (MAPWIDTH - 4) + 2;
			food.y = rand() % (MAPHEIGHT - 2) + 1;
			//产生的食物不能在蛇身上
			for (i = 0; i < snake.len; i++)
			{
				if (snake.x[i] == food.x && snake.y[i] == food.y)
				{
					flag = 0;
					break;
				}
			}
			if (flag && food.x % 2 == 0)
				break;
		}
		//产生新的食物
		gotoxy(food.x, food.y);
		printf("●");

		snake.len++;
		score += 10;      //每个食物得10分

		changeFlag = 1;   //很重要,因为吃到了食物,就不用再擦除蛇尾的那一节,以此来造成蛇身体增长的效果
	}
	return;
}
//5.蛇的状态:判断是否结束游戏
int  snakeStatus()
{
	if (snake.y[0] == 0 || snake.y[0] == MAPHEIGHT)
		return 0;
	if (snake.x[0] == 0 || snake.x[0] == MAPWIDTH)
		return 0;

	//蛇头不能撞自己
	for (i = 1; i < snake.len; i++)
	{
		if (snake.x[i] == snake.x[0] && snake.y[i] == snake.y[0])
			return 0;
	}
	return 1;
}
//6.开始界面
void welcometogame()
{

	gotoxy(45, 12);
	printf("欢迎来到贪吃蛇游戏\n");
	gotoxy(45, 25);
	system("pause");
	system("cls");
	gotoxy(30, 12);
	printf("请用↑ ↓ ← → 分别控制蛇的移动\n");
	gotoxy(30, 13);
	system("pause");
	system("cls");
}
//7.控制游戏
void gamecircle()//控制游戏
{

	gotoxy(90, 7);
	printf("蛇吃得越长,游戏结束后的得分越高。");
	gotoxy(90, 20);
	printf("游戏小提示:");
	gotoxy(90, 22);
	printf("1.蛇不能穿墙,也不能咬到自己哦。");
	gotoxy(90, 23);
	printf("2.如果撞墙或者咬到自己游戏会失败哦。");
	gotoxy(90, 24);
	printf("3.请用↑ ↓ ← → 分别控制蛇的移动。");
	/*gotoxy(64,18)
	printf("F1 为加速,F2 为减速\n");*/
	gotoxy(90, 25);
	printf("4.鼠标点击暂停游戏。");
}
//8.游戏结束界面
void endgame()//游戏结束
{

	system("cls");
	system("color 8E");
	gotoxy(4, 2);
	printf("玩家需要多加练习才能得到更高的分数啊,加油哦!!!\n");
	gotoxy(18, 7);
	printf("游戏结束。");
	gotoxy(17, 8);
	printf("Game Over!!!");
	gotoxy(14, 10);
	printf("本次游戏的得分为: %d", score);

	exit(0);
}

//9.BGM
//9.1
void bgm1()
{
	//播放音乐
	PlaySound(TEXT("sounds\\bgm.wav"), NULL, SND_FILENAME | SND_ASYNC | SND_LOOP);
}
//9.2
void bgm2()
{
	//播放音乐
	PlaySound(TEXT("sounds\\b我是小绿.wav"), NULL, SND_FILENAME | SND_ASYNC | SND_LOOP);
}

//9.3
void bgm3()
{
	//播放音乐
	PlaySound(TEXT("sounds\\a赛车.wav"), NULL, SND_FILENAME | SND_ASYNC | SND_LOOP);
}

//10.用户注册系统
void regist()
{
	//清屏
	system("pause");
	system("cls");

	printf("\n\n\t\t\t欢迎使用注册系统\n\n");
	while (1)
	{
		//输入用户名
		printf("\t\t请输入用户名[不能大于10个字符]:");
		scanf("%s", reg_name);

		//判断用户名
		if (strlen(reg_name) <= 10)
		{
			while (1)
			{
				//输入密码
				printf("\n\t\t请输入密码[密码长度为八位]:");
				scanf("%s", reg_pwd);

				//判断密码
				if (strlen(reg_pwd) == 8)
				{
					printf("\n\n\t\t注册成功,您的用户名是%s,密码是%s\n\n", reg_name, reg_pwd);
					break;
				}
				else
				{
					printf("\n\t\t密码的长度为%d,请重新输入\n", strlen(reg_pwd));
				}
			}
			break;
		}
		else
		{
			printf("\n\t\t用户名的长度为%d,请重新输入\n\n", strlen(reg_name));
		}
	}
}

//判断是否注册
int judge()
{
	if (strcmp(reg_name, "") == 0 && strcmp(reg_pwd, "") == 0)
	{
		printf("\n\n\t\t您尚未注册,请先注册!\n\n");
		return 0;
	}
	else
	{
		return 1;
	}
}

//11.用户登录
void dl()
{
	int i;
	system("pause");
	system("cls");

	printf("\n\n\t\t\t欢迎登录系统\n\n");
	//三次登录验证
	for (i = 1; i <= 3; i++)
	{
		printf("\t\t请输入用户名:");
		scanf("%s", on_name);
		printf("\n\t\t请输入密  码:");
		scanf("%s", on_pwd);
		if (strcmp(reg_name, on_name) == 0 && strcmp(reg_pwd, on_pwd) == 0)
		{
			printf("\n\n\t\t登录成功,祝您游戏愉快\n\n");
			break;
		}
		else
		{
			printf("\n\n\t\t登录失败,请重新登录,您还有%d次机会\n\n", 3 - i);
		}

	}

}

//12隐藏光标
void HideCursor()  //隐藏光标,防止干扰视线
{
	CONSOLE_CURSOR_INFO cursor;
	cursor.bVisible = FALSE;
	cursor.dwSize = sizeof(cursor);
	HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);
	SetConsoleCursorInfo(handle, &cursor);
}



int main()
{

	SetConsoleTitle("贪吃蛇小游戏");  //编译控制栏信息

	HideCursor();//隐藏光标

	//用户系统
	system("color 70");
	bgm2();
	//定义变量
	int id;
	while (1)
	{
		HideCursor();//隐藏光标
		system("pause");
		system("cls");
		//输出界面
		printf("\n\n\t\t\t用户管理系统\n\n");

		printf("\t\t\t1:注册账号\n");
		printf("\t\t\t2:登录账号\n");
		printf("\t\t\t0:退出游戏\n\n");

		//输入功能编号
		printf("\t\t请选择功能编号:");
		scanf("%d", &id);

		//判断
		switch (id)
		{
		case 1:regist(); break;
		case 2:
			if (judge() == 1)
			{
				dl();
				goto skip;
			}
			break;
		case 0:exit(1); break;
		default:
			printf("\n\t\t您输入的功能编号有误,请重新输入!\n");
		}

	}




	//贪吃蛇游戏
skip:;
	system("pause");
	system("cls");

	system("color 70");
	bgm3();
	welcometogame();
	gamecircle();

	drawMap();
	while (1)
	{
		HideCursor();//隐藏光标
		keyDown();
		if (!snakeStatus()) break;
		creatFood();
		Sleep(snake.speed);
	}
	endgame();
	Sleep(5000);
	return 0;
}


发布了49 篇原创文章 · 获赞 15 · 访问量 3万+

猜你喜欢

转载自blog.csdn.net/wolfGuiDao/article/details/103818379