C语言编写一个简单的2048游戏

2048游戏

​ 文件规则:

​ main.c 程序主入口

​ game2048.c game2048.h 游戏的业务逻辑

​ direction.c direction.h 方向键的处理

​ tools.c tools.h 工具函数

​ Makefile 编译脚本文件

main函数

#include "game2048.h"

int main(int argc,char* argv[])
{
	init_game();
	
	run_game();
	
	return 0;
}

游戏逻辑函数

#include <getch.h>
#include <time.h>
#include <stdlib.h>
#include "game2048.h"
#include "direction.h"
#include "tools.h"

int (*view)[4] = NULL;
bool is_move_meger = true;
int score = 0;

//初始化相关资源、加载数据
void init_game(void)
{
	debug("%s\n",__func__);
	//初始化随机数
	srand(time(NULL));
	//申请堆内存
	view = malloc(sizeof(view[0][0])*4*4);
	//从文件中加载数据
}

//运行游戏
void run_game(void)
{
	debug("%s\n",__func__);
	for(;;)
	{
		//随机产生一个2或者4
		rand_number();
		//显示界面
		show_view();
		is_move_meger = false;
		//判断能否移动
		if(is_godie())
		{
			exit_game();
			return;
		}
		//获取方向键并处理
		switch(getch())
		{
			case 183:up();break;
			case 184:down();break;
			case 185:right();break;
			case 186:left();break;
		}
	}
}

//释放相关资源,保存数据
void exit_game(void)
{
	debug("%s\n",__func__);
	//保存数据
	
	//释放堆内存
	free(view);
	view = NULL;
}
#ifndef GAME2048_H
#define GAME2048_H
#include <stdbool.h>
extern int (*view)[4];
extern bool is_move_meger;
extern int score;

//初始化相关资源、加载数据
void init_game(void);

//运行游戏
void run_game(void);

//释放相关资源,保存数据
void exit_game(void);

#endif//GAME2048_H

方向键函数

#include "direction.h"
#include "game2048.h"
#include "tools.h"

void up(void)
{
	debug("%s\n",__func__);
	for(int y=0;y<4;y++)
	{
		//合并的边界
		int end = 0;
		for(int x=1;x<4;x++)
		{
			for(int i=x;i>end;i--)
			{
				if(view[i][y] && view[i-1][y] == view[i][y])
				{
					score += view[i][y];
					view[i-1][y] *= 2;
					view[i][y] = 0;
					end = i;	//当有合并的方块时,合并完同时合并边界往下挪一层,防止多层同时合并
					is_move_meger = true;
				}
				else if(view[i][y] && !view[i-1][y])
				{
					view[i-1][y] = view[i][y];
					view[i][y] = 0;
					is_move_meger = true;
				}
			}
		}
	}
}

void down(void)
{
	debug("%s\n",__func__);
	for(int y=0;y<4;y++)
	{
		//合并的边界
		int end = 3;
		for(int x=2;x>=0;x--)
		{
			for(int i=x;i<end;i++)
			{
				if(view[i][y] && view[i+1][y] == view[i][y])
				{
					score += view[i][y];
					view[i+1][y] *= 2;
					view[i][y] = 0;
					end = i;
					is_move_meger = true;
				}
				else if(view[i][y] && !view[i+1][y])
				{
					view[i+1][y] = view[i][y];
					view[i][y] = 0;
					is_move_meger = true;
				}
			}
		}
	}
}

void right(void)
{
	debug("%s\n",__func__);
	for(int x=0;x<4;x++)
	{	
		int end = 3;
		for(int y=2;y>=0;y--)
		{
			for(int i=y;i<end;i++)
			{
				if(view[x][i] && view[x][i] == view[x][i+1])
				{
					score += view[x][i];
					view[x][i+1] *= 2;
					view[x][i] = 0;
					end = i;
					is_move_meger = true;
				}
				else if(view[x][i] && !view[x][i+1])
				{
					view[x][i+1] = view[x][i];
					view[x][i] = 0;
					is_move_meger = true;
				}
			}
		}
	}
}

void left(void)
{
	debug("%s\n",__func__);
	for(int x=0;x<4;x++)
	{
		//合并的边界
		int end = 0;
		for(int y=1;y<4;y++)
		{
			for(int i=y;i>end;i--)
			{
				if(view[x][i] && view[x][i-1] == view[x][i])
				{
					score += view[x][i];
					view[x][i-1] *= 2;
					view[x][i] = 0;
					end = i;
					is_move_meger = true;
				}
				else if(view[x][i] && !view[x][i-1])
				{
					view[x][i-1] = view[x][i];
					view[x][i] = 0;
					is_move_meger = true;
				}
			}
		}
	}
}
#ifndef DIRECTION_H
#define DIRECTION_H

void up(void);
void down(void);
void right(void);
void left(void);

#endif//DIRECTION_H

工具类函数

#include <stdlib.h>
#include "tools.h"
#include "game2048.h"

//显示界面
void show_view(void)
{
	debug("%s\n",__func__);
	system("clear");
	for(int i = 0;i < 4;i++)
	{
		printf("---------------------\n");
		for(int j = 0;j < 4;j++)
		{
			if(view[i][j]!=0)
			{
				printf("|%4d",view[i][j]);
			}
			else
			{
				printf("|    ");
		 	}
		}
		printf("|\n");
	}
	printf("---------------------\n");
	printf("SCORE = %d\n",score);
}

//判断棋盘是否已满
static bool is_full(void)
{
	int* arr = (int*)view;
	for(int i = 0; i < 16; i++)
	{
		if(arr[i] == 0)
		{
			return false;
		}
	}
	return true;
}

//随即产生2或4
void rand_number(void)
{
	debug("%s\n",__func__);
	if(is_full())
	{
		debug("没有空位置");
		return;
	}
	for(;is_move_meger == true;)
	{
		int x = rand()%4;
		int y = rand()%4;
		if(0 == view[x][y])
		{
			view[x][y] = 2; //方便测试,只产生2
			return;
		}
	}
}

//检查是否结束
bool is_godie(void)
{
	debug("%s\n",__func__);
	if(!is_full())
	{
		return false;
	}
	for(int x=0;x<4;x++)
	{
		for(int y=0;y<3;y++)
		{
			if(view[x][y] == view[x][y+1])
			{
				return false;
			}
		}
	}
	for(int y=0;y<4;y++)
	{
		for(int x=0;x<3;x++)
		{
			if(view[x][y] == view[x+1][y])
			{
				return false;
			}
		}
	}
	return true;
}
#ifndef TOOLS_H
#define TOOLS_H
#include <stdbool.h>
#include <stdio.h>

#ifdef DEBUG
	#define debug(...) printf(__VA_ARGS__)
#else
	#define debug(...)
#endif

//显示界面
void show_view(void);

//随即产生2或4
void rand_number(void);

//检查是否结束
bool is_godie(void);

#endif//TOOLS_H

Makefile

CC=gcc
STD=-std=gnu99
BIN=game.bin
FLAG=-Wall -Werror -DDEBUG
OBJ=main.o direction.o game2048.o tools.o

all:$(OBJ)
	$(CC) -o $(BIN) $(OBJ)
main.o:main.c game2048.h
	$(CC) $(STD) $(FLAG) -c main.c
game2048.o:game2048.c game2048.h tools.h direction.h
	$(CC) $(STD) $(FLAG) -c game2048.c
direction.o:direction.c direction.h tools.h game2048.h
	$(CC) $(STD) $(FLAG) -c direction.c
tools.o:tools.c tools.h game2048.h
	$(CC) $(STD) $(FLAG) -c tools.c
clean:
	rm -rf $(OBJ) $(BIN)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值