コード例 #1
0
        private OwnVector2 findNearestOppositeEdge(CircularLinkedList<Vertex> LAV, Vertex current, out Vertex firstEdgePoint, out Vertex secondEdgePoint)
        {
            firstEdgePoint = null;
            secondEdgePoint = null;
            Node<Vertex> temp = LAV.Find(current).Next;
            Point2D intersectionPoint = new Point2D(0,0);
            Point2D currentClosest = new Point2D(0, 0);
            Vertices testPoly = new Vertices();
            foreach(Vertex v in LAV)
            {
                testPoly.Add(v.getPoint());
            }
            while (!temp.Next.Value.Equals(current))
            {
                //check if the edge is not behind the vertex
                if(LineTools.LineIntersect(
                    current.getRayStart(),
                    new Point2D(current.getRayStart().X + (-current.getRayDirection().X * int.MaxValue), -current.getRayStart().Y + (-current.getRayDirection().Y * int.MaxValue)),
                    temp.Value.getPoint(),
                    temp.Next.Value.getPoint(),
                    true,false, out intersectionPoint))
                {
                    //Calc Bi (intersection ray current + bisector of triangle)
                    Point2D intersect1 = new Point2D(LineTools.LineIntersect(
                        current.prevEdge.getFirstPoint(),
                        current.prevEdge.getSecondPoint(),
                        temp.Value.getPoint(),
                        temp.Next.Value.getPoint()));
                    Point2D intersect2 = new Point2D(LineTools.LineIntersect(
                        current.nextEdge.getFirstPoint(),
                        current.nextEdge.getSecondPoint(),
                        temp.Value.getPoint(),
                        temp.Next.Value.getPoint()));

                    Vertices tempVer = new Vertices();
                    tempVer.Add(current.getPoint());
                    tempVer.Add(intersect1);
                    tempVer.Add(intersect2);

                    Vertex edgeBisector1 = new Vertex(intersect1, -1);
                    edgeBisector1.prevEdge = new Edge(current.getPoint(), intersect1);
                    edgeBisector1.nextEdge = new Edge(intersect1, intersect2);
                    edgeBisector1.update();

                    Point2D Bi = new Point2D(LineTools.LineIntersect(
                        current.getRayStart(),
                        current.getRayStepPoint(),
                        edgeBisector1.getRayStart(),
                        edgeBisector1.getRayStepPoint()));

                    if (tempVer.PointInPolygon(ref Bi) == -1)
                    {

                        edgeBisector1 = new Vertex(intersect2, -1);
                        edgeBisector1.prevEdge = new Edge(current.getPoint(), intersect2);
                        edgeBisector1.nextEdge = new Edge(intersect2, intersect1);
                        edgeBisector1.update();

                        Bi = new Point2D(LineTools.LineIntersect(
                            current.getRayStart(),
                            current.getRayStepPoint(),
                            edgeBisector1.getRayStart(),
                            edgeBisector1.getRayStepPoint()));
                        if (tempVer.PointInPolygon(ref Bi) == -1)
                        {
                            temp = temp.Next;
                            continue;
                        }
                    }

                    //check if Bi inside polygon to begin with
                    if (testPoly.PointInPolygon(ref Bi) == -1)
                    {
                        temp = temp.Next;
                        continue;
                    }

                    //check if Bi is in area defined by opposing edge and it's bisectors
                    //first check if both bisectors of edge are convex so we can see if Bi is inside the defined triangle
                    if(temp.Value.isConvex() && temp.Next.Value.isConvex())
                    {
                        OwnVector2 trianglePoint = LineTools.LineIntersect(
                            temp.Value.getRayStart(),
                            temp.Value.getRayStepPoint(),
                            temp.Next.Value.getRayStart(),
                            temp.Next.Value.getRayStepPoint());

                        if (!MathHelper.PointInTriangle(trianglePoint, temp.Value.getPoint(), temp.Next.Value.getPoint(), Bi))
                        {
                            temp = temp.Next;
                            continue;
                        }
                    }
                    else{
                        Vertices test = new Vertices();
                        int sign1 = temp.Value.isConvex() ? 1 : -1;
                        int sign2 = temp.Next.Value.isConvex() ? 1 : -1;

                        test.Add(temp.Value.getPoint());
                        test.Add(temp.Next.Value.getPoint());
                        test.Add(new Point2D(
                            temp.Next.Value.getPoint().X + (sign2 * temp.Next.Value.getRayDirection().X * int.MaxValue),
                            temp.Next.Value.getPoint().Y + (sign2 * temp.Next.Value.getRayDirection().Y * int.MaxValue)));
                        test.Add(new Point2D(
                            temp.Value.getPoint().X + (sign1 * temp.Value.getRayDirection().X * int.MaxValue),
                            temp.Value.getPoint().Y + (sign1 * temp.Value.getRayDirection().Y * int.MaxValue)));

                        if (test.PointInPolygon(ref Bi) == -1)
                        {
                            temp = temp.Next;
                            continue;
                        }
                    }

                    if (currentClosest.Equals(Point2D.Zero) || Point2D.Distance(current.getPoint(), currentClosest) > Point2D.Distance(current.getPoint(), Bi))
                    {
                        currentClosest = Bi;
                        firstEdgePoint = temp.Value;
                        secondEdgePoint = temp.Next.Value;
                    }
                }
                temp = temp.Next;
            }

            testDots.Add(currentClosest);
            return currentClosest;
        }
コード例 #2
0
        private void findClosestIntersectionAndStore(CircularLinkedList<Vertex> LAV, Vertex prev, Vertex current, Vertex next)
        {
            Vertices testPoly = new Vertices();
            foreach (Vertex v in LAV)
            {
                testPoly.Add(v.getPoint());
            }
            OwnVector2 prevIntersection = LineTools.LineIntersect(
                prev.getRayStart(), prev.getRayStepPoint(),
                current.getRayStart(), current.getRayStepPoint());
            OwnVector2 nextIntersection = LineTools.LineIntersect(
                current.getRayStart(), current.getRayStepPoint(),
                next.getRayStart(), next.getRayStepPoint());
            OwnVector2 nearestOppositeIntersection = OwnVector2.Zero;

            Point2D testPrev = new Point2D(prevIntersection);
            if (testPoly.PointInPolygon(ref testPrev) == -1)
            {
                prevIntersection = Point2D.Zero;
            }
            Point2D testNext = new Point2D(nextIntersection);
            if (testPoly.PointInPolygon(ref testNext) == -1)
            {
                nextIntersection = Point2D.Zero;
            }

            Vertex firstEdgePoint = null;
            Vertex secondEdgePoint = null;
            if(current.isConcave())
            {
                nearestOppositeIntersection = findNearestOppositeEdge(LAV, current, out firstEdgePoint, out secondEdgePoint);
            }

            float distPrev = prevIntersection.Equals(Point2D.Zero) ? float.MaxValue : OwnVector2.Distance(current.getPoint(), prevIntersection);
            float distNext = nextIntersection.Equals(Point2D.Zero) ? float.MaxValue : OwnVector2.Distance(current.getPoint(), nextIntersection);
            float distOpposite = float.MaxValue;

            if (distPrev == 0)
            {
                prevIntersection = Point2D.Zero;
            }
            if (distNext == 0)
            {
                nextIntersection = Point2D.Zero;
            }
            if (current.isConcave())
            {
                distOpposite = OwnVector2.Distance(current.getPoint(), nearestOppositeIntersection);
            }

            if (prevIntersection.Equals(OwnVector2.Zero) && nextIntersection.Equals(OwnVector2.Zero) && nearestOppositeIntersection.Equals(OwnVector2.Zero))
            {
                return;
            }
            if ((nextIntersection.Equals(OwnVector2.Zero) && nearestOppositeIntersection.Equals(OwnVector2.Zero)) || distPrev < distNext && distPrev < distOpposite)
            {
                Event e = new Event(new Point2D(prevIntersection), SLAV.IndexOf(LAV), EventType.Edge);
                e.storeFirstPoint(prev);
                e.storeSecondPoint(current);
                Q.Enqueue(e, distPrev);
            }
            else if ((nearestOppositeIntersection.Equals(OwnVector2.Zero) && prevIntersection.Equals(OwnVector2.Zero)) || distNext <= distPrev && distNext <= distOpposite)
            {
                Event e = new Event(new Point2D(nextIntersection), SLAV.IndexOf(LAV), EventType.Edge);
                e.storeFirstPoint(current);
                e.storeSecondPoint(next);
                Q.Enqueue(e, distNext);
            }
            else
            {
                Event e = new Event(new Point2D(nearestOppositeIntersection), SLAV.IndexOf(LAV), EventType.Split);
                e.storeFirstPoint(current);
                e.storeFirstEdgePoint(firstEdgePoint);
                e.storeSecondEdgePoint(secondEdgePoint);
                Q.Enqueue(e, distOpposite);
            }
        }