예제 #1
0
    private IEnumerator UpdatingDatabase()
    {
        var replacement = new GameDatabase();

        using (var call = new APICall("build"))
        {
            yield return(call.Requesting());

            // Bail early if the database is up-to-date.
            int build = (int)call.Data["id"];
            if (this.GameDatabase.BuildId == build)
            {
                this.Console.InfoFade("Game database already up-to-date ({0}).", this.GameDatabase.BuildId);
                yield break;
            }

            this.Console.Info("Updating game database ({0} => {1}).", this.GameDatabase.BuildId, build);

            // Create a new database.
            replacement = new GameDatabase()
            {
                BuildId = build
            };
        }

        using (var pMaps = new APICall("maps?ids=all"))
            using (var continents = new APICall("continents"))
            {
                Coroutine cMaps = this.StartCoroutine(pMaps.Requesting());
                yield return(continents.Requesting());

                foreach (string continentId in continents.Data.Skip(0))
                {
                    using (var floors = new APICall("continents", continentId, "floors?ids=all"))
                    {
                        yield return(floors.Requesting());

                        var maps = new Dictionary <int, Map>();
                        foreach (JContainer mapData in (from floor in floors.Data
                                                        from regions in floor["regions"]
                                                        from region in regions
                                                        from mapList in region["maps"]
                                                        select mapList).Values())
                        {
                            int floor = (int)mapData.Parent.Parent.Parent.Parent.Parent.Parent.Parent.Parent["id"];
                            int mapId = (int)mapData["id"];
                            if (!maps.TryGetValue(mapId, out Map map))
                            {
                                yield return(cMaps);

                                string type = (string)pMaps.Data.First(m => (int)m["id"] == mapId)["type"];
                                map = new Map()
                                {
                                    Name = (string)mapData["name"],

                                    IsInstance = type == "Instance" || type == "Tutorial",

                                    Rect = new Map.ContinentRect()
                                    {
                                        ContinentId = int.Parse(continentId),
                                        Floors      = new HashSet <int>()
                                        {
                                            floor
                                        },

                                        Rect1X = (int)mapData["continent_rect"][0][0],
                                        Rect1Y = (int)mapData["continent_rect"][0][1],
                                        Rect2X = (int)mapData["continent_rect"][1][0],
                                        Rect2Y = (int)mapData["continent_rect"][1][1]
                                    }
                                };
                                maps[mapId] = map;
                            }
                            else
                            {
                                map.Rect.Floors.Add(floor);
                            }

                            foreach (JToken wpData in mapData["points_of_interest"].Values().Where(p => (string)p["type"] == "waypoint"))
                            {
                                map.Waypoints[(string)wpData["chat_link"]] = (string)wpData["name"];
                            }
                            foreach (JToken sectorData in mapData["sectors"].Values())
                            {
                                map.Sectors[(int)sectorData["id"]] = (string)sectorData["name"];
                            }

                            yield return(null);
                        }

                        // Add all non-instances first.
                        foreach (KeyValuePair <int, Map> map in maps.OrderBy(m => m.Value.IsInstance))
                        {
                            replacement.AddMap(map.Key, map.Value);
                        }
                    }
                }
            }

        this.GameDatabase = replacement;
        File.WriteAllText(Path, JsonConvert.SerializeObject(this.GameDatabase, Formatting.Indented));
        this.Console.Info("Game database updated.");
    }