Пример #1
0
        public static async Task <BusStop[]> GetBusStopsForArea(GeoboundingBox bounds, Action <BusStop[], GeoboundingBox> stopsLoadedCallback, CancellationToken cancellationToken, bool offlineOnly)
        {
            List <BusStop> totalFoundStops = new List <BusStop>();

            try
            {
                var offlineStops = await FileManager.GetStopsForArea(bounds.NorthwestCorner, bounds.SoutheastCorner, cancellationToken);

                totalFoundStops.AddRange(offlineStops);
                foreach (var stop in offlineStops)
                {
                    if (!CachedStops.ContainsKey(stop.ID))
                    {
                        CachedStops.Add(stop.ID, stop);
                    }
                }
                if (stopsLoadedCallback != null)
                {
                    stopsLoadedCallback(offlineStops, null);
                }
                cancellationToken.ThrowIfCancellationRequested();
                if (!offlineOnly)
                {
                    double latRange      = bounds.NorthwestCorner.Latitude - bounds.SoutheastCorner.Latitude;
                    double lonRange      = bounds.SoutheastCorner.Longitude - bounds.NorthwestCorner.Longitude;
                    int    latPieces     = (int)Math.Ceiling(latRange / MAX_LAT_RANGE);
                    int    lonPieces     = (int)Math.Ceiling(lonRange / MAX_LON_RANGE);
                    double smallLatRange = latRange / (double)latPieces;
                    double smallLonRange = lonRange / (double)lonPieces;
                    for (int i = 0; i < latPieces; i++)
                    {
                        for (int j = 0; j < lonPieces; j++)
                        {
                            BusStop[] foundStops = await ApiLayer.GetBusStopsForArea(new BasicGeoposition()
                            {
                                Latitude = bounds.SoutheastCorner.Latitude + (i + .5) * smallLatRange, Longitude = bounds.NorthwestCorner.Longitude + (j + .5) * smallLonRange
                            }, smallLatRange, smallLonRange, cancellationToken);

                            foreach (var item in foundStops ?? new BusStop[0])
                            {
                                if (!totalFoundStops.Contains(item))
                                {
                                    totalFoundStops.Add(item);
                                }
                                if (!CachedStops.ContainsKey(item.ID))
                                {
                                    CachedStops.Add(item.ID, item);
                                }
                            }
                            if (stopsLoadedCallback != null)
                            {
                                stopsLoadedCallback(foundStops, null);
                            }
                        }
                    }
                }
            }
            catch (OperationCanceledException) { }
            return(totalFoundStops.ToArray());
        }
Пример #2
0
        public static async Task <DownloadManager> Create(RouteListing listing, CancellationToken cancellationToken)
        {
            listing.Progress     = 0;
            listing.ShowProgress = true;
            DownloadManager result = new DownloadManager();

            result.Listing = listing;
            result._Route  = result.Listing.Route;
            var stopsAndShapes = await ApiLayer.GetStopsAndShapesForRoute(result.Listing.Route.ID, cancellationToken);

            result._Shapes       = stopsAndShapes.Item2;
            result._StopsPending = new ObservableCollection <BusStop>(stopsAndShapes.Item1);
            if (cancellationToken.IsCancellationRequested)
            {
                return(null);
            }
            result.Initialize();
            result._TotalStops = result.StopsPending.Count;
            DownloadsInProgress.Add(result);
            if (!FileManager.PendingDownloads.Any(item => item.First() == result.Route.ID))
            {
                List <string> pend = new List <string>()
                {
                    result.Route.ID
                };
                pend.AddRange(result.StopsPending.Select(stop => stop.ID));
                FileManager.PendingDownloads.Add(pend);
                await listing.RefreshIsDownloaded();

                await FileManager.SavePendingDownloads();
            }
            return(result);
        }
Пример #3
0
 public static async Task <Tuple <RealtimeArrival[], DataRetrievalMessage> > GetArrivals(string stopId, DataRetrievalOptions options, CancellationToken cancellationToken)
 {
     return(await CloudOrLocal(
                () => ApiLayer.GetBusArrivals(stopId, cancellationToken)
                ,
                () => FileManager.GetScheduledArrivals(stopId)
                ,
                options,
                typeof(OperationCanceledException)
                ));
 }
Пример #4
0
        public static async Task <BusRoute?> GetRoute(string id, CancellationToken cancellationToken)
        {
            if (CachedRoutes.ContainsKey(id))
            {
                return(CachedRoutes[id]);
            }
            var result = await CloudOrLocal(() => ApiLayer.GetBusRoute(id, cancellationToken), () => FileManager.GetRouteFromCache(id), new DataRetrievalOptions(DataSourceDescriptor.Local), typeof(OperationCanceledException));

            if (!CachedRoutes.ContainsKey(id) && result.Item2.FinalSource != null)
            {
                CachedRoutes.Add(id, result.Item1.Value);
            }
            return(result.Item1);
        }
Пример #5
0
        public static async Task <WeekSchedule> GetScheduleForStop(string id, CancellationToken cancellationToken)
        {
            WeekSchedule result = new WeekSchedule();

            for (int i = 0; i < 8; i++)
            {
                DaySchedule daySched = new DaySchedule();
                ServiceDay  day      = (ServiceDay)(int)Math.Pow(2, i);
                DateTime?   date     = HelperFunctions.DateForServiceDay(day);
                if (date.HasValue)
                {
                    daySched.LoadFromVerboseString(await ApiLayer.SendRequest("schedule-for-stop/" + id, new Dictionary <string, string>()
                    {
                        ["date"] = date.Value.ToString("yyyy-MM-dd")
                    }, false, cancellationToken), id);
                    result.AddServiceDay(day, daySched);
                }
            }
            return(result);
        }
Пример #6
0
 public static async Task <Tuple <BusRoute[], DataRetrievalMessage> > GetBusRoutesForAgency(string agencyId, DataRetrievalOptions options, CancellationToken cancellationToken)
 {
     return(await CloudOrLocal(() => ApiLayer.GetBusRoutesForAgency(agencyId, cancellationToken), () => FileManager.GetBusRoutesForAgencyFromCache(agencyId), options, typeof(OperationCanceledException)));
 }
Пример #7
0
 public static async Task <Tuple <TransitAgency[], DataRetrievalMessage> > GetTransitAgencies(DataRetrievalOptions options, CancellationToken cancellationToken)
 {
     return(await CloudOrLocal(() => ApiLayer.GetTransitAgencies(cancellationToken), () => FileManager.GetAgenciesFromCache(), options, typeof(OperationCanceledException)));
 }
Пример #8
0
 public static async Task <Tuple <Tuple <BusStop[], string[]>, DataRetrievalMessage> > GetStopsAndShapesForRoute(string routeId, DataRetrievalOptions options, CancellationToken cancellationToken)
 {
     return(await CloudOrLocal(() => ApiLayer.GetStopsAndShapesForRoute(routeId, cancellationToken), () => FileManager.GetStopsAndShapesForRouteFromCache(routeId), options, typeof(OperationCanceledException)));
 }
Пример #9
0
 public static async Task <Tuple <WeekSchedule, DataRetrievalMessage> > GetScheduleForStop(string id, DataRetrievalOptions options, CancellationToken cancellationToken)
 {
     return(await CloudOrLocal(() => ApiLayer.GetScheduleForStop(id, cancellationToken), () => FileManager.LoadSchedule(id), options, typeof(OperationCanceledException)));
 }
Пример #10
0
 public static async Task <TransitAgency?> GetTransitAgency(string id, CancellationToken cancellationToken)
 {
     return((await ApiLayer.GetTransitAgencies(cancellationToken)).First(agency => agency.ID == id));
 }
Пример #11
0
        public static async Task <RouteListing[]> DownloadAll(Action <double, string> statusChangedCallback, CancellationToken cancellationToken, params RouteListing[] routeListings)
        {
            List <RouteListing> errorList = new List <RouteListing>();
            List <BusStop>      allStops  = new List <BusStop>();
            await FileManager.LoadPendingDownloads();

            try
            {
                for (int i = 0; i < routeListings.Length; i++)
                {
                    statusChangedCallback(0.15 * i / routeListings.Length, "Getting stops (" + (i + 1).ToString() + " of " + routeListings.Length.ToString() + ")" + " " + (routeListings[i].Name.All(chr => char.IsDigit(chr)) ? "Route " : "") + routeListings[i].Name);
                    try
                    {
                        var manager = await DownloadManager.Create(routeListings[i], cancellationToken);

                        await FileManager.SaveRoute(manager.Route, manager.StopsPending.Select(item => item.ID).ToArray(), manager.Shapes);

                        foreach (var stop in manager.StopsPending)
                        {
                            if (!allStops.Contains(stop))
                            {
                                allStops.Add(stop);
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        cancellationToken.ThrowIfCancellationRequested();
                        errorList.Add(routeListings[i]);
                        ex.ToString();
                    }
                }

                WeekSchedule schedule;
                string[]     routeFilters = DownloadsInProgress.Select(download => download.Listing.Route.ID).ToArray();

                for (int i = 0; i < allStops.Count; i++)
                {
                    statusChangedCallback(0.15 + 0.85 * i / allStops.Count, "Downloading schedules (" + (i + 1).ToString() + " of " + allStops.Count.ToString() + ") " + allStops[i].Name);
                    try
                    {
                        var pend = FileManager.PendingDownloads.Where(item => routeFilters.Contains(item.First())).ToArray();
                        if (pend.Any(item => item.Contains(allStops[i].ID)))
                        {
                            schedule = await ApiLayer.GetScheduleForStop(allStops[i].ID, cancellationToken);

                            schedule.FilterByRoutes(routeFilters);
                            await FileManager.SaveScheduleAsync(schedule, allStops[i]);

                            foreach (var item in pend)
                            {
                                if (item.Contains(allStops[i].ID))
                                {
                                    item.Remove(allStops[i].ID);
                                }
                                if (item.Count == 1)
                                {
                                    FileManager.PendingDownloads.Remove(item);
                                }
                            }
                            await FileManager.SavePendingDownloads();
                        }
                        foreach (var manager in DownloadsInProgress.ToArray())
                        {
                            if (manager.StopsPending.Contains(allStops[i]))
                            {
                                manager.StopsPending.Remove(allStops[i]);
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        cancellationToken.ThrowIfCancellationRequested();
                        foreach (var download in DownloadsInProgress.Where(item => item.StopsPending.Contains(allStops[i])))
                        {
                            if (!errorList.Contains(download.Listing))
                            {
                                errorList.Add(download.Listing);
                            }
                        }
                        ex.ToString();
                    }
                }
                statusChangedCallback(1, "Download complete.");
            }
            catch (OperationCanceledException)
            {
                statusChangedCallback(1, "Download cancelled.");
                while (DownloadsInProgress.Count > 0)
                {
                    DownloadsInProgress[0].StopsPending.Clear();
                }
            }
            return(errorList.ToArray());
        }