跳转到内容

结构定义

CFG文件结构定义系统旨在表达复杂的数据结构和关系网络。系统通过以下核心组件构建:

基础类型(int, float, str, bool, long, text)
枚举(enum)定义编译时常量
结构体(struct)聚合基础类型和枚举,支持嵌套
容器类型(list, map)表达集合数据
接口(interface)实现多态行为
数据表(table)存储具体数据,通过主键、唯一键、外键建立关联

最终形成一个相互关联的数据网络,支持复杂游戏逻辑的配置。

枚举用于在 schema 文件中定义编译时常量,语法格式:enum 名称 { 值; 值; }

enum ArgCaptureMode {
Snapshot; // 快照模式
Dynamic; // 动态模式
}

等价于:

// 在.cfg中配置table
table ArgCaptureMode[name] (enum='name') {
name:str;
comment:str;
}
// 在excel中配置数据
// Snapshot, 快照模式
// Dynamic, 动态模式

使用:

captureMode:ArgCaptureMode;
// 等价于: captureMode:str ->ArgCaptureMode
// 也支持list<ArgCaptureMode>和map<str, ArgCaptureMode>等容器类型
特性Schema EnumTable Enum
数据位置.cfg 文件中配置Excel 中配置
成员字段固定 name + comment可定制更多字段

结构体用于定义复合数据类型,是构建复杂数据结构的基础。

  • 定义格式struct 结构体名称 { 字段定义 }
  • 字段定义字段名:字段类型; // 注释
  • 字段类型
    • 基础类型bool, int, float, long, str, text
    • 聚合类型struct, interface
    • 容器类型list<类型>, map<键类型,值类型>

外键用于建立表之间的关联关系,支持多种引用方式。

  • 单向外键(->):指向表的主键或唯一键
    • 格式:字段类型 ->表名(指向主键)
    • 格式:字段类型 ->表名[唯一键](指向唯一键)
  • 多向外键(=>):指向表的任意字段,生成反向引用列表
    • 格式:字段类型 =>表名[字段名]
  • 独立外键->外键名:[字段列表] ->|=> 目标表

详细说明请参考:表键、枚举与数据关联

// 数值范围结构
// 用于定义最小值和最大值
struct Range {
rmin:int; // 最小值
rmax:int; // 最大值
}
// 奖励物品结构
// 包含掉落概率、物品ID列表和数量范围
struct RewardItem {
chance:int; // 掉落概率
itemids:list<int> ->item.item (fix=2); // 掉落物品列表,每个物品指向item表
range:Range; // 数量范围(嵌套结构)
}
// 时间结构
// 使用冒号分隔的小时、分钟、秒配置
struct Time (sep=':'){
hour:int; // 小时
minute:int; // 分钟
second:int; // 秒
}

特性说明:

  • Range:基础结构体,定义数值范围
  • RewardItem:复杂结构体,包含列表外键和嵌套结构
  • Time:使用(sep=':')属性,支持Excel中以冒号分隔的时间格式

接口用于定义多态行为,支持多种实现类,常用于游戏逻辑的条件判断和公式计算。

  • enumRef(可选):指向枚举表,该表包含接口所有实现类的信息

    • 作用:让策划在Excel中通过下拉菜单选择实现类,无需查看CFG文件
    • 要求:枚举表必须包含实现类名称,可包含ID和其他信息
  • defaultImpl(可选):指定默认实现类

    • 作用:Excel中可不显式配置接口字段,系统自动使用默认实现
// 任务完成条件接口
// 定义多种任务完成条件的实现方式,通过枚举表completeconditiontype选择
interface completecondition (enumRef='completeconditiontype') {
// 击杀怪物条件
struct KillMonster {
monsterid:int ->npc.monster; // 怪物ID,外键指向npc表
count:int; // 需要击杀的数量
}
// 与NPC对话条件
struct TalkNpc {
npcid:int ->npc.npcid; // NPC ID,外键指向npc表
}
// 多条件与逻辑
struct ConditionAnd {
cond1:task.completecondition; // 条件1,递归引用
cond2:task.completecondition; // 条件2,递归引用
}
// 收集物品条件
struct CollectItem {
itemid:int ->item.item; // 物品ID,外键指向item表
count:int; // 需要收集的数量
}
}
// 任务经验公式接口
// 定义多种经验计算方式,默认使用固定值
interface taskexp (enumRef='taskexptype', defaultImpl='ConstValue') {
// 基于玩家等级的经验公式
struct ByLevel {
levelcoef:float; // 等级系数
value:int; // 基础值
}
// 基于服务器开服天数的经验公式
struct ByServerUpDay {
updaycoef1:float; // 天数系数1
updaycoef2:float; // 天数系数2
value:int; // 基础值
}
// 固定经验值
struct ConstValue {
value:int; // 固定经验值
}
}

设计优势:

  • 可扩展性:新增任务完成条件只需添加新的struct实现
  • 易用性:策划通过下拉菜单选择,无需了解技术细节
  • 灵活性:支持递归组合,可构建复杂条件树

数据表是实际存储配置数据的容器,支持索引、约束和多态字段。

  • 主键:表名后的[]内定义主键字段
  • 表属性:主键后的()内定义表级属性
  • 唯一键{}内以[字段名]开头的行定义唯一键
  • 字段定义:与struct语法相同

详细主键、唯一键说明请参考:主键、枚举、外键

  • enum:指定枚举字段,该表作为枚举表使用

    • 作用:Excel中该列由程序员填写,每行都必须有值
    • 用途:配合interface的enumRef属性
  • entry:指定入口字段,生成静态访问代码

    • 作用:Excel中该列由程序员填写,只有特定行需要值
    • 用途:程序代码中通过静态成员直接访问特定行

详细说明请参考:表键、枚举与数据关联

// 任务完成条件类型枚举表
// 为completecondition接口提供下拉选项
table completeconditiontype[id] (enum='name') {
id:int; // 任务完成条件类型ID
name:str; // 程序用名称(必须包含completecondition接口的所有实现类名)
}
// 任务经验公式类型枚举表
// 为taskexp接口提供下拉选项
table taskexptype[id] (enum='name') {
id:int; // 经验公式类型ID
name:str; // 程序用名称(必须包含taskexp接口的所有实现类名)
}
// 任务配置表
// 存储所有任务数据和完成条件
table task[taskid] (entry='entry') {
[nexttask]; // 定义唯一键
taskid:int ->task.taskextraexp (nullable); // 任务ID,外键(可空)
entry:str; // 入口标识,程序代码直接访问
text:text; // 国际化文本
nexttask:int ->task (nullable); // 下一个任务ID,外键(可空)
completecondition:task.completecondition; // 任务完成条件(多态接口)
exp:taskexp (mustFill); // 经验奖励公式(多态接口,必须填写)
rewardItems:list<RewardItem> (block=1); // 物品奖励列表
time:Time; // 时间配置
}

表设计说明:

  • completeconditiontype:枚举表,定义任务完成条件类型
  • taskexptype:枚举表,定义经验公式类型
  • task:主任务表,包含复杂的数据结构和关联关系
  • 唯一键[nexttask]会生成GetByNextTask访问方法
  • 多态字段completeconditionexp字段支持多种实现

字段可以配置多种属性来控制数据验证和生成行为。

属性用途适用类型示例
nullable允许字段为空所有类型field:int (nullable)
mustFill必须填写,不能为空所有类型field:str (mustFill)
fix=N固定长度,占用N倍元素类型的列数list, mapitems:list<int> (fix=3)
block=N块状映射,横向固定N个元素,纵向可扩展list, maprewards:list<Reward> (block=1)
pack压缩到1列,用逗号或分号分隔struct, list, mappos:Position (pack)
sep='分隔符'自定义分隔符,压缩到1列struct, listtime:Time (sep=':')

详细映射规则请参考:映射到表格

构造语法用途
枚举enum 名称 { 值; 值; }定义编译时常量枚举
结构体struct 名称 { 字段:类型; }定义复合数据类型
接口interface 名称 { struct 实现类 { ... } }定义多态行为
数据表table 表名[主键] { [唯一键]; 字段:类型; }存储配置数据
外键字段:类型 ->目标表建立表间关联
多向外键字段:类型 =>目标表[字段]建立反向引用
属性位置用途
enumRef='表名'interface指定枚举表
defaultImpl='类名'interface指定默认实现
enum='字段名'table指定枚举字段
entry='字段名'table指定入口字段
nullable字段允许为空
mustFill字段必须填写
fix=N映射…
block=N映射…
pack映射…
sep='分隔符'映射…
类型分类具体类型描述
基础类型bool, int, float, long, str, text基本数据类型
枚举类型枚举名称编译时常量枚举
容器类型list<T>, map<K,V>集合数据类型
聚合类型struct, interface复合数据类型
引用->表名,->表名[唯一键], =>表名[字段]表间关联