diff --git a/Source/Editor/SceneGraph/SceneEditingTools.cs b/Source/Editor/SceneGraph/SceneEditingTools.cs index d9ad2c5fc..d767d4ae6 100644 --- a/Source/Editor/SceneGraph/SceneEditingTools.cs +++ b/Source/Editor/SceneGraph/SceneEditingTools.cs @@ -1,6 +1,7 @@ // Copyright (c) Wojciech Figat. All rights reserved. using FlaxEditor.GUI.ContextMenu; +using FlaxEditor.Scripting; using FlaxEngine; using System; @@ -12,6 +13,22 @@ namespace FlaxEditor /// internal static class SceneEditingTools { + public static Actor SpawnActorMenu(ContextMenuButton button) + { + var type = (ScriptType)button.Tag; + if (new ScriptType(typeof(FlaxEngine.GUI.Control)).IsAssignableFrom(type)) + { + // UI Control + var actor = new UIControl(); + actor.Name = type.Name; + actor.Control = (FlaxEngine.GUI.Control)type.CreateInstance(); + return actor; + } + + // Create actor + return (Actor)FlaxEngine.Object.New(type.TypeName); + } + public static void AddActorContextMenu(ContextMenu contextMenu, Action spawn, bool isConvert = false) { // Go through each actor and add it to the context menu if it has the ActorContextMenu attribute @@ -33,17 +50,38 @@ namespace FlaxEditor bool mainCM = true; for (int i = 0; i < splitPath?.Length; i++) { + var name = splitPath[i].Trim(); if (i == splitPath.Length - 1) { + // Hardcoded UI Controls toolbox + if (!isConvert && childCM != null && actorType.Type == typeof(UIControl)) + { + var menu = childCM.ContextMenu.GetOrAddChildMenu(name); + menu.ButtonClicked += spawn; + menu.Tag = actorType; + menu.ContextMenu.AutoSort = true; + var b = menu.ContextMenu.AddButton("Empty", spawn); + b.Tag = actorType; + foreach (var controlType in Editor.Instance.CodeEditing.Controls.Get()) + { + if (controlType.IsAbstract) + continue; + name = Utilities.Utils.GetPropertyNameUI(controlType.Name); + b = menu.ContextMenu.AddButton(name, spawn); + b.Tag = controlType; + } + continue; + } + if (mainCM) { - var b = contextMenu.AddButton(splitPath[i].Trim(), spawn); + var b = contextMenu.AddButton(name, spawn); b.Tag = actorType; mainCM = false; } else if (childCM != null) { - var b = childCM.ContextMenu.AddButton(splitPath[i].Trim(), spawn); + var b = childCM.ContextMenu.AddButton(name, spawn); b.Tag = actorType; } } @@ -55,13 +93,13 @@ namespace FlaxEditor if (mainCM) { - childCM = contextMenu.GetOrAddChildMenu(splitPath[i].Trim()); + childCM = contextMenu.GetOrAddChildMenu(name); childCM.ContextMenu.AutoSort = true; mainCM = false; } else if (childCM != null) { - childCM = childCM.ContextMenu.GetOrAddChildMenu(splitPath[i].Trim()); + childCM = childCM.ContextMenu.GetOrAddChildMenu(name); childCM.ContextMenu.AutoSort = true; } } diff --git a/Source/Editor/Windows/Assets/PrefabWindow.Hierarchy.cs b/Source/Editor/Windows/Assets/PrefabWindow.Hierarchy.cs index 0b91ba4f2..fe80ac34c 100644 --- a/Source/Editor/Windows/Assets/PrefabWindow.Hierarchy.cs +++ b/Source/Editor/Windows/Assets/PrefabWindow.Hierarchy.cs @@ -325,7 +325,10 @@ namespace FlaxEditor.Windows.Assets // Spawning actors contextMenu.AddSeparator(); - SceneEditingTools.AddActorContextMenu(contextMenu, b => Spawn(((ScriptType)b.Tag).Type)); + SceneEditingTools.AddActorContextMenu(contextMenu, b => { + Spawn(SceneEditingTools.SpawnActorMenu(b)); + RenameSelection(); + }); // Custom options bool showCustomNodeOptions = Selection.Count == 1; @@ -417,20 +420,6 @@ namespace FlaxEditor.Windows.Assets Spawn(actor, parentActor); } - /// - /// Spawns the actor of the specified type to the prefab (adds actor to root). - /// - /// The actor type. - public void Spawn(Type type) - { - // Create actor - Actor actor = (Actor)FlaxEngine.Object.New(type); - - // Spawn it - Spawn(actor); - RenameSelection(); - } - /// /// Spawns the specified actor. /// diff --git a/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs b/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs index 42e7510ae..93b1dfb33 100644 --- a/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs +++ b/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs @@ -120,7 +120,7 @@ namespace FlaxEditor.Windows // Spawning actors contextMenu.AddSeparator(); - SceneEditingTools.AddActorContextMenu(contextMenu, b => Spawn(((ScriptType)b.Tag).Type)); + SceneEditingTools.AddActorContextMenu(contextMenu, b => Spawn(SceneEditingTools.SpawnActorMenu(b))); // Custom options bool showCustomNodeOptions = Editor.SceneEditing.Selection.Count == 1; diff --git a/Source/Editor/Windows/SceneTreeWindow.cs b/Source/Editor/Windows/SceneTreeWindow.cs index e7dcb3319..f74463afc 100644 --- a/Source/Editor/Windows/SceneTreeWindow.cs +++ b/Source/Editor/Windows/SceneTreeWindow.cs @@ -198,10 +198,8 @@ namespace FlaxEditor.Windows PerformLayout(); } - private void Spawn(Type type) + private void Spawn(Actor actor) { - // Create actor - Actor actor = (Actor)FlaxEngine.Object.New(type); Actor parentActor = null; if (Editor.SceneEditing.HasSthSelected && Editor.SceneEditing.Selection[0] is ActorNode actorNode) { @@ -220,7 +218,7 @@ namespace FlaxEditor.Windows actor.Transform = parentActor.Transform; // Rename actor to identify it easily - actor.Name = Utilities.Utils.IncrementNameNumber(type.Name, x => parentActor.GetChild(x) == null); + actor.Name = Utilities.Utils.IncrementNameNumber(actor.Name, x => parentActor.GetChild(x) == null); } // Spawn it