public void AddEdgeTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new Vector2(2, 2));

            dcel.AddEdge(v1, v2);
            Assert.AreEqual(1, dcel.EdgeCount);
            dcel.AddEdge(new Vector2(0, 2), new Vector2(2, 0));
            Assert.AreEqual(4, dcel.EdgeCount);

            Assert.Throws <GeomException>(() => dcel.AddEdge(new DCELVertex(-1, -1), v1));
        }
        public void GetContainingFaceTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new DCELVertex(10, 10));
            var v3   = dcel.AddVertex(new DCELVertex(20, 0));

            dcel.AddEdge(v1, v2);
            dcel.AddEdge(v2, v3);
            dcel.AddEdge(v3, v1);
            var expFace = dcel.InnerFaces.FirstOrDefault();

            Assert.AreEqual(expFace, dcel.GetContainingFace(new Vector2(10, 5)));
            Assert.AreEqual(dcel.OuterFace, dcel.GetContainingFace(new Vector2(-1, 0)));
        }
        public void AdjacentEdgesTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new DCELVertex(10, 10));
            var v3   = dcel.AddVertex(new DCELVertex(20, 0));

            dcel.AddEdge(v1, v2);
            dcel.AddEdge(v2, v3);

            Assert.AreEqual(2, dcel.AdjacentEdges(v1).Count);
            Assert.AreEqual(4, dcel.AdjacentEdges(v2).Count);
            Assert.AreEqual(2, dcel.AdjacentEdges(v3).Count);
            Assert.AreEqual(1, dcel.OutgoingEdges(v1).Count);
            Assert.AreEqual(2, dcel.OutgoingEdges(v2).Count);
            Assert.AreEqual(1, dcel.OutgoingEdges(v3).Count);
        }
示例#4
0
        /// <summary>
        /// Creates a Voronoi DCEL from a triangulation. Triangulation should be Delaunay
        /// </summary>
        /// <param name="m_Delaunay"></param>
        /// <returns></returns>
        public static DCEL Create(Triangulation m_Delaunay)
        {
            if (!Delaunay.IsValid(m_Delaunay))
            {
                throw new GeomException("Triangulation should be delaunay for the Voronoi diagram.");
            }

            var dcel = new DCEL();

            // create vertices for each triangles circumcenter and store them in a dictionary
            Dictionary <Triangle, DCELVertex> vertexMap = new Dictionary <Triangle, DCELVertex>();

            foreach (var triangle in m_Delaunay.Triangles)
            {
                // degenerate triangle, just ignore
                if (!triangle.Circumcenter.HasValue)
                {
                    continue;
                }

                var vertex = new DCELVertex(triangle.Circumcenter.Value);
                dcel.AddVertex(vertex);
                vertexMap.Add(triangle, vertex);
            }

            // remember which edges where visited
            // since each edge has a twin
            var edgesVisited = new HashSet <TriangleEdge>();

            foreach (var edge in m_Delaunay.Edges)
            {
                // either already visited twin edge or edge is outer triangle
                if (edgesVisited.Contains(edge) || edge.IsOuter)
                {
                    continue;
                }

                // add edge between the two adjacent triangles vertices
                // vertices at circumcenter of triangle
                if (edge.T != null && edge.Twin.T != null)
                {
                    var v1 = vertexMap[edge.T];
                    var v2 = vertexMap[edge.Twin.T];

                    HalfEdge e1 = dcel.AddEdge(v1, v2);

                    e1.Twin.Face.owner = m_Delaunay.GetOwner(edge.Point1);
                    e1.Face.owner      = m_Delaunay.GetOwner(edge.Point2);

                    edgesVisited.Add(edge);
                    edgesVisited.Add(edge.Twin);
                }
            }

            return(dcel);
        }
        public void CycleTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new DCELVertex(10, 10));
            var v3   = dcel.AddVertex(new DCELVertex(20, 0));
            var e1   = dcel.AddEdge(v1, v2);
            var e2   = dcel.AddEdge(v2, v3);
            var e3   = dcel.AddEdge(v3, v1);

            Assert.Contains(e1, DCEL.Cycle(e1));
            Assert.Contains(e2, DCEL.Cycle(e1));
            Assert.Contains(e3, DCEL.Cycle(e1));
            Assert.Contains(e1, DCEL.Cycle(e2));
            Assert.Contains(e2, DCEL.Cycle(e2));
            Assert.Contains(e3, DCEL.Cycle(e2));
            Assert.Contains(e1, DCEL.Cycle(e3));
            Assert.Contains(e2, DCEL.Cycle(e3));
            Assert.Contains(e3, DCEL.Cycle(e3));
        }
        public void InnerFacesTest()
        {
            var dcel = new DCEL();

            // create large triangle
            var v1 = dcel.AddVertex(new DCELVertex(0, 0));
            var v2 = dcel.AddVertex(new DCELVertex(10, 10));
            var v3 = dcel.AddVertex(new DCELVertex(20, 0));

            dcel.AddEdge(v1, v2);
            dcel.AddEdge(v2, v3);
            dcel.AddEdge(v3, v1);


            // create smaller inner triangle
            var v4 = dcel.AddVertex(new DCELVertex(9, 2));
            var v5 = dcel.AddVertex(new DCELVertex(10, 3));
            var v6 = dcel.AddVertex(new DCELVertex(11, 2));

            dcel.AddEdge(v4, v5);
            dcel.AddEdge(v5, v6);
            dcel.AddEdge(v6, v4);

            Assert.AreEqual(6, dcel.VertexCount);
            Assert.AreEqual(6, dcel.EdgeCount);
            Assert.AreEqual(3, dcel.FaceCount);
            Assert.AreEqual(1, dcel.OuterFace.InnerComponents.Count);
            Assert.AreEqual(1, dcel.InnerFaces.FirstOrDefault().InnerComponents.Count);

            // create outside triangle
            // create smaller inner triangle
            var v7 = dcel.AddVertex(new DCELVertex(-1, -1));
            var v8 = dcel.AddVertex(new DCELVertex(-2, -2));
            var v9 = dcel.AddVertex(new DCELVertex(-3, -1));

            dcel.AddEdge(v7, v8);
            dcel.AddEdge(v8, v9);
            dcel.AddEdge(v9, v7);

            Assert.AreEqual(9, dcel.VertexCount);
            Assert.AreEqual(9, dcel.EdgeCount);
            Assert.AreEqual(4, dcel.FaceCount);
            Assert.AreEqual(2, dcel.OuterFace.InnerComponents.Count);
        }
        public void AddVertexInEdgeTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new Vector2(2, 2));
            var e    = dcel.AddEdge(v1, v2);
            var v3   = dcel.AddVertexInEdge(e, new Vector2(1.5f, 1.5f));

            Assert.AreEqual(3, dcel.VertexCount);
            Assert.AreEqual(2, dcel.EdgeCount);

            var e2 = new HalfEdge(v3, v1);

            Assert.Throws <GeomException>(() => dcel.AddVertexInEdge(e2, v3.Pos));
            Assert.Throws <GeomException>(() => dcel.AddVertexInEdge(e, new Vector2(-1, -1)));
        }
        public void AddVertexTest()
        {
            var dcel = new DCEL();
            var v1   = dcel.AddVertex(new DCELVertex(0, 0));
            var v2   = dcel.AddVertex(new Vector2(2, 2));

            Assert.AreEqual(2, dcel.VertexCount);

            // vertex on edge test
            var e = dcel.AddEdge(v1, v2);

            Assert.AreEqual(e, v1.Leaving);
            Assert.AreEqual(e.Twin, v2.Leaving);
            dcel.AddVertex(new Vector2(1, 1));
            Assert.AreEqual(3, dcel.VertexCount);
            Assert.AreEqual(2, dcel.EdgeCount);
        }