Beispiel #1
0
        /// <summary>
        /// Flips the given triangle edge in the triangulation.
        /// Flipping for Delaunay means changing the edge for the adjacent two triangles to the other possibility.
        /// </summary>
        /// <param name="T"></param>
        /// <param name="a_Edge"></param>
        private static void Flip(Triangulation T, TriangleEdge a_Edge)
        {
            var a_Triangle = a_Edge.T;
            var a_Twin     = a_Edge.Twin.T;

            if (a_Triangle == null || a_Twin == null)
            {
                throw new GeomException("Cannot flip edge if neighbouring triangles don't exist");
            }

            // retrieve other adjacent edges to edge vertices
            // e3  .  e1
            //   / | \
            //  .  |  .
            //   \ | /
            // e2  .  e0
            var e0 = a_Triangle.OtherEdge(a_Edge, a_Edge.Point1);
            var e1 = a_Triangle.OtherEdge(a_Edge, a_Edge.Point2);
            var e2 = a_Twin.OtherEdge(a_Edge.Twin, a_Edge.Point1);
            var e3 = a_Twin.OtherEdge(a_Edge.Twin, a_Edge.Point2);

            // create new triangle edges
            var euv = new TriangleEdge(e0.Point1, e2.Point2, null, null);
            var evu = new TriangleEdge(e2.Point2, e0.Point1, euv, null);

            euv.Twin = evu;

            // Remove old triangles
            T.RemoveTriangle(a_Triangle);
            T.RemoveTriangle(a_Twin);

            // add new triangles
            T.AddTriangle(new Triangle(e0, e2, evu));
            T.AddTriangle(new Triangle(e3, e1, euv));
        }
        public void InValidTriangulationTest()
        {
            var m_delaunay = new Triangulation();
            var t1         = new Triangle(m_topVertex, m_rightVertex, m_botVertex);
            var t2         = new Triangle(m_topVertex, m_botVertex, m_leftVertex);

            t1.E2.Twin = t2.E0;
            t2.E0.Twin = t1.E2;
            m_delaunay.AddTriangle(t1);
            m_delaunay.AddTriangle(t2);
            Assert.IsFalse(Delaunay.IsValid(m_delaunay));
        }
Beispiel #3
0
        public void AddTriangleTest()
        {
            var tr = new Triangle(v1, v2, v4);
            var T2 = new Triangulation();

            T2.AddTriangle(tr);
            Assert.AreEqual(1, T2.Triangles.Count);
        }
Beispiel #4
0
        public TriangulationTest()
        {
            v1 = new Vector2(0, 0);
            v2 = new Vector2(1, 1);
            v3 = new Vector2(2, 0);
            v4 = new Vector2(1, -1);

            e1 = new TriangleEdge(v1, v2);
            e2 = new TriangleEdge(v2, v3);
            e3 = new TriangleEdge(v3, v1);
            t1 = new Triangle(e1, e2, e3);

            e4 = new TriangleEdge(v1, v3);
            e5 = new TriangleEdge(v3, v4);
            e6 = new TriangleEdge(v4, v1);
            t2 = new Triangle(e4, e5, e6);

            T = new Triangulation();
            T.AddTriangle(t1);
            T.AddTriangle(t2);
        }
        /// <summary>
        /// Triangulates the polygon recursively.
        /// Finds the leftmost point and creates a triangle with that or splits polygon in two.
        /// </summary>
        /// <param name="vertices"></param>
        /// <returns></returns>
        private static Triangulation TriangulateRecursive(List <Vector2> vertices)
        {
            if (vertices.Count == 3)
            {
                return(new Triangulation(vertices));
            }

            var triangulation = new Triangulation();

            //Find leftmost vertex
            var leftVertex = LeftMost(vertices);
            var index      = vertices.IndexOf(leftVertex);
            var prevVertex = vertices[MathUtil.PositiveMod(index - 1, vertices.Count)];
            var nextVertex = vertices[MathUtil.PositiveMod(index + 1, vertices.Count)];

            //Create triangle with diagonal
            Debug.Assert(leftVertex != prevVertex && leftVertex != nextVertex && prevVertex != nextVertex);

            var triangle = new Triangle(prevVertex, leftVertex, nextVertex);

            //check for other vertices inside the candidate triangle
            var   baseline      = new Line(prevVertex, nextVertex);
            float distance      = -1f;
            int   diagonalIndex = -1;

            for (int i = 0; i < vertices.Count; i++)
            {
                var v = vertices[i];
                if (v != leftVertex && v != prevVertex && v != nextVertex &&
                    triangle.Contains(v))
                {
                    if (baseline.DistanceToPoint(v) > distance)
                    {
                        distance      = baseline.DistanceToPoint(v);
                        diagonalIndex = i;
                    }
                }
            }

            //Do Recursive call
            if (diagonalIndex == -1) //didn't change
            {
                if (!triangle.IsClockwise())
                {
                    // shouldnt happen but in case it does
                    // reverse triangle
                    triangle = new Triangle(triangle.P0, triangle.P2, triangle.P1);
                }

                triangulation.AddTriangle(triangle);
                vertices.Remove(leftVertex);
                triangulation.AddTriangulation(TriangulateRecursive(vertices));
            }
            else
            {
                var minIndex = Mathf.Min(index, diagonalIndex);
                var maxIndex = Mathf.Max(index, diagonalIndex);

                var poly1List = vertices.Skip(minIndex).Take(maxIndex - minIndex + 1).ToList();
                var poly2List = vertices.Skip(maxIndex).Concat(vertices.Take(minIndex + 1)).ToList();

                triangulation.AddTriangulation(TriangulateRecursive(poly1List));
                triangulation.AddTriangulation(TriangulateRecursive(poly2List));
            }

            return(triangulation);
        }