为什么FLAG_ACTIVITY_CLEAR_TOP无法正常工作?

25

正如标题所说,为什么 intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP) 或者 intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP) 不起作用?

我有3个活动,我们称之为A、B和C。

当我尝试从C启动Activity A的代码如下:

Intent i = new Intent(this, A.class);
i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(i);

它只是启动Activity A但不清除顶部。! -_-

我也尝试使用setFlags()

我在SO上读了不同的关于这个问题的问题,但是我找不到正确的答案。 >_<

有人请帮忙!

编辑

@codeMagic要求在活动“ A”中按下返回键的代码。

@Override
public void onBackPressed(){
    if(wvLogin.canGoBack())
        wvLogin.goBack();
    else
        super.onBackPressed();
}

1
它为什么不能清除顶部? - codeMagic
1
你是说怎么做吗?当A被启动后,按下返回按钮应该退出应用程序,但在这种情况下,C从后台进入焦点。 - ashu
2
这正是我所说的“how”的意思。在进一步查看之前,我只是需要确保你对“how”的定义与我的相同。 - codeMagic
@ashu 那么FLAG_ACTIVITY_CLEAR_TOP将不起作用。请参见http://developer.android.com/reference/android/content/Intent.html#FLAG_ACTIVITY_CLEAR_TOP - matiash
@matiash:在上一条评论中,我的意思是不是'A'而是现在的'A'。请注意这一点,我在开发者网站上阅读了相关信息,但使用新任务以及清除顶部也无法解决问题! - ashu
显示剩余11条评论
3个回答

55
FLAG_ACTIVITY_CLEAR_TOP的文档中得知:
如果设置了该标志,并且要启动的活动已在当前任务中运行,则除了该活动之外的所有其他活动将被关闭,该意图将被传递到该旧活动(现在在顶部)作为新意图。
正如您在评论中添加的那样,在调用B之前,活动A已经完成,因此不会出现这种情况。而是会启动活动A的一个新实例。
就我所看到的,您有两个选择:
1) 使用Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK标志。这将以堆栈的根开始活动A。它有效,但是堆栈中的任何其他活动都将丢失。假设A是第一个活动(或者至少,您对任务堆栈中的任何先前活动不感兴趣),那么无所谓。注意:CLEAR_TASK需要API Level 11。 2) 另一个可能的解决方案(如果之前的假设不成立)是根本不使用意图标志:
  • B使用startActivityForResult()启动C。
  • C完成后,为B设置一个结果,指示必须启动A,而不是调用A。
  • B.afterActivityResult()中,完成B并启动A。

另一个选择是将活动A保留在堆栈中(在启动其他活动时不调用finish())。这样可以使用FLAG_ACTIVITY_CLEAR_TOP。但是,您需要处理用户可能返回到活动A的情况。 - David Wasser
如果在A之前有更多的活动(如此SO问题中所提到的),而且我必须将它们保留在堆栈中,那么NEW_TASK就会失败,是吗? - Saravanabalagi Ramachandran
兄弟,我爱你。我尝试了大约十几种组合来关闭该死的自定义Chrome标签页。该死的三天啊。只有这个Intent.FLAG_ACTIVITY_CLEAR_TOP或Intent.FLAG_ACTIVITY_CLEAR_TASK对我起作用。 - Zakhar Rodionov
FLAG_ACTIVITY_NEW_TASK | ...CLEAR_TASK 可以使用,但是会给人一种你已经切换到了一个新的应用程序的错觉。在我看来并不好。我更喜欢这样做:intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP activity.startActivity(intent) activity.finish() - KBog

12

您缺少Intent.FLAG_ACTIVITY_SINGLE_TOP标志。

尝试以下方法:

Intent i = new Intent(this, A.class);
i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
startActivity(i);

6
您使用了一个不同的意图:请使用您初始化的那个意图:
  Intent i = new Intent(this, A.class);
  intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); \\WRONG;;
  startActivity(i);

解决方案:

i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); \\RIGHT;;

你可以在清单文件中的Activity A上添加noHistory属性,并将其设置为true。该属性的作用是禁止Activity A被存储在返回栈中。
android:noHistory=true

为什么即使Activity A运行正常,也要将noHistory设置为它?我遇到了问题B和C因为它们没有在后台完成! - ashu
谢谢@Rod_Algonquin - RAJESH KUMAR ARUMUGAM
1
android:noHistory="true" 是完美的答案,只有一行代码! - Rickster

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