android在非UI线程中更新UI
来源:互联网 发布:手机淘宝页头图片 编辑:程序博客网 时间:2024/05/23 01:40
序
Android采用UI单线程模型,如果在非UI线程直接对UI进行了操作,则会报错:
CalledFromWrongThreadException:only the original thread that created a view hierarchy can touch its views
所以不能直接在非ui线程操作ui,那如果有这个需求怎么办呢,有以下几种方法概述
- handler
- View的post方法,本质上就是添加到主线程的消息队列里
- runOnUiThread(Runnable),这是Activity的一个方法,在Activity类里建线程就可以用,缺点是需要一个Activity引用
- 使用AsyncTask
- asyncTask和handler是最常用的,asyncTask内部是有handler的相当于对handler做了封装。asyncTask内部实际只有一个线程(默认实现方法,当然你可以提供Executor解决此问题)。如果你的任务很耗时,那后面的任务无法执行。asyncTask不适合长期任务
view的post方法
public boolean post(Runnable action) { final AttachInfo attachInfo = mAttachInfo; if (attachInfo != null) { return attachInfo.mHandler.post(action); } // Assume that post will succeed later ViewRootImpl.getRunQueue().post(action); return true; }看源码可以发现post就是把当前runnable加到消息队列里去,2种方法ViewRootImpl.getRunQueue().post(action)或者attachInfo.mHandler.post(action)
Activity的runOnUiThread
本质也是调用handler的post方法
/** * Runs the specified action on the UI thread. If the current thread is the UI * thread, then the action is executed immediately. If the current thread is * not the UI thread, the action is posted to the event queue of the UI thread. * * @param action the action to run on the UI thread */ public final void runOnUiThread(Runnable action) { if (Thread.currentThread() != mUiThread) { mHandler.post(action); } else { action.run(); } }
判断当前线程是否是主线程
判断当前线程是否是主线程主要2种方法
Looper.myLooper() == Looper.getMainLooper()
以及
Thread.currentThread() == Looper.getMainLooper().getThread()
有些场景会用到如下代码
public final void runOnUiThread(Runnable action) { if (Thread.currentThread() != mUiThread) { mHandler.post(action); } else { action.run(); } }
总结
handler和asyncTask是用的比较多的。AsyncTask面对handler的不足之处AsyncTask虽然是个轻量级的类(实际线程由ExecutorService管理),但不适合频繁操作,因为这很快会聚集需要垃圾回收的对象,导致界面卡顿。而且不能设置执行时间,也无法间隔一段时间执行操作。
补充
对话框操作也属于ui操作,必须主线程
参考资料
http://blog.csdn.net/mylzc/article/details/6736988
http://blog.csdn.net/guolin_blog/article/details/11711405(好文章)
http://www.cnblogs.com/xiaoluo501395377/p/3430542.html
http://blog.csdn.net/honeybaby201314/article/details/42680607
0 0
- Android在非UI线程中更新UI的方法
- Android开之在非UI线程中更新UI
- android在非UI线程中更新UI
- Android 非UI线程中更新UI
- Android 非UI线程中更新UI
- Android 在非UI线程直接更新UI信息
- 为什么我们可以在非UI线程中更新UI
- 为什么我们可以在非UI线程中更新UI
- 基础篇-在非UI线程中更新UI元素
- 为什么我们可以在非UI线程中更新UI
- 为什么我们可以在非UI线程中更新UI
- 为什么我们可以在非UI线程中更新UI
- 为什么我们可以在非UI线程中更新UI
- Android非UI线程中更新UI界面
- 非UI线程更新UI!?
- ProgressBar 为什么可以在非UI线程中更新进度。
- 再谈子线程-居然可以在非UI线程中更新UI
- Android 线程中更新UI
- angular-leaflet 小例
- 排队规则网卡青涩瞬间
- Codeforces Round #170 (Div. 2)
- 历届试题 买不到的数目
- html学习笔记(2)
- android在非UI线程中更新UI
- ineligible devices xcode6.3
- velocity
- [思路题] upcoj 2219 A^X mod P
- 历届试题 连号区间数
- cocos2d-x项目移植
- Codeforces Round #176 (Div. 2)
- 各种排序算法的分析及java实现
- 历届试题 翻硬币