安卓错误:recreate()必须从主线程调用。

9

我遇到了一个Android错误,虽然错误信息很明显,但我仍然无法弄清楚如何使其正常工作。

错误信息如下:

 java.lang.IllegalStateException: Must be called from main thread
        at android.app.Activity.recreate(Activity.java:4193)

在我的应用中,当用户的令牌过期时,会发送一个通知以注销该用户。

在旧版的 Android 上,我没有问题这样做,但是从 SDK 11 开始,我必须使用 recreate() 方法。我遇到了错误,要求必须从主线程调用。

我将 recreate() 语句移动到 MainActivity 类中,但是当我从 IntentService 调用该方法时,它不起作用。我仍然遇到同样的错误。消息传递部分运行良好,只有处理注销信息时才出现此错误。

以下是一些片段:

在 GcmIntentService.java 中:

if (logout!=null) {
    VarControl.ma.logout();
}

在MainActivity.java内部

public void logout() {
    deleteToken();
    closeWebView();
    restartApp();
}

public void restartApp() {
    if (Build.VERSION.SDK_INT >= 11) {
        this.recreate(); // THE ERROR OCCURS HERE
    }
    else{
        //left out this part because its not relevant
    }
}

如何在主线程中调用重新创建(但代码必须在接收到intent时处理)?

2个回答

8
如果您想在主线程上运行某些内容,仍然可以执行以下操作:
public void restartApp() {
    if (Build.VERSION.SDK_INT >= 11) {
        runOnUiThread(new Runnable() {
            @Override
            public void run() {
                recreate();
            }
        });
    }
    else{
    //left out this part because its not relevant
    }
}

this.recreate 无法解析,但是引用 VarControl.ma.recreate() 就可以了!非常感谢,正是我所需要的! - Bart Hofma
是的,我稍后进行了编辑。如果您编写this.recreate(),'this' 将指向 Runnable。您可以省略 'this',它将使用唯一一个上下文,即在此处具有意义的活动,或者指定 MainActivity.this.recreate(); - Xavier Falempin

0

创建一个可被两个线程访问的列表。使用synchronized或类似的方法将其保护起来。每当收到Intent时,向列表中添加一个包含相应代码的Runnable。

在主线程中定期检查列表是否非空。如果不为空,从列表中弹出第一个Runnable并运行它。直到列表为空为止。

这通常是处理将代码从一个线程传递到另一个线程的好方法。


谢谢回复,我该如何定期检查列表?在无限的Thread.sleep循环中获取主线程对我来说并不是一个真正的选择..... - Bart Hofma

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接