走迷宫小游戏课设(C语言)

1.游戏效果

在这里插入图片描述

2.设计思路与所用数据结构梗概

玩家可以初始化姓名以及宝箱个数(default=5);wasd控制上下左右移动;右键单机开始显示所有宝箱

2.1人物USER结构体

typedef struct user {
	int score;
	char name[20];
	int position_x, position_y;
	int p_x, p_y;
}USER;

2.2宝箱BOX结构体

typedef struct box {
	int data;//钻石或炸弹
	int stage;//存活状态
	int score;
	struct box* next;
	int position_x, position_y;
}BOX;

3模块化设计

3.1加载数据

void startup(int maze[Row][Col], USER& user, BOX* h, int& gamestate, int& flower_number) {
	initgraph(WIDTH, HEIGHT);

	loadimage(&victory, "./游戏背景1.png", 640, 480);
	loadimage(&playground, "./游戏背景8.jpg", WIDTH, HEIGHT);
	loadimage(&diamond, "./钻石图标2.jfif", D_SIZE_W, D_SIZE_H);
	loadimage(&box, "./宝箱未开箱.jpg", B_SIZE_W, B_SIZE_H);
	loadimage(&box_min, "./宝箱小图标.jpg", WIDTH / 30, HEIGHT / 20);
	loadimage(&character, "./人物.jpg", WIDTH / 30, HEIGHT / 20);
	loadimage(&boom, "./炸弹.jfif", WIDTH / 30, HEIGHT / 20);
	loadimage(&diamond_min, "./钻石图标2.jfif", WIDTH / 30, HEIGHT / 20);
	loadimage(&wall, "./石块.png", WIDTH / 30, HEIGHT / 20);//长36 高35
	loadimage(&button_down, "./buttonon.png", 190, 60);
	loadimage(&button_up, "./buttonun.png", 190, 60);
	BeginBatchDraw();
	mciSendString("play ./bkbk.mp3 repeat", 0, 0, 0);
	while (gamestate == 0)
		startMenu(gamestate, user, maze, h, flower_number);

}

3.2欢迎页面

void startMenu(int& gamestate, USER& user, int maze[Row][Col], BOX* h, int& flower_number) {
	putimage(0, 0, &playground);
	setbkmode(TRANSPARENT);
	settextcolor(BLACK);
	settextstyle(50, 0, "楷体");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.2, "新游戏 press '1'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.3, "继续游戏 press '2'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.4, "退出 press '3'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.5, "关闭/打开音乐 press '4'/'5'");
	FlushBatchDraw();
	Sleep(2);
	char input;
	if (_kbhit()) {
		mciSendString("play ./点击音效.mp3", 0, 0, 0);
		input = _getch();
		if (input == '1')
		{
			inituser(user, flower_number);
			createMaze(maze, user);
			createBox(maze, h, flower_number);
			gamestate = 1;
		}
		if (input == '2') {
			readRecord(maze, user, h, flower_number);
			user.p_x = user.position_x * 36;
			user.p_y = user.position_y * 35;
			gamestate = 2;
		}
		if (input == '3')
			exit(0);
		if (input == '4')
			mciSendString("pause ./bkbk.mp3", 0, 0, 0);//为何用close会导致卡顿?
		if (input == '5')
			mciSendString("play ./bkbk.mp3 repeat", 0, 0, 0);
	}

}

3.3玩家初始化

void inituser(USER& user, int& flower_number) {
	InputBox(user.name, 20, "请输入用户名:");
	char buf[10];
	InputBox(buf, 10, "请输入宝箱个数");
	flower_number = atoi(buf);
	if (flower_number == 0)
		flower_number = 5;
}

3.4处理键盘消息

void checkKsg(int& gamestate) {
	char ksg;
	if (_kbhit()) {
		ksg = _getch();
		switch (ksg) {
		case 'w':gamestate = -1; break;
		case 's':gamestate = -2; break;
		case 'a':gamestate = -3; break;
		case 'd':gamestate = -4; break;
		case ' ': gamestate = -7; break;//checksecret(maze, user, h); break;//显示特定的flower or boom
		default:break;
		}
	}
}

3.5处理鼠标消息

void checkMsg(int& gamestate, char button[6][5], int& show_or_hide) {
	MOUSEMSG msg;
	if (MouseHit()) {
		msg = GetMouseMsg();
		switch (msg.uMsg) {
		case WM_LBUTTONDOWN:
			mciSendString("play ./点击音效.mp3", 0, 0, 0);
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y> 480 && msg.y < 540)
			{
				if (show_or_hide == 0) {
					gamestate = -5;//显示隐藏
					show_or_hide = 1;
					strcpy_s(button[3], "隐藏");
				}
				else if (show_or_hide == 1) {
					gamestate = -6;
					show_or_hide = 0;
					strcpy_s(button[3], "显示");
				}
				putimage(START_BUTTON_X1, 480, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}

			if (msg.x > START_BUTTON_X1 && msg.x<1060 && msg.y>START_BUTTON_Y1 && msg.y < 320)
			{

				gamestate = -6;//开始
				show_or_hide = 0;
				strcpy_s(button[3], "显示");
				putimage(START_BUTTON_X1, 270, &button_down);
				FlushBatchDraw();
				Sleep(50);

			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>410 && msg.y < 470)
			{
				gamestate = -4;//存档
				setfillcolor(YELLOW);

				putimage(START_BUTTON_X1, 410, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>550 && msg.y < 610)
			{
				gamestate = -3;//增加
				putimage(START_BUTTON_X1, 550, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>340 && msg.y < 400)
			{
				gamestate = -2;//退出
				setfillcolor(YELLOW);
				putimage(START_BUTTON_X1, 340, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.y > 620 && msg.x < 1060 && msg.y < 680)
			{
				gamestate = -1;//清空
				setfillcolor(YELLOW);
				putimage(START_BUTTON_X1, 620, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}


		}
	}
}

3.6处理gamestate状态

void bodyRun(int maze[Row][Col], USER& user, BOX* h, int& gamestate, int& gamestate2, int& flower_number) {

	//BOX* p = NULL;
	if (gamestate == -7) {
		checksecret(maze, user, h);
		delbox(h, flower_number, maze);
	}
	if (gamestate2 == -5) {
		ShoworHide(h);
	}
	if (gamestate2 == -6) {
		showBox(h);
	}
	if (gamestate2 == -4) {
		writeRecord(maze, user, h, flower_number);
	}
	if (gamestate2 == -3) {
		addBox(h, flower_number, maze);
		gamestate2 = -6;
	}
	if (gamestate2 == -2) {
		gameover(user);
	}
	if (gamestate2 == -1) {
		delall(h, flower_number);
	}
	characterWalk(user, gamestate, maze, h);
	FlushBatchDraw();
	if (maze[user.position_y][user.position_x] == -1) {
		gameResult(user);
	}

}

3.7从文件读入迷宫数据

void createMaze(int maze[Row][Col], USER& user) {
	FILE* fp;
	fopen_s(&fp, "maze_init.txt", "r");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fscanf_s(fp, "%d", &maze[i][j]);
			}
		fclose(fp);
		fp = NULL;
	}

	user.position_x = 0;
	user.position_y = 1;
	user.p_x = user.position_x * 36;
	user.p_y = user.position_y * 35;
	user.score = 0;

}

3.8宝箱初始化

void createBox(int maze[Row][Col], BOX* h, int flower_number) {
	BOX* p;
	int i;
	srand((int)time(NULL));
	for (i = 0; i < flower_number; i++) {
		p = (BOX*)malloc(sizeof(BOX));
		p->stage = 1;
		p->data = rand() % 2;//0为宝石1为炸弹
		if (p->data) {
			p->score = rand() % 5;
		}
		else {
			p->score = -(rand() % 5);
		}
		while (1) {
			p->position_x = rand() % Col;
			p->position_y = rand() % Row;
			if (maze[p->position_y][p->position_x] != 1 && maze[p->position_y][p->position_x] != 2 && maze[p->position_y][p->position_x] != -1)
				break;
		}
		maze[p->position_y][p->position_x] = 2;

		p->next = h->next;
		h->next = p;
	}
}

3.9删除宝箱

void delbox(BOX* h, int& flower_number, int maze[Row][Col]) {
	BOX* p, * r;
	r = h;
	p = h->next;
	while (p != NULL) {
		if (p->stage == 0) {
			maze[p->position_y][p->position_x] = 0;
			flower_number--;
			r->next = p->next;
			free(p);
			p = r->next;
			r = r->next;
		}
		else {
			p = p->next;
			r = r->next;
		}
	}
}

3.10添加宝箱

void addBox(BOX* h, int& flower_number, int maze[Row][Col]) {
	BOX* p;
	p = (BOX*)malloc(sizeof(BOX));
	p->stage = 1;
	p->data = rand() % 2;
	if (p->data) {
		p->score = rand() % 5;
	}
	else {
		p->score = -(rand() % 5);
	}
	p->next = h->next;
	h->next = p;
	while (1) {
		p->position_x = rand() % Col;
		p->position_y = rand() % Row;
		if (maze[p->position_y][p->position_x] != 1 && maze[p->position_y][p->position_x] != 2)
			break;//避开墙和已生成的箱子
	}
	maze[p->position_y][p->position_x] = 2;

	flower_number++;
}

3.11人物移动+碰撞检测

void characterWalk(USER& user, int& gamestate, int maze[Row][Col], BOX* head) {
	getimage(&bkbkbk, 0, 0, 1080, 700);
	switch (gamestate) {
	case -1: {
		if (maze[(user.position_y) - 1][user.position_x] != 1) {//-1判上一个,-0判当前
			user.position_y -= 1;
			for (int i = 0; i < 35; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_y -= 1;
				FlushBatchDraw();
				Sleep(5);

			}
		}
		else
			break; }break;

	case -2: {
		if (maze[(user.position_y) + 1][user.position_x] != 1) {
			user.position_y += 1;
			for (int i = 0; i < 35; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_y += 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}

		else
			break; }break;
	case -3: {
		if (maze[user.position_y][(user.position_x) - 1] != 1) {
			user.position_x -= 1;
			for (int i = 0; i < 36; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_x -= 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}

		else
			break; }break;
	case -4: {
		if (maze[user.position_y][(user.position_x) + 1] != 1) {

			user.position_x += 1;
			for (int i = 0; i < 36; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_x += 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}
		else
			break; }break;
	default:break;
	}
	if (maze[user.position_y][user.position_x] == 2)
		gamestate = 0;//往后不能在出现gamestate的判断语句,所以将checksecret移动到characterwalk前方。
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] <= 1)
		gamestate = 0;//判断是路口//bug:没有墙,碰到两坨box在顶角也会停。
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] == 3)
		gamestate = 0;
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] == 5)
		gamestate = 0;
	putimage(user.p_x, user.p_y, &character);

}

3.12查看宝箱

void checksecret(int maze[Row][Col], USER& user, BOX* h) {
	BOX* p;
	p = h->next;
	while (p != NULL) {

		if (p->position_x == user.position_x && p->position_y == user.position_y) {
			if (p->data)
			{
				mciSendString("play ./dimond.mp3", 0, 0, 0);
				user.score += p->score;
				p->stage = 0;
				//gamestate = 0;
				putimage(p->position_x * 36, p->position_y * 35, &diamond_min);
				FlushBatchDraw();
				Sleep(1500);
				break;
			}
			else
			{
				mciSendString("play ./boom.mp3", 0, 0, 0);
				user.score += p->score;
				p->stage = 0;
				//gamestate = 0;
				putimage(p->position_x * 36, p->position_y * 35, &boom);
				FlushBatchDraw();
				Sleep(1500);
				break;
			}
		}
		p = p->next;
	}
}

3.13显示/隐藏

void ShoworHide(BOX* h) {
	BOX* p;
	p = h->next;
	while (p != NULL) {
		if (p->data)
			putimage(p->position_x * 36, p->position_y * 35, &diamond_min);

		else
			putimage(p->position_x * 36, p->position_y * 35, &boom);

		p = p->next;
	}


}

3.14存档

void writeRecord(int maze[Row][Col], USER user, BOX* h, int flower_number) {
	FILE* fp;
	fopen_s(&fp, "user_info.txt", "w");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fprintf_s(fp, "%d ", maze[i][j]);
			}//二维数组 1 0 2
		fprintf_s(fp, "\n%d %d %d %d\n", user.position_x, user.position_y, user.score, flower_number);
		fputs(user.name, fp);
		h = h->next;
		while (h != NULL) {
			fprintf_s(fp, "\n%d %d %d %d %d", h->data, h->stage, h->score, h->position_x, h->position_y);//data stage positionx positiony
			h = h->next;
		}
		fclose(fp);
		fp = NULL;
	}
	gameover(user);
}

3.15读档

void readRecord(int maze[Row][Col], USER& user, BOX* h, int& flower_number) {
	FILE* fp;
	fopen_s(&fp, "user_info.txt", "r");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fscanf_s(fp, "%d", &maze[i][j]);
			}
		fscanf_s(fp, "%d%d%d%d", &user.position_x, &user.position_y, &user.score, &flower_number);
		fgetc(fp);
		fgets(user.name, 20, fp);
		BOX* p;
		for (int i = 0; i < flower_number; i++) {
			p = (BOX*)malloc(sizeof(BOX));
			fscanf_s(fp, "%d %d %d %d %d", &p->data, &p->stage, &p->score, &p->position_x, &p->position_y);
			p->next = h->next;
			h->next = p;
		}
		fclose(fp);
		fp = NULL;


	}
}

3.16结束游戏

void gameover(USER user) {
	FILE* fp;
	fopen_s(&fp, "user_all_info.txt", "a");
	if (fp != NULL) {
		fprintf_s(fp, "\n%d ", user.score);
		fputs(user.name, fp);
	}
	exit(0);
}
void gameResult(USER user) {
	if (user.score >= 0) {
		//closegraph();
		initgraph(640, 480);
		putimage(0, 0, &victory);
		mciSendString("play ./victory.mp3", 0, 0, 0);
		settextcolor(BLACK);
		setbkmode(TRANSPARENT);
		settextstyle(30, 20, "楷体");
		outtextxy(200, 200, "你赢了!得分:");
		char buf[10];
		sprintf_s(buf, "%d", user.score);
		outtextxy(480, 200, buf);
		outtextxy(250, 250, "按任意键退出");
		FlushBatchDraw();
		getchar();
		gameover(user);
	}
}

4.完整代码

#include<stdio.h>
#include<graphics.h>
#include<stdlib.h>
#include<time.h>
#include<conio.h>
#include<mmsystem.h>
#pragma comment(lib,"winmm.lib")

#define WIDTH 1080
#define HEIGHT 700
#define D_SIZE_W 100
#define D_SIZE_H 120
#define D_X 1080*4/5
#define D_Y 50
#define B_SIZE_W 100
#define B_SIZE_H 90
#define B_X 1080*4/5
#define B_Y 170
#define START_BUTTON_X1 870
#define START_BUTTON_Y1 270
#define LINE1_X1 WIDTH*4/5
#define LINE1_Y1 0
#define LINE1_X2 LINE1_X1
#define LINE1_Y2 HEIGHT*7/8-10
#define WELCOME_X1 D_X
#define WELCOME_Y1 D_Y-50
#define WELCOME_X2 D_X+150
#define WELCOME_Y2 D_Y
#define Row 16
#define Col 24

typedef struct user {
	int score;
	char name[20];
	int position_x, position_y;
	int p_x, p_y;
}USER;
typedef struct box {
	int data;//钻石或炸弹
	int stage;//存活状态
	int score;
	struct box* next;
	int position_x, position_y;

}BOX;
typedef struct alluser {
	char name[20];
	int score;
}allUser;
void startup(int maze[Row][Col], USER& user, BOX* h, int& gamestate, int& flower_number);//startup(int maze[Row][Col], USER& user, int& gamestate);
void startMenu(int& gamestate, USER& user, int maze[Row][Col], BOX* h, int& flower_number);
void bodyRun(int maze[Row][Col], USER& user, BOX* head, int& gamestate, int& gamestate2, int& flower_number);
void show(USER user, int flower_number, int maze[Row][Col], char button[6][5]);
void inituser(USER& user, int& flower_number);
void createMaze(int[Row][Col], USER& user);
void createBox(int maze[Row][Col], BOX* h, int flower_number);
void ShoworHide(BOX* h);
void addBox(BOX* h, int& flower_number, int maze[Row][Col]);
void delbox(BOX* h, int& flower_number, int maze[Row][Col]);
void delall(BOX* h, int& flower_number);
void showBox(BOX* h);
void checksecret(int maze[Row][Col], USER& user, BOX* h);
void checkMsg(int& gamestate, char button[6][5], int& show_or_hide);
void checkKsg(int& gamestate);
void characterWalk(USER& user, int& gamestate, int maze[Row][Col], BOX* h);
void walkslowly(int& position_, int& p_, USER user, int flag);
void writeRecord(int maze[Row][Col], USER user, BOX* h, int flower_number);
void readRecord(int maze[Row][Col], USER& user, BOX* h, int& flower_number);
void gameover(USER user);
void gameResult(USER user);


IMAGE victory;
IMAGE playground;
IMAGE diamond;
IMAGE box;
IMAGE box_min;
IMAGE character;
IMAGE boom;
IMAGE diamond_min;
IMAGE wall;
IMAGE bkbkbk;
IMAGE button_down;
IMAGE button_up;

int main() {
	USER user;
	int maze[Row][Col] = { 0 };
	int gamestate_ksg = 0, gamestate_msg = 0;

	BOX* head;
	head = (BOX*)malloc(sizeof(BOX));
	head->next = NULL;
	char button[6][5] = { "开始","退出","存档","显示","增加","清空" };
	int flower_number = 5;
	int show_or_hide = 0;
	startup(maze, user, head, gamestate_ksg, flower_number);
	while (1) {
		checkMsg(gamestate_msg, button, show_or_hide);//-3-4-5-6
		checkKsg(gamestate_ksg);//-7
		bodyRun(maze, user, head, gamestate_ksg, gamestate_msg, flower_number);
		show(user, flower_number, maze, button);
	}
}
void startup(int maze[Row][Col], USER& user, BOX* h, int& gamestate, int& flower_number) {
	initgraph(WIDTH, HEIGHT);

	loadimage(&victory, "./游戏背景1.png", 640, 480);
	loadimage(&playground, "./游戏背景8.jpg", WIDTH, HEIGHT);
	loadimage(&diamond, "./钻石图标2.jfif", D_SIZE_W, D_SIZE_H);
	loadimage(&box, "./宝箱未开箱.jpg", B_SIZE_W, B_SIZE_H);
	loadimage(&box_min, "./宝箱小图标.jpg", WIDTH / 30, HEIGHT / 20);
	loadimage(&character, "./人物.jpg", WIDTH / 30, HEIGHT / 20);
	loadimage(&boom, "./炸弹.jfif", WIDTH / 30, HEIGHT / 20);
	loadimage(&diamond_min, "./钻石图标2.jfif", WIDTH / 30, HEIGHT / 20);
	loadimage(&wall, "./石块.png", WIDTH / 30, HEIGHT / 20);//长36 高35
	loadimage(&button_down, "./buttonon.png", 190, 60);
	loadimage(&button_up, "./buttonun.png", 190, 60);
	BeginBatchDraw();
	mciSendString("play ./bkbk.mp3 repeat", 0, 0, 0);
	while (gamestate == 0)
		startMenu(gamestate, user, maze, h, flower_number);

}
void startMenu(int& gamestate, USER& user, int maze[Row][Col], BOX* h, int& flower_number) {
	putimage(0, 0, &playground);
	setbkmode(TRANSPARENT);
	settextcolor(BLACK);
	settextstyle(50, 0, "楷体");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.2, "新游戏 press '1'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.3, "继续游戏 press '2'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.4, "退出 press '3'");
	outtextxy(WIDTH * 0.3, HEIGHT * 0.5, "关闭/打开音乐 press '4'/'5'");
	FlushBatchDraw();
	Sleep(2);
	char input;
	if (_kbhit()) {
		mciSendString("play ./点击音效.mp3", 0, 0, 0);
		input = _getch();
		if (input == '1')
		{
			inituser(user, flower_number);
			createMaze(maze, user);
			createBox(maze, h, flower_number);
			gamestate = 1;
		}
		if (input == '2') {
			readRecord(maze, user, h, flower_number);
			user.p_x = user.position_x * 36;
			user.p_y = user.position_y * 35;
			gamestate = 2;
		}
		if (input == '3')
			exit(0);
		if (input == '4')
			mciSendString("pause ./bkbk.mp3", 0, 0, 0);
		if (input == '5')
			mciSendString("play ./bkbk.mp3 repeat", 0, 0, 0);
	}

}
void checkMsg(int& gamestate, char button[6][5], int& show_or_hide) {
	
	MOUSEMSG msg;
	if (MouseHit()) {

		msg = GetMouseMsg();

		switch (msg.uMsg) {
		case WM_LBUTTONDOWN:
			mciSendString("play ./点击音效.mp3", 0, 0, 0);
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y> 480 && msg.y < 540)
			{

				if (show_or_hide == 0) {
					gamestate = -5;//显示隐藏
					show_or_hide = 1;
					//char c[5] = "隐藏";
					strcpy_s(button[3], "隐藏");
					//*button[3] = "隐藏";//相当于仅仅赋值了第一位
				}
				else if (show_or_hide == 1) {
					gamestate = -6;
					show_or_hide = 0;
					strcpy_s(button[3], "显示");
				}
				putimage(START_BUTTON_X1, 480, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}

			if (msg.x > START_BUTTON_X1 && msg.x<1060 && msg.y>START_BUTTON_Y1 && msg.y < 320)
			{

				gamestate = -6;//开始
				show_or_hide = 0;
				strcpy_s(button[3], "显示");
				putimage(START_BUTTON_X1, 270, &button_down);
				FlushBatchDraw();
				Sleep(50);

			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>410 && msg.y < 470)
			{
				gamestate = -4;//存档
				setfillcolor(YELLOW);

				putimage(START_BUTTON_X1, 410, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>550 && msg.y < 610)
			{
				gamestate = -3;//增加
				putimage(START_BUTTON_X1, 550, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.x < 1060 && msg.y>340 && msg.y < 400)
			{
				gamestate = -2;//退出
				setfillcolor(YELLOW);
				putimage(START_BUTTON_X1, 340, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}
			if (msg.x > START_BUTTON_X1 && msg.y > 620 && msg.x < 1060 && msg.y < 680)
			{
				gamestate = -1;//清空
				setfillcolor(YELLOW);
				putimage(START_BUTTON_X1, 620, &button_down);
				FlushBatchDraw();
				Sleep(50);
			}


		}
	}
}
void checkKsg(int& gamestate) {
	char ksg;
	if (_kbhit()) {
		ksg = _getch();
		switch (ksg) {
		case 'w':gamestate = -1; break;
		case 's':gamestate = -2; break;
		case 'a':gamestate = -3; break;
		case 'd':gamestate = -4; break;
		case ' ': gamestate = -7; break;
		default:break;

		}
	}

}
void bodyRun(int maze[Row][Col], USER& user, BOX* h, int& gamestate, int& gamestate2, int& flower_number) {

	//BOX* p = NULL;
	if (gamestate == -7) {
		checksecret(maze, user, h);
		delbox(h, flower_number, maze);
		//gamestate = 0;
	}
	
	if (gamestate2 == -5) {
		ShoworHide(h);
	}
	if (gamestate2 == -6) {
		showBox(h);
	}
	if (gamestate2 == -4) {
		writeRecord(maze, user, h, flower_number);
	}
	if (gamestate2 == -3) {
		addBox(h, flower_number, maze);
		gamestate2 = -6;
	}
	if (gamestate2 == -2) {
		gameover(user);
	}
	if (gamestate2 == -1) {
		delall(h, flower_number);
	}
	characterWalk(user, gamestate, maze, h);
	
	FlushBatchDraw();
	if (maze[user.position_y][user.position_x] == -1) {
		gameResult(user);
	}

}
void inituser(USER& user, int& flower_number) {
	InputBox(user.name, 20, "请输入用户名:");
	char buf[10];
	InputBox(buf, 10, "请输入宝箱个数");
	flower_number = atoi(buf);
	if (flower_number == 0)
		flower_number = 5;
}
void createMaze(int maze[Row][Col], USER& user) {
	FILE* fp;
	fopen_s(&fp, "maze_init.txt", "r");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fscanf_s(fp, "%d", &maze[i][j]);
			}
		fclose(fp);
		fp = NULL;
	}

	user.position_x = 0;
	user.position_y = 1;
	user.p_x = user.position_x * 36;
	user.p_y = user.position_y * 35;
	user.score = 0;

}
void createBox(int maze[Row][Col], BOX* h, int flower_number) {
	BOX* p;
	int i;
	srand((int)time(NULL));
	for (i = 0; i < flower_number; i++) {
		p = (BOX*)malloc(sizeof(BOX));
		p->stage = 1;
		p->data = rand() % 2;//0为宝石1为炸弹
		if (p->data) {
			p->score = rand() % 5;
		}
		else {
			p->score = -(rand() % 5);
		}
		while (1) {
			p->position_x = rand() % Col;
			p->position_y = rand() % Row;
			if (maze[p->position_y][p->position_x] != 1 && maze[p->position_y][p->position_x] != 2 && maze[p->position_y][p->position_x] != -1)
				break;
		}
		maze[p->position_y][p->position_x] = 2;

		p->next = h->next;
		h->next = p;
	}
}
void delbox(BOX* h, int& flower_number, int maze[Row][Col]) {
	BOX* p, * r;
	r = h;
	p = h->next;
	while (p != NULL) {
		if (p->stage == 0) {
			maze[p->position_y][p->position_x] = 0;
			flower_number--;
			r->next = p->next;
			free(p);
			p = r->next;
			r = r->next;
		}
		else {
			p = p->next;
			r = r->next;
		}
	}
}
void addBox(BOX* h, int& flower_number, int maze[Row][Col]) {
	BOX* p;
	p = (BOX*)malloc(sizeof(BOX));
	p->stage = 1;
	p->data = rand() % 2;
	if (p->data) {
		p->score = rand() % 5;
	}
	else {
		p->score = -(rand() % 5);
	}
	p->next = h->next;
	h->next = p;
	while (1) {
		p->position_x = rand() % Col;
		p->position_y = rand() % Row;
		if (maze[p->position_y][p->position_x] != 1 && maze[p->position_y][p->position_x] != 2)//避开墙和已生成的箱子
			break;
	}
	maze[p->position_y][p->position_x] = 2;

	flower_number++;
}
void delall(BOX* h, int& flower_number) {
	BOX* p;
	p = h->next;
	while (p != NULL) {
		h->next = p->next;
		free(p);
		p = h->next;
	}
	flower_number = 0;
}
void show(USER user, int flower_number, int maze[Row][Col], char button[6][5]) {
	cleardevice();
	putimage(0, 0, &playground);
	putimage(D_X, D_Y, &diamond);
	putimage(B_X, B_Y, &box);
	setlinecolor(BLACK);
	setlinestyle(PS_SOLID, 4);
	line(LINE1_X1, LINE1_Y1, LINE1_X2, LINE1_Y2);

	for (int i = 0; i < 6; i++) {
		putimage(START_BUTTON_X1, START_BUTTON_Y1 + i * 70, &button_up);
	}
	setbkmode(TRANSPARENT);
	settextstyle(30, 20, "行体");
	settextcolor(WHITE);
	outtextxy(WELCOME_X1 + 10, WELCOME_Y1 + 10, user.name);
	char buf1[10];
	sprintf_s(buf1, 10, "%d", flower_number);
	outtextxy(B_X + B_SIZE_W + 20, B_Y + B_SIZE_H / 3, buf1);//打印宝箱数量
	char buf2[10];
	sprintf_s(buf2, "%d", user.score);
	outtextxy(D_X + D_SIZE_W + 20, D_Y + D_SIZE_H / 3, buf2);
	settextcolor(BLACK);
	for (int i = 0; i < Row; i++) {
		for (int j = 0; j < Col; j++) {
			if (maze[i][j] == 1)
				putimage(j * 36, i * 35, &wall);
		}
	}

	for (int i = 0; i < 6; i++) {
		outtextxy(START_BUTTON_X1 + 50, 285 + i * 70, button[i]);
	}
	for (int i = 0; i < Row; i++) {
		for (int j = 0; j < Col; j++) {
			if (maze[i][j] == 1)
				putimage(j * 36, i * 35, &wall);
		}
	}
}
void ShoworHide(BOX* h) {
	BOX* p;
	p = h->next;
	while (p != NULL) {
		if (p->data)
			putimage(p->position_x * 36, p->position_y * 35, &diamond_min);

		else
			putimage(p->position_x * 36, p->position_y * 35, &boom);

		p = p->next;
	}


}
void showBox(BOX* h) {
	BOX* p;
	p = h->next;
	while (p != NULL) {
		putimage(p->position_x * 36, p->position_y * 35, &box_min);
		p = p->next;
	}

}
void writeRecord(int maze[Row][Col], USER user, BOX* h, int flower_number) {
	FILE* fp;
	fopen_s(&fp, "user_info.txt", "w");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fprintf_s(fp, "%d ", maze[i][j]);
			}//二维数组 1 0 2
		fprintf_s(fp, "\n%d %d %d %d\n", user.position_x, user.position_y, user.score, flower_number);
		fputs(user.name, fp);
		h = h->next;
		while (h != NULL) {
			fprintf_s(fp, "\n%d %d %d %d %d", h->data, h->stage, h->score, h->position_x, h->position_y);//data stage positionx positiony
			h = h->next;
		}
		fclose(fp);
		fp = NULL;
	}
	gameover(user);
}
void readRecord(int maze[Row][Col], USER& user, BOX* h, int& flower_number) {
	FILE* fp;
	fopen_s(&fp, "user_info.txt", "r");
	if (fp != NULL) {
		for (int i = 0; i < Row; i++)
			for (int j = 0; j < Col; j++) {
				fscanf_s(fp, "%d", &maze[i][j]);
			}
		fscanf_s(fp, "%d%d%d%d", &user.position_x, &user.position_y, &user.score, &flower_number);
		fgetc(fp);
		fgets(user.name, 20, fp);
		BOX* p;
		for (int i = 0; i < flower_number; i++) {
			p = (BOX*)malloc(sizeof(BOX));
			fscanf_s(fp, "%d %d %d %d %d", &p->data, &p->stage, &p->score, &p->position_x, &p->position_y);
			p->next = h->next;
			h->next = p;
		}
		fclose(fp);
		fp = NULL;


	}
}
void characterWalk(USER& user, int& gamestate, int maze[Row][Col], BOX* head) {
	getimage(&bkbkbk, 0, 0, 1080, 700);
	switch (gamestate) {
	case -1: {
		if (maze[(user.position_y) - 1][user.position_x] != 1) {//-1判上一个,-0判当前
			user.position_y -= 1;
			for (int i = 0; i < 35; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_y -= 1;
				FlushBatchDraw();
				Sleep(5);

			}
		}
		else
			break; }break;

	case -2: {
		if (maze[(user.position_y) + 1][user.position_x] != 1) {
			user.position_y += 1;
			for (int i = 0; i < 35; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_y += 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}

		else
			break; }break;
	case -3: {
		if (maze[user.position_y][(user.position_x) - 1] != 1) {
			user.position_x -= 1;
			for (int i = 0; i < 36; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_x -= 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}

		else
			break; }break;
	case -4: {
		if (maze[user.position_y][(user.position_x) + 1] != 1) {

			user.position_x += 1;
			for (int i = 0; i < 36; i++) {
				cleardevice();
				putimage(0, 0, &bkbkbk);
				putimage(user.p_x, user.p_y, &character);
				user.p_x += 1;
				FlushBatchDraw();
				Sleep(5);
			}
		}
		else
			break; }break;
	default:break;
	}
	if (maze[user.position_y][user.position_x] == 2)
		gamestate = 0;
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] <= 1)
		gamestate = 0;
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] == 3)
		gamestate = 0;
	if (maze[user.position_y][user.position_x + 1] + maze[user.position_y][user.position_x - 1] + maze[user.position_y + 1][user.position_x] + maze[user.position_y - 1][user.position_x] == 5)
		gamestate = 0;
	putimage(user.p_x, user.p_y, &character);

}
void checksecret(int maze[Row][Col], USER& user, BOX* h) {
	BOX* p;
	p = h->next;
	while (p != NULL) {

		if (p->position_x == user.position_x && p->position_y == user.position_y) {
			if (p->data)
			{
				mciSendString("play ./dimond.mp3", 0, 0, 0);
				user.score += p->score;
				p->stage = 0;
				//gamestate = 0;
				putimage(p->position_x * 36, p->position_y * 35, &diamond_min);
				FlushBatchDraw();
				Sleep(1500);
				break;
			}
			else
			{
				mciSendString("play ./boom.mp3", 0, 0, 0);
				user.score += p->score;
				p->stage = 0;
				//gamestate = 0;
				putimage(p->position_x * 36, p->position_y * 35, &boom);
				FlushBatchDraw();
				Sleep(1500);
				break;
			}
		}
		p = p->next;
	}
}
void gameover(USER user) {
	FILE* fp;
	fopen_s(&fp, "user_all_info.txt", "a");
	if (fp != NULL) {
		fprintf_s(fp, "\n%d ", user.score);
		fputs(user.name, fp);

	}
	exit(0);
}
void gameResult(USER user) {
	if (user.score >= 0) {
		//closegraph();
		initgraph(640, 480);
		putimage(0, 0, &victory);
		mciSendString("play ./victory.mp3", 0, 0, 0);
		settextcolor(BLACK);
		setbkmode(TRANSPARENT);
		settextstyle(30, 20, "楷体");
		outtextxy(200, 200, "你赢了!得分:");
		char buf[10];
		sprintf_s(buf, "%d", user.score);
		outtextxy(480, 200, buf);
		outtextxy(250, 250, "按任意键退出");
		FlushBatchDraw();
		getchar();
		gameover(user);
	}
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值