描述

这个是使用python的xlrd库实现的一个简易导lua表格的工具的工具,支持多sheet,相对来说比较简单,原理就是读表拼接字符串,然后生成文件,总代码行数差不多60行,如果不算注释和日志的话应该是只有50行左右。

表格结构

image-20220610183733163

我这边使用的表格结构

  • 第一行是字段名称
  • 第二次是字段描述
  • 第三行是字段类型
  • 第四行是字段的可选类型
  • 第五行是字段导出筛选(不需要,客户端列,服务器列)
  • 第六行是字段的默认值(用来优化LuaTable的方案,使用元表优化法)

核心逻辑

  • def format_val :这个函数是格式化数据类型
  • def save_to_file :保存字符串到文件
  • def parse_excel :导表的核心函数
  • def main :主入口,可以从命令行传入参数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
import xlrd


def format_val(field_type, val):
# todo 实现其他的比如说list转table
if field_type == "string":
return "'%s'" % val
elif field_type == 'int':
return int(val)
else:
return val


def save_to_file(path, contents):
fh = open(path, 'w', encoding='utf-8')
fh.write(contents)
fh.close()


def parse_excel(file_path):
workbook = xlrd.open_workbook(file_path)
for i in range(workbook.nsheets):
sheet = workbook.sheet_by_index(i)
fields, describes, field_types, export_filter, default_val = {}, {}, {}, {}, {}
for col in range(sheet.ncols):
fields[col] = sheet.cell_value(0, col)
describes[col] = sheet.cell_value(1, col)
field_types[col] = sheet.cell_value(2, col)
export_filter[col] = sheet.cell_value(4, col)
default_val[col] = sheet.cell_value(6, col)
print(default_val)
sb = "local %s = { \n" % sheet.name
for row in range(sheet.nrows - 6):
row += 6
s = "\t[%s] = { \n" % format_val(field_types[0], sheet.cell_value(row, 0))
for v in fields.items():
# 过滤不需要的列,比如描述,或者服务器列客户端列
if int(export_filter[v[0]]) != 0:
if default_val[v[0]] != sheet.cell_value(row, v[0]):
s += "\t\t['%s'] = %s, \n" % (v[1], format_val(field_types[v[0]], sheet.cell_value(row, v[0])))
s += "\t},\n"
sb += s

# print(s)
sb += "}\n"

# 写入原表优化

meta = "local default = { \n"
for v in fields.items():
meta += "\t['%s'] = %s, \n" % (v[1], format_val(field_types[v[0]], default_val[v[0]]))
meta += "}\n"
meta += "local mt = {\n\t__index = default,\n\t__newindex = function()\n \t--自己实现设置限制 \n\tend \n} \n"
meta += "local setmetatable = setmetatable\n"
meta += "local pairs = pairs\n"
meta += "for _, v in pairs(%s) do \n\tsetmetatable(v, mt) \nend\n" % sheet.name
sb += meta
# 写入字段描述
describe = ""
for v in fields.items():
if int(export_filter[v[0]]) != 0:
describe += "%s \t\t: %s \n" % (v[1], describes[v[0]])

sb += "--[[\n%s --]]\n" % describe
sb += "return %s" % sheet.name
save_to_file(sheet.name + ".lua", sb)


if __name__ == "__main__":
# 使用命令行参数
file_name = "测试表格.xlsx"
parse_excel(file_name)

核心导表的结构详细分析

  1. 先通过xlrd.open_workbook 打开一个Excel文件

  2. workbook.nsheets读取所有的sheet,遍历sheet导表

  3. fields, describes, field_types, export_filter, 分别读出我们表头定义,这里少了我们的第六行默认数据列,这个暂时没做,也很简单就10行代码。

    字段名 描述 对应表格行数
    fields 字段合集 1
    describes 描述合集 2
    field_types 字段类型 3
    export_filter 过滤合集 5
  4. 这里需要看下我们的表格结构,立马就能明白为什么代码要这样写

  5. ```lua
    local InteractionTable2 = {
    [711000001] = {

      ['ID'] = 711000001, 
      ['Name'] = '抱拳', 
      ['Icon'] = 'ico_jiaohu_dan01', 
      ['Type'] = 1, 
      ['Loop'] = 0, 
      ['Action'] = 'Jh_Fuels', 
    

    },
    return InteractionTable2

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10

    6. 看下面的结构你就知道字符串怎么拼接了。

    7. ```lua
    local sheet名字 = {
    [Id] = {
    [key1] = val1,
    [key2] = val2,
    }
    }
  6. 然后遍历我们的sheet的行数 for row in range(sheet.nrows - 6): 注意我们要过滤掉表头

  7. 核心逻辑遍历字段 for v in fields.items():

  8. 过滤掉不需要的字段 if int(export_filter[v[0]]) != 0:

  9. 拼接字符串

  10. 拼接描述

  11. 返回表格

Git链接

源码链接