序言
在游戏开发过程中,需要提供一套配置数据的解决方案。这套解决方案中,就包含了配表数据
有两种配表的形式我比较认可:
- 提供一个数据的在线管理平台,此平台提供了一套数据维护的解决方案
- 使用Excel表格,对数据进行配置
对于1而言,它对数据做了有效的保护,能够配置用户的权限,对于有保密需求的公司而言,是一个很好的选择。不足之处是,提供此套解决方案的成本过高。
对于2而言,基本没有开发的成本,维护人员在掌握了配表规则后,可以非常方便的使用,缺点是,数据的访问权限完全开放。
若未特别声明,本文所指的配表数据就是指Excel的.xls
格式的配表数据,以及将其转换为程序所使用的.lua
格式的配表数据
围绕着配表数据,本篇将从以下几个要点进行讲述:
.xls
配表的需求分析
-
.xls
配表的设计 -
.lua
格式的配表数据的格式设计 -
.lua
格式的配表数据的生成工具
.xls
配表数据的需求分析
我们先来看看配置人员是如何配置.xls
表格的:
- 导航到配置数据的文件夹路径
- 新建一份.xls表格,对其命名
- 打开.xls文件,能够设置属性字段、配置属性数值
- 能够建立不同的sheet,每一个sheet能够配置是否导出到
.lua
文件(.lua
文件是提供给程序使用的文件) - 使用导出工具,导出到
.lua
文件,提供给相关人员使用
从配置的过程,我们分析并确定了我们需要完成的任务:
- 提供
.xls
配表的文件框架 - 提供
.xls
配表文件的命名规范 - 提供
.xls
配表文件的表格格式 - 提供
.xls
配表文件的导出配置 - 提供
.xls
配置文件导出到.lua
的工具
.xls
配表的设计
于是我们给出了我们的.xls
配表的设计方案:
- 配置人员在指定的文件夹
xls
下进行表格的配置 - 此文件夹下只有
.xls
文件,不允许出现子文件夹,文件命名为[module1][_module2].xls
,其中module1, module2为模块标识,如
文件夹 PATH 列表
卷序列号为 000E-EB46
C:.
└─xls
example_building.xls
object_monster.xls
object_role.xls
system_daily.xls
我们通过文件名,就可以方便的知道:
object
模块下有子模块monster
、role
的配置.
system
模块有子模块daily
的配置.
-
.xls
配置格式
以example_building.xls
为例
id | name | use_money | use_food | is_init | defense | args1 | args2 | args3 | args4 |
---|---|---|---|---|---|---|---|---|---|
i | s | i | f | b | i | ai | af | as | ab |
编号 | 名称 | 金钱消耗 | 食物消耗 | 是否初始化 | 防御 | 数组1 | 数组2 | 数组3 | 数组4 |
1 | house | 1000 | 2.33 | TRUE | 100 | 1;2;3 | 1.23;2;3.23 | sdf;23e;s | true;false;true |
2 | house2 | 123 | 336.2 | TRUE | 1;2;3 | 1.23;2;3.23 | 你好;你在哪 | true;false | |
3 | 456 | 222.33665 | FALSE | 130 | 3;2;5;; | 1.23;2;3.23 | 我在这里啊;你在那;呢 | false;true | |
4 | farm | 100 | 220 | FALSE | 200 | 2;3 | 1.23;2;3.23 | df;ssd;dd;dd | |
5 | house5 | 22.1 | 2343;6;6;;;7 | 3;6.3;6;;;7 | 1.23;2;3.23 | true;true | |||
6 | horse6 | 200 | FALSE | 333 | 2e;w;e;we | false;false;false;false |
Note:
第一行是属性字段名,可用的字符集为(英文字母+数字+下划线),满足通常意义下的变量命名规范
第二行是类型声明
第三行是备注——不导出到最后的数据中
- 导出设置
在.xls
文件中,我们将一个sheet命名为output_xxxx,那么在后续的导出工具中,就会得到一个名为xxxx.lua
的文件,如果当前的.xls
中,有多个以output_开头的sheet,那么就会导出多个对应的.lua
文件。
.lua
格式的配表数据的设计
这里给出一个生成的结果,再解释为何.lua
配置成如此。
使用上图中的object_monster.xls
,
通过生成工具,生成了如图的数据结构:
我们导出的
object_monster.lua
不但完整的保存了配置数据,还拥有对数据内容的一些访问接口,先来看看如何使用数据表
数据表加载
local CnfObjectMonster = require("object_monster")
打印表数据项个数
print(">>>> 数据项个数")
print(CnfObjectMonster.len())
输出
>>>> 数据项个数
3
属性访问
local printMonster = function(monsterID)
local monsterName = CnfObjectMonster.name(monsterID)
local monsterResName = CnfObjectMonster.res_name(monsterID)
print(string.format(">>>> monster of id(%d), its name is %s, its resource name is %s", monsterID, monsterName, monsterResName))
local monsterSkillList = CnfObjectMonster.skill_list(monsterID)
print(">>>> 打印技能列表")
monsterSkillList.walk(print)
print(">>>> 技能列表长度")
print(monsterSkillList.len())
end
local monsterID = 10001
printMonster(monsterID)
输出
>>>> monster of id(10001), its name is 哥布林小怪, its resource name is spine_small_goblin
>>>> 打印技能列表
1 101
2 102
>>>> 技能列表长度
2
访问ID列表
local ids = CnfObjectMonster.getIDList()
for k, v in ipairs(ids) do
print(k, v)
end
输出
1 10001
2 10002
3 10003
全表遍历
CnfObjectMonster.walk(function(k, id)
printMonster(id)
end)
输出
>>>> monster of id(10001), its name is 哥布林小怪, its resource name is spine_small_goblin
>>>> 打印技能列表
1 101
2 102
>>>> 技能列表长度
2
>>>> monster of id(10002), its name is 哥布林精英, its resource name is spine_elite_goblin
>>>> 打印技能列表
1 101
2 102
3 103
>>>> 技能列表长度
3
>>>> monster of id(10003), its name is 哥布林头领, its resource name is spine_boss_goblin
>>>> 打印技能列表
1 101
2 102
3 104
4 105
>>>> 技能列表长度
4
我们可以看到:.lua
数据文件提供了非常便捷的属性访问接口、遍历接口,另一方面,对于真正的数据data
,被屏蔽了对它的增加、减少或者修改它的任一内容的操作。
这样的数据结构,既提供了读取数据的接口,又屏蔽了针对数据的修改操作,十分令人满意。
.lua
格式的配表数据的生成工具
关于这份工具,我使用的是:
Github上的一份开源python脚本
在它的基础之上,我进行了针对性的修改。
结束
我们底层的数据框架搭建好了,工作和生活更加愉快起来了_~