When an Activity receives focus, it will be requested to draw its layout. The Android framework will handle the procedure for drawing, but the Activity must provide the root node of its layout hierarchy.
ui一般只有主线程才能更新,子线程何以直接更新ui,上面是官方文档提供的,要想重画界面,必须先提供根节点
其实在每次activity通过ui线程draw时,它都会记住当前ui线程,所以每次子线程调用更新ui时会报这样的错"Only the original thread that created a view hierarchy can touch its views."看下该异常抛出的源代码android.view.ViewRoot
void checkThread() {
if (mThread != Thread.currentThread()) {
throw new CalledFromWrongThreadException(
"Only the original thread that created a view hierarchy can touch its views.");
}
}
mThread 代表主线程,当然子线程和主线程不等,所以抛出异常,所以子线程要想更新ui,必须确保你能获取viewroot.而WindowManagerImpl便符合条件,下面是一个简单的实例
package sanjie.test;
import android.app.Activity;
import android.os.Bundle;
import android.os.Looper;
import android.view.WindowManager;
import android.view.WindowManager.LayoutParams;
import android.widget.TextView;
public class UiandsonthreadtestActivity extends Activity {
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
new Thread(new WorkThread()).start();
}
private class WorkThread implements Runnable {
@Override
public void run() {
Looper.prepare();
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
WindowManager manager = UiandsonthreadtestActivity.this
.getWindowManager();
TextView view = new TextView(UiandsonthreadtestActivity.this);
view.setText("test");
LayoutParams params = new LayoutParams();
params.width=WindowManager.LayoutParams.WRAP_CONTENT;
params.height=WindowManager.LayoutParams.WRAP_CONTENT;
System.out.println("窗口对象是--------->"
+ UiandsonthreadtestActivity.this.getWindowManager());
manager.addView(view, params);
Looper.loop();
}
}
}
通过它便可以在子线程内更新ui了
分享到:
相关推荐
这两种方法都是为了确保UI更新操作在主线程上执行,避免了“从不是创建控件的线程访问它”的异常。选择哪种方法取决于你是否需要等待更新完成(Invoke适合同步更新,Post适合异步更新)。 在实际应用中,通常建议...
这个"wpf 子线程更新UI demo"是一个展示如何在后台线程执行任务并安全更新UI的实例。下面将详细介绍这两种方法及其背后的原理。 1. **Dispatcher对象** WPF提供了一个名为`Dispatcher`的对象,它是每个UI线程的...
首先,让我们详细讨论如何在非MainActivity类的子线程中进行UI更新。通常,我们可以使用Handler、AsyncTask或者RunOnUiThread方法来实现这一目标。 1. **Handler机制**:创建一个Handler对象,将其绑定到UI线程。...
Handler子线程更新ui的简单demo
### Python+PyQT5的子线程更新UI界面的实例详解 #### 一、引言 在GUI编程中,为了提高程序的响应性和执行效率,通常会使用多线程技术来处理耗时的操作,如网络请求、文件读写等。然而,直接在非UI线程中更新UI界面...
在Android开发中,由于UI操作必须在主线程中执行,因此当我们在子线程中处理数据后,需要将结果安全地传递到主线程进行UI更新。以下将详细讲解三种在子线程中更新UI线程的方法,特别是Handler的两种用法。 1. ...
### 解决PySide+Python子线程更新UI线程的问题 #### 一、问题背景与重要性 在GUI编程中,界面的响应速度直接影响用户体验。为了保持用户界面(UI)的流畅度,通常会将耗时操作放到后台线程进行处理,避免阻塞UI...
主线程拥有GUI事件循环,子线程可以有自己的事件循环,但通常不处理GUI事件。 3. **QThread的使用**:要创建一个子线程,首先需要继承QThread并重写run()方法,这里放入耗时操作。然后实例化并启动线程。但是,直接...
这样,Runnable内部的UI更新操作就会在主线程中完成,避免了线程安全问题。 3. **AsyncTask** AsyncTask是一个轻量级的异步任务类,适合于简单且快速的后台操作。它包含三个泛型参数,分别代表后台操作的数据类型...
子线程则常用于执行长时间运行的任务,以避免阻塞UI。但直接在子线程中修改UI控件可能导致未定义的行为,因为这些控件是由主线程创建和管理的。为了解决这个问题,我们需要使用特定的方法来委托更新给主线程。 首先...
一般情况下我们都说子线程不能更新UI,这里说的子线程可以更新UI,只是为了探讨子线程更新UI这个问题,第三种情况实现的子线程更新UI感觉并没有太大的使用意义,只是为了深刻认识更新UI的问题。 看下这个异常 ...
在多线程编程中,"子线程更新主线程数据"是一个常见的需求,尤其是在UI界面交互和后台处理相结合的应用中。主线程通常负责用户界面的显示与交互,而子线程则用于执行耗时的任务,避免阻塞主线程,提供良好的用户体验...
当UI更新频繁或处理大量数据时,如果这些操作都在主线程上进行,就可能导致界面卡顿,用户体验下降。为了解决这个问题,WPF引入了多线程技术,允许开发者在后台线程处理耗时任务,然后通过特定的方式安全地更新UI。 ...
c#子线程如何读取及设置主线程ui的值,自己录的一个小视频,方便理解,比较菜鸟的方法,请勿喷!
当后台线程需要更新用户界面(UI)时,由于.NET Framework的安全机制,直接操作UI控件会引发“Cross-thread operation not valid”异常。为了解决这个问题,有四种常用的方法:使用Delegate和Invoke、使用Delegate和...
OkHttp3在Android中的应用和子线程更新UI线程的方法 OkHttp3是一个功能强大且流行的HTTP客户端库,在Android开发中广泛应用于处理HTTP请求。然而,在使用OkHttp3时,需要注意一些关键点,以避免一些常见的错误。 ...
因此,在MFC中,我们需要采用合适的方法确保UI更新操作在主线程中执行。本文将详细介绍MFC中更新控件内容的两种主要方法,并提供具体的代码示例。 #### MFC中的线程类型 在MFC中,线程可以分为两大类:工作者线程...
特别是在C#多线程编程中,子线程更新UI控件是一个常见的问题。本文将总结C#子线程更新UI控件的方法,介绍两种常用的方法,以便读者更好地理解和应用。 一、使用控件自身的Invoke/BeginInvoke方法 Control类实现了...
- `BeginInvoke`:这是一个异步调用,子线程不会阻塞,而是立即返回,UI更新在后台进行。适用于非阻塞式操作,以保持子线程的运行效率。 4. 示例代码 - 不带参数: ```csharp private delegate void ...