FairyGUI编辑器自定义菜单扩展插件

本文涉及到的软件有:FairyGUI,VSCode

代码环境涉及到了:Lua

VSCode插件:EmmyLua

在编写FairyGUI编辑器菜单前,了解一下FairyGUIEditor的API会有效的帮助我们解决很多问题。FairyGUI的扩展是通过编辑器自带的插件功能实现的,插件中我使用的是lua环境模板。导入编辑器的LuaAPI,文件可以在FairyGUI-Editor源码的插件目录中找到。接下来将通过功能来说明对应的API作用。

插件的位置

 如果找不到插件面板,可以通过“视图→插件”或“工具→插件”添加插件面板。

1、打开插件目录,插件目录是在“项目目录/plugins"文件夹下,每个插件对应一个子文件夹。

2、创建新插件

3、刷新插件列表

一个新插件的诞生

点击创建新插件,可以在插件模板选择要写的插件类型和语言格式

点击创建后,插件列表中就会出现刚刚创建的新插件。

这时候,点击打开插件目录,会发现原本空空的插件目录中多了一个刚刚新建的插件文件夹,右键使用VSCode打开。

可以注意到,目录下有两个文件“main.lua”和“package.json”。其中main.lua是插件的入口脚本,package.json是插件的配置文件。

双击main.lua后可以看到“onDestroy”方法,可以将之后的清理代码添加到此处。保存编写后的代码,在编辑器中点击刷新插件列表,可以将最新插件代码同步到编辑器。如果这时候编辑器保存,如果不是代码书写错误,可以通过重启编辑器进行刷新插件。

 编辑器的个人常用API

App是工程入口类,类型:CS.FairyEditor.App。通过LuaAPI中的CS_FairyEditor_App可以看到编辑器中的功能字段。下面将列出将要用的字段和方法。

CS.FairyEditor.App
字段名类型作用
projectCS.FairyEditor.FProject记录当前工程的配置和资源
libViewCS.FairyEditor.View.LibraryView编辑器的资源库面板
inspectorViewCS.FairyEditor.View.InspectorView编辑器的检查器面板
consoleViewCS.FairyEditor.View.ConsoleView编辑器的控制台面板
menuCS.FairyEditor.Component.IMenu编辑器的菜单栏
pluginManagerCS.FairyEditor.PluginManager插件管理
CS.FairyEditor.FProject
字段名类型作用
namestring工程名“如:FGUIProject”
basePathstring工程的路径“如:D:\Documents\FGUIProject”
assetsPathstring工程的路径“如:D:\Documents\FGUIProject\assets”
allPackagesCS.FairyEditor.Fpackage[]工程中的所有包
allBranchesstring[]工程中的所有分支
CS.FairyEditor.Fpackage
字段名类型作用
namestring当前包的名字
itemsCS.FairyEditor.FPackageItem[]当前包下的资源
CS.FairyEditor.FPackageItem
字段名类型作用
pathstring资源路径
namestring资源名
CS.FairyEditor.View.LibraryView
字段名类型作用
contextMenuCS.FairyEditor.Component.NPopupMenu资源库的右键菜单
CS.FairyEditor.Component.NPopupMenu
方法名参数作用
AddItemcaption:string, name:string, selectCallback:(fun():void)添加一个菜单项并设置选中回调事件
AddSeperator添加菜单分割线
SetItemGrayedstring name, bool grayed设置目标不能点击
onPopupCS.FairyGUI.EventListener菜单弹出事件

 开始编写插件代码

需求1

需求1:在工具菜单中添加“导出所有UI名字”的菜单项,点击后复制结果。

前提:所有UI界面具有相同的命名规则,这里我用的是UIXXX,所以在获取所有UI的时候只需要检测当前文件的名字UI是否存在。在这个需求实现的功能中,需要准备一个lua代码格式的文本代码,之后会将classField替换为获取到的UI名。

local tmp_ui_type = [[
---@class UIType
return {classField
}
]]

代码已经加了详细的注解,可以直接查看完整代码:

---@type CS.FairyEditor.App
local _app = CS.FairyEditor.App
local project = _app.project
---输出绝对文件路径
local file_out_path =("%s/UIType.lua"):format(project.basePath)
---Lua模板
local tmp_ui_type = [[
---@class UIType
return {classField
}
]]
---获取工具菜单
---@type CS.FairyEditor.Component.MenuBar
local toolMenu = _app.menu:GetSubMenu("tool")
---添加分隔符
toolMenu:AddSeperator()
---添加菜单,显示名字,内部标签名,回调方法
toolMenu:AddItem("导出UIType","XiaoExportUIType",function()local _classField = ""---获取工程中的所有包,返回值是列表local allPackages = _app.project.allPackagesfor i = 1, allPackages.Count do---C#索引从0开始---@type CS.FairyEditor.FPackagelocal package = allPackages[i - 1]---获取当前包中的所有子项,返回值是列表local items = package.itemsfor i = 1, items.Count do---@type CS.FairyEditor.FPackageItemlocal item = items[i - 1]---记录所有UI开头的子项if string.find(item.name,"UI") == 1 thenlocal uiType = string.format("%s = %s_%s,\n\t",item.name,package.name,item.name)_classField = _classField .. uiTypeendendend---输出日志打印fprint(_classField)---替换模板tmp_ui_type = tmp_ui_type:gsub("classField",_classField)---写出模板local f = io.open(file_out_path,"w")f:write(tmp_ui_type)f:close()---输出路径打印fprint(string.format("导出UIType:[url]%s[/url]",file_out_path))
end)
function onDestroy()
-------do cleanup here-------toolMenu:RemoveItem("XiaoExportUIType")
end

 需求2:

需求2:在资源库的右键菜单中添加“复制组件脚本路径”,方便提取当前组件的require路径。并且实现组件筛选,在不满足条件的情况下,“复制组件脚本路径”菜单项置灰不可用。

前提:所有非UI的组件都在当前包的Comps的文件夹下存放。

重新新建一个插件或者在之前的插件中继续编写,这里我是接着之前的插件继续写。

---添加资源库右键菜单
---需求:复制Comps文件夹下的组件所转化的脚本路径
---获取右键菜单
local libcontextMenu = _app.libView.contextMenu
---添加分割线
libcontextMenu:AddSeperator()
libcontextMenu:AddItem("复制组件脚本路径","XiaoCopyAssetPath",function()---获取当前选中的资源---@type CS.FairyEditor.FPackageItemlocal item = _app.libView:GetSelectedResource()---检测资源是否满足条件if item.path:find("/Comps/") == 1 then---准备复制local cp_str = ("require(\"UI.%s.Comps.%s\")"):format(item.owner.name,item.name)---Unity复制操作CS.UnityEngine.GUIUtility.systemCopyBuffer = cp_str---弹窗提示_app.Alert("复制成功")else_app.Alert("复制失败")end
end)
---在弹出的菜单中检测当前选择的资源是否满足条件
libcontextMenu.onPopup:Add(function()---@type CS.FairyEditor.FPackageItemlocal item = _app.libView:GetSelectedResource()local grayed = trueif item.path:find("/Comps/") == 1 then-- bodygrayed = falseendlibcontextMenu:SetItemGrayed("XiaoCopyAssetPath",grayed)
end)

之后不要忘记在onDestroy方法中移除我们的菜单项“XiaoCopyAssetPath”

toolMenu:RemoveItem("XiaoCopyAssetPath")

 

完整插件代码

---@type CS.FairyEditor.App
local _app = CS.FairyEditor.App
local project = _app.project---输出绝对文件路径
local file_out_path =("%s/UIType.lua"):format(project.basePath)---Lua模板
local tmp_ui_type = [[
---@class UIType
return {classField
}
]]---获取工具菜单
---@type CS.FairyEditor.Component.MenuBar
local toolMenu = _app.menu:GetSubMenu("tool")
---添加分隔符
toolMenu:AddSeperator()
---添加菜单,显示名字,内部标签名,回调方法
toolMenu:AddItem("导出UIType","XiaoExportUIType",function()local _classField = ""---获取工程中的所有包,返回值是列表local allPackages = _app.project.allPackagesfor i = 1, allPackages.Count do---C#索引从0开始---@type CS.FairyEditor.FPackagelocal package = allPackages[i - 1]---获取当前包中的所有子项,返回值是列表local items = package.itemsfor i = 1, items.Count do---@type CS.FairyEditor.FPackageItemlocal item = items[i - 1]---记录所有UI开头的子项if string.find(item.name,"UI") == 1 thenlocal uiType = string.format("%s = %s_%s,\n\t",item.name,package.name,item.name)_classField = _classField .. uiTypeendendend---输出日志打印fprint(_classField)---替换模板tmp_ui_type = tmp_ui_type:gsub("classField",_classField)---写出模板local f = io.open(file_out_path,"w")f:write(tmp_ui_type)f:close()---输出路径打印fprint(string.format("导出UIType:[url]%s[/url]",file_out_path))
end)---添加资源库右键菜单
---需求:复制Comps文件夹下的组件所转化的脚本路径
---获取右键菜单
local libcontextMenu = _app.libView.contextMenu
---添加分割线
libcontextMenu:AddSeperator()
libcontextMenu:AddItem("复制组件脚本路径","XiaoCopyAssetPath",function()---获取当前选中的资源---@type CS.FairyEditor.FPackageItemlocal item = _app.libView:GetSelectedResource()---检测资源是否满足条件if item.path:find("/Comps/") == 1 then---准备复制local cp_str = ("require(\"UI.%s.Comps.%s\")"):format(item.owner.name,item.name)---Unity复制操作CS.UnityEngine.GUIUtility.systemCopyBuffer = cp_str---弹窗提示_app.Alert("复制成功")else_app.Alert("复制失败")end
end)---在弹出的菜单中检测当前选择的资源是否满足条件
libcontextMenu.onPopup:Add(function()---@type CS.FairyEditor.FPackageItemlocal item = _app.libView:GetSelectedResource()local grayed = trueif item.path:find("/Comps/") == 1 then-- bodygrayed = falseendlibcontextMenu:SetItemGrayed("XiaoCopyAssetPath",grayed)
end)function onDestroy()
-------do cleanup here-------toolMenu:RemoveItem("XiaoExportUIType")toolMenu:RemoveItem("XiaoCopyAssetPath")
end

菜单的操作目前只用到了这两种,后面在实际操作中如果还有,则会继续更新!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/42046.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【嵌入式】MKV31F512VLL12 微控制器 (MCU) 、Cyclone® IV E EP4CE10E22I8LN,FPGA-现场可编程门阵列芯片

1、MKV31F512VLL12 微控制器 (MCU) 是适用于BLDC、PMSM和ACIM电机控制应用的高性能解决方案。这些MCU采用运行频率为100MHz/120MHz、带数字信号处理 (DSP) 和浮点单元 (FPU) 的ARM Cortex-M4内核。KV3x MCU配备两个采样率高达1.2MS/s的16位ADC、多个控制定时器以及512KB闪存。 …

Codeforces Round 893 (Div. 2) D.Trees and Segments

原题链接&#xff1a;Problem - D - Codeforces 题面&#xff1a; 大概意思就是让你在翻转01串不超过k次的情况下&#xff0c;使得a*&#xff08;0的最大连续长度&#xff09;&#xff08;1的最大连续长度&#xff09;最大&#xff08;1<a<n&#xff09;。输出n个数&…

模糊测试面面观 | 模糊测试工具知多少

自1988年威斯康星大学的Barton Miller首次提出模糊测试这一概念以来&#xff0c;模糊测试领域经历了持续长久发展。模糊测试作为一种软件测试方法&#xff0c;旨在通过向程序输入模糊、随机、异常的数据&#xff0c;探测和发现潜在的漏洞和错误。这种方法备受安全研究人员的青睐…

助推打造全球研发中心城市 | 李彦团队:研发,带来了二次文艺复兴

2017年&#xff0c;长沙经联合国教科文组织评选&#xff0c;成为中国首座获评世界“媒体艺术之都”称号的城市。6年后&#xff0c;基于时代发展的新要求&#xff0c;长沙再次提出了“打造全球研发中心城市”的目标&#xff0c;并朝着新的方向迈进。 旧有的优势产业在新的研发浪…

信安通用基础知识

文章目录 密码学经典误区PGP优良保密协议信安经典其它安全手段XSS与CSRF cross site request forgeryCSRF的利用逻辑CSRF示例CSRF防范检查Referer字段添加校验token XSS cross site scripting common weakness enumeration常见密码api误用&#xff08;摘自毕设参考文献&#xf…

用Java实现原神抽卡算法

哈喽~大家好&#xff0c;好久没有更新了&#xff0c;也确实遇到了很多事&#xff0c;这篇开始恢复更新&#xff0c;喜欢的话&#xff0c;可以给个的三连&#xff0c;什么&#xff1f;你要白嫖&#xff1f;那可以给个免费的赞麻。 &#x1f947;个人主页&#xff1a;个人主页​​…

七月 NFT 行业解读:游戏和音乐 NFT 引领增长,Opepen 掀起热潮

作者&#xff1a;lesleyfootprint.network 2023 年 7 月&#xff0c;NFT 市场的波动性持续存在&#xff0c;交易量呈下降趋势。然而&#xff0c;游戏和音乐 NFT 等领域的增长引人注目。参与这些细分领域的独立用户数量不断增加&#xff0c;反映了这些领域的复苏。 本综合报告…

lvs负载均衡群集

lvs组成 1、lvs基于内核态的netfilter框架实现的IPVS功能&#xff0c;工作在内核态用户配置VIP等相关信息并且传递到IPVS 就需要用到IPVSadm工具。 2、ipvsadm&#xff1a;IPVSadm是lvs用户态的配套的工具&#xff0c;可以实现VIP和RS 增删改查。 IPVSadm就是类似于iptables…

侯捷 八部曲 C++面向对象高级开发(上)+(下)【C++学习笔记】 超详细 万字笔记总结 笔记合集

文章目录 Ⅰ C part1 面向对象编程1 头文件与类的声明1.1 c vs cpp关于数据和函数1.2 头文件与类1.2.1 头文件1.2.2 class的声明1.2.3 模板初识 2 构造函数2.1 inline 函数2.2 访问级别2.3 ctor 构造函数2.3.1 ctor 的写法2.3.2 ctor/函数 重载2.3.3 ctor 放在 private 区 2.4 …

生活随笔,记录我的日常点点滴滴.

前言 &#x1f618;个人主页&#xff1a;曲终酣兴晚^R的小书屋&#x1f971; &#x1f615;作者介绍&#xff1a;一个莽莽撞撞的&#x1f43b; &#x1f496;专栏介绍&#xff1a;日常生活&往事回忆 &#x1f636;‍&#x1f32b;️每日金句&#xff1a;被人暖一下就高热&…

【sgDragSize】自定义拖拽修改DIV尺寸组件,适用于窗体大小调整

核心原理就是在四条边、四个顶点加上透明的div&#xff0c;给不同方向提供按下移动鼠标监听 &#xff0c;对应计算宽度高度、坐标变化 特性&#xff1a; 支持设置拖拽的最小宽度、最小高度、最大宽度、最大高度可以双击某一条边&#xff0c;最大化对应方向的尺寸&#xff1b;再…

一次Linux中的木马病毒解决经历(6379端口---newinit.sh)

病毒入侵解决方案 情景 最近几天一直CPU100%,也没有注意看到了以为正常的服务调用,直到腾讯给发了邮件警告说我的服务器正在入侵其他服务器的6379端口,我就是正常的使用不可能去入侵别人的系统的,这是违法的. 排查 既然入侵6379端口,就怀疑是通过我的Redis服务进入的我的系统…

JDBC封装与设计模式

什么是 DAO &#xff1f; Data Access Object(数据存取对象) 位于业务逻辑和持久化数据之间实现对持久化数据的访问 DAO起着转换器的作用&#xff0c;将数据在实体类和数据库记录之间进行转换。 ----------------------------------------------------- DAO模式的组成部分 …

数据结构--拓扑排序

数据结构–拓扑排序 AOV⽹ A O V ⽹ \color{red}AOV⽹ AOV⽹(Activity On Vertex NetWork&#xff0c;⽤顶点表示活动的⽹)&#xff1a; ⽤ D A G 图 \color{red}DAG图 DAG图&#xff08;有向⽆环图&#xff09;表示⼀个⼯程。顶点表示活动&#xff0c;有向边 < V i , V j …

算法与数据结构(二十四)最优子结构原理和 dp 数组遍历方向

注&#xff1a;此文只在个人总结 labuladong 动态规划框架&#xff0c;仅限于学习交流&#xff0c;版权归原作者所有&#xff1b; 本文是两年前发的 动态规划答疑篇open in new window 的修订版&#xff0c;根据我的不断学习总结以及读者的评论反馈&#xff0c;我给扩展了更多…

【STM32】高效开发工具CubeMonitor快速上手

工欲善其事必先利其器。拥有一个辅助测试工具&#xff0c;能极大提高开发项目的效率。STM32CubeMonitor系列工具能够实时读取和呈现其变量&#xff0c;从而在运行时帮助微调和诊断STM32应用&#xff0c;类似于一个简单的示波器。它是一款基于流程的图形化编程工具&#xff0c;类…

链表之第二回

欢迎来到我的&#xff1a;世界 该文章收入栏目&#xff1a;链表 希望作者的文章对你有所帮助&#xff0c;有不足的地方还请指正&#xff0c;大家一起学习交流 ! 目录 前言第一题&#xff1a;反转一个链表第二题&#xff1a;链表内指定区间反转第三题&#xff1a;判断一个链表…

opencv+ffmpeg+QOpenGLWidget开发的音视频播放器demo

前言 本篇文档的demo包含了 1.使用OpenCV对图像进行处理&#xff0c;对图像进行置灰&#xff0c;旋转&#xff0c;抠图&#xff0c;高斯模糊&#xff0c;中值滤波&#xff0c;部分区域清除置黑&#xff0c;背景移除&#xff0c;边缘检测等操作&#xff1b;2.单纯使用opencv播放…

一个案例:Vue2组件化开发组件从入门到入土

1. 环境搭建 1.1. 创建项目 npm install -g vue/clivue create vue_study_todolist1.2. 清空项目代码 清楚HelloWorld.Vue代码中的内容。 1.3. 启动空项目 1.4 项目目标 项目组件实现以下效果 2. 组件拆分代码 Vue是一个基于组件的框架&#xff0c;允许您将界面拆分成小的…

Golang使用MinIO

最近在使用Golang做了一个网盘项目&#xff08;学习&#xff09;&#xff0c;文件存储一直保存在本地&#xff08;各厂商提供的oss贵&#xff09;&#xff0c;所以就在思考怎么来处理这些文件&#xff0c;类似的方案很对hdfs、fastdfs&#xff0c;但这其中MinIO是最近几年比较火…