Example #1
0
        public Voronoi(IEnumerable<PointF> points, int w = 800, int h = 600, bool debug=false) {
            _sites = new SiteList(points);
            _sites.LogSites();
            _graph = new VoronoiGraph(w, h) {Debug = debug};
            
            _edgeList = new EdgeList(_sites);
            _eventQueue = new EventQueue();
            _edgeFixup = false;

            StepNumber = 0;

        }
Example #2
0
        public static VoronoiGraph ComputeVoronoiGraph(IEnumerable <PointF> points, int w = 800, int h = 600, bool debug = false)
        {
            var sites = new SiteList(points);

            if (debug)
            {
                sites.LogSites();
            }
            var graph = new VoronoiGraph(w, h)
            {
                Debug = debug
            };

            try {
                var edgeList   = new EdgeList(sites);
                var eventQueue = new EventQueue();

                sites.BottomSite = sites.ExtractMin();

                graph.PlotSite(sites.BottomSite);

                var newSite    = sites.ExtractMin();
                var newIntStar = new Site(Single.MaxValue, Single.MaxValue);

                while (true)
                {
                    if (!eventQueue.IsEmpty)
                    {
                        newIntStar = eventQueue.Min();
                    }

                    if (newSite != null && (eventQueue.IsEmpty || newSite.CompareTo(newIntStar) < 0))
                    {
                        // new site is smallest
                        graph.PlotSite(newSite);

                        var lbnd = edgeList.LeftBound(newSite);
                        var rbnd = lbnd.Right;

                        var bot = edgeList.RightRegion(lbnd);

                        var e = Edge.CreateBisectingEdge(bot, newSite);
                        graph.PlotBisector(e);

                        var bisector = new HalfEdge(e, Side.Left);
                        EdgeList.Insert(lbnd, bisector);

                        var p = Site.CreateIntersectingSite(lbnd, bisector);
                        if (p != null)
                        {
                            eventQueue.Delete(lbnd);
                            if (debug)
                            {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(lbnd, p, Site.Distance(p, newSite));
                        }

                        lbnd     = bisector;
                        bisector = new HalfEdge(e, Side.Right);
                        EdgeList.Insert(lbnd, bisector);

                        p = Site.CreateIntersectingSite(bisector, rbnd);
                        if (p != null)
                        {
                            if (debug)
                            {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(bisector, p, Site.Distance(p, newSite));
                        }
                        newSite = sites.ExtractMin();
                    }
                    else if (!eventQueue.IsEmpty)
                    {
                        // intersection is smallest
                        var lbnd  = eventQueue.ExtractMin();
                        var llbnd = lbnd.Left;
                        var rbnd  = lbnd.Right;
                        var rrbnd = rbnd.Right;
                        var bot   = edgeList.LeftRegion(lbnd);
                        var top   = edgeList.RightRegion(rbnd);
                        graph.PlotTriple(bot, top, edgeList.RightRegion(lbnd));

                        var v = lbnd.Vertex;
                        graph.PlotVertex(v);

                        graph.EndPoint(lbnd.Edge, lbnd.Side, v);
                        graph.EndPoint(rbnd.Edge, rbnd.Side, v);
                        EdgeList.Delete(lbnd);
                        eventQueue.Delete(rbnd);
                        EdgeList.Delete(rbnd);

                        var pm = Side.Left;
                        if (bot.Y > top.Y)
                        {
                            var temp = bot;
                            bot = top;
                            top = temp;
                            pm  = Side.Right;
                        }
                        var e = Edge.CreateBisectingEdge(bot, top);
                        graph.PlotBisector(e);

                        var bisector = new HalfEdge(e, pm);
                        EdgeList.Insert(llbnd, bisector);
                        graph.EndPoint(e, Side.Other(pm), v);
                        var p = Site.CreateIntersectingSite(llbnd, bisector);
                        if (p != null)
                        {
                            eventQueue.Delete(llbnd);
                            if (debug)
                            {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(llbnd, p, Site.Distance(p, bot));
                        }
                        p = Site.CreateIntersectingSite(bisector, rrbnd);
                        if (p != null)
                        {
                            if (debug)
                            {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(bisector, p, Site.Distance(p, bot));
                        }
                    }
                    else
                    {
                        break;
                    }
                }
                for (var lbnd = edgeList.LeftEnd.Right; lbnd != edgeList.RightEnd; lbnd = lbnd.Right)
                {
                    var e = lbnd.Edge;
                    graph.PlotEndpoint(e);
                }
            } catch (Exception ex) {
                Console.WriteLine("########################################");
                Console.WriteLine(ex.Message);
                Console.WriteLine(ex.StackTrace);
            }
            graph.SweepLine = graph.Height;
            graph.ResetNewItems();
            foreach (var edge in graph.Edges)
            {
                edge.ClipVertices(new Rectangle(0, 0, w, h));
            }

            return(graph);
        }
Example #3
0
        public static VoronoiGraph ComputeVoronoi(IEnumerable<PointF> points, int w = 800, int h = 600, bool debug=false) {
            var sites = new SiteList(points);
            sites.LogSites();
            var graph = new VoronoiGraph(w, h) { Debug = debug };
            try {
                var edgeList = new EdgeList(sites);
                var eventQueue = new EventQueue();

                sites.BottomSite = sites.ExtractMin();

                graph.PlotSite(sites.BottomSite);

                var newSite = sites.ExtractMin();
                var newIntStar = new Site(float.MaxValue, float.MaxValue);

                while (true) {
                    if (!eventQueue.IsEmpty) {
                        newIntStar = eventQueue.Min();
                    }
                    // new site is smallest
                    if (newSite != null && 
                        (eventQueue.IsEmpty || newSite.Y < newIntStar.Y || (Math.Abs(newSite.Y - newIntStar.Y) < Geometry.Tolerance && newSite.X < newIntStar.X))) {

                        graph.PlotSite(newSite);

                        var lbnd = edgeList.LeftBound(newSite);
                        var rbnd = lbnd.Right;
                        var bot = edgeList.RightRegion(lbnd);
                        var e = Geometry.Bisect(bot, newSite);
                        graph.PlotBisector(e);
                        var bisector = new HalfEdge(e, Side.Left);
                        edgeList.Insert(lbnd, bisector);
                        var p = Geometry.Intersect(lbnd, bisector);
                        if (p != null) {
                            eventQueue.Delete(lbnd);
                            if (debug) {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(lbnd, p, Geometry.Distance(p, newSite));
                        }
                        lbnd = bisector;
                        bisector = new HalfEdge(e, Side.Right);
                        edgeList.Insert(lbnd, bisector);
                        p = Geometry.Intersect(bisector, rbnd);
                        if (p != null) {
                            if (debug) {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(bisector, p, Geometry.Distance(p, newSite));
                        }
                        newSite = sites.ExtractMin();
                    } else if (!eventQueue.IsEmpty) { // intersection is smallest
                        var lbnd = eventQueue.ExtractMin();
                        var llbnd = lbnd.Left;
                        var rbnd = lbnd.Right;
                        var rrbnd = rbnd.Right;
                        var bot = edgeList.LeftRegion(lbnd);
                        var top = edgeList.RightRegion(rbnd);
                        graph.PlotTriple(bot, top, edgeList.RightRegion(lbnd));
                        var v = lbnd.Vertex;

                        graph.PlotVertex(v);



                        Geometry.EndPoint(lbnd.Edge, lbnd.Side, v, graph);
                        Geometry.EndPoint(rbnd.Edge, rbnd.Side, v, graph);
                        edgeList.Delete(lbnd);
                        eventQueue.Delete(rbnd);
                        edgeList.Delete(rbnd);
                        var pm = Side.Left;
                        if (bot.Y > top.Y) {
                            var temp = bot;
                            bot = top;
                            top = temp;
                            pm = Side.Right;
                        }
                        var e = Geometry.Bisect(bot, top);
                        graph.PlotBisector(e);
                        var bisector = new HalfEdge(e, pm);
                        edgeList.Insert(llbnd, bisector);
                        Geometry.EndPoint(e, Side.Other(pm), v, graph);
                        var p = Geometry.Intersect(llbnd, bisector);
                        if (p != null) {
                            eventQueue.Delete(llbnd);
                            if (debug) {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(llbnd, p, Geometry.Distance(p, bot));
                        }
                        p = Geometry.Intersect(bisector, rrbnd);
                        if (p != null) {
                            if (debug) {
                                Console.WriteLine("Inserting {0}", p);
                            }
                            eventQueue.Insert(bisector, p, Geometry.Distance(p, bot));
                        }
                    } else {
                        break;
                    }
                }
                for (var lbnd = edgeList.LeftEnd.Right; lbnd != edgeList.RightEnd; lbnd = lbnd.Right) {
                    var e = lbnd.Edge;
                    graph.PlotEndpoint(e);
                }
            } catch (Exception ex) {
                Console.WriteLine("########################################");
                Console.WriteLine(ex.Message);
                Console.WriteLine(ex.StackTrace);
            }
            graph.SweepLine = graph.Height;
            graph.ResetNewItems();
            foreach (var edge in graph.Edges) {
                edge.ClipVertices(new Rectangle(0,0, w, h));
            }
            
            return graph;
        }