2017-02-10 12 views
0

私にはアクティビティがあり、2つのリストビューがあります。最初のリストビューには音楽があります。 2番目のリストビューにはダウンロード項目が表示され、各ダウンロード項目にはダウンロード率の進行状況バーが表示されます。 ユーザーがミュージックアイテムをクリックすると、ダウンロード項目を2番目のリストビューに追加し、AsyncTaskでダウンロードファイルを開始します。ユーザーは複数の音楽をクリックすることができ、複数のファイルを同時にダウンロードすることを意味します。 AsyncTaskを使用してファイルをダウンロードできます。しかし、アプリケーションを閉じてもダウンロードを続ける必要があるため、サービス中のファイルをダウンロードしたい。複数のファイルをAndroidで同時にダウンロードするには

サービスと同時に複数のファイルをダウンロードするにはどうすればいいですか?どの手順を踏む必要がありますか?このためのチュートリアルはありますか?

+1

答えはありませんが、考えてみましょう。これがあなたのサーバーならば、大量のファイルを同時に過剰にダウンロードしないようにしたいでしょう。 – Lukasz

答えて

7

私は私の生産のアプリのいずれかで同じことを実現しています

  1. は、あなたがダウンロードしたい項目を追加するテーブルを作成します。並べ替えは、アイテムがダウンロード用に追加された時刻に基づいている必要があります。これをキューと見なしてください。また、ファイルがすでにダウンロードされているかどうかをチェックするために1つの列を追加します。ダウンロードされた場合は、キューから削除します。
  2. IntentServiceを作成します。これは、アプリケーションが終了してもバックグラウンドでデータをダウンロードする責任があります。このServiceは、テーブルのキューが空になるまで実行を継続する必要があります。新しい項目が追加されたとき、またはネットワークの接続状態が死んでいるから生きているときに開始する必要があります。このServiceの中で、キューが空であるかどうかを確認する必要があります。空の場合は、Nテーブルからの行数をキューに追加して(ExecutorService)ダウンロードします。ネットワーク状態のチャネージを確認するには、BroadcastReceiver‎LocalBroadcastManagerに作成します。
  3. これでコードを書くことができますDownloadIntentService。あなたのニーズに従って変更しよう:

    private static int NUMBER_OF_CORES = 
        Runtime.getRuntime().availableProcessors() * 2; 
    private final ExecutorService executorService; 
    private final ExecutorCompletionService<DownloadModel> executorCompletionService; 
    
    public DownloadIntentService() { 
    super("DownloadIntentService"); 
    executorService = Executors.newFixedThreadPool(NUMBER_OF_CORES); 
    executorCompletionService = new ExecutorCompletionService<>(executorService); 
    } 
    
    ...... 
    @Override 
    protected void onHandleIntent(Intent intent) { 
    
    //Check to see for storage permission 
    if (ActivityCompat.checkSelfPermission(this, 
         Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED 
         && ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) 
         == PackageManager.PERMISSION_GRANTED) { 
    ..... 
    //Now create job queue 
    .... 
    //Fetch rows to download from table 
    DownloadQuery downloadQuery = new DownloadQuery(DownloadIntentService.this); 
    
    ArrayList<DownloadModel> downloadModelArrayList = downloadQuery.getDownload(DownloadContract.IFileDownloadStatus.NOT_DOWNLOADED, 
          0, NUMBER_OF_CORES); 
    //Check if queue contains any item 
    if (downloadModelArrayList.size() > 0) { 
    if (!executorService.isShutdown()) 
            executorCompletionService.submit(new DownloadWorkerCallable(**Your download model from table to download**, DownloadIntentService.this)); 
    } 
    ..... 
    //Don't forget to shutdown the executorService 
    } 
    } 
    

このDownloadWorkerCallableは、実際にファイルをダウンロードしたRunnableを実施しています。

+0

@Alexanderあなたは何とおっしゃいますか? –

+0

ありがとうございます。しかし、サービス開始後、ユーザーはいつでも新しいダウンロードアイテムを追加できます。追加された各ダウンロード項目で、新しいダウンロード項目のダウンロードを開始する必要があります。あなたの例で私が間違っていない場合は、開始サービスの開始時にすべてのダウンロードアイテムを取得していますか?しかしサービス開始後のコードで、ユーザーは新しいダウンロード項目を追加することができます – Alexander

+0

IntentServiceが起動すると、タスクまたはonHandleIntent()が実行されなくなるまで、IntentServiceは実行を継続します。私はonHandleIntent()で項目を取得します。 onHandleIntent()が終了していない場合でも、ダウンロードを開始する新しいリクエストはキューに入れられ、DownloadIntentService()は再び開始されません。また、whileHandleIntent()からアイテムを取得する別の方法もあります(テーブルの項目が多い場合) –

2

ThreadPool以上のEventBusを使用する必要があります。 AsyncTaskは、複数のダウンロードには適していません。

関連する問題