1、让IT教学更简单,让IT学习更有效Android程序设计教程第6章 Service服务目录 6.1 Service简介 6.1.1 Service分类 6.1.2 Service基本示例 6.2 Service详解 6.2.1 Start方式启动Service 6.2.2 Bind方式启动Service 6.2.3 混合方式启动Service 6.2.4 前台Service 6.2.5 Service执行耗时任务 6.2.6 远程Service学习目标 了解Service分类 掌握Service的创建、配置和编写 掌握Service生命周期 掌握Service组件的通信6.1 Service简
2、介 Service组件表示一种服务,专门用于执行一些持续的、耗时长的并且无须与用户界面交互的操作。Service的运行时不可见的,通常用于执行一些无须用户交互,并需要持续运行的任务 Service拥有独立的生命周期,其启动、停止以及运行的控制可以由其他组件完成 一个处于运行状态的Service拥有的优先级要比暂停和停止状态的Activity级别更高 如果在Service中需要执行耗时操作,必须新开线程运行,否则会阻塞主线程,从而造成界面卡顿现象6.1.1 Service分类 按照运行的形式和使用方式的不同,可以对Service进行分类:(1)按照运行的进程不同,可以将Service分为本地(L
3、ocal)Service和远程(Remote)Service。(2)按照运行的形式分为前台Service和后台Service。(3)按照使用Service的方式可以分为启动(Start)方式Service、绑定(Bind)方式Service和混合方式Service。6.1.2 Service基本示例 创建一个Service组件只需要两步,而启动Service可以使用Start和Bind两种方式。创建Service的步骤如下:(1)通过继承Service的方式来定义一个Service的子类;(2)在应用程序的AndroidManifest.xml中配置Service组件。6.2 Service详
4、解6.2.1 Start方式启动Service Start方式通过调用Context.startService()方法来启动Service。Service将自行管理生命周期,并会一直运行下去,直到Service调用自身的stopSelf()方法或其他组件调用该Service的stopService()方法时为止。一个组件通过startService()方法启动Service后,该组件与Service之间并没有关联,即使组件被销毁,也并不影响Service的运行 关于onStartCommand()方法的语法格式如下所示:public int onStartCommand(Intent inte
5、nt,int flags,int startId)其中:参数intent是在启动Service时所传入的Intent对象。参数flags取值范围为0、Service.START_FLAG_REDELIVERY和Service.START_FLAG_RETRY。startID表示启动请求的ID,用于唯一标识一次启动请求,在调用stopSelfResult()方法停止Service时,可以传入特定的startId,用于对停止Service操作的附加条件 onStartCommand()方法的返回值有Service.START_NOT_STICKY、Service.START_STICKY和Serv
6、ice.START_REDELIVER_INTENT三种情况。6.2.2 Bind方式启动Service 通过调用Context的bindService()方法也可以启动Service。使用Bind方式启动的Service会和启动它的组件关联在一起,并可以进行通信,组件可以通过unbindService()方法来解除绑定。bindService()方法的语法结构如下所示:public boolean bindService(Intent service,ServiceConnection conn,int flags)bindService()方法用于绑定Service,其返回值代表是否绑定成
7、功,其参数如下:(1)参数service,在绑定Service时所传入的Intent对象。(2)参数conn,这是一个ServiceConnection接口类型的对象,在绑定或解除绑定时,系统会调用ServiceConnection接口中对应的回调方法(3)参数flags,用于决定Service的一些行为规则,常用的取值有0、BIND_AUTO_CREATE、BIND_NOT_FOREGROUND、BIND_WAIVE_PRIORITY、BIND_IMPORTANT、BIND_ABOVE_CLIENT和BIND_ADJUST_WITH_ACTIVITY。6.2.3 混合方式启动Service6
8、.2.4 前台Service Service启动后,其所在的进程默认是服务进程,优先级并不高,如果该进程非常重要,可以通过Service的startForeground()方法将其改为前台进程。调用startForeground()方法后,Service运行时会在通知栏显示一个通知(Notification),Service停止后通知会消失。startForeground()方法声明格式如下:public final void startForeground(int id,Notification notification)其中:参数id是通知的id;参数notification需要显示的通知
9、。当Service成为前台进程后,需要恢复原有的优先级可以调用stopForeground()方法取消其前台状态,从而允许系统在内存不足时更容易终止这个Service。stopForeground()方法声明格式如下:public final void stopForeground(int flags)stopForeground()方法只有一个参数,当降低Service的前台优先级时,指用该参数指定是否移除startForeground()方法所创建的通知。6.2.5 Service执行耗时任务 Service运行于UI线程中,如果直接在UI线程中执行耗时或可能被阻塞的任务,会造成界面无响应
10、异常,因此这种耗时任务通常都需要新开线程执行。针对在Service中执行耗时任务,Android系统还专门提供了一种特殊的Service:IntentService。抽象类android.add.IntentService是Service的子类,其内部会自动开始一个新线程来执行任务,并在任务执行完毕后停止Service。当有多个任务时,IntentService会将任务加到一个队列中,按照次序依次执行,直到所有任务执行完毕后停止Service。使用IntentService非常简单,只需继承IntentService并重写onHandleIntent()方法即可,onHandleIntent(
11、)方法的语法格式如下所示:protected abstract void onHandleIntent(Intent intent);其中,参数intent是Service客户端以Start方式启动Service时startService()方法所传入的intent对象。6.2.6 远程Service Android系统提供了远程Service,即允许被另一个进程中的组件访问的Service。为使远程Service能被其他进程访问,需要一种进程间通信的机制。进程是操作系统的概念,因此,跨进程通信需要将传递的对象分解成操作系统可以理解的基本单元,并且有序地通过进程边界。通过代码实现进程间通信数据的解析和传输需要编写冗长的模板式代码,为此,Android系统提供了AIDL(Android Interface Definition Language,Android接口定义语言)工具来完成这项工作。谢谢