一、什么是IntentService?
IntentService本质上是一个特殊的Service,它继承了Service,是一个抽象的类型的Servive,内部运用Service和HandlerThread的机制,实现异步耗时操作。
二、IntentService源码分析
public abstract class IntentService extends Service { private volatile Looper mServiceLooper; private volatile ServiceHandler mServiceHandler; private String mName; private boolean mRedelivery; 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); } } public IntentService(String name) { super(); mName = name; } public void setIntentRedelivery(boolean enabled) { mRedelivery = enabled; } @Override public void onCreate() { super.onCreate(); HandlerThread thread = new HandlerThread("IntentService[" + mName + "]"); thread.start(); mServiceLooper = thread.getLooper(); mServiceHandler = new ServiceHandler(mServiceLooper); } @Override public void onStart(@Nullable Intent intent, int startId) { Message msg = mServiceHandler.obtainMessage(); msg.arg1 = startId; msg.obj = intent; mServiceHandler.sendMessage(msg); } @Override public int onStartCommand(@Nullable Intent intent, int flags, int startId) { onStart(intent, startId); return mRedelivery ? START_REDELIVER_INTENT : START_NOT_STICKY; } @Override public void onDestroy() { mServiceLooper.quit(); } @Override @Nullable public IBinder onBind(Intent intent) { return null; } @WorkerThread protected abstract void onHandleIntent(@Nullable Intent intent);
分析:
1、怎么使用:
从源码上IntentService被声明为abstract的抽象类,有抽象方法onHandleIntent,因此子类继承需要实现onHandleIntent(Intent i)的方法。
2、onHandleIntent(Intent i) 在什么时候调用:
从源码中我们可以看到 在 Service 的生命周期函数onCreate()方法中,
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]"); thread.start(); mServiceLooper = thread.getLooper(); mServiceHandler = new ServiceHandler(mServiceLooper);
创建了HandlerThread和Handler用于执行异步任务,Service 的生命周期函数onStart()的时候,
Message msg = mServiceHandler.obtainMessage(); msg.arg1 = startId; msg.obj = intent; mServiceHandler.sendMessage(msg);
发送了一个消息,
public void handleMessage(Message msg) { onHandleIntent((Intent)msg.obj); stopSelf(msg.arg1); }
中不断执行onHandleIntent()方法,因此onHandleIntent方法内部是在线程中进行的,可以进行异步操作。
3、怎么启动IntentService和关闭IntentService:
IntentService跟系统的Service一样,可以通过startService的方法启动Service,而且可以多次启动,而不会重复创建和移除原来的异步任务(因为Service的onCreate方法不会重复调用,OnStart()会多次调用,在onStart()方法内部去不断排队异步任务)。
最关键的是,多次创建的异步任务,会排队进行异步任务,其依靠的是HandlerThread的异步机制,而HandlerThread其实是最终依靠的是Looper去实现。
@Override public void handleMessage(Message msg) { onHandleIntent((Intent)msg.obj); stopSelf(msg.arg1); }
从异步处理完任务后,IntentService调用stopSelf(),主动销毁了自己。因此,不用主动去关闭IntentService.
4、什么时候可以用IntentService?
从源码上分析到,我觉得以下几点的应用场景可以用IntentService
1、运用了Service的组件独立生命周期的特点,但是Service内部不能执行耗时操作,而HandlerService刚好可以用于异步操作,又可以排队执行多任务,因此,如果我们有个需求需要你长时间执行任务,而不依赖于可视化组件如Activity的话,又需要执行多个不同的任务,就可以考虑IntentService。 比如在后台下载多张图片。