Class used to run a message loop for a thread. Threads by default do not have a message loop associated with them; to create one, call Most interaction with a message loop is through the This is a typical example of the implementation of a Looper thread, using the separation of class LooperThread extends Thread {
public Handler mHandler;
public void run() {
Looper.prepare();
mHandler = new Handler() {
public void handleMessage(Message msg) {
// process incoming messages here
}
};
Looper.loop();
}
}
|
/** * Default constructor associates this handler with the queue for the * current thread. * * If there isn't one, this handler won't be able to receive messages. */ public Handler() { if (FIND_POTENTIAL_LEAKS) { final Class<? extends Handler> klass = getClass(); if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) && (klass.getModifiers() & Modifier.STATIC) == 0) { Log.w(TAG, "The following Handler class should be static or leaks might occur: " + klass.getCanonicalName()); } } //从TLS(局部线程存储)中取出已寄存好的Looper对象 mLooper = Looper.myLooper(); if (mLooper == null) { throw new RuntimeException( "Can't create handler inside thread that has not called Looper.prepare()"); } //将Looper对象中的MessageQueue赋值给Handler中的对象 mQueue = mLooper.mQueue; mCallback = null; } |
sendMessage(...) -> sendMessageDelayed(...) -> sendMessageAtTime(...) 终究会通过sendMessageAtTime发送消息对象。 public boolean sendMessageAtTime(Message msg, long uptimeMillis) { boolean sent = false; MessageQueue queue = mQueue; if (queue != null) { msg.target = this; //将消息对象加入到消息队列 sent = queue.enqueueMessage(msg, uptimeMillis); } else { RuntimeException e = new RuntimeException( this + " sendMessageAtTime() called with no mQueue"); Log.w("Looper", e.getMessage(), e); } return sent; } 然后我们在来看看enqueueMessage进行了甚么操作。 final boolean enqueueMessage(Message msg, long when) { ... if (needWake) { nativeWake(mPtr); } ... } nativeWake是1个java本地方法,这里触及了消息机制中的Sleep-Wakeup机制,关于如何唤醒Looper线程的动作,这里不做赘述,其终究就是调用了 native层的Looper的wake函数,唤醒了这个函数以后,就开始进行消息循环 |