安卓Android service+BroadcastReceiver+thread(帶開始停止控制)

直接上代碼



import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Environment;
import android.os.IBinder;
import android.text.TextUtils;

import androidx.annotation.Nullable;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.Serializable;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.HashMap;
import java.util.Map;



public class DownloadService extends Service {

    private final String TAG = "DownloadService";

    private static Map<String, DownloadThread> downLoadTaskMap = new HashMap<>();

    // 添加下載
    public static boolean taskAdd(Context ctx, String unique, String type, String url, Object data) {
        if (TextUtils.isEmpty(url)) {
            ToastUtil.show("下載地址不能爲空");
            return false;
        } else if (downLoadTaskMap.get(unique) != null) {
            ToastUtil.show("正在取消");
            taskCancel(unique);
            return false;
        }

        Intent intent = new Intent(ctx, DownloadService.class);
        intent.putExtra("unique", unique);
        intent.putExtra("type", type);
        intent.putExtra("url", url);
        intent.putExtra("data", (Serializable) data);
        ctx.startService(intent);

        return true;
    }

    // 任務停止
    public static boolean taskCancel(String unique) {
        DownloadThread downLoadTask = downLoadTaskMap.get(unique);
        if (downLoadTask != null) {
            downLoadTask.cancel();
        }
        return true;
    }

    @Override
    public int onStartCommand(@Nullable Intent intent, int flags, int startId) {
        Bundle bundle = intent.getExtras();
        String unique = bundle.getString("unique");
        String type = bundle.getString("type");
        String urlStr = bundle.getString("url");
        String fileName = bundle.getString("fileName");
        if (TextUtils.isEmpty(urlStr)) {
            ToastUtil.show("下載地址不能爲空");
            return super.onStartCommand(intent, flags, startId);
        }
        if (TextUtils.isEmpty(fileName)) {
            File file = new File(urlStr);
            intent.putExtra("fileName", file.getName());
        }

        System.out.println("unique ===> " + unique + ", type=" + type);

        DownloadThread downLoadTask = new DownloadThread(intent);
        new Thread(downLoadTask).start();
        downLoadTaskMap.put(unique, downLoadTask);

        return super.onStartCommand(intent, flags, startId);
    }

    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    /**
     * 下載類
     * */
    private class DownloadThread implements Runnable {

        private int status = 0;

        private Intent taskIntent = null;

        private Intent sendIntent = null;

        public DownloadThread(Intent intent) {
            status = 1;
            taskIntent = intent;
            Bundle bundle = taskIntent.getExtras();
            sendIntent = new Intent(DownloadReceiver.ACTION);
            sendIntent.putExtra("unique", bundle.getString("unique"));
            sendIntent.putExtra("type", bundle.getString("type"));
            sendIntent.putExtra("url", bundle.getString("url"));
            sendIntent.putExtra("data", (Serializable) bundle.get("data"));
        }

        public void cancel() {
            status = 4;
        }

        private void onCancel() {
            sendIntent.putExtra("status", DownloadReceiver.Status.cancel);
            sendBroadcast(sendIntent);
            downLoadTaskMap.remove(sendIntent.getStringExtra("unique"));
        }

        private void onFinish() {
            sendIntent.putExtra("status", DownloadReceiver.Status.complate);
            sendBroadcast(sendIntent);
            downLoadTaskMap.remove(sendIntent.getStringExtra("unique"));
        }

        private void onFail() {
            sendIntent.putExtra("status", DownloadReceiver.Status.fail);
            sendBroadcast(sendIntent);
            downLoadTaskMap.remove(sendIntent.getStringExtra("unique"));
        }

        @Override
        public void run() {
            // 數據
            Bundle bundle = taskIntent.getExtras();
            String fileName = bundle.getString("fileName");
            String filePath = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS).getPath() + fileName;
            String urlStr = bundle.getString("url");
            // 準備回覆 Intent
            sendIntent.putExtra("fileName", fileName);
            sendIntent.putExtra("filePath", filePath);

            try {
                URL url = new URL(urlStr);
                HttpURLConnection conn = (HttpURLConnection) url.openConnection();
                long fileSize = conn.getContentLength(); //  獲取到最大值之後設置到進度條的MAX

                // 開始下載通知
                sendIntent.putExtra("status", DownloadReceiver.Status.start);
                sendBroadcast(sendIntent);

                //  開始下載
                byte[] bytes = new byte[1024 * 512];    //  爲方便測試故將其設置較小
                int len = -1;
                long downTotal = 0;
                InputStream in = conn.getInputStream();
                FileOutputStream out = new FileOutputStream(filePath);
                while ((len = in.read(bytes)) != -1) {
                    out.write(bytes, 0, len);
                    out.flush();
                    downTotal += len;
                    // 取消
                    if (status == 4) {
                        onCancel();
                        out.close();
                        in.close();
                        return;
                    }
                    // 千分比
                    double progNumFloat = (double) downTotal / (double) fileSize;
                    long progNum = (long) (progNumFloat * 1000f);
                    // 模擬下載發送進度
                    sendIntent.putExtra("status", DownloadReceiver.Status.progress);
                    sendIntent.putExtra("fileSize", fileSize);
                    sendIntent.putExtra("downTotal", downTotal);
                    sendIntent.putExtra("progNum", progNum);
                    //System.out.println("fileSize ===> " + fileSize + ", downTotal ===> " + downTotal);
                    sendBroadcast(sendIntent);
                }
                out.close();
                in.close();
            } catch (Exception e) {
                e.printStackTrace();
                onFail();
                return;
            }

            onFinish();
        }
    }

}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章