Handler的原理-----源码剖析
来源:互联网 发布:网龙网络 编辑:程序博客网 时间:2024/06/01 07:53
1. handler是什么?
Handler是android给我们提供的用来更新UI的一套机制,也是一套消息处理机制,我们可以发送消息,也可以通过它处理消息。
2. 为什么要用handler?
Android在设计时就封装了一套消息创建,传递,处理机制。如果不遵循这样的机制,就没办法更新UI信息,就会抛异常。
3. handler如何使用?
sendMessage();sendMessageDelay();post(Runnable);postDelay(Runnable, long);//前两个方法一般用于耗时性操作后的更新UI。//后两个方法可以用来完成周期性的任务,如视频播放器进度条一秒跑一下.............
4. Android中Message的生成方式
Message msg = new Message();Message msg = Message.obtain();
5. 初始化一个Handler对象
Handler handler = new Handler(){ Void handlerMessage(Message msg){} //接受子线程发来的消息,在主线程中进行处理 //不会有ANR,不会在子线程中更新UI}
6. Handler的构造函数中初始化Looper(轮询器),MessageQueue(消息队列).
Public Handler(CallBack callBack){ … mLooper = Looper.myLooper(); … mQueue = mLooper.mQueue(); mCallback = callback;}
7. Looper在ActivityThread的main函数中初始化:
Public static final void main(String[] args){ //初始化Looper Looper.prepareMainLooper(); Looper.loop();}
8. Looper进行消息队列的循环,可能导致阻塞,但是界面不卡(原因:管道pipe)。
Pipe是linux下的一个特殊的文件,是一种linux的线程通讯机制。只存在在内存中。拥有两个描述符(对文件操作的句柄,其实就是引用),一个是用来写入,一个用来读取。
应用场景:一个主线程拿着读取描述符,等待读取。子线程拿着写入的描述符,将数据写入管道,发出通知,主线程开始读取,实现不同线程之间的通讯问题。
Handler的应用场景:handler拿着读取描述符,阻塞主线程(睡眠),等待读取。子线程通过handler的sendMessage()将一个Message放入MessageQueue消息队列中,通知主线程,主线程开始轮询。
9. Loop中的循环代码
Public static final void loop(){ Looper me = myLooper(); MessageQueue queue = me.mQueue(); While(true){ //死循环,不断去消息队列中的数据。 //如果没有消息,则睡眠等待。 Message msg = queue.next(); //might block }}
10. Handler的sendMessage(),消息的转发。
Public final Boolean sendMessage(Message msg){ //第一次转发 Return snedMessageDelayed(msg,0);}
Public final Boolean send snedMessageDelayed(Message msg, long delayMillis){ //第二次转发 If(delayMillis < 0){ delayMillis = 0; } Return sendMessageAtTime(msg, SystemClock.upTimeMillis() +delayMillis);}
public Boolean sendMessageAtTime(Message msg, long upTimeMillis){ Boolean sent = false; MessageQueue queue = mQueue; If(queue != null){ //把当前的Handler对象的引用交给Message的target对象 Msg.target = this; //把消息放入MessageQueue Sent = queue.enqueueMessage(msg, upTimeMillis); } Return sent;}
11. 在loop中如果收到消息,next拿到Message,通过handler.dispatch()进行分发。
Public static final void loop(){ Looper me = myLooper(); MessageQueue queue = me.mQueue(); While(true){ //死循环,不断去消息队列中的数据。 //如果没有消息,则睡眠等待。 Message msg = queue.next(); //might block msg .target.dispatchMessage(); //如果拿到了消息,则进行分发 }}
12. 进入到handler进行消息的转发处理
Public void dispatchMessage(Message msg){ handlerMessage(msg);
}
13. 子类实现handlerMessage()方法。
public void handlerMessage(Message msg){ switch(msg.what){ ....... }}
总结:
第5步和第13步是我们在代码中写的,其余的系统自动完成。
1 0
- Handler的原理-----源码剖析
- Android的Handler,Looper源码剖析
- Handler原理剖析
- Handler原理剖析
- Handler原理剖析
- Android Handler源码剖析
- Handler源码剖析
- android 开发Handler源码剖析
- Handler源码分析原理
- Handler源码原理分析
- Android之Handler原理回顾和剖析
- handler机制原理源码分析
- Android源码剖析之-------Handler机制详解
- 从源码角度剖析Handler 机制
- 从源码角度剖析Handler机制
- Android源码分析--Handler机制的实现与工作原理
- 最简洁的Handler、Looper、Message源码级原理分析
- STL源码剖析---红黑树原理
- iOS巅峰之Swift函数的详细用法(中)
- LeetCode 27: Remove Element
- Android基础入门教程——8.3.4 Paint API之—— Xfermode与PorterDuff详解(一)
- ios深度解析之Swift(基本数据类型)
- HVM的缓存与内存控制
- Handler的原理-----源码剖析
- 下载ABIDE,GITHUB
- c++ primer第五版(中文)习题答案 第一章-开始
- Cocos2d-JS中的常见元素
- C# 从需要登录的网站上抓取数据
- thinkphp——前台关键字搜索页面实现
- Unity之线性渲染器
- HDOJ--1203--I NEED A OFFER!
- 黑马程序员——Java 基础:this 关键字的使用