1 三种消息循环模型
1.1 主线程消息循环
第12章最后,AMS请求Zygote创建应用程序进程后,会自动进入主线程的消息循环,也就是ActivityThread。
//创建一个主线程消息循环
Looper.prepareMainLooper();
//创建一个ActivityThread实例
ActivityThread thread = new ActivityThread();
thread.attach(false);
//当前主线程进入到消息循环
Looper.loop();
Looper.prepareMainLooper()方法只能在主线程中调用,而且只能被调用一次。所以我们写代码时不能调用这个方法,否则会出异常。这个方法会生成一个Looper对象mMainLoopeer,在其他的子线程中就可以通过 Looper.getMainLooper()获取mMainLopper,完成与主线程的界面更新。
1.2 与UI无关的子线程消息循环模型
子线程有两类,一种是不具有消息循环的子线程,这种是我们经常见到的Thread,一般不直接使用new Thread的方式来创建一个子线程,而是自定义一个Thread实现类,然后用这个实现类创建子线程,在重写的run()中实现业务逻辑。
这种子线程没有消息循环,run方法执行完毕线程就会结束。
另一种是具有消息循环的子线程,也就是与UI无关的子线程消息循环模型。
我们使用HandlerThread创建一个具有消息循环的子线程。HandlerThread继承自Thread.
1.2.2 消息循环的创建
public class HandlerThread extends Thread{
private Looper mLooper;
public HandlerThread(String name){
super(name);
}
public void run(){
Looper.prepare();
synchronized(this){
mLooper = Looper.myLooper();
}
Looper.loop();
}
public Looper getLopper(){
return mLooper;
}
public boolean quit(){
Looper looper = getLooper();
if(looper!=null){
looper.quit();
return true;
}
return false;
}
}
可以看到, run方法里面首先调用Looper.prepare()创建了一个消息循环,然后Looper.loop()使得当前线程进入消息循环。所以HandlerThread就有了消息循环。
1.2.2 HandlerThread的使用
首先创建一个HandlerThread
HandlerThread handlerThread = new HandlerThread("handler thread");
handlerThread.start();
定义一个实现了Runnable的类ThreadTask
public class ThreadTask implements Runnable{
public ThreadTask(){
}
public void run(){
}
}
新建一个ThreadTask实例
ThreadTask threadTask = new ThreadTask();
将threadTask封装成一个消息发送到消息队列
Handler handler = new Handler(handlerThread.getLooper());
handler.post(threadTask);
消息被处理时就会调用threadTask的run方法,执行自定义任务。
如果一直不往子线程消息队列发送消息,那么子线程就会进入睡眠等待状态。
退出子线程时,只需要
handlerThread.quit();
调用了looper.quit();
Message msg =Message.obtain();
mQueue.enqueueMessage(msg,0);
通过向线程的消息队列发送一个target为null的Message对象,线程就会退出消息循环,停止线程 。
1.3 与UI有关的子线程消息循环模型 AsyncTask
AysncTask的三个主要方法:doInBackground(),onProgressUpdate(),onPostExecute();
其中doInBackground()执行耗时操作,是在子线程运行,onProgressUpdate(),onPostExecute()都可以操作界面,是在主线程运行。
frameworks/base/core/java/android/os/AsyncTask.java
public abstract class AsyncTask<Params,Progress,Result>{}
未完,待续