1、Service必须在Manifest中注册
2、startService:
如果没有创建过,会执行onCreate一次,onStartCommand随startService调用次数增加
startService开启的服务实际上与当前页面无关
3、bindService:
如果没有创建过,会执行onCreate,onBind,如果onBind有返回值,
那么serviceConnection的onServiceConnected也会执行,多次bindService,以上步骤只执行一次
bindService与unBindService必须严格成对出现,单独执行unBindService会报错,
而且已bindService关闭页面时未执行unBindService也会出错。
onUnBind的返回值为true(默认为false)的情况下,下次执行bind(service没有destroy的前提下),不会走onBind,会执行onReBind回调
bindService开启的服务与发起context绑定
4、onDestroy:
如果只通过bind方式创建service,那么所有bind对象执行完unBind之后,会执行onDestroy;
如果期间有执行过startService方法,那么只有进行stopService才会执行onDestroy
如果startService后又执行了bindService,那么直接执行stopService是不会进行onDestroy的,
这时再执行unBindService,会回调onDestroy
5、service跟activity一样,属于系统组件,只是没有UI而已,当不设置process时,运行在主进程主线程,
所以与activity一样,不能执行耗时任务,耗时任务需要单独开子线程
6、process:
①如果未设置process,则service运行在主进程,ServiceConnection的onServiceConnected方法
获得的IBinder与service的onBind返回的IBinder是同一个对象,
Activity可以通过这个对象与Service进行通信,这种方式适合轻量级的后台任务通信
②如果service的process设置为其他值,那么代表service运行在另外的进程中
这时,service的各种生命周期回调发生在这个新进程中,
而serviceConnection的onServiceConnected则仍发生在主进程,
onServiceConnected获取到的IBinder是一个BinderProxy类对象,非service onBind方法返回的
7、service还可以通过Messenger(意为通信员,信使),与Activity通信。注意区分,不是Message(意为消息)
Messenger的构造方法有两种:
①、public Messenger(Handler target) {
......
}
②、public Messenger(IBinder target) {
......
}
可以在service中定义一个Handler来处理消息,并通过该Handler来生成Messenger,然后在Service的onBind中返回Messenger.getBinder(),
@Nullable
@Override
public IBinderonBind(Intent intent) {
IBinder binder =messenger.getBinder();
return binder;
}
在ServiceConnection的onServiceConnected方法中,通过接收到的IBinder构建一个客户端的Messenger,
private ServiceConnectionserviceConnection =new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
messengerService =new Messenger(service);
}
@Override
public void onServiceDisconnected(ComponentName name) {
}
};
这样操作,客户端的Messenger就可以向服务端service发送消息了(即Messenger.send(Message)),service可以在Handler中处理客户端发来的消息。另外,将发送的Message的replyTo设置为Messenger,
那再service端也可以接收到客户端的Messenger
try {
Message obtain = Message.obtain();
obtain.replyTo = messengerClient;
messengerService.send(obtain);
} catch (RemoteException e) {
e.printStackTrace();
}
通过Messenger可以实现双方互通消息,需要注意的是,如果service是远程服务(设置有process),那么在通信的过程中,仅可通过Message传输放置在bundle中的数据
8、可以通过AIDL方式通信,AIDL具体创建方法,首先建立一个实现ParcelAble接口的实体类x,然后在项目的java文件夹的同级目录建立一个名为aidl的文件夹,最后在aidl文件夹相同路径下建立同名实体类的aidl文件(比如java文件夹下,x的路径为aaa/bbb/ccc/x.java,那就在aidl文件夹下也建立一个aaa/bbb/ccc/x.aidl文件):
package aaa.bbb.ccc;
parcelable x;
在x.aidl文件同目录建立aidl接口文件:
package aaa.bbb.ccc;
import aaa.bbb.ccc.x;
// 定义一些接口
interface IxManager {
//do sth
}
在Service中可以使用new IXManager.Stub()的方式创建binder,然后在Activity中可以在ServiceConnection中以IXManager.Stub.asInterface(service)的方式获取到接口,这样Activity中就可以以通过调用接口进行通信
9、通过aidl可以实现两个App通信,一个为服务端,一个为客户端,保证两端有相同的model类和aidl类(包名路径一直,内容一直),
客户端通过隐式intent启动服务端Service,其他操作同上。
网友评论