Android:清除返回栈

362

在Android中,我有一些活动,假设它们是A,B,C。

在A中,我使用以下代码打开B:

Intent intent = new Intent(this, B.class);
startActivity(intent);
在B中,我使用以下代码来打开C:
Intent intent = new Intent(this, C.class);
startActivity(intent);

当用户在C中点击按钮时,我希望返回A并清除后退栈(关闭B和C)。因此,当用户使用后退按钮时,B和C将不会出现。我一直在尝试以下操作:

Intent intent = new Intent(this, A.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); 
startActivity(intent);

但是当我回到活动A时,如果我使用后退按钮,B和C仍然会出现。我该如何避免这种情况?

39个回答

9

对于未来的研究,可以尝试使用这段代码。

Intent intent = new Intent(context, LoginActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_CLEAR_TASK | Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
finish();

1
这些标志最终对我起作用了。我的做法是使用这些标志和一个布尔型额外参数EXIT=true启动与我当前Activity相同的Activity。在onCreate()中,我检查了启动参数是否为EXIT,并在其设置为true时调用finish()。这样做很麻烦,只是为了关闭自己的应用程序。 - Janne Oksanen

9
在启动任务A时,使用finishAffinity(); 在任务C中以清除返回栈活动。

只有这个答案对我有用。Intent.FLAG_ACTIVITY_CLEAR_TOP和Intent.FLAG_ACTIVITY_NEW_TASK不是必需的。 - chrizonline

8

使用此代码启动新活动并关闭或销毁所有其他活动堆栈或后退堆栈。

Intent intent = new Intent(this, MainActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
startActivity(intent);

7

我找到了一个有趣的解决方案,可能会有所帮助。我在我的 onBackPressed() 方法中进行了如下操作。

finishAffinity();
finish();

FinishAffinity 可以断开现有活动与其栈之间的连接。然后,finish 帮助您退出该活动。这最终将退出应用程序。


7
在Kotlin中,与Java几乎相同。只有|符号被or文本替换。因此,它的书写方式为-
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK or Intent.FLAG_ACTIVITY_NEW_TASK)

5

高级,可重用的Kotlin:

您可以直接使用setter方法设置标志。在 Kotlin 中,or 是 Java 位或 |替代方案

intent.flags = FLAG_ACTIVITY_NEW_TASK or FLAG_ACTIVITY_CLEAR_TASK

如果使用超过一次,创建一个Intent扩展函数。
fun Intent.clearStack() {
    flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
}

在启动意图之前,您可以直接调用此函数。

intent.clearStack()

如果您需要在其他情况下添加附加标志的选项,请向扩展函数添加可选参数。
fun Intent.clearStack(additionalFlags: Int = 0) {
    flags = additionalFlags or Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
}

4
我觉得你需要使用startActivityForResult()Activity B启动Activity C。当你在Activity C中点击一个按钮时,调用setResult(RESULT_OK)finish(),以结束Activity C。在Activity B中,你可以让onActivityResult()也调用finish()来结束自身,然后回到Activity A

7
如果A和C之间有42项活动,那会相当繁琐。FLAG_ACTIVITY_CLEAR_TOP标志应该直接做到OP想要的。 - Guillaume Brunerie
这将是实现 OP 所需的不太理想的方式,正如 @Guillaume 所说,它需要在根和堆栈顶部之间的所有活动中编写代码。 - jakebasile
已经注意到了。显然这些是我需要学习的标志。 - Maximus

4
我发现这里的答案有点误导,因为原始问题中的代码对我来说似乎可以正常工作?
如果A是根Activity,使用FLAG_ACTIVITY_CLEAR_TOP从B或C启动它,将会将B和C从返回堆栈中删除。

3

我尝试了所有的解决方案,但没有一个能够单独为我解决问题。

我的解决方案是:

在Android清单中使用[android:launchMode="singleTop"]Activity A声明为SingleTop

现在在从任何地方启动A时添加以下标志。它会清除堆栈。

Intent in = new Intent(mContext, A.class);
in.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK );
startActivity(in);
finish();

3

Kotlin示例:

      val intent = Intent(this@LoginActivity, MainActivity::class.java)
      intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP or Intent.FLAG_ACTIVITY_NEW_TASK
      startActivity(intent)
      finish()

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