原因

开发过程中遇到button.performClick()无效,原因是View.performClick()需要再UI线程中调用才会有效执行。

响应系统调用的方法(比如报告用户动作的onKeyDown()或一个生命周期回调方法)永远在界面线程中进程,所以onCreate里面调用button的performClick没问题,
而通过code直接调用相当于是代码执行,并不会触发android的UI线程。

什么是UI线程,以下来自官网翻译

当一个应用被启动,系统创建一个执行线程,叫做"main"。这个线程是十分重要的,因为它主管向用户界面控件派发事件。其中包含绘图事件。它也是你的应用与界面工具包(android.widget和 android.view包中的组件)交互的地方。于是main线程也被称为界面线程。

系统不会为每个组件的实例分别创建线程。所有运行于一个进程的组件都在界面线程中被实例化,并且系统对每个组件的调用都在这个线程中派发。因此,响应系统调用的方法(比如报告用户动作的onKeyDown()或一个生命周期回调方法)永远在界面线程中进程。

例如,当用户触摸屏幕上的一个按钮时,你的应用的界面线程把触摸事件派发给控件,然后控件设置它的按下状态再向事件队列发出一个自己界面变得无效的请求,界面线程从队列中取出这个请求并通知这个控件重绘它自己。

http://wiki.eoeandroid.com/Processes_and_Threads

解决方法,最简单的方式

View.post(new Runnable(){
@Override
public void run() {
button.performClick();
}
});

View.post(Runnable)方法。在post(Runnable action)方法里,View获得当前线程(即UI线程)的Handler,然后将action对象post到Handler里。在Handler里,它将传递过来的action对象包装成一个Message(Message的callback为action),然后将其投入UI线程的消息循环中。在Handler再次处理该Message时,有一条分支(未解释的那条)就是为它所设,直接调用runnable的run方法。而此时,已经路由到UI线程里,因此,我们可以毫无顾虑的来更新UI。

Activity.runOnUiThread(new Runnable() {
@Override
public void run() {
button.performClick();
}
});

Activity.runOnUiThread(Runnable)把更新ui的代码创建在Runnable中,然后在需要更新ui时,把这个Runnable对象传给Activity.runOnUiThread(Runnable)。 这样Runnable对像就能在ui程序中被调用。如果当前线程是UI线程,那么行动是立即执行。如果当前线程不是UI线程,操作是发布到事件队列的UI线程

android提供了几种常用的方式,用于实现后台线程与UI线程的交互

  • 1. handler
  • 2. Activity.runOnUIThread(Runnable)
  • 3. View.Post(Runnable)
  • 4. View.PostDelayed(Runnabe,long)
  • 5. AsyncTask

[原] Android performClick无效,UI线程理解的更多相关文章

  1. Android 高级UI设计笔记17:Android在非UI线程中显示Toast

    1. 子线程的Toast怎么显示不出来? 因为Toast在创建的时候会依赖于一个Handler,并且一个Handler是需要有一个Looper才能够创建,而普通的线程是不会自动去创建一个Looper对 ...

  2. Android 关于操作UI线程

    在非UI线程里访问 Android UI toolkit—这个在一个worker线程修改了 View .这会导致不可预期的结果,而且还难以调试. 为了修复这个问题,Android提供了几个方法从非UI ...

  3. android 在非UI线程更新UI仍然成功原因深入剖析

    ”只能在UI主线程中更新View“. 这句话很熟悉吧? 来来,哥们,看一下下面的例子 @Override       protected void onCreate(Bundle savedInsta ...

  4. Android在非UI线程中更新UI的方法

    1.使用Thread+Handler实现非UI线程更新UI界面 在UI Thread中创建Handler.用sendMessage(message)或者obtainMessage(result, ob ...

  5. Android 实战之UI线程和Worker线程交互

    哈哈,博文取了个比较霸气的名字,大家不都喜欢这样忽悠人吗 呵呵! 好了,现在就是很简单的点击查询,然后这个查询有点花时间,不想见面出现假死现象,所以在另外的线程进行查询. 好了,代码在此: packa ...

  6. Android允许在UI线程中使用网络访问

    StrictMode.ThreadPolicy policy=new StrictMode.ThreadPolicy.Builder().permitAll().build(); StrictMode ...

  7. Android中UI线程与后台线程交互设计的5种方法

    我想关于这个话题已经有很多前辈讨论过了.今天算是一次学习总结吧. 在android的设计思想中,为了确保用户顺滑的操作体验.一 些耗时的任务不能够在UI线程中运行,像访问网络就属于这类任务.因此我们必 ...

  8. Android中UI线程与后台线程交互设计的6种方法

    在android的设计思想中,为了确保用户顺滑的操作体验.一些耗时的任务不能够在UI线程中运行,像访问网络就属于这类任务.因此我们必须要重新开启 一个后台线程运行这些任务.然而,往往这些任务最终又会直 ...

  9. Android中后台线程如何与UI线程交互

    我想关于这个话题已经有很多前辈讨论过了.今天算是一次学习总结吧. 在android的设计思想中,为了确保用户顺滑的操作体验.一些耗时的任务不能够在UI线程中运行,像访问网络就属于这类任务.因此我们必须 ...

随机推荐

  1. 接收content-type:multipart/form-data类型的参数

    一.问题描述 最近在写接口程序,该接口需要与其他公司的程序对接.对方发送content-type:multipart/form-data类型的参数,结果通过request.getParameter(p ...

  2. 报这个错 unrecognized selector sent to instance

    1.给一个对象赋空值: 2.调不存在的方法:3.数据类型不对.

  3. 闭包拾遗 & 垃圾回收机制

    闭包拾遗 之前写了篇<闭包初窥>,谈了一些我对闭包的浅显认识,在前文基础上,补充并且更新些对于闭包的认识. 还是之前的那个经典的例子,来补充些经典的解释. function outerFn ...

  4. java之hashCode

    package com.simope.myTest; import java.util.HashMap; import java.util.Map; public class Test20151022 ...

  5. js中基本操作

    1.操作标签值 <!DOCTYPE html> <html> <meta charset="utf-8"> <meta http-equi ...

  6. AngularJS开发指南7:AngularJS本地化,国际化,以及兼容IE低版本浏览器

    AngularJS本地化,国际化 国际化,简写为i18n,指的是使产品快速适应不同语言和文化. 本地化,简称l10n,是指使产品在特定文化和语言市场中可用. 对开发者来说,国际化一个应用意味着将所有的 ...

  7. 每天一个linux命令(44):ifconfig命令

    许多windows非常熟悉ipconfig命令行工具,它被用来获取网络接口配置信息并对此进行修改.Linux系统拥有一个类似的工具,也就是ifconfig(interfaces config).通常需 ...

  8. hdu3986 spfa+枚举

    这题让我第一次感受到了什么叫做在绝望中A题.这题我总共交了18次,TLE不知道几次,WA也不知道几次. 这题不能用dijkstra,用这个我一直超时(我没试过dij+优先队列优化,好像优先队列优化后可 ...

  9. jquery无限级下拉框

    非原创,已修改成通用版,效果如下: 下载:http://files.cnblogs.com/files/EasonJim/jquery.menu.rar 项目相关地址 源码:https://githu ...

  10. ajax提交特殊字符的处理

    前台页面用encodeURIComponent()这个js方法 rule=encodeURIComponent(rule);//对特殊字符编码 后台页面 java.net.URLDecoder url ...