IntentService是一个抽象类,它的本质是Service组件,使用者需要重写它的onHandleIntent方法。
@WorkerThread
protected abstract void onHandleIntent(Intent intent);
从这个抽象方法可以看出,它并不在主线程中工作。Service组件虽然是后台服务,但是,他是在主线程工作的,不可以做耗时操作,而IntentService就是一种可以在非主线程工作的服务。
@Override
public void onCreate() {
super.onCreate();
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]");
thread.start();
mServiceLooper = thread.getLooper();
mServiceHandler = new ServiceHandler(mServiceLooper);
}
Service启动时,在onCreate方法,创建一个HandlerThread线程,它内部实现了Looper循环,可以接收消息。
public void run() {
mTid = Process.myTid();
Looper.prepare();
synchronized (this) {
mLooper = Looper.myLooper();
notifyAll();
}
Process.setThreadPriority(mPriority);
onLooperPrepared();
Looper.loop();
}
然后,创建一个ServiceHandler,绑定这个Looper。
private final class ServiceHandler extends Handler {
public ServiceHandler(Looper looper) {
super(looper);
}
@Override
public void handleMessage(Message msg) {
onHandleIntent((Intent)msg.obj);
stopSelf(msg.arg1);
}
}
这样,ServiceHandler专注处理HandlerThread线程队列的消息,在handleMessage方法处理消息时,调用实现类IntentService重写的onHandleIntent方法。onStart方法发送消息。
@Override
public void onStart(Intent intent, int startId) {
Message msg = mServiceHandler.obtainMessage();
msg.arg1 = startId;
msg.obj = intent;
mServiceHandler.sendMessage(msg);
}
具体流程是这样的:主线程启动IntentService服务,先调用第一个生命周期onCreate方法,构建一个线程消息循环和一个Handler触发器,然后,执行onStart方法时,向线程消息队列发送消息,线程处理耗时操作,在IntentService预留抽象方法实现。处理完成,stopSelf根据startId停止Service,并在onDestroy结束掉线程消息循环。
@Override
public void onDestroy() {
mServiceLooper.quit();
}
IntentService服务架构图。
IntentService服务架构图.jpg
总结
IntentService是框架层提供的可进行耗时操作的服务,原理是基于内部线程循环+Handler模型,与主线程消息循环不同的是,它建立的是非主线程的消息循环。当主线程启动服务,发送消息,线程便开始回调服务预留的耗时方法。主线程仅负责在服务onStart时发送消息的工作。当执行完成后,自动停止服务,关闭消息循环。HandlerThread是系统框架中一个自带启动Looper循环的线程。
任重而道远
网友评论