Exemplo n.º 1
0
        private static int MinDistToMapEdge(PlanarGraph graph, Node n, int limit)
        {
            if (n.Coordinate.X == 0 || n.Coordinate.X == Size ||
                n.Coordinate.Y == 0 || n.Coordinate.Y == Size)
            {
                return(0);
            }

            int ret = int.MaxValue;
            Stack <Tuple <int, Node> > stack   = new Stack <Tuple <int, Node> >();
            HashSet <Node>             visited = new HashSet <Node>();

            stack.Push(new Tuple <int, Node>(0, n));
            do
            {
                Tuple <int, Node> state = stack.Pop();
                if (state.Item2.Coordinate.X == 0 || state.Item2.Coordinate.X == Size ||
                    state.Item2.Coordinate.Y == 0 || state.Item2.Coordinate.Y == Size)
                {
                    if (state.Item1 < ret)
                    {
                        ret = state.Item1;
                    }
                    if (ret == 0)
                    {
                        return(0);
                    }

                    continue;
                }
                visited.Add(state.Item2);

                if (state.Item1 > limit)
                {
                    continue;
                }
                foreach (EdgeEnd i in state.Item2.Edges)
                {
                    Node node = graph.Find(i.DirectedCoordinate);
                    if (!visited.Contains(node))
                    {
                        stack.Push(new Tuple <int, Node>(state.Item1 + 1, node));
                    }
                }
            } while (stack.Count > 0);
            return(ret);
        }
Exemplo n.º 2
0
        public void Generate(int pointCount)
        {
            //Generate random points
            HashSet <Coordinate> hashSet = new HashSet <Coordinate>();
            {
                Random rand = new Random(seed);
                while (hashSet.Count < pointCount)
                {
                    double x = rand.NextDouble() * 2 - 1;
                    double y = rand.NextDouble() * 2 - 1;
                    if (x < -0.99 || y < -0.99 || x > 0.99 || y > 0.99)
                    {
                        continue;
                    }
                    hashSet.Add(new Coordinate(x, y));
                }
            }
            //Optimize points
            {
                Coordinate[] points = hashSet.ToArray();
                for (int i = 0; i < 2; i++)
                {
                    VoronoiDiagramBuilder builder = new VoronoiDiagramBuilder();
                    builder.SetSites(points);
                    VoronoiDiagram = builder.GetDiagram(new GeometryFactory());
                    for (int j = 0; j < points.Length; j++)
                    {
                        Polygon poly = VoronoiDiagram[j] as Polygon;
                        points[j] = new Coordinate(poly.Centroid.X, poly.Centroid.Y);
                    }
                }
            }
            //Build graph
            PlanarGraph graph;
            {
                VoronoiDiagram = ClipGeometryCollection(VoronoiDiagram, new Envelope(-1, 1, -1, 1));
                graph          = new PlanarGraph(new OverlayNodeFactory());
                List <Edge> edges = new List <Edge>();
                for (int i = 0; i < VoronoiDiagram.Count; i++)
                {
                    Polygon      poly   = VoronoiDiagram[i] as Polygon;
                    Coordinate[] coords = poly.Coordinates;
                    for (int j = 1; j < coords.Length; j++)
                    {
                        edges.Add(new Edge(new[] { coords[j - 1], coords[j] }, new Label(Location.Boundary)));
                    }
                }
                graph.AddEdges(edges);
            }
            //Convert graph
            Dictionary <Node, MapNode> nodeDict;

            {
                Dictionary <MapPolygon, HashSet <MapPolygon> > polys = new Dictionary <MapPolygon, HashSet <MapPolygon> >();
                nodeDict = new Dictionary <Node, MapNode>();
                Dictionary <MapNode, Tuple <HashSet <MapPolygon>, HashSet <MapEdge> > > dats =
                    new Dictionary <MapNode, Tuple <HashSet <MapPolygon>, HashSet <MapEdge> > >();
                for (int i = 0; i < VoronoiDiagram.Count; i++)
                {
                    List <MapNode> nodes = new List <MapNode>();
                    MapPolygon     poly  = new MapPolygon
                    {
                        CentroidX = VoronoiDiagram[i].Centroid.X,
                        CentroidY = VoronoiDiagram[i].Centroid.Y,
                        Polygon   = VoronoiDiagram[i] as Polygon
                    };
                    foreach (Coordinate j in VoronoiDiagram[i].Coordinates.Skip(1))
                    {
                        Node    n = graph.Find(j);
                        MapNode mapNode;
                        if (!nodeDict.TryGetValue(n, out mapNode))
                        {
                            mapNode = new MapNode {
                                X = j.X, Y = j.Y
                            };
                            dats[mapNode] =
                                new Tuple <HashSet <MapPolygon>, HashSet <MapEdge> >(new HashSet <MapPolygon> {
                                poly
                            },
                                                                                     new HashSet <MapEdge>());
                        }
                        else
                        {
                            dats[mapNode].Item1.Add(poly);
                        }
                        nodes.Add(nodeDict[n] = mapNode);
                    }
                    poly.Nodes = nodes.ToArray();
                    polys.Add(poly, new HashSet <MapPolygon>());
                }
                foreach (KeyValuePair <Node, MapNode> i in nodeDict)
                {
                    foreach (MapPolygon j in dats[i.Value].Item1)
                    {
                        foreach (MapPolygon k in dats[i.Value].Item1)
                        {
                            if (j != k)
                            {
                                polys[j].Add(k);
                                polys[k].Add(j);
                            }
                        }
                    }
                    foreach (EdgeEnd j in i.Key.Edges)
                    {
                        MapNode from = nodeDict[graph.Find(j.Coordinate)];
                        MapNode to   = nodeDict[graph.Find(j.DirectedCoordinate)];
                        dats[from].Item2.Add(new MapEdge {
                            From = from, To = to
                        });
                    }
                }
                int ftrh = dats.Count(_ => _.Value.Item2.Count == 0);
                foreach (KeyValuePair <MapNode, Tuple <HashSet <MapPolygon>, HashSet <MapEdge> > > i in dats)
                {
                    i.Key.Edges = i.Value.Item2.ToArray();
                }
                KeyValuePair <MapPolygon, HashSet <MapPolygon> >[] x = polys.ToArray();
                for (int i = 0; i < x.Length; i++)
                {
                    x[i].Key.Neighbour = x[i].Value.ToArray();
                    x[i].Key.Id        = i;
                }
                Polygons = x.Select(_ => _.Key).ToArray();
            }
            //Generate map
            DetermineLandmass();
            FindOceans();
            ComputeDistances();
            RedistributeElevation(nodeDict.Values);
            FindLakesAndCoasts();
        }