使用异步消息处理更新UI线程
1. Android的UI时线程不安全的,如果在子线程中更新UI会出现异常,导致程序崩溃。
为了解决如上这些问题,我们常用的做法就是使用Android的异步消息机制实现即可(创建一个Message对象,使用Handler发送出去,然后在Handler的handleMessage()方法中获得刚才发送的Message对象,然后在这里进行UI操作)。所以说还是很有必要了解异步消息机制的Looper , Handler , Message等原理的。
下面展示一个示例使用,然后通过源码分析吧。
public class MainActivity extends Activity { public static final int UPDATE_TEXT = 1; private TextView text; private Button changeText; private Handler handler = new Handler(){
@Override
public void handleMessage(Message msg) {
switch (msg.what){
case UPDATE_TEXT:
text.setText("Nice yo see you again");
break;
default:
break;
}
}
}; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
text = (TextView) findViewById(R.id.text);
changeText = (Button) findViewById(R.id.change_text);
// changeText.setOnClickListener(this); changeText.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View view) {
switch ((view.getId())){
case R.id.change_text:
new Thread(new Runnable() {
@Override
public void run() {
// 若直接更新TextView的内容会报错,下面使用异步消息处理机制
// text.setText("Nice to see you,BUG");
Message message = new Message();
message.what = UPDATE_TEXT;
handler.sendMessage(message);
}
}).start();
break;
default:
break;
}
}
});
} }
这里我们先是定义了一个整型常量UPDATE_TEXT,用于表示更新TextView 这个动作。然后新增一个Handler 对象,并重写父类的handleMessage 方法,在这里对具体的Message进行处理。如果发现Message 的what 字段的值等于UPDATE_TEXT,就将TextView 显示的内容改成Nice to see you again。
下面再来看一下Change Text 按钮的点击事件中的代码。可以看到,这次我们并没有在子线程里直接进行UI 操作,而是创建了一个Message(android.os.Message)对象,并将它what 字段的值指定为UPDATE_TEXT,然后调用Handler 的sendMessage()方法将这Message 发送出去。很快,Handler 就会收到这条Message,并在handleMessage()方法中对它进行处理。注意此时handleMessage()方法中的代码就是在主线程当中运行的了,所以我们可以放心地在这里进行UI 操作。接下来对Message 携带的what 字段的值进行判断,如果等于UPDATE_TEXT,就将TextView 显示的内容改成Nice to see you again。
2. Looper , Handler , Message的关系
(1)Looper中有一个Message队列,里面存储的是一个个待处理的Message。
(2)Message中有一个Handler,这个Handler是用来处理Message的。
使用异步消息处理更新UI线程的更多相关文章
- OkHttp3几个简单的例子和在子线程更新UI线程的方法
okHttp用于android的http请求.据说很厉害,我们来一起尝尝鲜.但是使用okHttp也会有一些小坑,后面会讲到如何掉进坑里并爬出来. 首先需要了解一点,这里说的UI线程和主线程是一回事儿. ...
- [Android学习笔记]子线程更新UI线程方法之Handler
关于此笔记 不讨论: 1.不讨论Handler实现细节 2.不讨论android线程派发细节 讨论: 子线程如何简单的使用Handler更新UI 问题: android开发时,如何在子线程更新UI? ...
- 异步消息处理机制,UI更新
UI只能在主线程中完成更新,在子线程中更新UI报错如下 Only the original thread that created a view hierarchy can touch its vie ...
- handler更新ui线程的基本用法
1.因为费时操作要放子线程,更新UI要放UI线程(主线程),所以子线程和主线程通信,通信的话要用到handler这个东西. 这里讲的比较简单,举2个例子说明 2.使用post的是handler ,使用 ...
- WPF Dispatcher.BeginInvoke子线程更新UI
在开发WPF应用时出现:”调用线程无法访问此对象,因为另一个线程拥有该对象.“ 是因为UI线程是WPF应用的主线程,若尝试子线程更新UI线程应使用Dispatcher.BeginInvoke()或者I ...
- Handler机制来处理子线程去更新UI线程控件
public class HandlerTestActivity extends Activity { private TextView tv; private static final int UP ...
- Android开之在非UI线程中更新UI
当在非UI线程中更新UI(程序界面)时会出现例如以下图所看到的的异常: 那怎样才干在非UI线程中更细UI呢? 方法有非常多种.在这里主要介绍三种: 第一种:调用主线程mHandler的post(Run ...
- Android之Handler,举例说明如何更新UI
方法一:(java习惯,在android不推荐使用) 刚刚开始接触android线程编程的时候,习惯好像java一样,试图用下面的代码解决问题 new Thread( new Runnable() { ...
- Android之Handler(异步消息处理)机制
1. 概述 Handler . Looper .Message 这三者都与Android异步消息处理线程相关的概念.那么什么叫异步消息处理线程呢?异步消息处理线程启动后会进入一个无限的循环体之中,每循 ...
随机推荐
- imx6dl uboot 移植
新版的BSP引进的设备树的机制,在uboot中还添加了menuconfig的配置菜单. 参考官网的文档进行uboot移植,本文使用的cpu是imx6dl,uboot版本2015.04. 我要添加一个名 ...
- tiny210V2开发板hdmi输出到10.1寸LCD,无图像
tiny210V2开发板hdmi输出到10.1寸LCD,无图像... 用tiny210V2开发板的HDMI接口输出到的10.1寸LCD,LCD无任何现象.说明一下我的情况,我的10.1寸屏LCD是HD ...
- Kernel.org 被黑,获取 Android 源码方法一则
8 月底 9 月初,作为 Linux 的老窝,Kernel.org 被黑客攻击了,其攻击原因众说纷纭.一直以来 Linux 对于我来说不是很感兴趣,所以从来不会关注类似事件,可是这次这个攻击,却影响到 ...
- CentOS 6.5 下利用命令行截图及设置快捷键截图
CentOS 6.5 下利用命令行截图及设置快捷键截图 1.利用命令模式 捕获整个屏幕 : $ gnome-screenshot 截完屏之后我们可以设置自定义图片存储位置,如图: 捕获当前终端Term ...
- Unity简介
Unity (也称 nity3D) 是一套包括图形. 声音.物理等功能的游戏引擎,提供了一个强大的关卡编辑器,支持大部分主流 3D 软件格式,使用 C# JavaScript 等高级语言实现脚本功能, ...
- PL/SQL developer(绿色版)安装及配置
1.PL/SQL Developer下载地址:百度网盘: 2.tsname.ora配置: orcl = (DESCRIPTION = (ADDRESS_LIST = (ADDRESS )) ) (CO ...
- 解决RaycastTarget勾选过多的烦恼
看过UGUI源码的朋友一定都知道,UI事件会在EventSystem在Update的Process触发.UGUI会遍历屏幕中所有RaycastTarget是true的UI,接着就会发射线,并且排序找到 ...
- Dedecms当前位置{dede:field name='position'/}修改,去掉>方法
Dedecms当前位置{dede:field name='position'/}修改,如何去掉> 一.修改{dede:field name='position'/}的文字间隔符,官方默认的是&g ...
- linux下 redis 启动
启动文件 startredis.sh : nohup /data/redis/bin/redis-server /data/redis/etc/redis.conf & 关闭文件 stopr ...
- ubuntu网页无法看视频
sudo apt-get install flashplugin-nonfree sudo apt-get install aptitude sudo aptitude install ubuntu- ...