Android基础之Handler分析,kotlin数据类

本文深入探讨了Android中的Handler和MessageQueue机制。首先介绍了Looper如何在不同线程中初始化,确保每个线程只有一个Looper。接着讲解了MessageQueue的创建、消息入队和出队的过程,以及如何保证线程安全。Message的创建、复用和绑定Handler的过程也被详细阐述。文章还提到了Handler设计的亮点,如享元模式和线程安全的实现。最后讨论了同步屏障的概念,解释了如何通过同步屏障处理紧急消息。
摘要由CSDN通过智能技术生成

//1.方式一:对当前线程的初始化,子线程要开启Looper必须调用该方法
public static void prepare() {
prepare(true); //消息队列可以quit
}

private static void prepare(boolean quitAllowed) {
if (sThreadLocal.get() != null) { //不为空表示当前线程已经创建了Looper
throw new RuntimeException(“Only one Looper may be created per thread”); //每个线程只能创建一个Looper
}
sThreadLocal.set(new Looper(quitAllowed)); //创建Looper并设置给sThreadLocal,这样get的 时候就不会为null了
}

//2.方式二:对主线程的初始化,在ActivityThread中被调用
@Deprecated
public static void prepareMainLooper() {
prepare(false); //消息队列不可以quit,主线程不可被销毁
synchronized (Looper.class) {
if (sMainLooper != null) {
throw new IllegalStateException(“The main Looper has already been prepared.”);
}
sMainLooper = myLooper();
}
}

Looper对象是一个TheadLocal ,即每一个线程只有一个Looper对象,保证Looper的唯一性。ThreadLocal线程隔离工具类:

image-20210412083733468

  1. 创建MessageQueue以及Looper与当前线程的绑定

private Looper(boolean quitAllowed) {
mQueue = new MessageQueue(quitAllowed);//创建了MessageQueue
mThread = Thread.currentThread(); //当前线程的绑定
}

  1. 开启循环

public static void loop() {
final Looper me = myLooper(); //里面调用了sThreadLocal.get()获得刚才创建的Looper对象
if (me == null) { //如果Looper为空则会抛出异常
throw new RuntimeException(“No Looper; Looper.prepare() wasn’t called on this thread.”);
}
if (me.mInLoop) {
Slog.w(TAG, “Loop again would have the queued messages be executed”

  • " before this one completed.");
    }

me.mInLoop = true;
final MessageQueue queue = me.mQueue;

// Make sure the identity of this thread is that of the local process,
// and keep track of what that identity token actually is.
Binder.clearCallingIdentity();
final long ident = Binder.clearCallingIdentity();

// Allow overriding a threshold with a system prop. e.g.
// adb shell ‘setprop log.looper.1000.main.slow 1 && stop && start’
final int thresholdOverride =
SystemProperties.getInt(“log.looper.”

  • Process.myUid() + “.”
  • Thread.currentThread().getName()
  • “.slow”, 0);

boolean slowDeliveryDetected = false;
//这是一个死循环,从消息队列不断的取消息
for (;😉 {
Message msg = queue.next(); // might block
if (msg == null) {
//由于刚创建MessageQueue就开始轮询,队列里是没有消息的,等到Handler sendMessage enqueueMessage后
//队列里才有消息
return;
}

// This must be in a local variable, in case a UI event sets the logger
final Printer logging = me.mLogging;
if (logging != null) {
logging.println(">>>>> Dispatching to " + msg.target + " " +
msg.callback + ": " + msg.what);
}
// Make sure the observer won’t change while processing a transaction.
final Observer observer = sObserver;

final long traceTag = me.mTraceTag;
long slowDispatchThresholdMs = me.mSlowDispatchThresholdMs;
long slowDeliveryThresholdMs = me.mSlowDeliveryThresholdMs;
if (thresholdOverride > 0) {
slowDispatchThresholdMs = thresholdOverride;
slowDeliveryThresholdMs = thresholdOverride;
}
final boolean logSlowDelivery = (slowDeliveryThresholdMs > 0) && (msg.when > 0);
final boolean logSlowDispatch = (slowDispatchThresholdMs > 0);

final boolean needStartTime = logSlowDelivery || logSlowDispatch;
final boolean needEndTime = logSlowDispatch;

if (traceTag != 0 && Trace.isTagEnabled(traceTag)) {
Trace.traceBegin(traceTag, msg.target.getTraceName(msg));
}

final long dispatchStart = needStartTime ? SystemClock.uptimeMillis() : 0;
final long dispatchEnd;
Object token = null;
if (observer != null) {
token = observer.messageDispatchStarting();
}
long origWorkSource = ThreadLocalWorkSource.setUid(msg.workSourceUid);
try {
///msg.target就是绑定的Handler,详见后面Message的部分,Handler开始
msg.target.dispat

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值