游戏开发 | Excel 表格批量转成lua的转表工具

Posted 烤地瓜的迷妹儿

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了游戏开发 | Excel 表格批量转成lua的转表工具相关的知识,希望对你有一定的参考价值。

一、简介

  在上篇推文《》 中,我们介绍了如何将策划提供的Excel表格转换为轻便的CSV文件供开发人员使用。实际在Unity开发中,很多游戏都是使用Lua语言进行开发的。如果要用Lua直接读取CSV文件的话,又要写个对应的CSV解析类,不方便的同时还会影响一些加载速度,牺牲游戏性能。因此我们可以直接将Excel表格转换为lua文件,这样就可以高效、方便地在Lua中使用策划配置的数据了。在本篇博客中,马三将会和大家一起,用C#语言实现一个Excel表格转lua的转表工具——Xls2Lua,并搭配一个通用的ConfigMgr来读取lua配置文件。


二、开发环境准备

  由于要使用C#来读取Excel表格文件,所以我们需要使用一些第三方库。针对C#语言,比较好用的Excel库有NPOI和CSharpJExcel 这两个,其实无论哪个库都是可以用的,我们只是用它来读取Excel表格中的数据罢了。马三在本篇博客中使用的是CSharpJExcel库,因为它相对来说更轻便一些。下面附上NPOI和CSharpJExcel库的下载链接:


三、转表工具

1.思路分析

  一切准备就绪,可以开始我们的开发任务了。首先我们来大致地说一下转表工具的思路:

 1.读取Excel表格文件的数据,依次读取配置目录下的Excel文件,然后逐个读取表里面Sheet的内容;

 2.根据Excel表格中配置的字段类型,对数据进行校验,判断数据是否合法;

 3.将通过校验的数据转为lua文件,一个Sheet切页对应一个lua配置文件;

 4.使用通用的ConfigMgr对转出来的lua配置文件进行读取操作;

2.目录结构

  项目整体的目录结构如下图所示:

  

  图1:转表工具整体目录结构

  ConfigMgr存放我们的ConfigMgr.lua,它是一个工具类,用来读取并管理转出来的Lua配置文件,兼具缓存数据的功能。Excel目录存放我们需要进行转换的Excel表格文件。LuaData目录存放转出来的Lua配置文件。Xls2Lua目录也就是我们的转表工具的目录了,它包含源代码和可直接运行的转表工具。

  转表工具的设计结构如下图所示:

  游戏开发 | Excel 表格批量转成lua的转表工具

  图2:转表工具设计结构

  FileExporter类专门用来读取Excel文件和导出lua配置文件;GlobalDef类中定义了一些通用的数据结构和枚举等信息;XlsTransfer类即为我们的转表工具核心类,大部分数据都是在这里进行校验处理的。

  下面我们就可以按照之前分析出来的思路编写具体的代码了,首先放上来的是我们主程序的入口,我们有一个名为config.ini的配置文件,程序运行的时候会先去这个配置信息中读取Excel的目录和输出目录,然后调用FileExporter.ExportAllLuaFile函数进行转表操作。

游戏开发 | Excel 表格批量转成lua的转表工具

  下面是FileExporter.cs的代码,在这里我们用到了之前提及的CSharpJExcel库,我们需要先把它加到我们工程的引用项中,然后在代码里调用即可。在这部分代码中,我们首先会调用ClearDirectory函数,清空之前转出来的lua配置文件。然后遍历Excel目录下的所有Excel文件,对其依次执行ExportSingleLuaFile函数。在ExportSingleLuaFile函数中主要做的是打开每一张Excel表格,并且依次遍历里面的Sheet文件,对其中命名合法的Sheet切页进行导出(sheet名称前带有#的为导出的表格,不带#的会被自动忽略掉,通过这个规则可以方便自由地控制导出规则,决定哪些Sheet导出,哪些Sheet不导出)。

游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具

   下面是GloablDef.cs的代码,我们主要在里面定义了一些字段类型的枚举和一些通用数据结构,其中的ColoumnDesc类用来存储表格数据:

游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具

   最后压轴出场的是我们的核心类:XlsTransfer,其核心代码如下: 

游戏开发 | Excel 表格批量转成lua的转表工具

游戏开发 | Excel 表格批量转成lua的转表工具

游戏开发 | Excel 表格批量转成lua的转表工具

游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具

       还记得上文提到的FileExporter类嘛,它会遍历每一张Sheet,然后调用XlsTransfer的GenLuaFile函数,把表格数据转为字符串,然后再把字符串导出为lua配置文件。在GenLuaFile函数中,将先对传入的sheet进行GetSheetColoumns处理,获取该Sheet中的每一个格子的信息(包括第几列Index,表格中的内容,对应的索引字段的名字,数据类型枚举,是否是数组标志位等等信息)。拿到这些信息以后,我们逐一对其进行进一步的处理,如果不是数组的话,我们将其直接添加到StringBuilder里面;如果是数组的话,我们根据字符"|",将其分解为n个单独的数据字段,然后存储为Lua中的table结构。在处理的过程中,会利用StringBuilder将数据自动化地格式为元表和table的lua数据结构,方便Lua端读取数据,具体操作可以看代码,这里就不再赘述。


四、读取Lua配置文件

  经过上面的一系列操作,我们得到了转换后的Lua配置文件,它长成下面这个样子:

游戏开发 | Excel 表格批量转成lua的转表工具

游戏开发 | Excel 表格批量转成lua的转表工具

  其实它们都是一段lua代码,因此可以直接执行,而不必再去解析,所以会节省不少性能。先来让我们看一下它的结构。首先第一行是一行注释说明,表示该配置文件是由软件自动生成的,请不要随意更改!然后定义了一个名为fieldIdx的table,顾名思义,他就是用来把字段名和对应的列的index建立起索引关系的一个数据结构。例如id字段对应第一列,path字段对应第二列,以此类推。那么我们定义这个table的用处是什么呢?别急,我们马上就会用到它,先接着往下看。我们在fieldIdx后面紧接着定义了名为data的table,从上述配置文件中,我们可以很明显地看到data才是真正存储着我们数据的结构。按照行、列的顺序和数据类型,我们将Excel表格中的数据依次存在了data结构里面。再接着,定义了一个名为mt的table,他重写了__index、__newindex、__metatable这样几个方法。通过设置mt.__metatable = false关闭它的元表,然后在重写的__newindex中我们输出一个error信息,表示配置文件不可以被更改,这样就保证了我们的配置文件的安全,使得它不能再运行时随意的增删字段。然后我们把__index指向了一个自定义函数function(a,b),其中第一参数是待查找的table,b表示的是想要索引的字段。(__index方法除了可以是一个表,也可以是一个函数,如果是函数的话,__index方法被调用时会返回该函数的返回值)在这个函数中,我们会先去之前定义的fieldIdx中,获取字段名所对应的index,然后再去data表中拿index对应的值。而这个值就是我们最后需要的值了。最后别忘了,在整段代码的最后,遍历data,将里面每个子table的元表设置为mt。这样就可以根据Lua查找表元素的机制方便地获取到我们需要的字段对应的值了。(对lua的查找表元素过程和元表、元方法等概念不熟悉的读者可以先去看一下这篇博客《》

  好了,我们的配置文件也成功获取到了,下面该去读取配置文件中的内容了。为了方便读取并且提高效率,我做了一个名ConfigMgr的类,它封装了一些函数,可以根据id获取对应的一行的数据或者根据表名获取该表的所有配置,并且兼具缓存功能,对已经加载过的配置文件直接做返回数据处理,不用多次加载读取,提高性能。ConfigMgr的代码如下所示:

游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具游戏开发 | Excel 表格批量转成lua的转表工具

  在这里我们先定义了_cacheConfig和_quickIndexConfig这样两个字段,_cacheConfig用来缓存配置文件名对应的数据,而_quickIndexConfig用来缓存配置文件名+id对应的数据,这样虽然稍稍多占用了一些内存空间,但是极大地提升了我们访问数据的速度。为了方便调用ConfigMgr,我将其做成了单例类,在需要的地方调用一下Instance()方法,就可以获取到ConfigMgr的实例了。

  在ConfigMgr中主要有两个供外界访问的接口:GetConfig(name)和GetItem(name,id)。在GetConfig(name)函数中,首先根据name去缓存中查看是否有缓存数据,如果有缓存数据则直接返回,如果没有加载过该配置文件,则会把配置文件的根目录和配置文件名拼接成一个完整的配置文件路径,然后调用dofile方法,把这个数据加载进来,并且缓存进_cacheConfig表中,以便下次快速访问。在GetItem(name,id)函数中,首先会判断_quickIndexConfig缓存中是否有name对应的数据存在。如果有,则直接返回self._quickIndexConfig[name][id],也就是id对应的那一行的配置数据。如果没有,则调用上面的GetConfig(name)函数,把对应的名称的数据文件先加载进来,然后按照对应的name和id把数据一一缓存起来。

  最后,让我们在Main.lua中实战检验一下上面一系列的操作是否成功: 

  其执行结果如下图所示:

  

  图3:最后的执行结果

  可以看到,我们成功地取到了表格中的数据并且输出了出来,因为lua编码的原因,中文变成了乱码,不过这并不影响我们在Unity开发中使用配置文件。

五、总结

  在本篇推文中,我们一起学习了如何使用C#制作一款简洁的转表工具,从而提升我们的工作效率。最后还是要推荐一款优秀的成熟的转表工具XlsxToLua。它是由tolua的开发者为广大的Unity开发人员制作的一款可以将Excel表格数据导出为Lua table、csv、json形式的工具,兼带数据检查功能以及导出、导入mysql数据库功能。除此之外,还支持GUI界面等很多实用的功能,大家感兴趣的话可以到Github去查看该项目的具体内容:https://github.com/zhangqi-ulua/XlsxToLua

 

 

以上是关于游戏开发 | Excel 表格批量转成lua的转表工具的主要内容,如果未能解决你的问题,请参考以下文章

lua的table转为excel表格的方法

游戏开发Excel表格批量转换成CSV的小工具

arcgis中excel转表工具不能用

如何利用excel批量填word中的表格?

如何把excel表格的数据批量导入word模板文档内?

VBA批量提取word表格中的自我评分