private void Fortunes() { Site nSite; Site bottomSite; Site topSite; Site tSite; Vertex v1; Vertex v2; Point newIntStar = null; Orientation lr; HalfEdge lBnd; HalfEdge rBnd; HalfEdge llBnd; HalfEdge rrBnd; HalfEdge bisector; Edge e; Rectangle dataBounds = sites.GetSitesBounds(); int sqrtNSites = (int)Math.Sqrt(sites.GetLength() + 4); HalfEdgePriorityQueue heap = new HalfEdgePriorityQueue(dataBounds.y, dataBounds.height, sqrtNSites); EdgeList edgeList = new EdgeList(dataBounds.x, dataBounds.width, sqrtNSites); List <HalfEdge> halfEdges = new List <HalfEdge>(); List <Vertex> vertices = new List <Vertex>(); Site lowestSite = this.sites.Next(); nSite = sites.Next(); for (;;) { if (heap.Empty() == false) { newIntStar = heap.Min(); } if (nSite != null && (heap.Empty() || CompareByYThenX(nSite, newIntStar) < 0)) { lBnd = edgeList.EdgeListLeftNeighbor(nSite.coord); rBnd = lBnd.edgeListRightNeighbor; bottomSite = RightRegion(lBnd, lowestSite); e = Edge.CreateBisectingEdge(bottomSite, nSite); this.edges.Add(e); bisector = HalfEdge.Create(e, Orientation.LEFT); halfEdges.Add(bisector); //Console.WriteLine(lBnd.edgeListLeftNeighbor); //Console.WriteLine(lBnd.edgeListRightNeighbor); edgeList.Insert(lBnd, bisector); if ((v2 = Vertex.Intersect(lBnd, bisector)) != null) { vertices.Add(v2); heap.Remove(lBnd); lBnd.v = v2; lBnd.yStar = v2.GetCoord().y + nSite.Dist(v2); heap.Insert(lBnd); } lBnd = bisector; bisector = HalfEdge.Create(e, Orientation.RIGHT); halfEdges.Add(bisector); edgeList.Insert(lBnd, bisector); if ((v2 = Vertex.Intersect(bisector, rBnd)) != null) { vertices.Add(v2); bisector.v = v2; bisector.yStar = v2.GetCoord().y + nSite.Dist(v2); heap.Insert(bisector); } nSite = this.sites.Next(); } else if (heap.Empty() == false) { lBnd = heap.ExtractMin(); llBnd = lBnd.edgeListLeftNeighbor; rBnd = lBnd.edgeListRightNeighbor; rrBnd = rBnd.edgeListRightNeighbor; bottomSite = LeftRegion(lBnd, lowestSite); topSite = RightRegion(rBnd, lowestSite); v1 = lBnd.v; v1.SetIndex(); lBnd.e.SetVertex(lBnd.orientation, v1); rBnd.e.SetVertex(rBnd.orientation, v1); edgeList.Remove(lBnd); heap.Remove(rBnd); edgeList.Remove(rBnd); lr = Orientation.LEFT; if (bottomSite.coord.y > topSite.coord.y) { tSite = bottomSite; bottomSite = topSite; topSite = tSite; lr = Orientation.RIGHT; } e = Edge.CreateBisectingEdge(bottomSite, topSite); this.edges.Add(e); bisector = HalfEdge.Create(e, lr); halfEdges.Add(bisector); edgeList.Insert(llBnd, bisector); e.SetVertex(Orientation.Other(lr), v1); if ((v2 = Vertex.Intersect(llBnd, bisector)) != null) { vertices.Add(v2); heap.Remove(llBnd); llBnd.v = v2; llBnd.yStar = v2.GetCoord().y + bottomSite.Dist(v2); heap.Insert(llBnd); } if ((v2 = Vertex.Intersect(bisector, rrBnd)) != null) { vertices.Add(v2); bisector.v = v2; bisector.yStar = v2.GetCoord().y + bottomSite.Dist(v2); heap.Insert(bisector); } } else { break; } } heap.Dispose(); edgeList.Dispose(); foreach (HalfEdge hE in halfEdges) { hE.Kill(); } halfEdges.Clear(); foreach (Edge tE in this.edges) { tE.ClipVertices(bounds); } foreach (Vertex v0 in vertices) { v0.Dispose(); } vertices.Clear(); }