引擎工具链基础
引擎工具链基础

什么是工具链

渲染,网络通讯,物理模拟等这些构成了游戏引擎的Runtime
Engine的Runtime上有大量的工具支持构建一个世界,它的复杂度大大高于Rumtime

工具链主要是搭建一个平台,让不同思维的人在一起协同工作。
工具链的GUI的设计模型
直接模式


直接绘制,快速,但是扩展性很差
保留模式


逻辑和绘制分开,扩展性很强,常用的工具模型
GUI的设计模式
MVC 模式

数据流清晰化了,底层的model单向的到view,不能从view 到model。
model的修改只能通过controller来做。
将View和model分离开的架构。
MVP 模式

所有的复杂度放到了Presenter,中间人负责处理View和model的交互
MVVM模式



由ViewModel来做中间层,view只是显示
序列化和反序列化

序列化后文件可以是磁盘文件,数据库中的block data,网络通讯的数据流

打包最简单的存储是Text文件,方便理解和处理
文本有不同的约定格式比如XML, Json

二进制存储存储容量很有优势
资产引用

提出重复的数据通过引用建立网状联系


实例变种来提供多样化


通过数据继承来扩展,避免简单拷贝带来的数据来源丢失
怎么反序列化加载数据

数据并不是一开始就全部加载
而是把数据拆分成一个个的语义,然后把关键的key,value, type放到一起

基于Asset引用的数据field展开的树状结构

使用二进制存储把对数据的解析信息存在了头部

遗留问题
- 大端:低位存后面,高位存前面
- 小端:低位存后面,高位存后面
资产版本兼容性

Unreal处理方法:数据有版本号,对于新增的数据,插入默认值,对于删除的数据,不进行读取
如果版本太多很难处理

Google的ProtoBuffer
每个field都有唯一的UID,版本变化后这个ID也会更新。
field的ID和类型会生成一个序列化的key
在反序列化时通过key查表处理,如果表格中没有则跳过,如果存在表格没有在数据中则默认初始化
怎么让工具更加鲁棒(Robust)
增加Undo & Redo 以及 Crash Recovery ,这也是工具最重要的功能能确保持续性开发,下面介绍解决方案:

把用户所有的操作分解成小的Command, 且尽量原子化
用户的一个操作可能会分解成很多Command
command会定时存放到磁盘上,当系统挂了后可以从磁盘上找到恢复
Command系统应该在Tool设计之初就要完成,大致定义如下:

Command定义的分析

UID 确保command操作执行的严格顺序

Command需要序列化反序列在内存中访问,且这个处理由具体的数据来实现提供原子化

Commond类型可以简单归纳为增 add, 删 delete, 修改 Update
Info
虽然Tool chain的开发是不同的,但是Asset system, Command system, g\Gui system 这些是实现Tool chain的基础。
如何制作工具链

需要明白tool chain面对的用户
我们需要针对不同的数据,数据是异构的,所以需要找出共性

如上图可以把数据拆分成更基础的数据。
Schema 数据描述结构

Schema系统是游戏工具链的核心底层
工具链流转的数据都是由Schema统一描述和定义的,这样才能确保数据彼此解读。
比如角色编辑器里的角色放到地图编辑器中能通过坐标,缩放,旋转等获取角色的数据


像高级语言一样,Schema支持数据类型,继承.

允许互相数据引用

两种定义流派
- 在文件中直接定义,比如XML。
- 在代码中定义,可以直接将方法包进去。

- 把数据实现和工程彻底剥离开了。但是需要代码的生成器,版本可能不兼容。
只有数据定义,缺少方法。 - 代码定义的话,复杂度比较高,稳定性不好
引擎数据的三个观察角度

运行时以高效处理为目标

存储中以节约存储空间为目标,要处理压缩

在工具界面中需要让用户更好的理解和使用,比如调色板
所见即所得
What You See is What You Get(WYSIWYG)
早期的工具链是单独存在的,为了所见即所得工具链会架设到游戏上

直接在编辑器运行,但是可能会遇到编辑器数据把游戏数据弄脏的问题

UE在沙盒世界运行模拟。这种模式架构比较困难
插件 Plugin

提供了额外的支持支持不同的需求
插件对引擎的要求:


需要开放API,供开发者自由开发功能
下面是插件的扩展样例:


现代游戏引擎要把功能接口化,可扩展性是一个核心需求

相关的文献

