MC新手入门(四十九)------ 文件操作
来源:互联网 发布:python项目开发实例 编辑:程序博客网 时间:2024/06/11 02:42
文件操作
就像看书一样,我们并不会总是一次性把游戏玩通关,往往需要做个记号,下次再继续。在单机游戏里,通常的记录方法就是做一个存档文件,把游戏里跟进度有关的参数存下来,然后下次读取存档的时候根据这些参数来还原上一次退出时的进度。在保存和读取存档的时候,就要用到文件操作的方法来实现。
相信大家都接触过不少单机RPG游戏吧,那么我们就以火焰纹章为例,来介绍一文件操作的在游戏中的实际应用。
下面我们将为你展示在MC中实现这种功能的方法。
相关函数
对文件的操作主要有以下几种:打开、关闭、读取、写入、修改、删除。下面根据不同的功能将函数一一列出。
Var文件的基本操作
Var_OpenFile
void* Var_OpenFile(const char *fileName, char *mode);
功能: 打开一个Var文件。打开成功返回该文件的指针,打开失败返回0, 如果模式为“r+”时且没有该文件,也同样返回0
参数:
fileName :代表文件名。
mode: 模式与C语言的模式相同,但需要注意的是,只能使用二进制文件的读写,即如果读文件模式为 “rb”;写文件模式为 “wb”;读写文件,且不覆盖原文件的模式为“rb+”;读写文件,并覆盖原文件的模式为“wb+”文件。
Var_CloseFile
int Var_CloseFile(void *fp);
功能: 关闭一个Var文件,关闭成功返回1,关闭失败返回0。
参数:
fileName:代表文件名。
Var_GetOneDimArraySize
int Var_GetOneDimArraySize(void *fp, char *variableName, int *arraySize);
功能:从文件中获得名为variableName的一维数组的大小。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针。
variableName:要读取的变量名。
arraySize:接收读取到的数组的大小。
Var_GetTwoDimArraySize
int Var_GetTwoDimArraySize(void *fp, char *variableName, int *rows, int *cols);
功能:从文件中获得名为variableName的二维数组的行数和列数。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针
variableName:要读取的变量名。
rowSize:接收该数组的行数。
colSize:接受该数组的列数。
Var文件的读操作
Var_ReadData
int Var_ReadData(void *fp, char *variableName, void *acceptVariable, int dataFlag);
功能:从文件中读取名为variableName的整数,或是一维整型数组。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针
variableName:要读取的变量名。
acceptVariable:接收读取到的数据。
dataFlag:值为0表示Int型, 1 表示Double型,2表示String型,3表示Char型
Var_ReadPart
int Var_ReadPart(void *fp, char *variableName, void *acceptVariable, int startIndex, int endIndex, int dataFlag);
功能:从文件中读取名为variableName的数组中的部分数据。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针。
variableName:要读取的变量名。
acceptVariable:接收读取到的数据。
startIndex:文件中变量的开始下标。
endIndex:文件中变量的结束下标。
dataFlag:值为0表示Int型,1 表示Double型,2表示String型,3表示Char型。
Var文件的写操作
Var_WriteData (会先删除掉文件中已有的变量)
int Var_WriteData(void *fp, char *variableName, char *groupName, void *writeVariable, int dataRows, int dataCols, int spaceRows, int spaceCols, int dataFlag);
功能:从文件中写入名为variableName,组为groupName的整数, 或是一维整型数组。返回1代表写入成功,返回0代表写入失败。
参数:
fp:文件的指针。
variableName:要写入的变量名。
groupName:变量的组名。
writeVariable:要写入的数据。
dataRows:要写入数据的行数。若为单个数据或一维数组,那么值为1。
dataCols:要写入数据的列数,若为单个数据,那么值等于1,如果为一维数组那么值大于1。
spaceRows:数据要开辟的行数。若为单个数据或一维数组,那么值为1。
spaceCols:数据要开辟的列数。若为单个数据,那么值等于1,如果为一维数组那么值大于1。
dataFlag:值为0表示int型,1 表示double型,2表示string型,3表示char型。
Var_WritePart
int Var_WritePart(void *fp, char *variableName, char *groupName, void *writeVariable, int startIndex, int endIndex, int dataFlag);
功能:从文件中写入名为variableName,组为groupName的一维整型数组中的部分数据。返回1代表写入成功,返回0代表写入失败。
参数:
fp:文件的指针。
variableName:要写入的变量名。
groupName:变量的组名。
writeVariable:要写入的数据。
startIndex:一维数组中表示文件中变量的开始下标, 二维数组中表示文件中变量的开始行下标。
endIndex:一维数组中表示文件中变量的结束下标, 二维数组中表示文件中变量的结束行下标。
dataFlag:值为0表示Int型,1 表示Double型,2表示String型,3表示Char型。
Var文件记录的删除操作
Var_DelateVariable
int Var_DelateVariable(void *fp, char *variableName);
功能:从文件中删除变量variableName,返回1代表删除成功,返回0代表删除失败。
参数:
fp:文件的指针。
variableName:要删除的变量。
Var_DelateFile
int Var_DelateFile(const char *FileName);
功能:删除该文件。返回1代表删除成功,返回0代表删除失败。
参数:
FileName:文件的名字
实例运用
在这里我们要模拟实现RPG游戏通常用到的存储,我们将创建一个玩家角色,以下记录的数据:人物所在坐标,姓名,金币,经验值,包裹信息。当我们捡起硬币、经验块或者物品的时候,对应的数值会增加。通过保存按钮,将这些数据写入文档,通过读取来还原现场。
下面进行实例的制作。
第一步,按照图示,摆好各个角色
在脚本中添加自定义变量,如下所示:
cha_name:
sprintf(text, ”Name:%s”, strName);
cha_gold:
sprintf(text, ”Gold:%d”, iGold);
cha_exp:
sprintf(text, ”Exp:%d”, iExp);
cha_pos:
sprintf(text, ”(%d,%d)”, actPlayer. x, image0. y);
bag_1:
sprintf(text, ”x%d”, iBag[0]);
bag_2:
sprint(text, “x%d”, iBag[1]);
gold,exp,wood,box这四个角色模拟场景中的宝物,用于捡取以改变角色的数据。这里不做捡取后消失的设定,故对这四个角色添加“物体碰撞”事件,碰撞条件“任何边沿”。其脚本如下:
actGold:
iGold += 100;
actExp:
iExp += 100;
actItem1:
iBag[0] += 1;
actItem2:
iBag[1] += 1;
对actPlayer角色,添加如下五个事件:
①“绘制角色”事件,添加“脚本编辑器”行为
代码:
//初始化站位
x = 0;
y = 0;
②上下左右四个“按键按下”事件,“脚本编辑器”行为
由于图片尺寸为33x33,所以偏移量统一设置成33。
上: 下: 左: 右:
y -= 33; y += 33; x -= 33; x += 33;
btnSave角色,用于存储数据,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
int size;
//打开文件
FILE *fp = Var_OpenFile("cha.sav", "wb");
//对角色命名并保存
strcpy(strName,"Nero");
Var_WriteData(fp, "cha_name", "player", &strName, 1, 10, 1, 10, 2);
//保存黄金数
Var_WriteData(fp, "cha_gold", "player", &iGold, 1, 1, 1, 1, 0);
//保存经验值
Var_WriteData(fp, "cha_exp", "player", &iExp, 1, 1, 1, 1, 0);
//先判断是否创建过坐标,通过读取cha_pos的位数来判断,然后进行写入,其中,写入的函数是不一样的
Var_GetOneDimArraySize(fp, "cha_pos", &size)
if( size != 2 )
{
iPos[0] = actPlayer.x;
iPos[1] = actPlayer.y;
Var_WriteData(fp, "cha_pos", "player", &iPos, 1, 2, 1, 2, 0);
}
else
{
iPos[0] = image0.x;
iPos[1] = image0.y;
Var_WritePart(fp, "cha_pos", "player", &iPos[0], 0, 0, 1);
Var_WritePart(fp, "cha_pos", "player", &cha_pos[1], 1, 1, 1);
}
//存储包裹信息
Var_WriteData(fp, "cha_bag", "player", &iBag, 1, 2, 1, 2, 0);
//关闭文件
Var_CloseFile(fp);
btnLoad角色,用于读取存档,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
//打开文件
FILE *fp = Var_OpenFile("cha.sav", "rb");
//读取操作
Var_ReadData(fp, "cha_name", &strName, 2);
Var_ReadData(fp, "cha_gold", &iGold, 0);
Var_ReadData(fp, "cha_exp", &iExp, 0);
Var_ReadPart(fp, "cha_pos", &iPos[0], 0, 0, 0);
Var_ReadPart(fp, "cha_pos", &iPos[1], 1, 1, 0);
actPlayer.x = iPos[0];
actPlayer.y = iPos[1];
Var_ReadData(fp, "cha_bag", &iBag, 0);
Var_CloseFile(fp) ;
btnDel角色,用于删除存档,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
FILE *fp = Var_OpenFile("cha.sav", "wb+") ;
//这是删除变量使用的,在不删除文件的情况下使用
Var_DelateVariable(fp, "cha_pos") ;
Var_CloseFile(fp) ;
//这是删除存档文件,这里只是列出使用方法,具体做法酌情而定
Var_DelateFile("cha.sav") ;
现在,编码结束,可以导出文件进行测试了。
运行以后,我们可以通过方向键控制角色小人的移动,通过吃宝物增加财富或者能力或者物品,数值在屏幕左上方显示,通过保存按钮可以生成存档文件,保存当前状态,点击读取按钮将读取存档文件,还原保存时的状态与数据,删除按钮会删除存档文件。
就像看书一样,我们并不会总是一次性把游戏玩通关,往往需要做个记号,下次再继续。在单机游戏里,通常的记录方法就是做一个存档文件,把游戏里跟进度有关的参数存下来,然后下次读取存档的时候根据这些参数来还原上一次退出时的进度。在保存和读取存档的时候,就要用到文件操作的方法来实现。
相信大家都接触过不少单机RPG游戏吧,那么我们就以火焰纹章为例,来介绍一文件操作的在游戏中的实际应用。
图9-4-1
在图中,我们能看到两个角色站在地图上的特定位置,并且这两个人物也是有区别的,他们的外形,血量,移动距离等等的属性都不尽相同。当我们要对游戏当前的状态进行保存时,我们需要关注的数据就包括:地图代号,人物代号,位置坐标,人物各项属性等。那么,只要把这些与状态相关的数据写入到存档文件,读取存档的时候就能够根据这些数据还原游戏保存之前的状态。下面我们将为你展示在MC中实现这种功能的方法。
相关函数
对文件的操作主要有以下几种:打开、关闭、读取、写入、修改、删除。下面根据不同的功能将函数一一列出。
Var文件的基本操作
Var_OpenFile
void* Var_OpenFile(const char *fileName, char *mode);
功能: 打开一个Var文件。打开成功返回该文件的指针,打开失败返回0, 如果模式为“r+”时且没有该文件,也同样返回0
参数:
fileName :代表文件名。
mode: 模式与C语言的模式相同,但需要注意的是,只能使用二进制文件的读写,即如果读文件模式为 “rb”;写文件模式为 “wb”;读写文件,且不覆盖原文件的模式为“rb+”;读写文件,并覆盖原文件的模式为“wb+”文件。
Var_CloseFile
int Var_CloseFile(void *fp);
功能: 关闭一个Var文件,关闭成功返回1,关闭失败返回0。
参数:
fileName:代表文件名。
Var_GetOneDimArraySize
int Var_GetOneDimArraySize(void *fp, char *variableName, int *arraySize);
功能:从文件中获得名为variableName的一维数组的大小。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针。
variableName:要读取的变量名。
arraySize:接收读取到的数组的大小。
Var_GetTwoDimArraySize
int Var_GetTwoDimArraySize(void *fp, char *variableName, int *rows, int *cols);
功能:从文件中获得名为variableName的二维数组的行数和列数。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针
variableName:要读取的变量名。
rowSize:接收该数组的行数。
colSize:接受该数组的列数。
Var文件的读操作
Var_ReadData
int Var_ReadData(void *fp, char *variableName, void *acceptVariable, int dataFlag);
功能:从文件中读取名为variableName的整数,或是一维整型数组。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针
variableName:要读取的变量名。
acceptVariable:接收读取到的数据。
dataFlag:值为0表示Int型, 1 表示Double型,2表示String型,3表示Char型
Var_ReadPart
int Var_ReadPart(void *fp, char *variableName, void *acceptVariable, int startIndex, int endIndex, int dataFlag);
功能:从文件中读取名为variableName的数组中的部分数据。返回1代表读取成功,返回0代表读取失败。
参数:
fp:文件的指针。
variableName:要读取的变量名。
acceptVariable:接收读取到的数据。
startIndex:文件中变量的开始下标。
endIndex:文件中变量的结束下标。
dataFlag:值为0表示Int型,1 表示Double型,2表示String型,3表示Char型。
Var文件的写操作
Var_WriteData (会先删除掉文件中已有的变量)
int Var_WriteData(void *fp, char *variableName, char *groupName, void *writeVariable, int dataRows, int dataCols, int spaceRows, int spaceCols, int dataFlag);
功能:从文件中写入名为variableName,组为groupName的整数, 或是一维整型数组。返回1代表写入成功,返回0代表写入失败。
参数:
fp:文件的指针。
variableName:要写入的变量名。
groupName:变量的组名。
writeVariable:要写入的数据。
dataRows:要写入数据的行数。若为单个数据或一维数组,那么值为1。
dataCols:要写入数据的列数,若为单个数据,那么值等于1,如果为一维数组那么值大于1。
spaceRows:数据要开辟的行数。若为单个数据或一维数组,那么值为1。
spaceCols:数据要开辟的列数。若为单个数据,那么值等于1,如果为一维数组那么值大于1。
dataFlag:值为0表示int型,1 表示double型,2表示string型,3表示char型。
Var_WritePart
int Var_WritePart(void *fp, char *variableName, char *groupName, void *writeVariable, int startIndex, int endIndex, int dataFlag);
功能:从文件中写入名为variableName,组为groupName的一维整型数组中的部分数据。返回1代表写入成功,返回0代表写入失败。
参数:
fp:文件的指针。
variableName:要写入的变量名。
groupName:变量的组名。
writeVariable:要写入的数据。
startIndex:一维数组中表示文件中变量的开始下标, 二维数组中表示文件中变量的开始行下标。
endIndex:一维数组中表示文件中变量的结束下标, 二维数组中表示文件中变量的结束行下标。
dataFlag:值为0表示Int型,1 表示Double型,2表示String型,3表示Char型。
Var文件记录的删除操作
Var_DelateVariable
int Var_DelateVariable(void *fp, char *variableName);
功能:从文件中删除变量variableName,返回1代表删除成功,返回0代表删除失败。
参数:
fp:文件的指针。
variableName:要删除的变量。
Var_DelateFile
int Var_DelateFile(const char *FileName);
功能:删除该文件。返回1代表删除成功,返回0代表删除失败。
参数:
FileName:文件的名字
实例运用
在这里我们要模拟实现RPG游戏通常用到的存储,我们将创建一个玩家角色,以下记录的数据:人物所在坐标,姓名,金币,经验值,包裹信息。当我们捡起硬币、经验块或者物品的时候,对应的数值会增加。通过保存按钮,将这些数据写入文档,通过读取来还原现场。
下面进行实例的制作。
第一步,按照图示,摆好各个角色
图9-4-2-1
第二步:给各角色添加脚本和自定义变量在脚本中添加自定义变量,如下所示:
图9-4-2-2
其中,cha_name,cha_gold,cha_exp,cha_pos,bag_1,bag_2这六个角色是用来显示数值的,对他们都添加“绘制角色”事件。cha_name:
sprintf(text, ”Name:%s”, strName);
cha_gold:
sprintf(text, ”Gold:%d”, iGold);
cha_exp:
sprintf(text, ”Exp:%d”, iExp);
cha_pos:
sprintf(text, ”(%d,%d)”, actPlayer. x, image0. y);
bag_1:
sprintf(text, ”x%d”, iBag[0]);
bag_2:
sprint(text, “x%d”, iBag[1]);
gold,exp,wood,box这四个角色模拟场景中的宝物,用于捡取以改变角色的数据。这里不做捡取后消失的设定,故对这四个角色添加“物体碰撞”事件,碰撞条件“任何边沿”。其脚本如下:
actGold:
iGold += 100;
actExp:
iExp += 100;
actItem1:
iBag[0] += 1;
actItem2:
iBag[1] += 1;
对actPlayer角色,添加如下五个事件:
①“绘制角色”事件,添加“脚本编辑器”行为
代码:
//初始化站位
x = 0;
y = 0;
②上下左右四个“按键按下”事件,“脚本编辑器”行为
由于图片尺寸为33x33,所以偏移量统一设置成33。
上: 下: 左: 右:
y -= 33; y += 33; x -= 33; x += 33;
btnSave角色,用于存储数据,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
int size;
//打开文件
FILE *fp = Var_OpenFile("cha.sav", "wb");
//对角色命名并保存
strcpy(strName,"Nero");
Var_WriteData(fp, "cha_name", "player", &strName, 1, 10, 1, 10, 2);
//保存黄金数
Var_WriteData(fp, "cha_gold", "player", &iGold, 1, 1, 1, 1, 0);
//保存经验值
Var_WriteData(fp, "cha_exp", "player", &iExp, 1, 1, 1, 1, 0);
//先判断是否创建过坐标,通过读取cha_pos的位数来判断,然后进行写入,其中,写入的函数是不一样的
Var_GetOneDimArraySize(fp, "cha_pos", &size)
if( size != 2 )
{
iPos[0] = actPlayer.x;
iPos[1] = actPlayer.y;
Var_WriteData(fp, "cha_pos", "player", &iPos, 1, 2, 1, 2, 0);
}
else
{
iPos[0] = image0.x;
iPos[1] = image0.y;
Var_WritePart(fp, "cha_pos", "player", &iPos[0], 0, 0, 1);
Var_WritePart(fp, "cha_pos", "player", &cha_pos[1], 1, 1, 1);
}
//存储包裹信息
Var_WriteData(fp, "cha_bag", "player", &iBag, 1, 2, 1, 2, 0);
//关闭文件
Var_CloseFile(fp);
btnLoad角色,用于读取存档,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
//打开文件
FILE *fp = Var_OpenFile("cha.sav", "rb");
//读取操作
Var_ReadData(fp, "cha_name", &strName, 2);
Var_ReadData(fp, "cha_gold", &iGold, 0);
Var_ReadData(fp, "cha_exp", &iExp, 0);
Var_ReadPart(fp, "cha_pos", &iPos[0], 0, 0, 0);
Var_ReadPart(fp, "cha_pos", &iPos[1], 1, 1, 0);
actPlayer.x = iPos[0];
actPlayer.y = iPos[1];
Var_ReadData(fp, "cha_bag", &iBag, 0);
Var_CloseFile(fp) ;
btnDel角色,用于删除存档,添加左键“鼠标键按下”事件,“脚本编辑器”行为
代码:
FILE *fp = Var_OpenFile("cha.sav", "wb+") ;
//这是删除变量使用的,在不删除文件的情况下使用
Var_DelateVariable(fp, "cha_pos") ;
Var_CloseFile(fp) ;
//这是删除存档文件,这里只是列出使用方法,具体做法酌情而定
Var_DelateFile("cha.sav") ;
现在,编码结束,可以导出文件进行测试了。
运行以后,我们可以通过方向键控制角色小人的移动,通过吃宝物增加财富或者能力或者物品,数值在屏幕左上方显示,通过保存按钮可以生成存档文件,保存当前状态,点击读取按钮将读取存档文件,还原保存时的状态与数据,删除按钮会删除存档文件。
本例只使用了整型和字符串数据,而上述的函数还能对实型和字符型数据进行处理,这些在未来的实践中慢慢体会吧。
Demo下载地址:http://www.dongyo.cn/bbs/forum.php?mod=viewthread&tid=2531&extra=page%3D1%26filter%3Dauthor%26orderby%3Ddateline%26orderby%3Ddateline
- MC新手入门(四十九)------ 文件操作
- MC新手入门(十六)------ 按键操作
- MC新手入门(一)-----角色
- MC新手入门(二)------路径
- MC新手入门(三十三)------ 数组
- MC新手入门(三十四)------ 函数
- MC新手入门(三十六)------ 指针
- MC新手入门(三)------活动区域
- MC新手入门(四)------设置、角色面板
- MC新手入门(五)------特殊属性
- MC新手入门(六)------动画设置
- MC新手入门(七)------文本设置
- MC新手入门(八)------特性设置
- MC新手入门(九)------物理属性
- MC新手入门(十)------事件设置
- MC新手入门(十二)------ 色彩色调
- MC新手入门(十三)------ 添加游戏角色
- MC新手入门(十四)------ 游戏帧事件
- poj 1067 博弈论
- linux 添加支持 U 盘热拔插功能
- pictureEdit 可以直接绑定Image 或者 Byte Array
- 解决subActivity里弹出框报错问题
- MFC中写文件时,如何将文件的属性修改为Unicode编码
- MC新手入门(四十九)------ 文件操作
- 谷歌开发工具android studio启动不了的解决方法
- 对于输入字符串数组的处理,三维数组
- 复选框单选
- CLR线程池的作用与原理介绍
- 【Linux操作系统分析】计算机是怎样工作的
- latex 如何使用bib产生多种文献格式
- dimension reduce(梯度下降)self-organizing maps(自组织映射)
- MC新手入门(五十)------服务器连接 一