Android 如果需要,标记活动重置任务与标记活动清除顶部标记活动单个顶部之间有什么区别?

Android 如果需要,标记活动重置任务与标记活动清除顶部标记活动单个顶部之间有什么区别?,android,android-intent,Android,Android Intent,我正在(最后)为我的书写关于任务的章节,我遇到了一些挥之不去的困惑 当启动请求的启动程序活动时,用作主屏幕启动程序的东西似乎结合使用了标记活动\u新任务和标记活动\u重置任务(如果需要): Intent i=new Intent(Intent.ACTION_MAIN); i.addCategory(Intent.CATEGORY_LAUNCHER); i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIV

我正在(最后)为我的书写关于任务的章节,我遇到了一些挥之不去的困惑

当启动请求的启动程序活动时,用作主屏幕启动程序的东西似乎结合使用了
标记活动\u新任务
标记活动\u重置任务(如果需要)

Intent i=new Intent(Intent.ACTION_MAIN);

i.addCategory(Intent.CATEGORY_LAUNCHER);
i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
            Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
i.setComponent(name);

startActivity(i);  
有:

如果已设置,并且此活动正在新任务中启动,或者正在将现有任务带到顶部,则它将作为任务的前门启动。这将导致应用使该任务处于适当状态所需的任何亲缘关系(将活动移动到该任务或从该任务移出),或者在需要时简单地将该任务重置为其初始状态

这还不是特别清楚

特别是,使用
标记活动\u清除\u顶部
标记活动\u单个\u顶部
的组合似乎可以看到相同的效果。引用
标记活动顶部的文档

如果已设置,并且正在启动的活动已在当前任务中运行,则不会启动该活动的新实例,而是关闭其上的所有其他活动,并且此意图将作为新意图传递给(现在位于顶部的)旧活动

[desired activity]当前正在运行的实例将接收您在其onNewIntent()方法中开始的新意图,或者自身完成并使用新意图重新启动。如果它已将其启动模式声明为“多”(默认),并且您没有在相同的意图中设置FLAG_ACTIVITY_SINGLE_TOP,则它将完成并重新创建;对于所有其他启动模式,或者如果设置了标志\u ACTIVITY\u SINGLE\u TOP,则此意图将传递到当前实例的onNewIntent()

FLAG\u ACTIVITY\u CLEAR\u TOP
文档至少对我来说是有意义的

那么,
FLAG\u ACTIVITY\u RESET\u TASK\u IF\u need
FLAG\u ACTIVITY\u CLEAR\u TOP
FLAG\u ACTIVITY\u SINGLE\u TOP
的组合有什么不同呢


如果您能解释这与上述两个选项中的任何一个有什么不同,则可获得额外积分

如果在传递给Context.startActivity()的意图中设置此标志,则该标志将导致在活动启动之前清除与该活动关联的任何现有任务。也就是说,该活动将成为其他空任务的新根,所有旧活动都将完成。这只能与标记\活动\新建\任务一起使用


这与
FLAG_ACTIVITY_CLEAR_TOP
FLAG_ACTIVITY_SINGLE_TOP之间的一个明显区别是
FLAG_ACTIVITY_CLEAR_TASK
需要
FLAG_ACTIVITY_NEW_TASK
。但是,除此之外,净效果似乎是相同的,如果需要,还可以匹配
标记活动重置任务,但据我所知,
FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_RESET_TASK_IF_need
会分析所有任务,并确保只有一个具有启动器活动的任务正在运行

FLAG_ACTIVITY_CLEAR_TOP | FLAG_ACTIVITY_SINGLE_TOP
将只检查当前任务,因此您可能会在同一时间运行两个启动器实例(如果第一个实例是作为单独的任务创建的)。

1)FLAG_ACTIVITY_RESET_task_,如果需要的话

如果某个任务处于挂起状态,它将破坏该进程并启动您请求的活动

2) 标记\u活动\u清除\u顶部

如果此活动的任何先前意图正在运行,则此方法将交付活动的正在运行实例,关闭所有其他活动,并使用先前实例启动活动

3) 标志\u活动\u单个\u顶部


如果最近启动了此活动,并且保存了实例,则不会启动此活动。

我查看了
活动管理器的源代码。标志
Intent.flag\u ACTIVITY\u RESET\u TASK\u如果需要的话
确实有一些魔力
Intent.flag\u ACTIVITY\u CLEAR\u TOP | Intent.flag\u ACTIVITY\u SINGLE\u TOP
不起作用:它触发任务重新分配

下面是一个(尽管有些蹩脚)例子:

在应用程序A中,我们有根活动
RootA
,还有另一个活动
ReparentableA

<application
        android:label="@string/app_name">
    <activity android:name=".RootA">
        <intent-filter>
            <action android:name="android.intent.action.MAIN"/>
            <category android:name="android.intent.category.LAUNCHER"/>
        </intent-filter>
    </activity>
    <activity android:name=".ReparentableA"
            android:allowTaskReparenting="true"/>
</application>
App B的包名为“com.App.B”,因此其组件的默认
taskafinity
为“com.App.B”

现在我们从主屏幕启动应用程序B。这将启动一个新任务,并创建活动
RootB
的新实例作为该任务中的根活动。Activity
RootB
现在以标准方式启动Activity
ReparentableA
,无需任何特殊标志。将创建
ReparentableA
的实例,并将其置于当前任务中的
RootB
之上

按回家

现在我们从主屏幕启动应用程序A。这将启动一个新任务,并创建活动
RootA
的新实例作为该任务中的根活动。注意:当Android启动“启动器”意图时,它会自动设置标志
Intent.FLAG\u ACTIVITY\u NEW\u TASK
Intent.FLAG\u ACTIVITY\u RESET\u TASK\u(如果需要)。因此,启动
RootA
现在会触发任务重新分配。Android会查看其他任务中是否有与此新任务相关的活动(并且可修复)。它在App B任务中找到
ReparentableA
(与
RootA
具有相同的任务关联性),并将其移动到新的App A任务。启动应用程序A时,我们没有看到
RootA
,实际上我们看到的是
ReparentableA
,因为它被移动到新任务的顶部

如果我们返回应用程序B,我们可以看到
ReparentableA
已从
<application
        android:label="@string/app_name">
    <activity android:name="RootB">
        <intent-filter>
            <action android:name="android.intent.action.MAIN"/>
            <category android:name="android.intent.category.LAUNCHER"/>
        </intent-filter>
    </activity>
</application>