在Android中,一般情况下(特殊情况先不说)只有UI线程才能对View进行操作,然而为了避免ANR等,耗时操作都放到子线程进行,操作完成之后再切换到UI线程,而Handler正好能够完成从子线程切换到UI线程的工作,那么Handler是如何从子线程切换到UI线程的呢?
消息传递机制切换
要了解Handler,就首先需要了解Android的消息传递机制,整个消息传递机制有四部分组成:
1.Message
消息,即线程间传递的对象,传递的信息包含在其中。例如后台线程在处理数据完毕后需要更新UI,则可发送一条包含更新信息的Message给UI线程。
2. Message Queue
消息队列,用来存放通过Handler发布的消息,按照先进先出执行。
3. Handler
Handler是Message的主要处理者,负责将Message添加到消息队列以及对消息队列中的Message进行处理。
4. Looper
循环器,扮演Message Queue和Handler之间桥梁的角色,循环取出Message Queue里面的Message,并交付给相应的Handler进行处理。
它们之间的协作如下图,
Handler
首先来看看Handler的实现源码
public Handler(Callback callback, boolean async) {
if (FIND_POTENTIAL_LEAKS) {
final Class<? extends Handler> klass = getClass();
if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) &&
(klass.getModifiers() & Modifier.STATIC) == 0) {
klass.getCanonicalName());
}
}
mLooper = Looper.myLooper();
if (mLooper == null) {
throw new RuntimeException(
"Can't create handler inside thread that has not called Looper.prepare()");
}
mQueue = mLooper.mQueue;
mCallback = callback;
mAsynchronous = async;
}
Handler的构造函数,在构造函数中初始化了一个Looper 和 MessageQueue。
Looper
接下来看看Looper.myLooper()的实现
static final ThreadLocal<Looper> sThreadLocal = new ThreadLocal<Looper>();
public static @