KeyWord : Csv、CCFileUtils
在一个游戏中,通常会有很多怪物、关卡、技能等数据,这些数据不可能在代码里写死,一般都会使用配置文件保存,使用时再加在到
内存。
这次,要给大家介绍在项目里常常使用的一个配置文件——Csv格子文件。
Csv文件其实很简单,它就是一组只用逗号分隔开的字符串,如图:
看起来像是excel文件一样,但是当我们用记事本打开Monster.csv时,可以看到:
我们看到,每一行的字符串都是用逗号分隔,除此之外没有任何多余的格式。
Csv格式的文件除了文件占用空间小之外,还有一个很重要的优点:方便程序解析。
创建一个Csv文件
首先,用微软的office办公软件新建一个Excel文件(或者WPS文档),命名为Monster.xls (Monster.et),然后打开创建的文件,单击菜单 [文件] -> [另存为] ,然后
选择Csv格式文件,如图:
编写字符串工具类——分离字符串
我们创建一个项目,再新建一个类,命名为StringUtil,先看下这个类的头文件:
StringUtil.h:
该类只有一个功能,就是拆分字符串。再来看看StringUtil的实现:
StringUtil.cpp:
我们来测试一下,看看StringUtil是否正常地工作,修改HelloWorldScene的init函数,代
码如下:
调试模式下运行项目,可看到日志输出:
可见,StringUtil正确地拆分了字符串。
接下来,我们马上开始解析Csv文件。
辅助工具——编写文本读写工具类
由于我们的配置文件一行就是一条数据,比如Monster.csv文件,第一行是怪物笨木头的数据,第二行是怪物旁白小若的数据。
因此,我们还需要再写一个类,这个类很简单,负责把一个文件按行加载,保存到CCArray里。
新建一个类,命名为FileLoadUtil,先看头文件:
依旧是一个单例类,只有一个函数,也就是我们刚刚说的,将文件按行存放到一个列表中。再来看看函数实现:
FileLoadUtil.cpp:
CCFileUtils是Cocos2d-x提供的用于文件操作的工具类,使用CCFileUtils的getFileData函数可以
读取
文件并保存为字符对象,然后再把
字符用CCString包装起来,得到一个CCString对象,最后就可
以使
用我们的StringUtil的split函数了。通过换行符将文本按行分隔,保存
到列表里。
getDataLines函数最终返回的列表如下:
编写Csv文件读写工具类
好了,我们要真正开始编写Csv文件读取工具类了。
新建一个类,命名为CsvUtil,来看看头文件:
这个类看起来有点复杂,我们先来看loadFile函数的实现:
loadFile做了三件事情:
(1)将csv文件按行读取保存到列表中,如:
(2)将第一步中的每一行字符串按逗号分隔,保存到列表里,如:
(3)用一个CCDictionary对象保存csvStrList和文件路径sPath的对应关系
我们再来看看第二个重要的函数,代码如下:
getFileRowColNum函数用于获取Csv文件的行和列的数量,由于我们是按行存放文件数据的,所以列
表的大小就是文件行的数量,而每一行又存放一组数据,因此,某行的一组数据列表的大小,就是文
件列的数量。
总结一下:loadFile函数存放文件数据的逻辑
(1)有一个CCDictionary类型的mCsvDict变量,存放一个csvStrList列表和Csv文件名的对应关系:
mCsvDict->setObject(csvStrList,sPath);
(2)csvStrList列表为CCArray类型,存放Csv文件每一行的数据,每一行的数据又由一个tArr列表
保存;
(3)tArr列表保存的是一个个的CCString对象,如ID Name Level HP MP HappyValue。
反过来,加载了Csv文件之后,读取文件数据的情况就是这样:
(1)根据文件名sPath从mCsvDict字典中获取一个csvStrList列表;
(2)csvStrList列表保存了Csv文件每一行的数据;
(3)如果要获取Csv文件第一行的数据,则取得csvStrList列表的第一行,取出来的值又是一个 列表tArr;
(4)tArr里保存了第一行的所有数据,这些数据以CCString类型保存
最后,再解释一个很重要的函数,代码如下: