安卓service
Service的生命周期
使用context.startService()启动Service
其生命周期为context.startService() ->onCreate()- >onStart()->Service running-->(如果调用context.stopService() )->onDestroy() ->Service shut down
如果Service还没有运行,则android先调用onCreate()然后调用onStart();
如果Service已经运行,则只调用onStart(),所以一个Service的onStart方法可能会重复调用多次。
调用stopService的时候直接onDestroy,
如果是调用者自己直接退出而没有调用stopService的话,Service会一直在后台运行。
该Service的调用者再启动起来后可以通过stopService关闭Service。
所以调用startService的生命周期为:onCreate --> onStart(可多次调用) --> onDestroy
对于bindService()启动Service会经历:
context.bindService()->onCreate()->onBind()->Service running-->onUnbind() -> onDestroy() ->Service stop
onBind将返回给客户端一个IBind接口实例,IBind允许客户端回调服务的方法,比如得到Service运行的状态或其他操作。
这个时候把调用者(Context,例如Activity)会和Service绑定在一起,Context退出了,
Srevice就会调用onUnbind->onDestroy相应退出。
所以调用bindService的生命周期为:onCreate --> onBind(只一次,不可多次绑定) --> onUnbind --> onDestory。
一但销毁activity它就结束,如果按home把它放到后台,那他就不退出。
PS:
在Service每一次的开启关闭过程中,只有onStart可被多次调用(通过多次startService调用),
其他onCreate,onBind,onUnbind,onDestory在一个生命周期中只能被调用一次。
Service在Manifest里的一些属性
android:enabled
是否这个service能被系统实例化-如果能则为true,否则为false。默认为true。
<application>元素有它自身的能应用到所有应用组件的enabled属性,包括services。要是这个service要enabled,那么这个<application>和<service>属性都必须为true(它们都是默认值)。如果有一个为false,这个服务就会disabled;它就不会被实例化。
android:exported
是否其它应用组件能调用这个service或同它交互-如果能则为true,否则为false。当值为false时,只有同一个应用的组件或有相同用户ID的应用能启动这个服务或绑定它。
默认值依赖于服务是否包含intent filters。过滤器的缺失意味着它只能通过指定它准确类名来调用它。这就意味着这个服务只能在应用内部被使用(因为其它应用不知道类名)。因此,在这种情况下,默认值是false。另一方面,至少有一个过滤器意味着这个服务可以在外部被使用,因此,默认值为true。
这个属性并非是限制这个服务暴漏给其它服务的唯一途径。你也能通过权限来限制跟服务交互的外部实体(参见permisson属性)。
android:icon
服务呈现的图标。这个属性必须被设置为包含图片的drawable资源的引用。如果没有设置,那么这个application的图标将代替它(参见<application>元素的icon属性)。
对所有的intent filters来说,这个服务的图标无论是自身设置的还是通过<application>设置的,都是它们的默认图标(参见<intent-filter>元素的icon属性)。
android:isolatedProcess
如果设置为true,这个服务将运行在专门的进程中,这个进程从系统的剩余部分独立出来,它自身没有权限。同它唯一的通信方式就是通过这个Service API(binding或starting)。
android:label
这个服务给用户显示的名称。如果这个属性没有设置,将使用<application>的label属性代替(参见<appliation>元素的label属性)。
这个服务的label,无论是通过自身设置的,还是通过application设置的,对于这个service的intent filters来说都是默认值(参见<intent-filter>元素的label属性)。
这个label应当设置为string资源的引用,以便在用户接口中能同其它string资源一样本地化。然而,在开发应用时为了方便起见,它也能被设置为raw串。
android:name
实现这个service的Service子类名称。这应当是完整格式的类名(例如,“com.example.project.RoomService”)。然而,作为一个简写,如果名称的第一个字母是点(例如,“.RoomService”), 它会被添加到在<manifest>元素中声明的包名后面。
一旦你发布了你的应用,你就不要修改这个名字(除非你设置了android:exported=false)。
没有默认值,这个名称必须被指定。
android:permission
为了启动这个service或绑定到它一个实体必须要有的权限的名称。如果startService(),bindService()或stopService()的调用者还没有获取这个授权,那么这些方法就不会工作,而且这个intent对象也不会传递到service。
如果这个属性没有设置,由<application>元素的permission属性设置的权限就会应用到这个service。如果都没有设置,那么这个服务就不再受权限保护。
android:process
服务将要运行的进程名称。一般来讲,应用的所有组件都运行在应用创建的默认进程中。就像应用的包名一样。<application>元素的process属性能对所有组件设置不同的默认值。然而,组件能通过它自身的process属性重写默认值,从而允许你扩展你的应用跨越多个进程。
如果分配到这个属性的名称以冒号(:)开始,那么当需要它的时候,一个新的、对这个应用私有的进程就被创建,同时这个服务就在哪个进程运行。如果进程的名字以小写字母开始,那么这个服务将运行在全局进程中。这就允许在不同应用中的组件共享这个进程,降低资源的消耗。
onStartCommand有4种返回值:
START_STICKY:如果service进程被kill掉,保留service的状态为开始状态,但不保留递送的intent对象。随后系统会尝试重新创建service,由于服务状态为开始状态,所以创建服务后一定会调用onStartCommand(Intent,int,int)方法。如果在此期间没有任何启动命令被传递到service,那么参数Intent将为null。
START_NOT_STICKY:“非粘性的”。使用这个返回值时,如果在执行完onStartCommand后,服务被异常kill掉,系统将会把它置为started状态,系统不会自动重启该服务,直到startService(Intent intent)方法再次被调用;。
START_REDELIVER_INTENT:重传Intent。使用这个返回值时,如果在执行完onStartCommand后,服务被异常kill掉,系统会自动重启该服务,并将Intent的值传入。
START_STICKY_COMPATIBILITY:START_STICKY的兼容版本,但不保证服务被kill后一定能重启。
将一个普通的Service转换成远程Service
<service
android:name="com.example.servicetest.MyService"
android:process=":remote" >
</service>
当Service变成远程的就不会出现应用程序有一段时间响应不够灵敏,系统会向用户显示一个对话框,这个对话框称作应用程序无响应(ANR:Application Not Responding)对话框。
AIDL(Android Interface Definition Language)
是Android接口定义语言的意思,它可以用于让某个Service与多个应用程序组件之间进行跨进程通信,从而可以实现多个应用程序共享同一个Service的功能。
它是一种android内部进程通信接口的描述语言,通过它我们可以定义进程间的通信接口
如何在eclipse中创建AIDL文件
直接在需存放的目录处右键,New->File->输入文件名:****.aisl。然后在这个文件中写入自定义接口点击保存之后,gen目录下就会生成一个对应的Java文件。