2013-10-29 6 views
5

Ich habe einige Dateien, die ich beim Start der App herunterladen muss (erster Lauf). Ich bin mit dem Background Downloader in Windows 8. Dies ist, wie ich es verwenden:Hintergrund Downloader Windows 8 Mehrere Dateien

BackgroundDownloader downloader = new BackgroundDownloader(); 

List<DownloadOperation> operations = new List<DownloadOperation>(); 
foreach (FileInfo info in infoFiles) 
{ 
    Windows.Storage.ApplicationData.Current.LocalFolder; 
    foreach (string folder in info.Folders) 
    { 
     currentFolder = await currentFolder.CreateFolderAsync(folder, CreationCollisionOption.OpenIfExists);  
    } 
    //folder hierarchy created, save the file 
    StorageFile file = await currentFolder.CreateFileAsync(info.FileName, CreationCollisionOption.ReplaceExisting); 

    DownloadOperation op = downloader.CreateDownload(new Uri(info.Url), file); 
    activeDownloads.Add(op); 
    operations.Add(op); 
} 


foreach (DownloadOperation download in operations) 
{ 
    //start downloads 
    await HandleDownloadAsync(download, true); 
} 

Wenn ich versuche, BackgroundDownloader.GetCurrentDownloadsAsync(); zu verwenden, erhalte ich nur einen Hintergrund herunterladen entdeckt. Also habe ich oben den Operator abwarten entfernt, um sie asynchron zu starten.

Allerdings muss ich wissen, wenn alle Dateien fertig sind, damit ich einen Fortschrittsbalken einstellen kann.

Ich brauche eine Möglichkeit, mehrere Dateien herunterzuladen, entdecken Sie alle in BackgroundDownloader.GetCurrentDownloadsAsync(); und wissen, wenn alle Downloads abgeschlossen sind.

private async Task HandleDownloadAsync(DownloadOperation download, bool start) 
    { 
     try 
     { 
      Debug.WriteLine("Running: " + download.Guid, NotifyType.StatusMessage); 

      // Store the download so we can pause/resume. 
      activeDownloads.Add(download); 

      Progress<DownloadOperation> progressCallback = new Progress<DownloadOperation>(DownloadProgress); 
      if (start) 
      { 
       // Start the download and attach a progress handler. 
       await download.StartAsync().AsTask(cts.Token, progressCallback); 
      } 
      else 
      { 
       // The download was already running when the application started, re-attach the progress handler. 
       await download.AttachAsync().AsTask(cts.Token, progressCallback); 
      } 

      ResponseInformation response = download.GetResponseInformation(); 

      Debug.WriteLine(String.Format("Completed: {0}, Status Code: {1}", download.Guid, response.StatusCode), 
       NotifyType.StatusMessage); 
     } 
     catch (TaskCanceledException) 
     { 
      Debug.WriteLine("Canceled: " + download.Guid, NotifyType.StatusMessage); 
     } 
     catch (Exception ex) 
     { 
      if (!IsExceptionHandled("Execution error", ex, download)) 
      { 
       throw; 
      } 
     } 
     finally 
     { 
      activeDownloads.Remove(download); 
     } 
    } 
+0

Haben Sie betrachtet [Quickstart: Das Herunterladen einer Datei] (http://msdn.microsoft.com/en-us/library/windows/apps/jj152726.aspx) – Harrison

Antwort

3

Wenn Sie speziell die Datei bei jedem App Start erneut herunterladen müssen, sollten Sie nicht BackgroundDownloader verwenden - es ist bestimmt für Szenarien, in denen Sie Downloads benötigen, die auf geschieht halten, auch wenn Ihre Anwendung ausgesetzt wird und dann neu gestartet . Wenn Sie die Dateien erneut herunterladen, wenn Ihre App das nächste Mal neu gestartet wird, verschwenden Sie nur den Akku, indem Sie die Downloads fortsetzen, sobald Ihre App verschwindet.

Sie haben einige Optionen für nicht Hintergrund-fähige Downloads in einer Windows Store App. Das einfachste ist Windows.Web.Http.HttpClient - here's a good primer auf, wie man es benutzt. Es ist jedoch nur in Windows 8.1-Apps und nicht in Windows 8.0 verfügbar. Wenn Sie Windows 8.0-Kompatibilität benötigen, ist der eindeutige aber ähnlich benannte System.Net.Http.HttpClient wahrscheinlich der Weg zu gehen. Harrison hat bereits einen Link zu the relevant Quickstart documentation bereitgestellt.

Wenn Sie wirklich wollen Hintergrund Download-Funktion, bitte überarbeiten Sie Ihre Frage, um Ihr Szenario genauer widerzuspiegeln. Es ist sicherlich möglich, mit BackgroundDownloader mehrere Hintergrund-Downloads gleichzeitig zu starten und ihnen jeweils Fortschritts- und Completion-Handler anzuhängen, aber das klingt nicht nach der besten Lösung für das Szenario in Ihrer Frage.


Nachdem Sie jetzt Ihre Verwendung geklärt haben, ist das Problem deutlicher. Ihre HandleDownloadAsync Methode fügt den gewünschten Fortschritts-Handler dem Download hinzu, wartet dann aber auf den Abschluss dieses Downloads. Wenn Sie

foreach (DownloadOperation download in operations) 
{ 
    //start downloads 
    await HandleDownloadAsync(download, true); 
} 

schreiben erwarten Sie also auf dem Abschluss jeden Download wiederum bevor Sie den nächsten Download zu starten.

Die Lösung ist hier zu nicht erwarten das Ergebnis Ihrer HandleDownloadAsync Anrufe bis nach Sie alle Anrufe durchgeführt haben - das wird jeder der Downloads sofort und legen die entsprechenden Fortschritte Handler starten, ohne zu warten einige von ihnen zu vervollständigen. Eine überarbeitete Version wie folgt aussehen könnte:

BackgroundDownloader downloader = new BackgroundDownloader(); 

List<Task> downloadCompletionTasks = new List<Task>(); 
foreach (FileInfo info in infoFiles) 
{ 
    StorageFile file = /* ... */; 

    DownloadOperation op = downloader.CreateDownload(new Uri(info.Url), file); 

    // Consider moving this line into HandleDownloadAsync so you won't have to repeat 
    // it in the code that's handling the GetCurrentDownloadsAsync logic. 
    activeDownloads.Add(op); 

    // Starting the download, but not awaiting its completion yet 
    Task downloadCompletionTask = HandleDownloadAsync(op, true); 
    downloadCompletionTasks.Add(downloadCompletionTask); 
} 

// Now that we've got all the downloads started concurrently, we can wait until all of them complete 
await Task.WhenAll(downloadCompletionTasks); 
+0

Eigentlich möchte ich sie nur einmal herunterladen (zuerst laufen). Wenn ich jedoch herunterfahre und fortfahre, bekomme ich nur einen Hintergrund-Download entdeckt. – user2932696

+0

BackgroundTransfer ist dann wahrscheinlich eine vernünftige Wahl. Bitte veröffentlichen Sie die Definition Ihrer HandleDownloadAsync-Methode. Es ist unmöglich, dies sicher zu sagen, ohne es zu sehen, aber es ist wahrscheinlich, dass Ihr 'harry HandleDownloadAsync (download, true)' Call tatsächlich auf jeden Download wartet, um ** zu beenden **, was erklären würde, warum Sie nur sehen zu jeder gegebenen Zeit. –

+0

System.Net. ** Http ** .HttpClient :) – kiewic