🎁
🏆 导航菜单
🎪 扩展内容
🎯 沙盘引擎文档
🕹️ 文章及书籍&教程
🎖️ 外部的链接
🎁
🏆 导航菜单
🎪 扩展内容
🎯 沙盘引擎文档
🕹️ 文章及书籍&教程
🎖️ 外部的链接
在沙盘引擎中,有关GUI的功能分成两个部分,分别是FairyGUI模板
与NativeGUI
组成。
沙盘引擎默认使用FairyGUI作为UI系统框架,经过综合考虑得出结果,引擎内的模组、衍生作品UI搭建也应使用FairyGUI工具进行制作。
FairyGUI是一个国产的优质游戏UI解决方案(社区免费),且经过沙盘引擎开发者的亲身体验,确实对GameUI开发会起到很大的帮助和简化流程,沙盘引擎本身就是使用FGUI作为UI框架,同时经过综合考虑后,引擎的模组、衍生作品也应使用此框架工具进行制作UI。
在早期引擎版本中,我们曾考虑过同时支持FGUI、NativeGUI(原生代码UI)的方案,但是考虑到实际开发阶段不会有太多开发者愿意使用代码的方式,而更多愿意使用“所见即所得”的制作界面,为了减少开发维护成本,所以最终只选择FairyGUI作为UI开发工具和框架。
尽管学习FairyGUI需要一点时间成本,但是好在工具的上手难度并不高,毕竟游戏UI也是决定作品是否精彩的关键组成,所以强烈建议开发者使用FairyGUI进行UI制作,可以无需代码+所见即所得实现大部分常用的UI功能和效果。
尽管沙盘引擎开放了绝大部分内容允许开发者进行自定义UI,但是仍然有部分内容属于引擎原生内容从而无法进行自定义UI及修改(因为理论上不应该被修改,且修改资源、重写API难度较大)。
常见的例如:引擎地图编辑器、设置界面、服务器浏览器界面、默认开发者名单等。
经过版本更新迭代,除地图编辑器这类并不建议修改的默认UI外,其他例如设置菜单、服务器浏览器等内容均可实现自定义UI,并提供了对应的API以供数据获取和保存,如果开发者并不喜欢引擎原生的设置菜单、服务器浏览器这些,完全可以使用FairyGUI(或修改Public包)等方式来重写这类UI,并且功能可做到完全一致。
例如关键API:SetGameOption
BindGameOption
目前版本来看,如果没有一定开发基础仍然不建议对原生UI进行修改,特别是设置菜单重写适配是有一定难度的。原生界面已经尽可能适配更多场景,除了UI风格固定外是十分稳定的,可以尝试接受它。
当模组开始加载时,遍历载入Store\GUI
文件夹内的FairyGUI导出文件.bytes
(提前预加载到内存中,无论是否使用)。
Store文件夹
内的文件大多数都是在加载模组时载入到内存中,所以开发者应该确保没有多余、重复、恶意的文件放到这里。
注意:GUI代码只能通过客户端脚本内实现,因为这属于客户端内容。
在沙盘引擎GUI框架设计中,虽然框架本身基于FairyGUI,但是为了更适合引擎内的直接使用,沙盘引擎对GUI内容重新封装了一个Client.GUI
类。
除此之外,开发者也应该遵守引擎所制定的UI制作及命名规范。
沙盘引擎是原生支持FairyGUI框架的,所以开发者只需要按照正常步骤,通过FairyGUI创建一个UI工程即可。
有关FairyGUI的工具内操作请访问https://www.fairygui.com/docs/editor查看。
注意:引擎最终需要读取的是由FairyGUI导出的bytes
文件及资源,并不需要UI工程源文件,所以工程文件夹可以不用放到模组文件夹中。
注意:导出这个词只是一个习惯性解释,在FairyGUI工具中应该叫作发布。
FairyGUI工具内的导出可参考文档:https://www.fairygui.com/docs/editor/publish。
关键在于导出的位置应该是模组独立目录\Store\GUI
,导出成功后应该包含xxx.bytes
与xxx.png
图集等文件,无需将FairyGUI源文件放到这里。
导出时的文件名称并不用太在意,引擎内实际引用时需要的是FairyGUI内的包名、组件名等。
补充:如果开发者模组拥有FairyGUI多语言文件(.xml),那么也需要将语言文件放到GUI目录下,关于语言适配详情参考《游戏多语言适配》。
当开发者将上述文件顺利发布导出到模组GUI目录后,在引擎下次加载此模组时就会尝试以FGUI的格式加载到内存中,无论最终是否使用。
开发者可通过开发者控制台(沙盘百科——控制台功能文档)使用重载模组命令进行快速重新加载,而不需要每次都重启游戏。
//使用此方法创建一个FGUI实例 let testView = GUI.Create("PackageName", "ViewName"); //创建UI之后,剩下的代码基本和FairyGUI使用方式相同,只不过需要注意JavaScript的限制和特性 let button = testView.GetChild("Button").asButton; if(button) { button.onClick.Set(() => { DLog(view.GetChild("n1").name); }); }
除了Client.GUI
一些由引擎封装的API之外,其他的代码很多都是基于FairyGUI代码,开发者可尝试直接按照FairyGUI的方式来使用。
注意:此功能在开发版本中暂时关闭,当前版本中暂不可用。
此项内容比较重要,建议开发者可以参考,可能会对开发UI事半功倍。
在GUI的制作过程中,经常会遇到某些附带功能且经常被复用的组件,比如说背包系统的背包格子,按照传统的方式可能需要每次建立一个格子就得绑定“此UI的文本、图片等引用”,哪怕是自行封装一个方法也仍然会比较麻烦。
GUI类延续了FairyGUI的UIObjectFactory.SetPackageItemExtension
方法,并根据需要对其封装成了GUI.BindExtend
方法。
使用此功能,开发者可以为某个GUI组件绑定一个扩展类,绑定的类负责此组件的全部生命周期事件,这样可以对一些复杂或频繁复用的UI组件更清晰的开发。
//需要在UI被建立之前,初始化一次绑定事件,以后就不需要再绑定了 GUI.BindExtend("SEngineGUI", "UIView_Test", "MyButton"); //包名、组件名、脚本扩展类名 //这里是自行在脚本中新建的一个“UI扩展类”,继承的是GButton(什么类型的组件就要扩展什么类型的类,最好按照规范) class MyButton extends FairyGUI.GButton { //定义了一个整数型变量 count = 0; constructor() { //此处的代码必须完整保留 super(); this.__onConstruct = () => { this.onConstruct(); }; } //初始化函数 onConstruct() { //获取了当前组件下的n1子组件下的title子组件,并修改其标题为“点击” this.GetChild("n1").GetChild("title").text = "点击"; //为当前组件绑定一个点击事件 this.onClick.Set(() => { this.count ++; this.GetChild("n1").GetChild("title").text = this.count.toString(); }); } //自定义函数 test() { DLog("test"); } } //确认已经绑定事件后,按正常方式创建UI即可 let view = GUI.Create("SEngineGUI", "UIView_Test"); view.Root.test(); //这里执行了扩展类的test方法,会输出一个“test” //Root表示的才是View的实体GComponent,CreateView返回的并不是FGUI的类,而是引擎GUI类下的UIView类
注意:如果组件A只是一个普通的组件,没有定义“扩展”,那么基类是GComponent,如上例所示;如果组件
UIView_Test
的FGUI编辑器内扩展是按钮
,那么MyButton
的基类应该为GButton
,如果扩展是进度条
,那么基类应该为GProgressBar
以此类推。这个千万不能弄错,否则会出现报错。
有关FairyGUI更多代码定义和内容,请访问https://www.fairygui.com/docs/editor 查看。
在当前版本下,目前仅支持使用用户本地系统字体、沙盘引擎内置字体,暂不支持通过资源的方式导入字体。
全局字体需要在加载模组之前进行设置,需要在Mod/Mod.json
配置文件提前设定,并使用标准的字体名称标识。
注意:不同用户本地系统存在的字体并不统一,有可能A用户存在AAA字体,但B用户系统没有安装此字体,这样的话实现的效果将不会达到预期。
沙盘引擎内置了数个优秀字体(免费+可商用),如需使用引擎内置字体,请填写《参考文档》内的字体标示名称。
对于一些UI全局的设定内容(如字体、原生组件)等需要在模组加载之前进行修改,如果有这些内容的修改需求,可以在模组目录下的Mod.json
进行设定。