StartService & BindService结合Down

2019-05-15  本文已影响0人  杰子他爸

1、startService和BindService都是作为后台服务,但区别在于生命周期,多次启动,Activity销毁是否解绑。

2、关于startService简介声明:

public  IBinder   onBind(Intent intent){

Log.e("call","onBind");   returnnull;    }

//开启服务Intent service =new Intent(this, MyService.class);  startService(service);

//结束服务stopService(service);

调用多次startService,onCreate只有第一次会被执行,而onStartCommand会执行多次。

3、关于BindService简介声明:

//开启服务   Intent service =newIntent(this, MyService.class); 

MyConnection conn =new  MyConnection();

//第一个参数:Intent意图

//第二个参数:是一个接口,通过这个接口接收服务开启或者停止的消息,并且这个参数不能为null

//第三个参数:开启服务时的操作,BIND_AUTO_CREATE代表自动创建

servicebindService(service, conn, BIND_AUTO_CREATE);

同时自己实现conn:

//结束服务unbindService(conn);

onBind返回值不为null的情况分析:

以下内容转自网友:

4、startService和bindService开启服务时,他们与activity之间的关系

1)startService开启服务以后,与activity就没有关联,不受影响,独立运行。

2)bindService开启服务以后,与activity存在关联,退出activity时必须调用unbindService方法,否则会报ServiceConnection泄漏的错误。

以上知识点结合DownloadManager实践:

public class DownloadServiceextends Service {

public static final StringBUNDLE_KEY_DOWNLOAD_URL ="download_url";

    public static final int UNBIND_SERVICE =0x002;

    private DownloadBinderbinder;

    public static final int HANDLE_DOWNLOAD =0x001;

    //下载任务ID

    private long downloadId;

    private StringdownloadUrl;

    private DownloadManagerdownloadManager;

    private OnProgressListeneronProgressListener;

    private BroadcastReceiverdownLoadBroadcast;

    private ScheduledExecutorServicescheduledExecutorService;

    @Override

    public void onCreate() {

super.onCreate();

        binder =new DownloadBinder();

        scheduledExecutorService = Executors.newSingleThreadScheduledExecutor();

        scheduledExecutorService.scheduleAtFixedRate(progressRunnable, 0, 1, TimeUnit.SECONDS);

    }

@Override

    public IBinderonBind(Intent intent) {

downloadUrl = intent.getStringExtra(BUNDLE_KEY_DOWNLOAD_URL);

        downloadApk(downloadUrl, "lotteryInstall.apk");

        return binder;

    }

/**

* 下载最新APK

*/

    private void downloadApk(String url, String name) {

downloadManager = (DownloadManager) getSystemService(DOWNLOAD_SERVICE);

        DownloadManager.Request request =new DownloadManager.Request(Uri.parse(url));

        /**设置用于下载时的网络状态*/

        request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI | DownloadManager.Request.NETWORK_MOBILE);

        /**设置通知栏是否可见*/

        request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE);

        /**设置漫游状态下是否可以下载*/

        request.setAllowedOverRoaming(false);

        /**如果我们希望下载的文件可以被系统的Downloads应用扫描到并管理,

我们需要调用Request对象的setVisibleInDownloadsUi方法,传递参数true.*/

        request.setVisibleInDownloadsUi(true);

        //设置可以被系统扫描到

        request.allowScanningByMediaScanner();

        /**设置文件保存路径*/

        request.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, name);

        /**将下载请求放入队列, return下载任务的ID*/

        downloadId =downloadManager.enqueue(request);

        registerBroadcast();

    }

/**

* 注册广播

*/

    private void registerBroadcast() {

/**注册service 广播 1.任务完成时 */

        IntentFilter intentFilter =new IntentFilter();

        intentFilter.addAction(DownloadManager.ACTION_DOWNLOAD_COMPLETE);

        registerReceiver(downLoadBroadcast =new DownLoadBroadcast(), intentFilter);

    }

/**

* 注销广播

*/

    private void unregisterBroadcast() {

if (downLoadBroadcast !=null) {

unregisterReceiver(downLoadBroadcast);

            downLoadBroadcast =null;

        }

}

public class DownloadBinderextends Binder {

/**

* 返回当前服务的实例

*

        * @return

        */

        public DownloadServicegetService() {

return DownloadService.this;

        }

}

/**

* 接受下载完成广播

*/

    private class DownLoadBroadcastextends BroadcastReceiver {

@Override

        public void onReceive(Context context, Intent intent) {

checkStatus();

        }

}

//检查下载状态

    private void checkStatus() {

DownloadManager.Query query =new DownloadManager.Query();

        //通过下载的id查找

        query.setFilterById(downloadId);

        Cursor c =downloadManager.query(query);

        if (c.moveToFirst()) {

int status = c.getInt(c.getColumnIndex(DownloadManager.COLUMN_STATUS));

            switch (status) {

//下载暂停

                case DownloadManager.STATUS_PAUSED:

break;

                //下载延迟

                case DownloadManager.STATUS_PENDING:

break;

                //正在下载

                case DownloadManager.STATUS_RUNNING:

LogWriter.writeExceptionLog("DownloadUtils  正在下载");

                    //下载完成

                case DownloadManager.STATUS_SUCCESSFUL:

LogWriter.writeExceptionLog("DownloadUtils  app下载完成");

                    close();

                    if (onProgressListener !=null) {

onProgressListener.onProgress(UNBIND_SERVICE);

                    }

DeviceAPIFactory.getRobotSystemServer().startApkUpdate(new IMessageBagReceiver() {

@Override

                        public void onMessageBagReceived(MessageBag resMsgBag) {

AppUpgradeService.startActionUpdateApp(App.getInstance(),

                                    Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS).getPath() +"/lotteryInstall.apk", BuildConfig.APPLICATION_ID);

                        }

@Override

                        public void onMessageBagTimeout(MessageBag reqMsgBag) {

ToastUtil.showMessage("发送数据超时,App升级失败,请重试!");

                        }

});

break;

                //下载失败

                case DownloadManager.STATUS_FAILED:

LogWriter.writeExceptionLog("DownloadUtils  下载失败");

break;

            }

}

c.close();

    }

/**

* 关闭定时器,线程等操作

*/

    private void close() {

if (scheduledExecutorService !=null && !scheduledExecutorService.isShutdown()) {

scheduledExecutorService.shutdown();

        }

if (downLoadHandler !=null) {

downLoadHandler.removeCallbacksAndMessages(null);

        }

}

public HandlerdownLoadHandler =new Handler() {

@Override

        public void handleMessage(Message msg) {

super.handleMessage(msg);

            switch (msg.what) {

case HANDLE_DOWNLOAD:

if (onProgressListener !=null &&HANDLE_DOWNLOAD == msg.what) {

onProgressListener.onProgress(getDownloadPercent(downloadId));

                    }

break;

                default:

break;

            }

}

};

    private RunnableprogressRunnable =new Runnable() {

@Override

        public void run() {

updateProgress();

        }

};

    /**

* 发送Handler消息更新进度和状态

*/

    private void updateProgress() {

downLoadHandler.sendEmptyMessage(HANDLE_DOWNLOAD);

    }

public interface OnProgressListener {

/**

* 下载进度

*

        * @param fraction 已下载/总大小

*/

        void onProgress(int fraction);

    }

/**

* 对外开发的方法

*

    * @param onProgressListener

    */

    public void setOnProgressListener(OnProgressListener onProgressListener) {

this.onProgressListener = onProgressListener;

    }

/**

* 获取下载进度

*

    * @param downloadId

    * @return

    */

    private int getDownloadPercent(long downloadId) {

DownloadManager.Query query =new DownloadManager.Query().setFilterById(downloadId);

        Cursor c =downloadManager.query(query);

        if (c.moveToFirst()) {

int downloadBytesIdx = c.getColumnIndexOrThrow(

DownloadManager.COLUMN_BYTES_DOWNLOADED_SO_FAR);

            int totalBytesIdx = c.getColumnIndexOrThrow(

DownloadManager.COLUMN_TOTAL_SIZE_BYTES);

            long totalBytes = c.getLong(totalBytesIdx);

            long downloadBytes = c.getLong(downloadBytesIdx);

            return (int) (downloadBytes *100 / totalBytes);

        }

return 0;

    }

@Override

    public void onDestroy() {

super.onDestroy();

        unregisterBroadcast();

    }

}

Activity部分代码掠影:

private ServiceConnectionconn =new ServiceConnection() {

@Override

    public void onServiceConnected(ComponentName name, IBinder service) {

DownloadService.DownloadBinder binder = (DownloadService.DownloadBinder) service;

        DownloadService downloadService = binder.getService();

        //接口回调,下载进度

        downloadService.setOnProgressListener(new DownloadService.OnProgressListener() {

@Override

            public void onProgress(float fraction) {

LogUtil.i(TAG, "下载进度:" + fraction);

                bnp.setProgress((int)(fraction *100));

                //判断是否真的下载完成进行安装了,以及是否注册绑定过服务

                if (fraction == DownloadService.UNBIND_SERVICE &&isBindService) {

unbindService(conn);

                    isBindService =false;

                    MToast.shortToast("下载完成!");

                }

}

});

    }

@Override

    public void onServiceDisconnected(ComponentName name) {

}

};

That's all !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

上一篇下一篇

猜你喜欢

热点阅读