本程序使用了以下的所有头文件
游戏地图及功能实现: TANXL_GAME_STATE.h
控制台游戏界面实现: TANXL_CONSOLE_LIST.h.
开发环境:Visual Studio 2019
推箱子
Version 1 完全采用控制台输出颜色以及游戏界面
一、系统功能分析
此程序采用了两个头文件进行各方面的设置,TANXL_GAME_STATE.h中包含了本地游戏关卡的文本文件创建和获取操作以及游戏移动、推动的规则设定,TANXL_CONSOLE_LIST.h用于完成列表输出、颜色输出、绘制地图的功能,主函数负责联系两个头文件的内容。
在游戏运行中会判断是否每一个箱子都在目标区域内,如果是,则立即进行一次绘制(绘制箱子在目标上的地图)然后输出通关提示。如果在此界面选择是则进入下一关,否则返回主界面,如果这一关已经是最后一关,则在选择是的情况下会回到第一关。
二、各功能模块设计与分析
完全调用的头文件提供的功能,完整模块功能分析请参考代码的注释。
三、系统实现
此为提前更新!内容将在稍后补充。
四、代码
TANXL_GAME_STATE.h(2021/8/1 Finished)
#ifndef TANXL_GAME_STATE
#define TANXL_GAME_STATE
#ifndef FSTREAM
#define FSTREAM
#include<fstream>
#endif
namespace GAME_STATE
{
std::ofstream fout;
std::ifstream fin;
typedef enum class Status
{
Status_Player,//玩家:>
Status_Player_On_Target,//处于目标上的玩家:<
Status_Object,//箱子:D
Status_Object_On_Target,//处于目标上的箱子:=
Status_Block,//围墙:H
Status_Ground,//空地:G
Status_Target,//目标:+
Status_Unknown//未知状态
}Status;
typedef struct Level
{
std::string LevelName{};
int Width{};
int Height{};
}Level;
typedef class GameState
{
public:
bool InitState(const int Width = 6, const int Height = 6);//地图初始化函数,返回True则初始化成功
bool CheckFile(const char* FileName);//判断本地关卡是否存在
bool CheckLevel();//判断是否通关
const int GetWidth();//获取地图宽度
const int GetHeight();//获取地图高度
const char* GetFileName(int LevelId);//获取关卡的文件名称
void InsertAction(char Keys);//输入控制
void ClearState();//释放指针,清空地图
void GetFileLevel(int LevelId);//获取本地文件的关卡
void DefaultLevel();//在本地生成默认关卡
Level GetState(int LevelId);//返回基础地图信息
Status* GetGameStates();//返回地图信息
private:
void MovePlayer(int MoveS);//移动玩家,MovesS:3为左,4为右,1为上,2为下
const char* Levels[5]{ "Level_1.txt","Level_2.txt","Level_3.txt","Level_4.txt","Level_5.txt" };//定义本地关卡文件名称
char SingleState{};
int PlayerX{}, PlayerY{};
int MoveX{}, MoveY{};
int MoveXP{}, MoveYP{};
int StateWidth{ 0 };//地图宽度
int StateHeight{ 0 };//地图高度
Status* GameStates{};
Level LocalLevel[5];
}State;
bool GameState::InitState(int Width, int Height)//地图初始化函数,返回True则初始化成功
{
StateWidth = Width;
StateHeight = Height;
GameStates = new Status[StateWidth * StateHeight];
if (StateWidth == 0 || StateHeight == 0)
return false;
return true;
}
bool GameState::CheckFile(const char* FileName)//判断本地关卡是否存在
{
std::ifstream Tfin(FileName);
if (!Tfin)
return false;
return true;
}
void GameState::ClearState()//释放指针,清空地图
{
delete[] GameStates;
GameStates = 0;
StateWidth = 0;
StateHeight = 0;
}
const int GameState::GetWidth()//获取地图宽度
{
return StateWidth;
}
const int GameState::GetHeight()//获取地图高度
{
return StateHeight;
}
void GameState::GetFileLevel(int LevelId)//获取本地文件的关卡
{
if (LevelId > 4 || LevelId < 0)
return;
Status Temp;
fin.open(GetFileName(LevelId));
fin >> LocalLevel[LevelId].LevelName >> LocalLevel[LevelId].Width >> LocalLevel[LevelId].Height;
InitState(LocalLevel[LevelId].Width, LocalLevel[LevelId].Height);
for (int i = 0; i < LocalLevel[LevelId].Height; i++)
{
for (int j = 0; j < LocalLevel[LevelId].Width; j++)
{
fin >> SingleState;
switch (SingleState)
{
case 'H':Temp = Status::Status_Block; break;
case 'G':Temp = Status::Status_Ground; break;
case 'D':Temp = Status::Status_Object; break;
case '+':Temp = Status::Status_Target; break;
case '>':Temp = Status::Status_Player; PlayerX = i; PlayerY = j; break;
case '<':Temp = Status::Status_Player_On_Target; PlayerX = i; PlayerY = j; break;
case '=':Temp = Status::Status_Object_On_Target; break;
case '\n':Temp = Status::Status_Unknown; break;
case 'X':return; break;
}
if (Temp != Status::Status_Unknown)
{
GameStates[i * LocalLevel[LevelId].Width + j] = Temp;
}
}
}
fin.close();
}
const char* GameState::GetFileName(int LevelId)//获取关卡的文件名称
{
if (LevelId > 4 || LevelId < 0)
return "Error";
return Levels[LevelId];
}
void GameState::DefaultLevel()//在本地生成默认关卡
{
for (int i = 0; i < 5; i++)
remove(Levels[i]);
fout.open(Levels[0]);
fout << "Level_1 8 8 HHHHHHHHHHH+HHHHHHHGHHHHHHHDGD+HH+GD>HHHHHHHDHHHHHHH+HHHHHHHHHHHX";
fout.close();
fout.open(Levels[1]);
fout << "Level_2 9 9 HHHHHHHHHH>GGHHHHHHGDDHHHHHHGDGHHH+HHHHGHHH+HHHHGGGG+HHHGGGHGGHHHGGGHHHHHHHHHHHHHX";
fout.close();
fout.open(Levels[2]);
fout << "Level_3 10 7 HHHHHHHHHHHHGGGGGHHHHHDHHHGGGHHGG>DGGDGHHG++HGDGHHHH++HGGGHHHHHHHHHHHHX";
fout.close();
fout.open(Levels[3]);
fout << "Level_4 6 8 HHHHHHHHGGHHH>DGHHHHDGHHHHGDGHH+DGGHH++=+HHHHHHHX";
fout.close();
fout.open(Levels[4]);
fout << "Level_5 8 8 HHHHHHHHHHGGHHHHHH>DGGHHHHHGHGHHH+HGHGGHH+DGGHGHH+GGGDGHHHHHHHHHX";
fout.close();
}
void GameState::MovePlayer(int MoveS)//移动玩家,MovesS:1为左,2为右,3为上,4为下
{
switch (MoveS)
{
case 1:MoveX = -1; MoveY = 0; MoveXP = -2; MoveYP = 0; break;
case 2:MoveX = 1; MoveY = 0; MoveXP = 2; MoveYP = 0; break;
case 3:MoveX = 0; MoveY = -1; MoveXP = 0; MoveYP = -2; break;
case 4:MoveX = 0; MoveY = 1; MoveXP = 0; MoveYP = 2; break;
}
if (GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] == Status::Status_Ground)//下一格为空地的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player;//在下一格为空地的情况下,设置下一位为玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
PlayerX += MoveX;
PlayerY += MoveY;
}
else if (GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] == Status::Status_Object)//下一格为箱子的情况
{
if (GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] == Status::Status_Ground)//下下格为空地的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player;//在下一格为箱子,下下格为空地的情况下,设置下一格为玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] = Status::Status_Object;//在下一格为箱子,下下格为空地的情况下,设置下下格为箱子
PlayerX += MoveX;
PlayerY += MoveY;
}
else if (GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] == Status::Status_Target)//下下格为目标的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player;//在下一格为箱子,下下格为目标的情况下,设置下一格为玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] = Status::Status_Object_On_Target;//在下一格为箱子,下下格为空地的情况下,设置下下格为目标上的箱子
PlayerX += MoveX;
PlayerY += MoveY;
}
}
else if (GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] == Status::Status_Object_On_Target)//下一格为目标上的箱子的情况
{
if (GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] == Status::Status_Ground)//下下格为空地的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player_On_Target;//在下一格为目标上的箱子,下下格为空地的情况下,设置下一格为目标上的玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] = Status::Status_Object;//在下一格为目标上的箱子,下下格为空地的情况下,设置下下格为箱子
PlayerX += MoveX;
PlayerY += MoveY;
}
else if (GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] == Status::Status_Target)//下下格为目标的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player_On_Target;//在下一格为目标上的箱子,下下格为目标的情况下,设置下一格为目标上的玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
GameStates[(PlayerX + MoveXP) * StateWidth + PlayerY + MoveYP] = Status::Status_Object_On_Target;//在下一格为目标上的箱子,下下格为目标的情况下,设置下下格为目标上的箱子
PlayerX += MoveX;
PlayerY += MoveY;
}
}
else if (GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] == Status::Status_Target)//下一格为目标的情况
{
GameStates[(PlayerX + MoveX) * StateWidth + PlayerY + MoveY] = Status::Status_Player_On_Target;//在下一格为目标的情况下,设置下一位为目标上的玩家
GameStates[PlayerX * StateWidth + PlayerY] = GameStates[PlayerX * StateWidth + PlayerY] == Status::Status_Player ? Status::Status_Ground : Status::Status_Target;//还原移动前的位置
PlayerX += MoveX;
PlayerY += MoveY;
}
}
Level GameState::GetState(int LevelId)//返回基础地图信息
{
return LocalLevel[LevelId];
}
Status* GameState::GetGameStates()//返回地图信息
{
return GameStates;
}
void GameState::InsertAction(char Keys)//输入控制
{
switch (Keys)
{
case 'w':case 'W':case 72:
MovePlayer(1); break;
case 's':case 'S':case 80:
MovePlayer(2); break;
case 'a':case 'A':case 75:
MovePlayer(3); break;
case 'd':case 'D':case 77:
MovePlayer(4); break;
}
}
bool GameState::CheckLevel()//判断是否通关
{
for (int i = 0; i < StateWidth * StateHeight; i++)
{
if (GameStates[i] == Status::Status_Object)
return false;
}
return true;
}
}
#endif
TANXL_CONSOLE_LIST.h
//TANXL_CONSOLE_LIST.H(ICUF_HEAD_07.H)
#ifndef TANXL_CONSOLE_LIST
#define TANXL_CONSOLE_LIST
#ifndef TANXL_LIST//检查是否使用了其他版本的TANXL_CONSOLE_LIST
#define TANXL_LIST 1
#define LIST 1
#else
#define LIST 0
#endif
#endif
#if LIST
#ifndef IOSTREAM//检查是否已经包含IOSTREAM
#define IOSTREAM
#include <iostream>
#endif
#ifndef STRING//检查是否已经包含STRING
#define STRING
#include <string>
#endif
#ifndef CONIO_H//检查是否已经包含CONIO_H
#define CONIO_H
#include <conio.h>
#endif
#ifndef IOMANIP//检查是否已经包含IOMANIP
#define IOMANIP
#include <iomanip>
#endif
namespace CONSOLE_LIST
{
const char* HeadFile = "HeadFile.txt";
inline void Col(int ColN)//设置自定义行的背景颜色
{
if (ColN == 0)std::cout << "\033[0m";//清除颜色
else
{
std::cout << "\033[4;1;7m";
if (ColN == 1)std::cout << "\033[31m";//背景红色
else if (ColN == 2)std::cout << "\033[32m";//背景绿色
else if (ColN == 3)std::cout << "\033[33m";//背景黄色
else if (ColN == 4)std::cout << "\033[34m";//背景蓝色
else if (ColN == 5)std::cout << "\033[35m";//背景紫色
else if (ColN == 6)std::cout << "\033[36m";//背景淡蓝
else if (ColN == 7)std::cout << "\033[37m";//背景白色
else if (ColN == 8)Col((rand() % 6) + 1);//随机颜色(1-7)
else if (ColN == 10)std::cout << "\033[40m";//字体黑色
else if (ColN == 11)std::cout << "\033[41m";//字体红色
else if (ColN == 12)std::cout << "\033[42m";//字体绿色
else if (ColN == 13)std::cout << "\033[43m";//字体黄色
else if (ColN == 14)std::cout << "\033[44m";//字体蓝色
else if (ColN == 15)std::cout << "\033[45m";//字体紫色
else if (ColN == 16)std::cout << "\033[46m";//字体淡蓝
else if (ColN == 17)std::cout << "\033[47m";//字体白色
else if (ColN == 18)Col((rand() % 6) + 11);//随机颜色(11-17)
}
}
typedef enum class Status
{
eMainList,
eSonList
}Status;
typedef class MainList
{
public:
void SetCol(int ColS, int ColU, int ColD = 7, int SonC = 6);//列表的背景颜色设置功能
void SetFont(int ColS, int ColU, int ColD, int SonC);//列表的字体颜色设置功能
void RecoverTimes();//复原被转移的Times值
void ResetTimes();//将Times的值转移到TempTimes
void InitList(int Start = 0);//列表初始化函数,默认初始化第一个选项为选定状态
void Append(std::string FunctionName, int Times = 1);//List数组添加String成员
void RemoveAll();//用于移除List数组中的所有String成员
void SetLimit(int Max);//设置每页的最大显示数量,超出范围则默认为9
void DisplayList(MainList List);//能够访问私有变量的子列表输出器
void SetListName(std::string Name);//设置列表的名称
void ShowTitle();//展示标题,标题背景色采用DefaultCol
void SetTitle(std::string Temp);//设置标题内容
void SetStatus(Status Sta);//设置页面级别
void SetSpace(int Left = 23, int Right = 17, int Title = 33);//设置空格数
int InsertAction();//输入控制(针对WASD、ZXC、↑↓←→以及数字1到9作出反应)
int DisplayList(int LStart = 0, int LEnd = 9, int Switch = 0, int Return = 0);//显示列表,两个默认参数表示显示的开始行和结束行
int DisplayListS(int LStart = 0, int LEnd = 9, int Return = 0);//子列表输出函数
int CheckCurrent();//找到当前指向的选项 当找不到时返回-1
int GetLimit();//获取每页的最大显示数量
int GetPages();//获取总页面数
int GetSonLists();//获取子页面选项数量
int GetTimes();//获取页面执行次数的值
int GetTimeS();//获取页面执行次数的值并在获取后加一
int GetTempTimes();//获取页面执行次数的临时值
Status GetStatus();//获取页面级别
std::string GetListName();//获取列表的名称
private:
void MoveUp();//选项上移
void MoveDown();//选项下移
int Times{};//用于计算某一函数的执行次数,同时用于限定某些代码只执行一次
int TempTimes{};//临时存放Times的值
int Page{ 1 };//当前指向的页面
int Pages{ 1 };//总页面数量
int LimitEachPage{ 9 };//页面选项上限
int SonLists{ 0 };//表示类中含有的字符串数量
int ListStatus[50]{ -1 };//存放选项状态
int SonCol{ 6 };//子列表背景颜色
int SelectedCol{ 7 };//选中的背景颜色
int UnSelectedCol{ 1 };//未选中的背景颜色
int DefaultCol{ 1 };//标题背景颜色
int SonFont{ 10 };//子列表字体颜色
int SelectedFont{ 10 };//选中的字体颜色
int UnSelectedFont{ 10 };//未选中的字体颜色
int DefaultFont{ 10 };//标题字体颜色
int WidthL{ 23 }, WidthR{ 17 }, WidthT{ 33 };//选项和标题的空格数
Status Stat{ Status::eSonList };//页面级别
std::string ListName;//列表的名称
std::string List[50]{};//存放选项名称
std::string Title{ "欢迎使用TANXL_CONSOLE_LIST WiChG_Trade" };//默认标题字符
}MainList;
inline void Free(MainList* Fun)//释放指针
{
delete Fun;
Fun = NULL;
}
void MainList::SetCol(int ColS, int ColU, int ColD, int SonC)//列表的背景颜色设置功能
{
this->SelectedCol = ColS;//选中物品栏的颜色
this->UnSelectedCol = ColU;//未选中的其他物品颜色
this->DefaultCol = ColD;//默认主题颜色
this->SonCol = SonC;//默认子列表颜色
}
void MainList::SetFont(int ColS, int ColU, int ColD, int SonC)//列表的字体颜色设置功能
{
this->SelectedFont = ColS;//选中物品栏的颜色
this->UnSelectedFont = ColU;//未选中的其他物品颜色
this->DefaultFont = ColD;//默认主题颜色
this->SonFont = SonC;//默认子列表颜色
}
void MainList::RecoverTimes()//复原被转移的Times值
{
this->Times += ++this->TempTimes;
this->TempTimes = 0;
}
void MainList::ResetTimes()//将Times的值转移到TempTimes
{
this->TempTimes += ++this->Times;
this->Times = 0;
}
void MainList::InitList(int Start)//列表初始化函数,默认初始化第一个选项为选定状态
{
for (int i = 0; i < SonLists; i++)
{
ListStatus[i] = 0;
}
for (int i = SonLists; i < 50; i++)
{
ListStatus[i] = -1;
}
ListStatus[Start] = 1;
}
void MainList::DisplayList(MainList TempList)
{
int Start = (TempList.Page - 1) * TempList.LimitEachPage;
int End = Start + TempList.LimitEachPage;
int UnSeCol = TempList.SonCol;
int UnSeFont = TempList.SonFont;
for (int i = Start; i < End + (9 - TempList.LimitEachPage); i++)
{
if (TempList.ListStatus[i] != -1)
{
if (TempList.ListStatus[i] == 1)
{
Col(TempList.SelectedCol);
Col(TempList.SelectedFont);
}
else
{
Col(UnSeCol);
Col(UnSeFont);
}
std::cout << std::setw(WidthL) << TempList.List[i] << std::setw(WidthR) << " " << std::endl;
Col(0);
}
}
std::cout << std::endl;
}
int MainList::DisplayList(int LStart, int LEnd, int Switch, int Return)//显示列表 ICUF_H_06中添加两个默认参数,可用于显示指定行
{
int Start = (Page - 1) * LimitEachPage;
int End = Start + LimitEachPage;
int UnSeCol = UnSelectedCol;
int UnSeFont = UnSelectedFont;
int ReturnS{};
if (Switch == 1)//Switch值为1时 显示此页面的各种基本信息
std::cout << "FunId: " << CheckCurrent() << " Limit: " << LimitEachPage << " Page: " << Page << " Start: " << Start << " End: " << End << std::endl << std::endl;
if (Switch == 2)//Switch值为2时 输出子页面的列表 且使用子页面的颜色
{
UnSeCol = SonCol;
UnSeFont = SonFont;
}
for (int i = Start + LStart; i < End + (LEnd - LimitEachPage); i++)
{
if (ListStatus[i] != -1)
{
if (ListStatus[i] == 1)
{
Col(SelectedCol);
Col(SelectedFont);
}
else
{
Col(UnSeCol);
Col(UnSeFont);
}
std::cout << std::setw(WidthL) << List[i] << std::setw(WidthR) << " " << std::endl;
if (Switch != 2)
std::cout << std::endl;
Col(0);
}
}
if (Switch == 2)
std::cout << std::endl;
if (Return != 0)
ReturnS = InsertAction();
else
return 0;
return ReturnS;
}
int MainList::InsertAction()//输入控制
{
char Key;
int Temp;
Key = _getch();
if (Key == 'c' || Key == 'C')//如果输入了大小写的C则返回上一级
return 3;
if (SonLists == 0)
return 0;
if ((int)(Key - 48) > 0 && (int)(Key - 48) <= 9)//判断是否是从零到九的数字
{
if ((int)(Key - 48) > SonLists)//如果是,且小于等于选项总数则直接指定这个选项
InitList(SonLists - 1);
else
InitList((int)(Key - 48) - 1);//如果超出了最大值,则指向最大值
return 4;
}
else if (Key == 'w' || Key == 'W' || Key == 72)//如果输入了大小写的W或者上箭头,则执行MoveUp函数
{
MoveUp();
return 0;
}
else if (Key == 's' || Key == 'S' || Key == 80)//如果输入了大小写的S或者下箭头,则执行MoveDown函数
{
MoveDown();
return 0;
}
else if (Key == 'a' || Key == 'A' || Key == 75)//如果输入了大小写的A或者左箭头,则执行向上翻页函数
{
if (Page == GetPages() && GetPages() == 1)
{
Temp = CheckCurrent();
ListStatus[Temp] = 0;
ListStatus[0] = 1;
}
else if (Page != 1)
{
Page--;
Temp = CheckCurrent();
ListStatus[Temp] = 0;
ListStatus[Temp - LimitEachPage] = 1;
}
else
{
Page = GetPages();
Temp = CheckCurrent();
ListStatus[Temp] = 0;
ListStatus[(Page - 1) * LimitEachPage] = 1;
}
return 0;
}
else if (Key == 'd' || Key == 'D' || Key == 77)//如果输入了大小写的D或者右箭头,则执行向下翻页函数
{
if (Page == GetPages() && GetPages() == 1)
{
Temp = CheckCurrent();
ListStatus[Temp] = 0;
ListStatus[SonLists - 1] = 1;
}
else if (Page != GetPages())
{
Page++;
Temp = CheckCurrent();
ListStatus[Temp] = 0;
if (Temp + LimitEachPage >= SonLists - 1)
ListStatus[SonLists - 1] = 1;
else
ListStatus[Temp + LimitEachPage] = 1;
}
else
{
Page = 1;
Temp = CheckCurrent();
ListStatus[Temp] = 0;
ListStatus[Temp % LimitEachPage] = 1;
}
return 0;
}
else if (Key == 'z' || Key == 'Z')//保留原功能的情况下,预留两个用户自定义返回值
{
return 1;
}
else if (Key == 'x' || Key == 'X')
{
return 2;
}
else if (Key == '\r')//回车确认
return 4;
return 0;
}
int MainList::CheckCurrent()//找到当前指向的选项 当找不到时返回-1
{
for (int j = 0; j < SonLists; j++)
{
if (ListStatus[j] == 1)
return j;
}
return -1;
}
void MainList::Append(std::string FunctionName, int Times)//List数组添加String成员
{
if (Times != 0)
return;
List[SonLists] = FunctionName;
SonLists += 1;//成员计数器
}
void MainList::RemoveAll()//用于移除List数组中的所有String成员
{
for (int i = 0; i < 10; i++)
{
List[i] = {};
SonLists = 0;
}
}
void MainList::SetLimit(int Max)//设置每页的最大显示数量,超出范围则默认为9
{
LimitEachPage = (Max > 9 || Max <= 0) ? 9 : Max;
}
int MainList::GetPages()//获取总页面数
{
if (SonLists % LimitEachPage != 0)
Pages = SonLists / LimitEachPage + 1;
else
Pages = SonLists / LimitEachPage;
return Pages;
}
int MainList::GetLimit()//获取每页的最大显示数量
{
return LimitEachPage;
}
void MainList::MoveUp()//选项上移
{
int i = CheckCurrent();//找到当前指向的选项
if (i == 0 && SonLists == 1)//如果只有一个选项则不变
ListStatus[i] = 1;
else if (i == 0 && SonLists != 1)//如果指向第一个且不止包含一个选项,则改为指向最下方的选项
{
ListStatus[i] = 0;
Page = GetPages();
ListStatus[SonLists - 1] = 1;
}
else if ((i + 1) % LimitEachPage == 1)//如果指向某一页面的第一项则翻页,并指向前一页的最后一项
{
if (Page != 1)
{
Page--;
ListStatus[i] = 0;
ListStatus[i - 1] = 1;
}
else
{
Page = GetPages();
ListStatus[i] = 0;
ListStatus[SonLists - 1] = 1;
}
}
else//正常情况
{
ListStatus[i] = 0;
ListStatus[i - 1] = 1;
}
}
void MainList::MoveDown()//选项下移
{
int i = CheckCurrent();//找到当前指向的选项
if (i == 0 && SonLists == 1)//如果只有一个选项则不变
ListStatus[i] = 1;
else if (i != 0 && i == SonLists - 1)//如果指向最后一个且不止包含一个选项,则改为指向最上方的选项
{
ListStatus[SonLists - 1] = 0;
Page = 1;
ListStatus[0] = 1;
}
else if ((i + 1) % LimitEachPage == 0)//如果指向某一页面的最后一项则翻页,并指向下一页的第一项
{
if (Page != GetPages())
{
Page++;
ListStatus[i] = 0;
ListStatus[i + 1] = 1;
}
else
{
Page = 1;
ListStatus[i] = 0;
ListStatus[0] = 1;
}
}
else//正常情况
{
ListStatus[i] = 0;
ListStatus[i + 1] = 1;
}
}
void MainList::SetListName(std::string Name)
{
this->ListName = Name;
}
std::string MainList::GetListName()
{
return this->ListName;
}
void MainList::SetTitle(std::string Temp)
{
Title = Temp;
}
void MainList::ShowTitle()
{
Col(DefaultCol); Col(DefaultFont);
std::cout << std::endl << std::endl << std::endl << std::endl;
std::cout << std::setw(WidthL) << " " << std::setw(WidthT) << Title << std::setw(WidthR) << " " << std::endl << std::endl; Col(0);
}
int MainList::DisplayListS(int LStart, int LEnd, int Return)//显示列表 ICUF_H_06中添加两个默认参数,可用于显示指定行
{
int Start = (Page - 1) * LimitEachPage;
int End = Start + LimitEachPage;
int ReturnS{};
for (int i = Start + LStart; i < End + (LEnd - LimitEachPage); i++)
{
if (ListStatus[i] != -1)
{
if (ListStatus[i] == 1)
{
Col(SelectedCol);
Col(SelectedFont);
}
else
{
Col(SonCol);
Col(SonFont);
}
std::cout << std::setw(WidthL) << List[i] << std::setw(WidthR) << " " << std::endl;
Col(0);
}
}
std::cout << std::endl;
if (Return != 0)
ReturnS = InsertAction();
else
return 0;
return ReturnS;
}
int MainList::GetSonLists()
{
return SonLists;
}
int MainList::GetTimes()
{
return Times;
}
int MainList::GetTimeS()
{
return Times++;
}
int MainList::GetTempTimes()
{
return TempTimes;
}
void MainList::SetStatus(Status Sta)
{
Stat = Sta;
}
Status MainList::GetStatus()
{
return Stat;
}
void MainList::SetSpace(int Left, int Right, int Title)
{
WidthL = Left;
WidthR = Right;
WidthT = Title;
}
}
#endif
GAME.cpp
#include"TANXL_GAME_STATE.h"
#include"TANXL_CONSOLE_LIST.h"
#ifndef IOSTREAM
#define IOSTREAM
#include<iostream>
#endif
#ifndef CONIO_H
#define CONIO_H
#include <conio.h>
#endif
void Game(int X);
void Title();
using namespace std;
CONSOLE_LIST::MainList MainPage;
GAME_STATE::GameState TANXL_GAME;
int main(int T=1)
{
if (T == 1)
Title();
TANXL_GAME.DefaultLevel();
for (int i = 0; i < 5; i++)
{
if (TANXL_GAME.CheckFile(TANXL_GAME.GetFileName(i)))
MainPage.Append(TANXL_GAME.GetFileName(i), MainPage.GetTimes());
}
MainPage.SetTitle("欢迎来到C++控制台推箱子 WiChG_Game");
MainPage.GetTimeS();
MainPage.InitList();
MainPage.SetCol(4, 6, 4);
MainPage.SetFont(15, 16, 15, 15);
int Level{};
while (1)
{
system("cls");
MainPage.ShowTitle();
int i = MainPage.DisplayList(0, 9, 0, 1);
if (i == 4)
{
Level = MainPage.CheckCurrent();
Game(Level);
}
TANXL_GAME.ClearState();
}
TANXL_GAME.ClearState();
system("pause");
return 0;
}
void Title()
{
int a{ 1 }, b{ 2 };
cout << endl << endl << endl << endl;
CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " " << endl; CONSOLE_LIST::Col(0);
CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " " << endl; CONSOLE_LIST::Col(0);
CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " " << endl; CONSOLE_LIST::Col(0);
CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " " << endl; CONSOLE_LIST::Col(0);
CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " "; CONSOLE_LIST::Col(a); cout << " "; CONSOLE_LIST::Col(b); cout << " " << endl; CONSOLE_LIST::Col(0);
cout << endl << endl << endl << endl;
CONSOLE_LIST::Col(a); cout << " "; system("pause"); CONSOLE_LIST::Col(0);
}
void Game(int Level)
{
while (1)
{
TANXL_GAME.GetFileLevel(Level);
while (!TANXL_GAME.CheckLevel())
{
system("cls");
cout << endl << endl << endl << endl;
for (int i = 0; i < TANXL_GAME.GetState(Level).Height; i++)
{
cout << " ";
for (int j = 0; j < TANXL_GAME.GetState(Level).Width; j++)
{
if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 0)
CONSOLE_LIST::Col(1);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 1)
CONSOLE_LIST::Col(2);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 2)
CONSOLE_LIST::Col(3);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 3)
CONSOLE_LIST::Col(4);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 4)
CONSOLE_LIST::Col(5);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 5)
CONSOLE_LIST::Col(6);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 6)
CONSOLE_LIST::Col(7);
cout << " ";
}
cout << endl;
CONSOLE_LIST::Col(0);
}
char c = _getch();
if (c == 'c' || c == 'C')
main(0);
TANXL_GAME.InsertAction(c);
}
system("cls");
cout << endl << endl << endl << endl;
for (int i = 0; i < TANXL_GAME.GetState(Level).Height; i++)
{
cout << " ";
for (int j = 0; j < TANXL_GAME.GetState(Level).Width; j++)
{
if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 0)
CONSOLE_LIST::Col(1);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 1)
CONSOLE_LIST::Col(2);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 2)
CONSOLE_LIST::Col(3);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 3)
CONSOLE_LIST::Col(4);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 4)
CONSOLE_LIST::Col(5);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 5)
CONSOLE_LIST::Col(6);
else if ((int)TANXL_GAME.GetGameStates()[i * TANXL_GAME.GetState(Level).Width + j] == 6)
CONSOLE_LIST::Col(7);
cout << " ";
}
cout << endl;
CONSOLE_LIST::Col(0);
}
cout << endl << endl << endl;
cout << " ";
CONSOLE_LIST::Col(1); cout << " 恭喜过关 进入下一关? Y/N" << endl; CONSOLE_LIST::Col(0);
char c = _getch();
switch (c)
{
case 'y':case'Y':
if (Level < 4)
{
Level++;
}
else Level = 0;
continue;
case 'n':case'N':
Level = -1; main(0);
}
if (Level == -1)
main(0);
}
}