android

Service-服务(一)生命周期及使用方式

2019-01-23  本文已影响37人  林锦洲

一、Service(服务)概述

二、两种启动方式

服务基本上分为两种形式:

虽然上文是分开概括讨论这两种服务,但是您的服务可以同时以这两种方式运行,也就是说,它既可以是start服务(以无限期运行),也允许bind。问题只是在于您是否实现了一组回调方法:onStartCommand()(允许组件启动服务)和 onBind()(允许绑定服务)。
无论应用是处于启动状态还是绑定状态,抑或处于启动并且绑定状态,任何应用组件均可像使用Activity 那样通过调用 Intent 来使用服务(即使此服务来自另一应用)。 不过,可以通过AndroidManifest.xml将服务声明为私有服务,并阻止其他应用访问。

三、生命周期

Service生命周期。左图显示了使用 startService() 所创建的服务的生命周期,右图显示了使用 bindService() 所创建的服务的生命周期。

Service生命周期

四、使用Service的步骤

1.定义一个类继承Service(或使用它的一个现有子类如IntentService
2.在Manifest.xml文件中配置该Service
3.使用startService()bindService()方法启动该Service
4.不再使用时,调用stopService()stopSelf()unbindService()方法停止该服务

4.1定义一个类继承Service

public class MService extends Service {  
    /**
    * 首次创建服务时,系统将调用此方法来执行一次性设置程序(在调用 onStartCommand() 或 onBind() 之前)。
    * 如果服务已在运行,则不会调用此方法。该方法只被调用一次
    */
    @Override  
    public void onCreate() {  
        super.onCreate();  
    }  
    /**
    * 每次通过startService()方法启动Service时都会被回调。
    */
    @Override  
    public int onStartCommand(Intent intent, int flags, int startId) {  
        return super.onStartCommand(intent, flags, startId);
    }  
    /**
    * 服务销毁时的回调
    */
    @Override  
    public void onDestroy() {  
        super.onDestroy();  
    }  
    /**
    * 绑定服务时才会调用 必须要实现的方法 
    */
    @Override  
    public IBinder onBind(Intent intent) {  
        return null;  
    }  
  
}  

虽然这个Service什么都没干,但实际上它是Service组件的框架,如果希望Service组件做某些事情,那么只要在onCreate()onStartCommand()方法中定义相关业务代码即可

4.2在清单文件声明

定义了上面的Service之后,接下来需要在Androidmaniferst.xml文件中配置该Service,配置Service使用<service../>元素。与配置Activity显示的是,配置Service时也可为<service../>元素配置<intent-filter.../>子元素,用于说明该Service可被那些Intent启动。

<application
        ...
        <service android:name=".MService" >
            <intent-filter>
                <action android:name="..." />
            </intent-filter>
        <service/>
</application>

Service包含的属性有

<service android:enabled=["true" | "false"]
    android:exported=["true" | "false"]
    android:icon="drawable resource"
    android:isolatedProcess=["true" | "false"]
    android:label="string resource"
    android:name="string"
    android:permission="string"
    android:process="string" >
    . . .
</service>
属性 说明
description 对服务进行描述,属性值应为对字符串资源的引用,以便进行本地化
directBootAware 设置是否可以在用户解锁设备之前运行,默认值为“false”
enabled 设置是否可以由系统来实例化服务。< application >元素有自己的enabled属性,适用于包括服务在内的所有应用程序组件。要启用服务,< application >和< service >属性必须都为“true”(默认情况下都为true)。如果其中一个是“false”,则服务被禁用
exported 设置其他应用程序的组件是否可以调用本服务或与其交互,如果可以,则为“true”。当值为“false”时,只有同一个应用程序或具有相同用户ID的应用程序的组件可以启动该服务或绑定到该服务。该属性的默认值取决于服务是否包含Intent filters。没有任何过滤器意味着它只能通过指定其确切的类名来调用,这意味着该服务仅用于应用程序内部使用(因为其他人不知道类名)。所以在这种情况下,默认值为“false”。 另一方面,如果存在至少一个过滤器,意味着该服务打算供外部使用,因此默认值为“true”
icon 服务的图标,属性值应是对drawable资源的引用。如果未设置,则将使用应用程序图标
isolatedProcess 设置该服务是否作为一个单独的进程运行,如果设置为true,此服务将在与系统其余部分隔离的特殊进程下运行,并且没有自己的权限,与它唯一的通信是通过服务API(绑定和启动)
label 可以向用户显示的服务的名称,属性值应是对字符串资源的引用
name 服务类的完全限定名
permission 设定组件必须具有的权限,得以启动服务或绑定服务。如果startService(),bindService()或stopService()的调用者没有被授予此权限,则该方法将不会工作,并且Intent对象不会传递到服务中
process 用来运行服务的进程的名称。通常,应用程序的所有组件都运行在应用程序创建的默认进程中,它与应用程序包名具有相同的名称。 < application >元素的process属性可以为所有组件设置不同的默认值,但组件可以使用自己的进程属性覆盖默认值,从而允许跨多个进程扩展应用程序

4.3启动和停止Service

通过将 Intent(指定要启动的服务)传递给 startService(),从 Activity 或其他应用组件启动服务。Android 系统调用服务的 onStartCommand() 方法,并向其传递 Intent

Intent intent = new Intent(this, MService.class);
startService(intent);

注意:为了避免浪费系统资源和消耗电池电量,应用必须在工作完成之后停止其服务。 如有必要,其他组件可以通过调用stopService() 来停止服务。即使为服务启用了绑定,一旦服务收到对 onStartCommand() 的调用,您始终仍须亲自停止服务。

4.4绑定Service并与之通讯

待续。。。

上一篇下一篇

猜你喜欢

热点阅读