Handler 原理分析
核心类,在主线程中定义:
Handler,ActivityThread,Looper,MessageQueue。
Looper类
- 包含MessageQueue,Thread,ThreadLocal
- 通过ThreadLocal.set(key) 保存线程唯一的Looper
- 每个线程仅有一个Looper
private static void prepare(boolean quitAllowed) { if (sThreadLocal.get() != null) { throw new RuntimeException("Only one Looper may be created per thread"); } sThreadLocal.set(new Looper(quitAllowed)); }
Looper.loop()
从 Looper类中的MessageQueue,不断取出message,调用msg.tartget.dispathMessage方法
1、取出message
/** * Run the message queue in this thread. Be sure to call * {@link #quit()} to end the loop. */ public static void loop() { final Looper me = myLooper();final MessageQueue queue = me.mQueue;for (;;) { Message msg = queue.next(); // might block if (msg == null) { // No message indicates that the message queue is quitting. return; }try { msg.target.dispatchMessage(msg); } catch (Exception exception) { } msg.recycleUnchecked(); } }
2、dispatchMessage方法走向
/** * Handle system messages here. */ public void dispatchMessage(@NonNull Message msg) { if (msg.callback != null) { handleCallback(msg); } else { if (mCallback != null) { if (mCallback.handleMessage(msg)) { return; } } handleMessage(msg); } }
Handler
- 内部维护一个MessageQueue,指向Looper类中的MessageQueue
- sendMessage()添加到MessageQueue中
public boolean sendMessageAtTime(@NonNull Message msg, long uptimeMillis) { MessageQueue queue = mQueue; if (queue == null) { RuntimeException e = new RuntimeException( this + " sendMessageAtTime() called with no mQueue"); Log.w("Looper", e.getMessage(), e); return false; } return enqueueMessage(queue, msg, uptimeMillis); }
private boolean enqueueMessage(@NonNull MessageQueue queue, @NonNull Message msg, long uptimeMillis) { msg.target = this; msg.workSourceUid = ThreadLocalWorkSource.getUid(); if (mAsynchronous) { msg.setAsynchronous(true); } return queue.enqueueMessage(msg, uptimeMillis); }