public async void Run(IBackgroundTaskInstance taskInstance)
        {
            BackgroundTaskDeferral deferral = taskInstance.GetDeferral();

            try
            {
                // 获取 ToastNotificationActionTriggerDetail 对象
                ToastNotificationActionTriggerDetail toastDetail = taskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                if (toastDetail != null)
                {
                    string result = "";

                    result  = "argument: " + toastDetail.Argument;
                    result += Environment.NewLine;

                    foreach (string key in toastDetail.UserInput.Keys)
                    {
                        result += $"key:{key}, value:{toastDetail.UserInput[key]}";
                        result += Environment.NewLine;
                    }

                    // 将获取到的 toast 信息保存为文件
                    StorageFile file = await ApplicationData.Current.LocalFolder.CreateFileAsync(@"webabcdBackgroundTask\toast.txt", CreationCollisionOption.ReplaceExisting);

                    await FileIO.WriteTextAsync(file, result);
                }
            }
            finally
            {
                deferral.Complete();
            }
        }
        public void OnBackgroundActivated(IBackgroundTaskInstance taskInstance)
        {
            switch (taskInstance.Task.Name)
            {
            case CALL_ORIGIN_DATA_REQUEST:
                //PhoneCallOriginDataRequestTriggerDetails originDataRequest = args.TaskInstance.TriggerDetails as PhoneCallOriginDataRequestTriggerDetails;
                //PhoneCallOrigin data = new PhoneCallOrigin();
                //data.Category = "Category";
                //data.CategoryDescription = "CategoryDescription";
                //data.DisplayName = "DisplayName";
                //data.Location = "Location";
                //PhoneCallOriginManager.SetCallOrigin(originDataRequest.RequestId, data);
                break;

            case LINE_STATE_CHANGED:
                PhoneLineChangedTriggerDetails lineChangedDetails = taskInstance.TriggerDetails as PhoneLineChangedTriggerDetails;
                if (!Skip && !App.Current.IsForeground)
                {
                    Skip = true;
                    OnLateBackgroundActivation();
                }
                break;

            case TOAST_BACKGROUNG_ACTIVATED:
                ToastNotificationActionTriggerDetail toastDetails = taskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                App.Current.OnToastNotificationActivated(ToastActivationType.Background, toastDetails.Argument);
                break;
            }
        }
Beispiel #3
0
        private ApplicationDataContainer appSetting = ApplicationData.Current.LocalSettings; //本地存储
        public async void Run(IBackgroundTaskInstance taskInstance)
        {
            var deferral = taskInstance.GetDeferral();

            if (bool.Parse(appSetting.Values["isUseingBackgroundTask"].ToString()))
            {
                var vault          = new Windows.Security.Credentials.PasswordVault();
                var credentialList = vault.FindAllByResource(resourceName);
                credentialList[0].RetrievePassword();
                stuNum = credentialList[0].UserName;
                idNum  = credentialList[0].Password;
                ToastNotificationActionTriggerDetail details = taskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                if (details != null)
                {
                    // 是否选择“确定”
                    string arg = details.Argument;
                    if ((arg.Split('+'))[0].Substring(0, 2) == "ok")
                    {
                        // 获取数据
                        string value = details.UserInput["content"] as string;
                        Debug.WriteLine(arg.Substring(2));
                        if (value != "")
                        {
                            List <KeyValuePair <String, String> > paramList = new List <KeyValuePair <String, String> >();
                            paramList.Add(new KeyValuePair <string, string>("article_id", arg.Substring(2)));
                            paramList.Add(new KeyValuePair <string, string>("type_id", "5"));
                            paramList.Add(new KeyValuePair <string, string>("stuNum", stuNum));
                            paramList.Add(new KeyValuePair <string, string>("idNum", idNum));
                            paramList.Add(new KeyValuePair <string, string>("content", "回复 " + arg.Split('+')[2] + " : " + value));
                            paramList.Add(new KeyValuePair <string, string>("answer_user_id", arg.Split('+')[1]));
                            string sendMark = await NetWork.getHttpWebRequest("cyxbsMobile/index.php/Home/ArticleRemark/postremarks", paramList);

                            Debug.WriteLine(sendMark);
                            try
                            {
                                if (sendMark != "")
                                {
                                    JObject obj = JObject.Parse(sendMark);
                                    if (Int32.Parse(obj["state"].ToString()) == 200)
                                    {
                                        Utils.Toast("评论成功");
                                    }
                                    else
                                    {
                                        Utils.Toast("评论失败");
                                    }
                                }
                                else
                                {
                                    Utils.Toast("评论失败");
                                }
                            }
                            catch (Exception) { }
                        }
                    }
                    deferral.Complete();
                }
            }
        }
Beispiel #4
0
        private static void HandleBackgroundSnoozeActivation(ToastNotificationActionTriggerDetail details)
        {
            string snoozeMinutesTxt = (string)details.UserInput[INPUT_SNOOZEMINUTES];
            uint   snoozeMinutes    = uint.Parse(snoozeMinutesTxt);

            // Register a time trigger background task to fire at the requested snooze time, which will then pop a new notification
            BackgroundTaskHelper.Register(TOAST_TIME_TRIGGER_BACKGROUND_TASK, new TimeTrigger(snoozeMinutes, oneShot: true));
        }
        private void SaveToastResponse(ToastNotificationActionTriggerDetail toastNotificationResponse)
        {
            var userInput = toastNotificationResponse.UserInput;
            var reply = userInput.Values.FirstOrDefault();

            var note = ApplicationData.Current.LocalSettings.Values["note"] as string;

            var newNote = $"{note}{Environment.NewLine}[toast reply] {reply}";

            ApplicationData.Current.LocalSettings.Values["note"] = newNote;
        }
        private async Task HandleLike(ToastNotificationActionTriggerDetail details, QueryString args)
        {
            // Get the conversation the toast is about
            int conversationId = int.Parse(args["conversationId"]);

            // In a real app, this would be making a web request, sending the like command
            await Task.Delay(TimeSpan.FromSeconds(1.1));

            // In a real app, you most likely should NOT notify your user that the request completed (only notify them if there's an error)
            SendToast("Your like has been sent!");
        }
        private async Task HandleLike(ToastNotificationActionTriggerDetail details, QueryString args)
        {
            // Get the conversation the toast is about
            int conversationId = int.Parse(args["conversationId"]);

            // In a real app, this would be making a web request, sending the like command
            await Task.Delay(TimeSpan.FromSeconds(1.1));

            // In a real app, you most likely should NOT notify your user that the request completed (only notify them if there's an error)
            SendToast("Your like has been sent!");
        }
Beispiel #8
0
        private void SaveToastResponse(ToastNotificationActionTriggerDetail toastNotificationResponse)
        {
            var userInput = toastNotificationResponse.UserInput;
            var reply     = userInput.Values.FirstOrDefault();

            var note = ApplicationData.Current.LocalSettings.Values["note"] as string;

            var newNote = $"{note}{Environment.NewLine}[toast reply] {reply}";

            ApplicationData.Current.LocalSettings.Values["note"] = newNote;
        }
Beispiel #9
0
        public async void Run(IBackgroundTaskInstance taskInstance)
        {
            var d = taskInstance.GetDeferral();

            // Get the id
            ToastNotificationActionTriggerDetail details = (ToastNotificationActionTriggerDetail)taskInstance.TriggerDetails;
            var id = QueryString.Parse(details.Argument)["id"];

            await RunAsync(id);

            d.Complete();
        }
Beispiel #10
0
        protected override async void OnBackgroundActivated(BackgroundActivatedEventArgs args)
        {
            BackgroundTaskDeferral deferral = args.TaskInstance.GetDeferral();

            switch (args.TaskInstance.Task.Name)
            {
            case BackgroundTaskHelper.TOAST_BACKGROUND_TASK_NAME:
                ToastNotificationActionTriggerDetail details = args.TaskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                if (details != null)
                {
                    InitLogger();

                    string   arguments = details.Argument;
                    ValueSet userInput = details.UserInput;

                    Logger.Debug("App activated in background through toast with: " + arguments);
                    AbstractToastActivation abstractToastActivation = ToastActivationArgumentParser.parseArguments(arguments);

                    if (abstractToastActivation is null)
                    {
                        Logger.Warn("Unable to evaluate toast activation string - unknown format");
                    }
                    else if (abstractToastActivation is MarkChatAsReadToastActivation markChatAsRead)
                    {
                        ToastHelper.removeToastGroup(markChatAsRead.CHAT_ID);
                        ChatDBManager.INSTANCE.markAllMessagesAsRead(markChatAsRead.CHAT_ID);
                    }
                    else if (abstractToastActivation is MarkMessageAsReadToastActivation markMessageAsRead)
                    {
                        ChatDBManager.INSTANCE.markMessageAsRead(markMessageAsRead.CHAT_MESSAGE_ID);
                    }
                    else if (abstractToastActivation is SendReplyToastActivation sendReply)
                    {
                        ChatTable chat = ChatDBManager.INSTANCE.getChat(sendReply.CHAT_ID);
                        if (!(chat is null) && userInput[ToastHelper.TEXT_BOX_ID] is string text)
                        {
                            string trimedText = text.Trim(UiUtils.TRIM_CHARS);
                            await SendChatMessageAsync(chat, trimedText);
                        }
                        ChatDBManager.INSTANCE.markMessageAsRead(sendReply.CHAT_MESSAGE_ID);
                    }

                    ToastHelper.UpdateBadgeNumber();
                }
                break;

            default:
                break;
            }

            deferral.Complete();
        }
        private async Task HandleReply(ToastNotificationActionTriggerDetail details, QueryString args)
        {
            // Get the conversation the toast is about
            int conversationId = int.Parse(args["conversationId"]);

            // Get the message that the user typed in the toast
            string message = (string)details.UserInput["tbReply"];

            // In a real app, this would be making a web request, sending the new message
            await Task.Delay(TimeSpan.FromSeconds(2.3));

            // In a real app, you most likely should NOT notify your user that the request completed (only notify them if there's an error)
            SendToast("Your message has been sent! Your message: " + message);
        }
Beispiel #12
0
        public static Dictionary <string, string> GetData(ToastNotificationActionTriggerDetail triggerDetail)
        {
            var dictionary = SplitArguments(triggerDetail.Argument);

            if (triggerDetail.UserInput != null && triggerDetail.UserInput.Count > 0)
            {
                foreach (var input in triggerDetail.UserInput)
                {
                    dictionary[input.Key] = input.Value.ToString();
                }
            }

            return(dictionary);
        }
        private async Task HandleReply(ToastNotificationActionTriggerDetail details, QueryString args)
        {
            // Get the conversation the toast is about
            int conversationId = int.Parse(args["conversationId"]);

            // Get the message that the user typed in the toast
            string message = (string)details.UserInput["tbReply"];

            // In a real app, this would be making a web request, sending the new message
            await Task.Delay(TimeSpan.FromSeconds(2.3));

            // In a real app, you most likely should NOT notify your user that the request completed (only notify them if there's an error)
            SendToast("Your message has been sent! Your message: " + message);
        }
Beispiel #14
0
 public static void HandleBackgroundActivation(ToastNotificationActionTriggerDetail details)
 {
     try
     {
         switch (details.Argument)
         {
         case ACTION_SNOOZE:
             HandleBackgroundSnoozeActivation(details);
             break;
         }
     }
     catch
     {
         // Report to telemetry
     }
 }
Beispiel #15
0
        protected override void OnBackgroundActivated(BackgroundActivatedEventArgs args)
        {
            var deferral = args.TaskInstance.GetDeferral();

            switch (args.TaskInstance.Task.Name)
            {
            case BackgroundTaskHelper.TOAST_BACKGROUND_TASK_NAME:
                ToastNotificationActionTriggerDetail details = args.TaskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                if (details != null)
                {
                    initLogLevel();

                    string arguments = details.Argument;
                    var    userInput = details.UserInput;

                    Logger.Debug("App activated in background through toast with: " + arguments);
                    AbstractToastActivation abstractToastActivation = ToastActivationArgumentParser.parseArguments(arguments);

                    if (abstractToastActivation is MarkChatAsReadToastActivation markChatAsRead)
                    {
                        ToastHelper.removeToastGroup(markChatAsRead.CHAT_ID);
                        ChatDBManager.INSTANCE.markAllMessagesAsRead(markChatAsRead.CHAT_ID);
                    }
                    else if (abstractToastActivation is MarkMessageAsReadToastActivation markMessageAsRead)
                    {
                        ChatDBManager.INSTANCE.markMessageAsRead(markMessageAsRead.CHAT_MESSAGE_ID);
                    }
                    else if (abstractToastActivation is SendReplyToastActivation sendReply)
                    {
                        ChatTable chat = ChatDBManager.INSTANCE.getChat(sendReply.CHAT_ID);
                        if (chat != null && userInput[ToastHelper.TEXT_BOX_ID] != null)
                        {
                            if (isRunning)
                            {
                            }
                            else
                            {
                            }
                        }
                    }
                }
                break;
            }

            deferral.Complete();
        }
        async Task HandleReplyPm(ToastNotificationActionTriggerDetail details, string args, CancellationTokenSource cts)
        {
            int    userId       = Convert.ToInt32(args.Substring("reply_pm=".Length));
            string replyContent = details.UserInput["inputPm"].ToString();

            if (string.IsNullOrEmpty(replyContent))
            {
                string _xml = "<toast>" +
                              "<visual>" +
                              "<binding template='ToastGeneric'>" +
                              "<text>对不起</text>" +
                              "<text>您输入的内容有误,消息发送不成功!</text>" +
                              "</binding>" +
                              "</visual>" +
                              "</toast>";
                SendToast(_xml);
            }

            var postData = new List <KeyValuePair <string, object> >();

            postData.Add(new KeyValuePair <string, object>("formhash", _formHash));
            postData.Add(new KeyValuePair <string, object>("handlekey", "pmreply"));
            postData.Add(new KeyValuePair <string, object>("lastdaterange", DateTime.Now.ToString("yyyy-M-d")));
            postData.Add(new KeyValuePair <string, object>("message", replyContent));

            string url           = string.Format("http://www.hi-pda.com/forum/pm.php?action=send&uid={0}&pmsubmit=yes&infloat=yes&inajax=1&_={1}", userId, DateTime.Now.Ticks.ToString("x"));
            string resultContent = await _httpClient.PostAsync(url, postData, cts);

            bool flag = resultContent.StartsWith(@"<?xml version=""1.0"" encoding=""gbk""?><root><![CDATA[<li id=""pm_") && resultContent.Contains(@"images/default/notice_newpm.gif");

            if (cts.IsCancellationRequested || flag == false)
            {
                string simpleContent = replyContent.Length > 10 ? replyContent.Substring(0, 9) + "..." : replyContent;
                string _xml          = "<toast>" +
                                       "<visual>" +
                                       "<binding template='ToastGeneric'>" +
                                       "<text>对不起</text>" +
                                       $"<text>“ {simpleContent} ” 发送不成功!</text>" +
                                       "</binding>" +
                                       "</visual>" +
                                       "</toast>";
                SendToast(_xml);
            }
            Debug.WriteLine("短消息回复结果:" + flag);
        }
Beispiel #17
0
        protected override async void OnBackgroundActivated(BackgroundActivatedEventArgs args)
        {
            base.OnBackgroundActivated(args);
            BackgroundTaskDeferral deferral = args.TaskInstance.GetDeferral();

            try
            {
                await Initialisation;
                switch (args.TaskInstance.Task.Name)
                {
                case CALL_ORIGIN_DATA_REQUEST:
                    //PhoneCallOriginDataRequestTriggerDetails originDataRequest = args.TaskInstance.TriggerDetails as PhoneCallOriginDataRequestTriggerDetails;
                    //PhoneCallOrigin data = new PhoneCallOrigin();
                    //data.Category = "Category";
                    //data.CategoryDescription = "CategoryDescription";
                    //data.DisplayName = "DisplayName";
                    //data.Location = "Location";
                    //PhoneCallOriginManager.SetCallOrigin(originDataRequest.RequestId, data);
                    break;

                case LINE_STATE_CHANGED:
                    PhoneLineChangedTriggerDetails lineChangedDetails = args.TaskInstance.TriggerDetails as PhoneLineChangedTriggerDetails;
                    await Task.Run(OnLateBackgroundActivation);

                    _CallHandler.WaitOne(WAIT_CALL_DURATION);
                    _CallHandler.Reset();
                    break;

                case TOAST_BACKGROUNG_ACTIVATED:
                    ToastNotificationActionTriggerDetail toastDetails = args.TaskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;
                    OnToastNotificationActivated(ToastActivationType.Background, toastDetails.Argument);
                    break;
                }
            }
            catch
            {
            }
            finally
            {
                deferral.Complete();
            }
        }
Beispiel #18
0
        private static void HandleBackgroundSnoozeActivation(ToastNotificationActionTriggerDetail details)
        {
            string snoozeMinutesTxt = (string)details.UserInput[INPUT_SNOOZEMINUTES];
            double snoozeMinutes    = double.Parse(snoozeMinutesTxt);

            // Generate the reminder toast content once again
            XmlDocument toastContentDoc = GenerateToastReminderContent();

            // Calculate the time we want the notification to re-appear based on the snooze time the user selected
            DateTimeOffset deliveryTime = DateTime.Now.AddMinutes(snoozeMinutes);

            // Create a scheduled notification with these values
            ScheduledToastNotification scheduledNotif = new ScheduledToastNotification(toastContentDoc, deliveryTime)
            {
                Tag = TAG_REGISTER_REMINDER
            };

            // And schedule the notification
            ToastNotificationManager.CreateToastNotifier().AddToSchedule(scheduledNotif);
        }
        async Task HandleAddBuddy(ToastNotificationActionTriggerDetail details, string args, CancellationTokenSource cts)
        {
            string[] tary     = args.Substring("add_buddy=".Length).Split(',');
            int      userId   = Convert.ToInt32(tary[0]);
            string   username = tary[1];

            string url = string.Format("http://www.hi-pda.com/forum/my.php?from=notice&item=buddylist&newbuddyid={0}&buddysubmit=yes&inajax=1&_={1}", userId, DateTime.Now.Ticks.ToString("x"));
            await _httpClient.GetAsync(url, cts);

            string _xml = "<toast>" +
                          "<visual>" +
                          "<binding template='ToastGeneric'>" +
                          "<text>恭喜您</text>" +
                          $"<text>成功添加 “{username}” 为好友!</text>" +
                          "</binding>" +
                          "</visual>" +
                          "</toast>";

            SendToast(_xml);
        }
        async Task HandleReplyPost(ToastNotificationActionTriggerDetail details, string args, CancellationTokenSource cts)
        {
            string[] tary            = args.Replace("__AND__", "&").Substring("reply_post=".Length).Split(',');
            int      threadId        = Convert.ToInt32(tary[0]);
            string   noticeauthor    = tary[1];
            string   noticetrimstr   = tary[2];
            string   noticeauthormsg = tary[3];
            string   replyContent    = details.UserInput["inputPost"].ToString();

            var postData = new List <KeyValuePair <string, object> >();

            postData.Add(new KeyValuePair <string, object>("formhash", _formHash));
            postData.Add(new KeyValuePair <string, object>("wysiwyg", "1"));
            postData.Add(new KeyValuePair <string, object>("noticeauthor", noticeauthor));
            postData.Add(new KeyValuePair <string, object>("noticetrimstr", noticetrimstr));
            postData.Add(new KeyValuePair <string, object>("noticeauthormsg", noticeauthormsg));
            postData.Add(new KeyValuePair <string, object>("subject", string.Empty));
            postData.Add(new KeyValuePair <string, object>("message", $"{noticetrimstr}{replyContent}\r\n \r\n[img=16,16]http://www.hi-pda.com/forum/attachments/day_140621/1406211752793e731a4fec8f7b.png[/img]"));

            string url           = string.Format("http://www.hi-pda.com/forum/post.php?action=reply&tid={0}&replysubmit=yes&handlekey=fastpost&inajax=1", threadId);
            string resultContent = await _httpClient.PostAsync(url, postData, cts);

            var flag = resultContent.Contains("您的回复已经发布");

            if (cts.IsCancellationRequested || flag == false)
            {
                string simpleContent = replyContent.Length > 10 ? replyContent.Substring(0, 9) + "..." : replyContent;
                string _xml          = "<toast>" +
                                       "<visual>" +
                                       "<binding template='ToastGeneric'>" +
                                       "<text>对不起,您两次发表间隔少于 30 秒,请不要灌水!</text>" +
                                       $"<text>“ {simpleContent} ” 回复不成功!</text>" +
                                       "</binding>" +
                                       "</visual>" +
                                       "</toast>";
                SendToast(_xml);
            }
            Debug.WriteLine("贴子回复结果:" + flag);
        }
Beispiel #21
0
        public async void Run(IBackgroundTaskInstance taskInstance)
        {
            var deferral = taskInstance.GetDeferral();

            ToastNotificationActionTriggerDetail details = taskInstance.TriggerDetails as ToastNotificationActionTriggerDetail;

            var args = ArgumentsHelper.ParseArguments(details.Argument);

            if (args is MarkCompleteArguments)
            {
                MarkCompleteArguments markCompleteArgs = args as MarkCompleteArguments;

                var additionalTasks = await DataStore.SetTaskCompletionStatusAsync(markCompleteArgs.TaskId, true);

                // Signal that changes to the data have been made before waiting for tiles and other tasks
                // The foreground app instance (if running) listens to progress change and then re-loads data
                taskInstance.Progress = 1;

                await additionalTasks.AwaitAll();
            }

            deferral.Complete();
        }
Beispiel #22
0
        public static Dictionary <string, string> GetData(IBackgroundTaskInstance args)
        {
            if (args.TriggerDetails is ToastNotificationActionTriggerDetail)
            {
                ToastNotificationActionTriggerDetail details = args.TriggerDetails as ToastNotificationActionTriggerDetail;
                if (details == null)
                {
                    return(null);
                }

                var dictionary = SplitArguments(details.Argument);
                if (details.UserInput != null && details.UserInput.Count > 0)
                {
                    for (int i = 0; i < details.UserInput.Count; i++)
                    {
                        dictionary.Add(details.UserInput.Keys.ElementAt(i), details.UserInput.Values.ElementAt(i).ToString());
                    }
                }

                return(dictionary);
            }

            return(null);
        }
Beispiel #23
0
        protected override void OnBackgroundActivated(BackgroundActivatedEventArgs args)
        {
            base.OnBackgroundActivated(args);


            // Run the background task accordingly
            if (args.TaskInstance.Task.Name.CompareTo(nameof(TileUpdateTask)) == 0)
            {
                var activity = new TileUpdateTask();
                activity.Run(args.TaskInstance);
            }
            else if (args.TaskInstance.Task.Name.CompareTo(nameof(WallpaperUpdateTask)) == 0)
            {
                var activity = new WallpaperUpdateTask();
                activity.Run(args.TaskInstance);
            }
            else if (args.TaskInstance.Task.Name.CompareTo(nameof(LockscreenUpdateTask)) == 0)
            {
                var activity = new LockscreenUpdateTask();
                activity.Run(args.TaskInstance);
            }
            else if (args.TaskInstance.Task.Name.CompareTo("ToastActionTask") == 0)
            {
                ToastNotificationActionTriggerDetail d = (ToastNotificationActionTriggerDetail)args.TaskInstance.TriggerDetails;
                QueryString queryString = QueryString.Parse(d.Argument);

                switch (queryString["action"])
                {
                case "favorite":
                    var favoriteTask = new FavoriteTask();
                    favoriteTask.Run(args.TaskInstance);
                    break;

                case "undoLockscreen":
                    var wallpaperUndoTask = new LockscreenUndoTask();
                    wallpaperUndoTask.Run(args.TaskInstance);
                    break;

                case "undoWallpaper":
                    var lockscreenUndoTask = new WallpaperUndoTask();
                    lockscreenUndoTask.Run(args.TaskInstance);
                    break;

                default:
                    break;
                }
            }
            else if (args.TaskInstance.Task.Name.StartsWith(nameof(FavoriteTask)))
            {
                var activity = new FavoriteTask();
                activity.Run(args.TaskInstance);
            }
            else if (args.TaskInstance.Task.Name.StartsWith(nameof(WallpaperUndoTask)))
            {
                var activity = new WallpaperUndoTask();
                activity.Run(args.TaskInstance);
            }
            else
            {
                var x         = args.TaskInstance.Task.Trigger;
                var details   = args.TaskInstance.TriggerDetails as BackgroundTransferCompletionGroupTriggerDetails;
                var downloads = details.Downloads.ToList();
                // TODO: validate the download
                ToastService.ToastDebug("Download Finished", $"{downloads.Where(o => o.Progress.Status == BackgroundTransferStatus.Completed).Count()}/{downloads.Count} images downloaded successfully.");
            }
        }