Handler知识点总结

  • Handler和Looper之间的关系,他们怎样通信的,怎么实现事件的分发

handler通过sendMessage()发送消息到MessageQueue中,然后looper的loop()方法不断从MessageQueue中去获取消息,然后回调msg.target.dispatchMessage方法,也就是最终消息由Looper交给Handler处理。

  • 如何再一个非UI线程中启动一个Looper?

为了保证Handler关联的线程有Looper对象,可分一下两种情况:

  1. 在主UI线程中,系统已经初始化了一个Looper对象,因此程序直接创建Handler即可,然后就可以通过Handler来发送消息、处理消息了。(即之前写的博客:Handler详解(一)—关联到UI线程,非UI线程向UI线程中发送消息)参考:http://www.it610.com/article/5036824.htm
  2. 程序员自己启动的子线程,必须自己创建一个Looper对象,并启动它。创建Looper对象调用它的prepare()方法即可。prepare()方法保证每个线程最多只有一个Looper对象。UI线程向非UI线程发送消息。
  • looper.loop()内部实现机制

loop()方法,不断从MessageQueue中去取消息,交给消息的target属性的dispatchMessage去处理。

  • Looper、Handler、Message三者关系

1、首先Looper.prepare()在本线程中保存一个Looper实例,然后该实例中保存一个MessageQueue对象;因为Looper.prepare()在一个线程中只能调用一次,所以MessageQueue在一个线程中只会存在一个。

2、Looper.loop()会让当前线程进入一个无限循环,不端从MessageQueue的实例中读取消息,然后回调msg.target.dispatchMessage(msg)方法。

3、Handler的构造方法,会首先得到当前线程中保存的Looper实例,进而与Looper实例中的MessageQueue想关联。

4、Handler的sendMessage方法,会给msg的target赋值为handler自身,然后加入MessageQueue中。

5、在构造Handler实例时,我们会重写handleMessage方法,也就是msg.target.dispatchMessage(msg)最终调用的方法。

https://blog.csdn.net/lmj623565791/article/details/38377229

  • 若消息队列为空,线程则会阻塞等待
  • 对于Handler,如何获取当前线程的Looper?

如果在创建Handler时不指定与其绑定的Looper对象,系统默认会将当前线程的Looper绑定到该Handler上。
在主线程中,可以直接使用new Handler()创建Handler对象,其将自动与主线程的Looper对象绑定;在非主线程中直接这样创建Handler则会报错,因为Android系统默认情况下非主线程中没有开启Looper,而Handler对象必须绑定Looper对象。这种情况下,需先在该线程中手动开启Looper(Looper.prepare()-->Looper.loop()),然后将其绑定到Handler对象上;或者通过Looper.getMainLooper(),获得主线程的Looper,将其绑定到此Handler对象上。

参考 利用Handler在主线程与子线程之间互发消息 https://blog.csdn.net/u011506413/article/details/50959969

  • Handler机制中线程切换和消息阻塞再剖析

参考 :https://blog.csdn.net/yus201120/article/details/82015980

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值