2025-01-22 Unity Editor 1 —— MenuItem 入门
文章目录
- 1 Editor 文件夹
- 2 MenuItem
- 3 使用示例
- 3.1 打开网址
- 3.2 打开文件夹
- 3.3 Menu Toggle
- 3.4 Menu 代码复用
- 3.5 MenuItem 激活与失活
- 4 代码示例
1 Editor 文件夹
Editor 文件夹是 Unity 中的特殊文件夹,Unity 中所有编辑器相关的脚本都需要放置在其中,其相关的命名空间为 UnityEditor。
使用命名空间 UnityEditor 的脚本最终不能被 Unity 打包,需要将这些脚本放置到 Editor 文件夹中,避免打包时报错。
2 MenuItem
在静态函数前加上特性:[MenuItem("页签/一级选项/二级选项/....")]
,则会在菜单栏显示对应的页签。
当点击页签时,特性修饰的静态函数将被执行。
[MenuItem("EditorExtension/01.Menu/01.Hello Editor")]
static void HelloEditor()
{
Debug.Log("Hello Editor");
}
3 使用示例
3.1 打开网址
使用 Application.OpenURL
打开网址。
[MenuItem("EditorExtension/01.Menu/02.Open Bilibili")]
static void OpenBilibili()
{
Application.OpenURL("https://bilibili.com");
}
3.2 打开文件夹
在 Editor 中,可以使用 EditorUtility 提供的 API 直接打开文件夹。
[MenuItem("EditorExtension/01.Menu/03.Open PersistentDataPath")]
static void OpenPersistentDataPath()
{
EditorUtility.RevealInFinder(Application.persistentDataPath);
}
[MenuItem("EditorExtension/01.Menu/04.打开策划目录")]
static void OpenDesignerFolder()
{
EditorUtility.RevealInFinder(Application.dataPath.Replace("Assets", "Library"));
}
3.3 Menu Toggle
Menu 类为页签提供 Toggle 功能,点击页签后,可在旁边显示 √。
[MenuItem("EditorExtension/01.Menu/05.快捷键开关")]
static void ToggleShotCut()
{
mOpenShotCut = !mOpenShotCut;
Menu.SetChecked("EditorExtension/01.Menu/05.快捷键开关", mOpenShotCut);
}
3.4 Menu 代码复用
使用 EditorApplication.ExecuteMenuItem 可复用执行 MenuItem 对应的静态函数。
尽管直接调用静态函数更为方便,但当该静态函数为 private 且需要在外部调用时,便可使用该方法。
[MenuItem("EditorExtension/01.Menu/06.Hello Editor _c")]
static void HelloEditorWithShotCut()
{
// 等价于调用 HelloEditor() 函数
EditorApplication.ExecuteMenuItem("EditorExtension/01.Menu/01.Hello Editor");
}
上述代码为菜单路径添加了快捷键 “C” 触发,因为在菜单路径 “EditorExtensions/01.Menu/06.Hello Editor” 后添加了 " _c":使用空格隔开菜单路径与快捷键,使用下划线表示快捷键是单个键 “C”。
- 单键:菜单路径 + 空格 + 下划线 + 想要的按键
- 组合键:下划线替换为
%
:表示 Ctrl#
:表示 Shift&
:表示 Alt- 其他支持的按键:
LEFT
、RIGHT
:#LEFT 表示左 Shift 按键。UP
、DOWN
、F1-F12
、HOME
、END
、PGUP
、PGDN
。
3.5 MenuItem 激活与失活
控制 MenuItem(path)
的激活与失活,需要:
- 额外声明一个静态方法,添加 MenuItem 特性。
- MenuItem 的菜单路径与目标路径 path 一致。
- MenuItem 额外添加参数
validate = true
。
- 静态方法方法返回 bool 类型值,表示 MenuItem 是否可被点击(被激活)。
[MenuItem("EditorExtension/01.Menu/06.Hello Editor _c", validate = true)]
static bool HelloEditorWithShotCutValidate()
{
// 由 Toggle:“05.快捷键开关” 控制
return Menu.GetChecked("EditorExtension/01.Menu/05.快捷键开关");
}
4 代码示例
using UnityEngine;
namespace EditorExtension
{
using UnityEditor;
public class MenuItemExample
{
[MenuItem("EditorExtension/01.Menu/01.Hello Editor")]
static void HelloEditor()
{
Debug.Log("Hello Editor!");
}
[MenuItem("EditorExtension/01.Menu/02.Open Bilibili")]
static void OpenBilibili()
{
Application.OpenURL("https://www.bilibili.com");
}
[MenuItem("EditorExtension/01.Menu/03.Open PersistentDataPath")]
static void OpenPersistentDataPath()
{
EditorUtility.RevealInFinder(Application.persistentDataPath);
}
[MenuItem("EditorExtension/01.Menu/04.打开策划目录")]
static void OpenDesignerFolder()
{
EditorUtility.RevealInFinder(Application.dataPath.Replace("Assets", "Library"));
}
[MenuItem("EditorExtension/01.Menu/05.快捷键开关")]
static void ToggleShotCut()
{
var menuPath = "EditorExtension/01.Menu/05.快捷键开关";
var check = Menu.GetChecked(menuPath);
Menu.SetChecked(menuPath, !check);
}
[MenuItem("EditorExtension/01.Menu/06.Hello Editor _c")]
static void HelloEditorWithShotCut()
{
// 复用方式 1:直接调用方法,但因为方法为 private,不可外部调用
// HelloEditor();
// 复用方式 2:复用菜单,可外部调用
EditorApplication.ExecuteMenuItem("EditorExtension/01.Menu/01.Hello Editor");
}
[MenuItem("EditorExtension/01.Menu/06.Hello Editor _c", validate = true)]
static bool HelloEditorWithShotCutValidate()
{
// 由 Toggle:“05.快捷键开关” 控制
return Menu.GetChecked("EditorExtension/01.Menu/05.快捷键开关");
}
[MenuItem("EditorExtension/01.Menu/07.Open Bilibili %e")]
static void OpenBilibiliWithShotCut()
{
EditorApplication.ExecuteMenuItem("EditorExtension/01.Menu/02.Open Bilibili");
}
[MenuItem("EditorExtension/01.Menu/07.Open Bilibili %e", validate = true)]
static bool OpenBilibiliWithShotCutValidate()
{
return Menu.GetChecked("EditorExtension/01.Menu/05.快捷键开关");
}
[MenuItem("EditorExtension/01.Menu/08.Open PersistentDataPath %#t")]
static void OpenPersistentDataPathWithShotCut()
{
EditorApplication.ExecuteMenuItem("EditorExtension/01.Menu/03.Open PersistentDataPath");
}
[MenuItem("EditorExtension/01.Menu/08.Open PersistentDataPath %#t", validate = true)]
static bool OpenPersistentDataPathWithShotCutValidate()
{
return Menu.GetChecked("EditorExtension/01.Menu/05.快捷键开关");
}
[MenuItem("EditorExtension/01.Menu/09.打开策划目录 &r")]
static void OpenDesignerFolderWithShotCut()
{
EditorApplication.ExecuteMenuItem("EditorExtension/01.Menu/04.打开策划目录");
}
[MenuItem("EditorExtension/01.Menu/09.打开策划目录 &r", validate = true)]
static bool OpenDesignerFolderWithShotCutValidate()
{
return Menu.GetChecked("EditorExtension/01.Menu/05.快捷键开关");
}
}
}