diff --git a/Scripts/Editor/NodeEditorGUI.cs b/Scripts/Editor/NodeEditorGUI.cs index 476153d..41df407 100644 --- a/Scripts/Editor/NodeEditorGUI.cs +++ b/Scripts/Editor/NodeEditorGUI.cs @@ -75,6 +75,17 @@ namespace XNodeEditor { public void ShowNodeContextMenu(Node node) { GenericMenu contextMenu = new GenericMenu(); contextMenu.AddItem(new GUIContent("Remove"), false, () => graph.RemoveNode(node)); + contextMenu.AddItem(new GUIContent("Duplicate"), false, () => { + Node n = graph.CopyNode(node); + n.position = node.position + new Vector2(30,30); + }); + contextMenu.AddItem(new GUIContent("Move To Top"), false, () => { + int index; + while((index = graph.nodes.IndexOf(node)) != graph.nodes.Count-1) { + graph.nodes[index] = graph.nodes[index+1]; + graph.nodes[index+1] = node; + } + }); AddCustomContextMenuItems(contextMenu, node); contextMenu.DropDown(new Rect(Event.current.mousePosition, Vector2.zero)); } diff --git a/Scripts/NodeGraph.cs b/Scripts/NodeGraph.cs index 8253a42..f6ff86d 100644 --- a/Scripts/NodeGraph.cs +++ b/Scripts/NodeGraph.cs @@ -11,10 +11,12 @@ namespace XNode { /// See: [SerializeField] public List nodes = new List(); + /// Add a node to the graph by type public T AddNode() where T : Node { return AddNode(typeof(T)) as T; } + /// Add a node to the graph by type public virtual Node AddNode(Type type) { Node node = ScriptableObject.CreateInstance(type) as Node; #if UNITY_EDITOR @@ -28,6 +30,21 @@ namespace XNode { return node; } + /// Creates a copy of the original node in the graph + public virtual Node CopyNode(Node original) { + Node node = ScriptableObject.Instantiate(original); + node.ClearConnections(); +#if UNITY_EDITOR + if (!Application.isPlaying) { + UnityEditor.AssetDatabase.AddObjectToAsset(node, this); + UnityEditor.AssetDatabase.SaveAssets(); + } +#endif + nodes.Add(node); + node.graph = this; + return node; + } + /// Safely remove a node and all its connections /// public void RemoveNode(Node node) {