Handler消息机制源码解析

1.

Looper.prepareMainLooper();
ActivityThread thread = new ActivityThread();
thread.attach(false);
if (sMainThreadHandler == null) {
    sMainThreadHandler = thread.getHandler();
}
if (false) {
    Looper.myLooper().setMessageLogging(new
            LogPrinter(Log.DEBUG, "ActivityThread"));
}
Looper.loop();

/************************************************/

public static void prepareMainLooper() {
    prepare(false);
    synchronized (Looper.class) {
        if (sMainLooper != null) {
            throw new IllegalStateException("The main Looper has already been prepared.");
        }
        sMainLooper = myLooper(); //设置主looper
    }
}

// looper是通过prepare进行实例化

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));
}

private Looper(boolean quitAllowed) {
    mQueue = new MessageQueue(quitAllowed);
    mThread = Thread.currentThread();
}

消息队列和当前线程就绑定在一起了,继续进行无限玄幻,阻塞队列,取出消息,响应消息

public static void loop() {
    final Looper me = myLooper();
    if (me == null) {
        throw new RuntimeException("No Looper; Looper.prepare() wasn't called on this thread.");
    }
    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();
    for (;;) {
        Message msg = queue.next(); // might block

if (msg == null) {
    // No message indicates that the message queue is quitting.
    return;
}

msg.target.dispatchMessage(msg);

}

 

 

2. 例子:

Acitivity中实例化Handler

private Handler mHandler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
        super.handleMessage(msg);
        int signal = msg.arg1;
        switch (signal) {
            case 0:
                progressView.setProgress(0);
                break;
        }
    }
};

点击

case R.id.btn_enen:
    Message message = new Message();
    message.arg1 = 0;
    mHandler.sendMessage(message);
    break;

handler构造函数中,获取到和当前线程绑定的looper,也就是主线程的looper对象,threadlocal就是和当前线程绑定数据的工具,是与线程对应的,不同线程绑定同一个变量,只影响在当前线程的值,当前activityhandler就获得了主线程的looper对象,接下来就可以用handler发送消息了,

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;

public static Looper myLooper() {
    return sThreadLocal.get();
}

发送消息,就是让消息进入主线程的消息队列中,有一部就是给当前handler设置给messagetarget变量

Handler

private boolean enqueueMessage(MessageQueue queue, Message msg, long uptimeMillis) {
    msg.target = this;
    if (mAsynchronous) {
        msg.setAsynchronous(true);
    }
    return queue.enqueueMessage(msg, uptimeMillis);
}

设置了targethandler以后,在looper.loop无限循环中,就会调用dispatchMessage()

msg.target.dispatchMessage(msg);

dispatchMessage function调用被activityhandler复写的handleMessage(),就完成了通信,

Handler

public void dispatchMessage(Message msg) {
    if (msg.callback != null) {
        handleCallback(msg);
    } else {
        if (mCallback != null) {
            if (mCallback.handleMessage(msg)) {
                return;
            }
        }
        handleMessage(msg);
    }
}

有个地方就是如果设置了message的回调,就会执行message的回调,不会执行handleMessage(),如果没有设置message的回调,但设置了handlercallback,就会优先执行handlercallback,看返回值,如果返回true,就代表已经处理了,如果返回false,就继续执行handlerhandlMessage()

private Handler mHandler = new Handler(new Handler.Callback() {
    @Override
    public boolean handleMessage(Message msg) {
        return false;
    }
}) {
    @Override
    public void handleMessage(Message msg) {
        super.handleMessage(msg);
        int signal = msg.arg1;
        switch (signal) {
            case 0:
                progressView.setProgress(0);
                break;
        }
    }
};

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值