2

所以首先我想出了如何从另一个线程更新 UI。我将 AsyncTask 和 Handler 类用于其他任何事情

首先我做错了,现在我真的想找出问题所在。

所以我的第一个尝试是创建一个MyListener带有方法的 java 接口,updateUI()并让主要活动实现该侦听器接口。比我在处理 http 请求的线程中将主要活动注册为侦听器。MyListener.updateUI()在请求完成后我从那个线程调用。updateUI()用请求的结果更新一些文本视图。

这在安卓中不起作用。我没想到。我不知道为什么。异常告诉我,我必须从 UI 线程进行这些更新。

当我使用从侦听器接口实现的主要活动进行调用时,我不明白为什么updateUI()不在 UI 线程中运行。MyListener.updateUI()updateUI()

你能解释一下这种行为吗?

4

3 回答 3

3

我看到你已经在其他线程中执行了 http 请求,但你没有使用AsyncTask,对吗?我建议你应该使用那个类,在doInBackground方法中执行 http 请求(因为它在主线程上工作),然后调用MyListener.updateUI()onPostExcute因为这个方法总是在主线程中被调用。试一试,让我知道它是否有效。

于 2013-02-28T17:11:40.203 回答
2

不管你是MyListener.updateUI()在你MainActivityonCreate()方法中调用还是在其他任何方法中调用,如果你是从另一个线程中调用它,它都会抛出一个异常,因为你只能在应用程序主线程中更新视图。为此,您可以执行以下操作:

public static void updateUI(){

       ((Activity) mContext).runOnUiThread(new Runnable() {

        @Override
        public void run() {
            // TODO Auto-generated method stub
            // update your UI here and be sure to give the activity context, not getApplicationContext();
        }
    });

}

把它放在你的活动中,并在你onCreate()做类似的事情:

public static Context mContext;
@Override
public void onCreate(Bundle savedInstanceState){
   super.onCreate(savedInstanceState);
   setContentView(R.layout.main);
   mContext = this;
}

updateUI()从您想要执行的任何线程调用。

当然,这不是您更新界面的唯一方法。您可以查看AsyncTaskAndroid SDK 中的实现。这是一个非常强大的类,我认为它会更有效地做你想做的事情。

于 2013-02-28T16:11:39.510 回答
1

您收到此错误是因为控件仍在后台线程中...尽管您已调用已在您的活动中实现的接口方法。因此,为了将控件返回到您的 UI 线程,您需要使用处理程序。控件不会通过调用位于您的活动中的方法从后台线程转到 UI 线程。

希望这能澄清你的疑问。

于 2013-02-28T16:07:28.273 回答