【问题标题】:Is it possible to show progress bar when download file via Retrofit 2, Android通过 Retrofit 2、Android 下载文件时是否可以显示进度条
【发布时间】:2016-04-26 08:20:57
【问题描述】:

我目前正在使用 Retrofit 2,我想从我的服务器下载一些文件。 我可以回调一些事件来捕获下载文件完成百分比以显示在通知中,如这张图片

我引用了那个链接,但它是上传的,我可以用同样的问题吗? Link

使用 Retrofit 2 库时是否可以显示进度?

【问题讨论】:

  • Check this的可能重复
  • 它正在上传图片,我可以这样做吗?
  • 是的,它正在上传文件。
  • 朋友,我需要下载文件。
  • @NguyễnHoàng 您能否将您的代码粘贴到您的帖子中,以便在解决您的问题后知道我们该如何解决?谢谢

标签: android download retrofit


【解决方案1】:

您可以使用ResponseBody 并将其设置为OkHttp 客户端并在UI 中更新进度您可以使用界面。check this link

【讨论】:

  • 您能否打印一些日志以验证是否有呼叫到达 ResponseBody。当您说它不起作用时是什么意思
  • 是的,我知道那是 java 代码,所以我将 System.out.println 更改为 Log.i。我看到了这个例外。 java.net.InetAddress.lookupHostByName 处的 android.os.NetworkOnMainThreadException
  • NetworkOnMainThread 是不同的异常,当您在 UI 中执行繁重的操作(如网络和其他阻塞调用)时会发生这种异常。所以将您的代码移动到后台线程
  • 是的,你拯救了我的一天:),tks这么多
  • 但是。不是改装!! :),任何想法>
【解决方案2】:

作为替代方案,您可以使用 here 所述的 Intent 服务。

我会告诉你我是如何使用上面的......唯一的区别是文件写入磁盘的部分。

定义服务:

public class BackgroundNotificationService extends IntentService {

    public BackgroundNotificationService() {
        super("Service");
    }

    private NotificationCompat.Builder notificationBuilder;
    private NotificationManager notificationManager;

    private String mAgentsID;
    private String mReportsID;
    private String mJobID;
    private String mFileName;


    @Override
    protected void onHandleIntent(Intent intent) {

        notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationChannel notificationChannel = new NotificationChannel("id", "an", NotificationManager.IMPORTANCE_LOW);

            notificationChannel.setDescription("no sound");
            notificationChannel.setSound(null, null);
            notificationChannel.enableLights(false);
            notificationChannel.setLightColor(Color.BLUE);
            notificationChannel.enableVibration(false);
            notificationManager.createNotificationChannel(notificationChannel);
        }


        notificationBuilder = new NotificationCompat.Builder(this, "id")
                .setSmallIcon(android.R.drawable.stat_sys_download)
                .setContentTitle("Download")
                .setContentText("Downloading Image")
                .setDefaults(0)
                .setAutoCancel(true);
        notificationManager.notify(0, notificationBuilder.build());

        mAgentsID = intent.getStringExtra("AgentsID");
        mReportsID = intent.getStringExtra("ReportsID");
        mJobID = intent.getStringExtra("JobID");
        mFileName = intent.getStringExtra("FileName");

        initRetrofit();

    }

    private void initRetrofit(){
        Call<ResponseBody> downloadCall = ApiManager.getJasperReportsService().DownloadAgentReportData(mAgentsID, mReportsID, mJobID, mFileName);

        try {
            writeResponseBodyToDisk(downloadCall.execute().body(), mFileName);
        } catch (IOException e) {
            e.printStackTrace();
        }

    }


    private boolean writeResponseBodyToDisk(ResponseBody body, String FileName) {
        try {
            File SDCardRoot = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS);
            File DownloadedFile = new File(SDCardRoot + File.separator + FileName);

            InputStream inputStream = null;
            OutputStream outputStream = null;

            try {
                byte[] fileReader = new byte[4096];

                long fileSize = body.contentLength();
                long fileSizeDownloaded = 0;

                long total = 0;
                boolean downloadComplete = false;

                inputStream = body.byteStream();
                outputStream = new FileOutputStream(DownloadedFile);

                while (true) {
                    int read = inputStream.read(fileReader);

                    if (read == -1) {
                        downloadComplete = true;
                        break;
                    }

                    total += read;
                    int progress = (int) ((double) (total * 100) / (double) fileSize);

                    updateNotification(progress);

                    outputStream.write(fileReader, 0, read);

                    fileSizeDownloaded += read;


                    Log.d("DOWNLOAD FILE", "file download: " + fileSizeDownloaded + " of " + fileSize);
                }
                onDownloadComplete(downloadComplete);

                outputStream.flush();

                return true;
            } catch (IOException e) {
                return false;
            } finally {
                if (inputStream != null) {
                    inputStream.close();
                }

                if (outputStream != null) {
                    outputStream.close();
                }
            }
        } catch (IOException e) {
            return false;
        }
    }

    private void updateNotification(int currentProgress) {


        notificationBuilder.setProgress(100, currentProgress, false);
        notificationBuilder.setContentText("Downloaded: " + currentProgress + "%");
        notificationManager.notify(0, notificationBuilder.build());
    }


    private void sendProgressUpdate(boolean downloadComplete) {

        Intent intent = new Intent("progress_update");
        intent.putExtra("downloadComplete", downloadComplete);
        LocalBroadcastManager.getInstance(BackgroundNotificationService.this).sendBroadcast(intent);
    }

    private void onDownloadComplete(boolean downloadComplete) {
        sendProgressUpdate(downloadComplete);

        notificationManager.cancel(0);
        notificationBuilder.setProgress(0, 0, false);
        notificationBuilder.setContentText("Download Complete");
        notificationManager.notify(0, notificationBuilder.build());

    }

    @Override
    public void onTaskRemoved(Intent rootIntent) {
        notificationManager.cancel(0);
    }

}

然后使用意图服务:

private void registerReceiver() {

    LocalBroadcastManager bManager = LocalBroadcastManager.getInstance(itemView.getContext());
    IntentFilter intentFilter = new IntentFilter();
    intentFilter.addAction("progress_update");
    bManager.registerReceiver(mBroadcastReceiver, intentFilter);

}

private BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
    @Override
    public void onReceive(Context context, Intent intent) {

        if (intent.getAction().equals("progress_update")) {

            boolean downloadComplete = intent.getBooleanExtra("downloadComplete", false);
            //Log.d("API123", download.getProgress() + " current progress");

            if (downloadComplete) {

                Toast.makeText(itemView.getContext(), "File download completed", Toast.LENGTH_SHORT).show();

            }
        }
    }
};

private void startDownload(String jobID, String FileName) {


    Intent intent = new Intent(itemView.getContext(), BackgroundNotificationService.class);
    // TODO customze to suit your own needs.
    intent.putExtra("AgentsID", mAgentsID);
    intent.putExtra("ReportsID", mReportsID);
    intent.putExtra("JobID", jobID);
    intent.putExtra("FileName", FileName);
    itemView.getContext().startService(intent);

}

所以你在活动开始时使用registerReceiver(),然后如果你有一个按钮来启动下载,你可以在 onClick 方法中运行startDownload()。作为额外说明,您可以根据需要自定义意图变量(如果需要)。

【讨论】:

    猜你喜欢
    • 2017-06-13
    • 2016-01-25
    • 1970-01-01
    • 2016-07-30
    • 1970-01-01
    • 1970-01-01
    • 2020-12-04
    • 1970-01-01
    • 2016-12-24
    相关资源
    最近更新 更多