原来还有这么通俗易懂的贪吃蛇写法之CFood类 && CMap类(思路很详细,有详细的代码解释)(二)

提示:阅读本文需要一定的C++基础,此思路只用于实现贪吃蛇的基本功能,没有图形化,没有使用EasyX库。(尊重原创,转载本文请指明出处)
此思路对于锦城的学生很适用,这就是一学期的一个小项目。


前言

提示:
了解代码框架戳这儿:https://blog.csdn.net/weixin_43929310/article/details/112667309
全部代码请点击–>https://github.com/qing-qing-mei/Snake

前一篇:CUnit类
后一篇(CSnake类):https://blog.csdn.net/weixin_43929310/article/details/112822955


提示:以下是本篇文章正文内容

一、代码

CFood类:

#pragma once
#include "CUnit.h"
class CFood :
    public Cunit
{
public:
    CFood(int x =0, int y=0, char pic = '#');
    virtual ~CFood();
    void createPos();   //创建食物位置
};

```cpp
#include "CFood.h"
#include"CUnit.h"
#include"CMap.h"
#include<iostream>
#include<ctime>
#include<cstdlib>

using namespace std;

CFood::CFood(int x, int y, char pic) : Cunit(x, y, pic)  //使用成员列表方式初始化
{

}

CFood::~CFood()
{

}

void CFood::createPos()
{
	/*m_ix = CMap::KLEFT + rand() % (CMap::KWIDTH - 2);
	m_iy = CMap::KUP + rand() % (CMap::KHEIGHT - 4);*/
	m_ix = CMap::KLEFT + rand() % (CMap::KWIDTH - CMap::KLEFT - 1);
	m_iy = CMap::KUP + rand() % (CMap::KHEIGHT - CMap::KUP - 1);
}

CMap类:

#pragma once
class CMap
{
public:
	void drawGameArea();
	void drawGameInfo();
	void drawGameWindows();
public:
	static const int KLEFT;
	static const int KUP;
	static const int KWIDTH;
	static const int KHEIGHT;
	static const int KSCORE_OFFSET;
	static const int KLEVEL_OFFSET;
};
#include "CMap.h"
#include<iostream>
#include<windows.h>
#include"Cunit.h"
using namespace std;

const int CMap::KLEFT = 1;    //地图左边界
const int CMap::KUP = 3;     //地图上边界
const int CMap::KWIDTH = 80;     //长
const int CMap::KHEIGHT = 30;    //高
const int CMap::KSCORE_OFFSET = 0;    //初始分数
const int CMap::KLEVEL_OFFSET = 1;   //初始游戏等级

void CMap::drawGameWindows()  //初始化游戏窗口大小
{
	SMALL_RECT win_size = { 0,0,KWIDTH ,KHEIGHT + 2 };  //定义上下左右四个点
	SetConsoleWindowInfo(GetStdHandle(STD_OUTPUT_HANDLE), true, &win_size);
}

void CMap::drawGameArea()  //绘制地图
{
	drawGameWindows();
	int wall[KHEIGHT][KWIDTH] = { {0} };
	for (int i = 1; i < KHEIGHT - 1; i++)
		for (int j = 1; j < KWIDTH - 1; j++)
			wall[i][j] = 1;
	for (int i = 0; i < KHEIGHT; i++)
	{
		for (int j = 0; j < KWIDTH; j++)
		{
			if (wall[i][j]) cout << " ";
			else
			{
				if (i == 0 || i == KHEIGHT - 1) cout << "-";
				else cout << "|";
			}
		}
		cout << endl;
	}
}

void CMap::drawGameInfo()  //功能:显示游戏信息
{
	Cunit::gotoxy(1, 2);
	for (int i = 0; i < KWIDTH - 2; i++)
	{
		cout << '-';
	}
	Cunit::gotoxy(KLEFT, 1);
	cout << "游戏名称:贪吃蛇";
	Cunit::gotoxy(KLEFT + 1 * (KWIDTH / 4), 1);
	cout << "编写者:***";
	Cunit::gotoxy(KLEFT + 2 * (KWIDTH / 4), 1);
	cout << "游戏得分:" << KSCORE_OFFSET;
	Cunit::gotoxy(KLEFT + 3 * (KWIDTH / 4), 1);
	cout << "游戏等级:" << KLEVEL_OFFSET;
}

二、思路

CFood类:
CFood类中唯一的难点就在于如何使食物随机产生在地图的范围内。
产生随机数,如何产生随机数请参考这篇文章–>c++产生随机数
CMap类:
在这个类中,我们使用到了三个成员函数分别是
void drawGameArea(); //初始化游戏窗口大小
void drawGameInfo(); //显示游戏信息
void drawGameWindows(); //绘制地图

显示游戏信息比较简单,调用CUnit类中的gotoxy()函数将光标定位到指定位置输出相应信息即可。

绘制地图只要将思路理清其实也不难,我们定义一个二维数组并初始化为0来表示地图,然后通过一个双重循环,将地图边界的地方变为1;这样,在接下来的双重循环中,我们将值为1的输出相应的边界符号,而值为0的则输出空格,这样,一个地图边框就绘制完成了!

初始化窗口大小其实并不难,难点在于其中的SMALL_RECT结构体,SetConsoleWindowInfo()接口我们都很陌生,因为都没见过,其实我们不必知道它到底是如何实现的,只需要知道它能够有什么用就行了!这里只需要说一句,基本上调用windows中结构体或者API的都需要添加 windows.h头文件。

关于SMALL_RECT结构体,它其实就是帮助我们定义游戏边框的四个点,也就是窗口边界值。
更加详细的解释我放在这里:
https://docs.microsoft.com/zh-cn/windows/console/small-rect-str
或者
https://wenku.baidu.com/view/380fae4dc850ad02de8041b0.html

关于SetConsoleWindowInfo(),它其实就是完成窗口大小初始化这个工作,我也整理了两个便于大家理解的链接:
https://docs.microsoft.com/en-us/windows/console/setconsolewindowinfo
或者
https://www.cnblogs.com/X-Jun/p/6910430.html?utm_source=itdadao&utm_medium=referral

总结

这一篇介绍了食物类和地图类,总体来说并不难,下一篇介绍贪吃蛇中至关重要的蛇类!

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值