EdgeGraph.Edge.SplitEdge C# (CSharp) Method

SplitEdge() public static method

Splits given edge into two edges at given point If a node is given, it will be used to split the edges Otherwise make a new node
public static SplitEdge ( Edge edge, Vector3 point, List nodes, List edges, Node node = null ) : Node
edge Edge
point Vector3
nodes List
edges List
node Node
return Node
        public static Node SplitEdge(Edge edge, Vector3 point, List<Node> nodes, List<Edge> edges, Node node = null)
        {
            bool isNewNode = false;
            // Create new node
            if (node == null)
            {
                node = new Node(point);
                isNewNode = true;
            }

            // Get start and end nodes of the edge
            Node start = Node.GetNode(nodes, edge.Node1);
            Node end = Node.GetNode(nodes, edge.Node2);

            // Add new node between start and end
            start.adjacents.Remove(end.ID);
            end.adjacents.Remove(start.ID);

            start.adjacents.Add(node.ID);
            end.adjacents.Add(node.ID);

            int startIndex = nodes.IndexOf(start);

            if (startIndex == -1)
            {
                Debug.LogError("Edge::SplitEdge() - StartIndex not found. Are you sure you gave the right node list?");
                return null;
            }

            if (isNewNode)
            {
                if (startIndex == nodes.Count - 1)
                    nodes.Add(node);
                else
                    nodes.Insert(startIndex + 1, node);
            }

            // Remove original edge from edges
            edges.Remove(edge);

            // Create new edges
            Edge e1 = new Edge(start.ID, node.ID, edge.width);
            Edge e2 = new Edge(node.ID, end.ID, edge.width);

            edges.Add(e1);
            edges.Add(e2);

            return node;
        }

Usage Example

Example #1
0
        void ConnectEndPoints(List <Node> _nodes, List <Edge> _edges)
        {
            // Find endpoints
            List <Node> endNodes = new List <Node>();

            for (int i = 1; i < _nodes.Count; i++)
            {
                if (_nodes[i].adjacents.Count == 1)
                {
                    endNodes.Add(_nodes[i]);
                }
            }

            // Connect endpoints to edges or other nodes
            for (int i = 0; i < endNodes.Count; i++)
            {
                // End node direction
                Node    adjacent = Node.GetNode(_nodes, endNodes[i].adjacents[0]);
                Vector3 nodeDir  = (endNodes[i].Position - adjacent.Position).normalized;

                //Check if there is any nodes in the rough direction of the end node
                float       roughAngle = 30f;
                List <Node> nodesInDir = new List <Node>();

                for (int j = 0; j < _nodes.Count; j++)
                {
                    if (_nodes[j] == endNodes[i])
                    {
                        continue;
                    }

                    Vector3 dirToNode = (_nodes[j].Position - endNodes[i].Position).normalized;
                    if (Vector3.Angle(nodeDir, dirToNode) < roughAngle && Vector3.Angle(nodeDir, dirToNode) > 30f)
                    {
                        nodesInDir.Add(_nodes[j]);
                    }
                }

                // The node with which this endpoint is connected to
                Node connectTo = null;

                // If there are some nodes in the rough direction, pick the one that is closest
                if (nodesInDir.Count > 0)
                {
                    float toClosest = Mathf.Infinity;
                    Node  closest   = null;
                    for (int j = 0; j < nodesInDir.Count; j++)
                    {
                        float toCurrent = Vector3.Distance(endNodes[i].Position, nodesInDir[j].Position);
                        if (toCurrent < toClosest)
                        {
                            toClosest = toCurrent;
                            closest   = nodesInDir[j];
                        }
                    }

                    if (toClosest < subEdgeEndConnectionRange)
                    {
                        connectTo = closest;
                    }
                }
                // Else get intersection with closest edge in the direction of this endpoint
                if (connectTo == null)
                {
                    // Ending point for tested segment in the direction of this endpoint
                    Vector3 segmentEnd = endNodes[i].Position + nodeDir * 1000f;

                    // Get the intersection
                    Vector3 intersectPoint = Vector3.zero;
                    // Convert all used points to XZ space
                    Vector3 intersectPointXZ = Vector2.zero;
                    Vector2 endPointXZ       = new Vector2(endNodes[i].Position.x, endNodes[i].Position.z);
                    Vector2 segmentEndXZ     = new Vector2(segmentEnd.x, segmentEnd.z);

                    List <Edge>    intersectedEdges = new List <Edge>();
                    List <Vector3> intersectPoints  = new List <Vector3>();

                    // Ignore the edge that starts on this endpoint
                    Edge endEdge = _edges.Find(e => (e.Node1 == endNodes[i].ID || e.Node2 == endNodes[i].ID));

                    for (int j = 0; j < _edges.Count; j++)
                    {
                        if (_edges[j] == endEdge)
                        {
                            continue;
                        }

                        Node n1 = Node.GetNode(_nodes, _edges[j].Node1);
                        Node n2 = Node.GetNode(_nodes, _edges[j].Node2);

                        Vector2 node1XZ = new Vector2(n1.Position.x, n1.Position.z);
                        Vector2 node2XZ = new Vector2(n2.Position.x, n2.Position.z);

                        if (UtilityTools.MathHelper.AreIntersecting(out intersectPointXZ, endPointXZ, segmentEndXZ, node1XZ, node2XZ) == 1)
                        {
                            intersectPoints.Add(new Vector3(intersectPointXZ.x, n1.Position.y, intersectPointXZ.y));
                            intersectedEdges.Add(_edges[j]);
                        }
                    }

                    // Get closest intersect point
                    float toClosest = Mathf.Infinity;
                    Edge  closestIntersectedEdge = null;
                    for (int j = 0; j < intersectPoints.Count; j++)
                    {
                        float toPoint = Vector3.Distance(endNodes[i].Position, intersectPoints[j]);
                        if (toPoint < toClosest)
                        {
                            toClosest              = toPoint;
                            intersectPoint         = intersectPoints[j];
                            closestIntersectedEdge = intersectedEdges[j];
                        }
                    }

                    // Split the intersected edge on the intersection
                    if (closestIntersectedEdge == null || intersectPoint == Vector3.zero)
                    {
                        Debug.Log("Primitive::ConnectEndPoints() - Intersect point not found.");
                        continue;
                    }
                    else
                    {
                        connectTo = Edge.SplitEdge(closestIntersectedEdge, intersectPoint, _nodes, _edges);
                    }
                }

                _edges.Add(new Edge(endNodes[i].ID, connectTo.ID, subEdgeWidth));
            }

            // Refresh adjacent nodes after all the endpoint connections
            EdgeGraphUtility.CheckAdjacentNodes(ref _nodes, ref _edges);
        }
All Usage Examples Of EdgeGraph.Edge::SplitEdge