/// <summary> /// Checks if the passed node connector can connect to this connector. /// </summary> public bool CanConnect(NodeConnector target) { if (ConnectedNodeConnectors.Count <= allowedConnectionCount) { if (target.ParentNodeType == allowedNodeType || Node.GetSuperiorType(target.ParentNodeType) == allowedNodeType || AllowedNodeType == NodeType.NONE) { return(true); } } return(false); }
/// <summary> /// Shows a node selection menu in the editor at the mouse position with all node which has a connection possibilities with the passed NodeConnector. /// </summary> /// <param name="connector"></param> public void ShowNodeSelectionMenuInNodeEditor(NodeConnector connector) { ClearNodeEditorContexMenu(); Assembly assembly = Assembly.GetExecutingAssembly(); foreach (var type in assembly.GetTypes()) { if (type.GetCustomAttribute <NodeAttribute>() == null || type.GetCustomAttribute <NodeAttribute>().AllowedTypes == null) { continue; } if (connector.CanConnect(type.GetCustomAttribute <NodeAttribute>().Type) && (type.GetCustomAttribute <NodeAttribute>().AllowedTypes.Contains(connector.ParentNodeType) || type.GetCustomAttribute <NodeAttribute>().AllowedTypes.Contains(Node.GetSuperiorType(connector.ParentNodeType)))) { NodeMenuItem menuItem = new NodeMenuItem(type.GetCustomAttribute <NodeAttribute>().Type, connector.ParentNode) { Header = type.GetCustomAttribute <NodeAttribute>().MenuName, }; menuItem.Click += HandleNodeMenu; if (type.Namespace.Contains("AIOwnerNodes")) { selectionMenuOwnerNodes.Items.Add(menuItem); } else if (type.Namespace.Contains("ActionNodes")) { selectionMenuActionNodes.Items.Add(menuItem); } else if (type.Namespace.Contains("EventNodes")) { selectionMenuEventNodes.Items.Add(menuItem); } else if (type.Namespace.Contains("TargetNodes")) { selectionMenuTargetNodes.Items.Add(menuItem); } } } }
/// <summary> /// Connects a node to a node inside this tree. /// The old tree of the node is combined with this tree. /// </summary> public void ConnectNode(Node _node, Node _originNode) { // Node tree of _connectTo node must be this tree! Debug.Assert(_originNode.NodeTree == this); if (_node.GetDirectlyConnectedNodes(NodeType.NONE).Contains(_originNode)) { return; } NodeConnector origin = null; NodeConnector target = null; foreach (NodeConnector originConnector in _originNode.Connectors) { foreach (NodeConnector targetConnector in _node.Connectors) { if (originConnector.CanConnect(targetConnector) && targetConnector.CanConnect(originConnector)) { origin = originConnector; target = targetConnector; } } } //Check if no connection possible if (origin == null || target == null) { MessageBox.Show("Nodes can't be connected!"); return; } //Link the connectors origin.ConnectTo(target); target.ConnectTo(origin); //Create visual connection visualConnectionsStore.Add(new VisualConnection(origin, target, nodeEditor)); //Combine the two trees if the new node has one if (_node.NodeTree != null && _node.NodeTree != this) { if (_node.NodeTree.NodeCount() > 0) { List <Node> removeNodes = new List <Node>(); foreach (Node node in _node.NodeTree.nodes) { //TODO: Tranfer connections from the old tree nodes.Add(node); removeNodes.Add(node); } foreach (Node node in removeNodes) { _node.NodeTree.RemoveNode(node); } } } else { _node.NodeTree = this; } nodes.Add(_node); //Sort the new node in right bucket int index = GetNodeVisualBucketIndex(_originNode); if (origin.Type == NodeConnectorType.INPUT) { index--; } else if (origin.Type == NodeConnectorType.OUTPUT) { index++; } if (!visualBuckets.ContainsKey(index)) { visualBuckets[index] = new VisualBucket(); } visualBuckets[index].Add(_node); AutoPosition(); }