diff --git a/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs b/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs index 0c8e0f283..b37353f8f 100644 --- a/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs +++ b/Source/Editor/Windows/SceneTreeWindow.ContextMenu.cs @@ -55,8 +55,6 @@ namespace FlaxEditor.Windows // Basic editing options b = contextMenu.AddButton("Rename", inputOptions.Rename, Rename); - b.Enabled = isSingleActorSelected; - b = contextMenu.AddButton("Duplicate", inputOptions.Duplicate, Editor.SceneEditing.Duplicate); b.Enabled = hasSthSelected; diff --git a/Source/Editor/Windows/SceneTreeWindow.RenameWindow.cs b/Source/Editor/Windows/SceneTreeWindow.RenameWindow.cs new file mode 100644 index 000000000..fdef598b2 --- /dev/null +++ b/Source/Editor/Windows/SceneTreeWindow.RenameWindow.cs @@ -0,0 +1,177 @@ +using System.Text; +using FlaxEditor.CustomEditors; +using FlaxEditor.GUI; +using FlaxEditor.Windows.Assets; +using FlaxEngine; +using FlaxEngine.GUI; + +namespace FlaxEditor.Windows +{ + /// + /// A window used to rename multiple actors. + /// + public class RenameWindow : EditorWindow + { + /// + private class RenameUndoAction : IUndoAction + { + /// + /// The old actors name to use on action. + /// + public string[] OldNames; + + /// + /// The new actors name to use on action. + /// + public string[] NewNames; + + /// + /// All actors to rename. + /// + public Actor[] ActorsToRename; + + /// + /// Create a undo action. + /// + /// + public RenameUndoAction(Actor[] nodes) + { + ActorsToRename = nodes; + OldNames = new string[nodes.Length]; + + for (int i = 0; i < nodes.Length; i++) + OldNames[i] = nodes[i].Name; + } + + /// + public void Do() + { + for (int i = 0; i < ActorsToRename.Length; i++) + ActorsToRename[i].Name = NewNames[i]; + } + + /// + public void Undo() + { + for (int i = 0; i < ActorsToRename.Length; i++) + ActorsToRename[i].Name = OldNames[i]; + } + + /// + public string ActionString => "Renaming actors."; + + /// + public void Dispose() { } + } + + /// + /// Rename options. + /// + private enum RenameOptions + { + OnlyName, + UsePrefix, + UseSufix + } + + private Label _label; + private TextBox _textBox; + private EnumComboBox _renameOptions; + private Button _renameButton; + + private Actor[] _actorsToRename; + + /// + /// Create an instance of the to rename actors. + /// + /// All actors to rename + /// The editor. + public RenameWindow(Actor[] actorsToRename, Editor editor) : base(editor, true, FlaxEngine.GUI.ScrollBars.None) + { + Title = "Rename"; + _actorsToRename = actorsToRename; + + var container = new VerticalPanel + { + Parent = this, + AnchorPreset = AnchorPresets.StretchAll, + Offset = Vector2.Zero, + + }; + + _label = new Label + { + Text = "New Name", + AnchorPreset = AnchorPresets.TopLeft, + Parent = container, + Size = new Float2(100, 25) + }; + + _textBox = new TextBox + { + Text = "Actor", + AnchorPreset = AnchorPresets.TopLeft, + Parent = container, + Size = new Float2(200, 25) + }; + + var renameOptionLabel = new Label + { + Text = "Rename Option", + AnchorPreset = AnchorPresets.TopLeft, + Parent = container, + Size = new Float2(100, 25) + }; + + _renameOptions = new EnumComboBox(typeof(RenameOptions)) + { + Parent = container, + Value = 0 + }; + + _renameButton = new Button + { + Text = "Rename", + AnchorPreset = AnchorPresets.TopLeft, + Parent = container, + Size = new Float2(200, 25), + }; + + _renameButton.Clicked += () => + { + var renameUndoAction = new RenameUndoAction(_actorsToRename); + Editor.Instance.SceneEditing.Undo.AddAction(renameUndoAction); + renameUndoAction.NewNames = new string[_actorsToRename.Length]; + for (int i = 0; i < _actorsToRename.Length; i++) + { + var actor = _actorsToRename[i]; + if (!actor) + continue; + var newName = new StringBuilder(_textBox.Text); + if (_renameOptions.Value == (int)RenameOptions.UsePrefix) + { + newName = new StringBuilder(); + newName.Append(i); + newName.Append(_textBox.Text); + } + else if (_renameOptions.Value == (int)RenameOptions.UseSufix) + newName.Append(i.ToString()); + var newNameStr = newName.ToString(); + actor.Name = newNameStr; + renameUndoAction.NewNames[i] = newNameStr; + } + Editor.Instance.Scene.MarkAllScenesEdited(); + Close(); + }; + } + + ~RenameWindow() + { + _actorsToRename = null; + _renameButton = null; + _label = null; + _textBox = null; + _renameOptions = null; + } + } +} diff --git a/Source/Editor/Windows/SceneTreeWindow.cs b/Source/Editor/Windows/SceneTreeWindow.cs index 63ba7b960..8ebd508a5 100644 --- a/Source/Editor/Windows/SceneTreeWindow.cs +++ b/Source/Editor/Windows/SceneTreeWindow.cs @@ -13,7 +13,6 @@ using FlaxEditor.Scripting; using FlaxEditor.States; using FlaxEngine; using FlaxEngine.GUI; -using static FlaxEditor.GUI.ItemsListContextMenu; namespace FlaxEditor.Windows { @@ -138,10 +137,24 @@ namespace FlaxEditor.Windows private void Rename() { var selection = Editor.SceneEditing.Selection; - if (selection.Count != 0 && selection[0] is ActorNode actor) + var selectionCount = selection.Count; + + // Show a window with options to rename multiple actors. + if (selectionCount > 1) { - if (selection.Count != 0) - Editor.SceneEditing.Select(actor); + var selectedActors = new Actor[selectionCount]; + + for (int i = 0; i < selectionCount; i++) + if (selection[i] is ActorNode actorNode) + selectedActors[i] = actorNode.Actor; + + new RenameWindow(selectedActors, Editor).Show(); + return; + } + + if (selectionCount != 0 && selection[0] is ActorNode actor) + { + Editor.SceneEditing.Select(actor); actor.TreeNode.StartRenaming(this, _sceneTreePanel); } }