//... void OnEnable() { var canvasIcon = (Texture)Resources.Load("CanvasIcon"); titleContent = new GUIContent("Finder", canvasIcon); wantsMouseMove = true; wantsMouseEnterLeaveWindow = true; GraphEditor.onCurrentGraphChanged -= GraphChanged; GraphEditor.onCurrentGraphChanged += GraphChanged; Graph.onGraphSerialized -= OnGraphSerialized; Graph.onGraphSerialized += OnGraphSerialized; GraphEditorUtility.onActiveElementChanged -= OnActiveElementChanged; GraphEditorUtility.onActiveElementChanged += OnActiveElementChanged; graphElement = null; search = null; lastHoverElement = null; scrollPos = default(Vector2); willRepaint = true; if (GraphEditor.currentGraph != null) { FetchElements(GraphEditor.currentGraph); } }
///Returns an element that includes tasks and parameters for target object recursively public static Hierarchy.Element GetTaskAndParametersStructureInTarget(object obj) { var parentElement = new Hierarchy.Element(obj); var resultObjects = new List <object>(); if (obj is ITaskAssignable && (obj as ITaskAssignable).task != null) { resultObjects.Add((obj as ITaskAssignable).task); } if (obj is ISubTasksContainer) { var subs = (obj as ISubTasksContainer).GetSubTasks(); if (subs != null) { resultObjects.AddRange(subs); } } //this also handles ISubParametersContainer resultObjects.AddRange(BBParameter.GetObjectBBParameters(obj).ToArray()); //recurse for (var i = 0; i < resultObjects.Count; i++) { parentElement.AddChild(GetTaskAndParametersStructureInTarget(resultObjects[i])); } return(parentElement); }
///---------------------------------------------------------------------------------------------- ///Returns a structure of the graphs that includes Nodes, Connections, Tasks and BBParameters, ///but with nodes elements all being root to the graph (instead of respective parent connections). virtual public Hierarchy.Element GetFlatGraphHierarchy() { var root = new Hierarchy.Element(this); int lastID = 0; for (var i = 0; i < allNodes.Count; i++) { root.AddChild(GetTreeNodeElement(allNodes[i], false, ref lastID)); } return(root); }
///Returns a structure of the graphs that includes Nodes, Connections, Tasks and BBParameters, ///but where node elements are parent to their respetive connections. Only possible for tree-like graphs. public Hierarchy.Element GetFullGraphHierarchy() { var root = new Hierarchy.Element(this); int lastID = 0; if (primeNode != null) { root.AddChild(GetTreeNodeElement(primeNode, true, ref lastID)); } for (var i = 0; i < allNodes.Count; i++) { var node = allNodes[i]; if (node.ID > lastID && node.inConnections.Count == 0) { root.AddChild(GetTreeNodeElement(node, true, ref lastID)); } } return(root); }
///---------------------------------------------------------------------------------------------- //Initialize the graph elements void FetchElements(Graph graph) { graphElement = graph.GetFlatGraphHierarchy(); willRepaint = true; }
///Focus element. This also Pings it. User click. void FocusElement(Hierarchy.Element e) { var element = e.GetFirstParentReferenceOfType <IGraphElement>(); EditorApplication.delayCall += () => GraphEditor.FocusElement(element, true); }
//... void DoElement(Hierarchy.Element element, Rect parentElementRect = default(Rect)) { if (element.children == null) { return; } foreach (var child in element.children) { var elementRect = default(Rect); if (child.reference == null) { continue; } //Dont show undefined parameters. //TODO: I dont like this "special case" here if (child.reference is BBParameter) { var bbPram = (BBParameter)child.reference; if (!bbPram.isDefined) { continue; } } var toString = child.reference.ToString(); var typeName = child.reference.GetType().FriendlyName(); var searchText = toString + " " + typeName; if (string.IsNullOrEmpty(search) || StringUtils.SearchMatch(search, searchText)) { GUI.color = EditorGUIUtility.isProSkin? Color.white : Colors.Grey(0.8f); GUILayout.BeginHorizontal("box"); GUILayout.Space(indent * INDENT_WIDTH); GUI.color = Color.white; var displayText = string.Format("<b>{0}</b>{1}", toString, NCPrefs.finderShowTypeNames? " (" + typeName + ")" : string.Empty); GUILayout.Label(string.Format("<size=9>{0}</size>", displayText)); GUILayout.EndHorizontal(); elementRect = GUILayoutUtility.GetLastRect(); EditorGUIUtility.AddCursorRect(elementRect, MouseCursor.Link); if (elementRect.Contains(Event.current.mousePosition)) { if (child != lastHoverElement) { lastHoverElement = child; willRepaint = true; PingElement(child); } GUI.color = new Color(0.5f, 0.5f, 1, 0.3f); GUI.DrawTexture(elementRect, EditorGUIUtility.whiteTexture); GUI.color = Color.white; if (Event.current.type == EventType.MouseDown) { FocusElement(child); Event.current.Use(); } } if (GraphEditorUtility.activeElement == child.reference) { GUI.color = new Color(0.5f, 0.5f, 1, 0.1f); GUI.DrawTexture(elementRect, EditorGUIUtility.whiteTexture); GUI.color = Color.white; } } indent++; DoElement(child, elementRect); indent--; if (elementRect != default(Rect)) { var rootOrNotParentHidden = indent == INDENT_START || parentElementRect != default(Rect); var lineVer = new Rect(); lineVer.xMin = elementRect.xMin + (indent * INDENT_WIDTH) - (INDENT_WIDTH / 2); lineVer.width = 2; lineVer.yMin = parentElementRect.yMax + 6; lineVer.yMax = elementRect.yMax - (elementRect.height / 2); var lineHor = new Rect(); lineHor.xMin = rootOrNotParentHidden? lineVer.xMin : (INDENT_WIDTH / 2); lineHor.xMax = lineVer.xMin + (INDENT_WIDTH / 2); lineHor.yMin = lineVer.yMax - 2; lineHor.height = 2; GUI.color = Colors.Grey(EditorGUIUtility.isProSkin? 0.6f : 0.3f); if (rootOrNotParentHidden) { GUI.DrawTexture(lineVer, Texture2D.whiteTexture); } GUI.DrawTexture(lineHor, Texture2D.whiteTexture); GUI.color = Color.white; } if (indent == INDENT_START && string.IsNullOrEmpty(search)) { EditorUtils.Separator(); } } }