在整个应用程序中仅保留每个活动的一个实例

8

我希望在我的应用程序中,每次启动一个 Activity 时只保留一个实例。虽然使用启动模式 singleTask 是一种方案,但它仅适用于一个 Activity

我希望实现以下功能:

  • 如果未存在该 Activity 的实例,则启动该 Activity
  • 如果已经存在该 Activity 的实例,则将该实例提到前台,而不是创建新的实例;
  • 该属性将应用于多个 Activity
  • 没有 Activity 可以保证始终位于历史记录堆栈的顶部。

目前我的工作进展如下:

我得到了许多与我的情况不符的建议,因此我想指出这些问题,以免其他人给出相同的建议。

  • 我将启动模式设置为 singleTop ,但只有当 Activity 位于历史记录堆栈的顶部时才能正常工作。如果 Activity 在堆栈中的任何位置,onNewIntent() 将不会被调用。因此,这种方案无法实现我的需求。

在每个活动中使用singleTop。 - stefana
3个回答

25

当您启动一个Activity时,请按照以下方式进行:

Intent intent = new Intent(this, MyActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
startActivity(intent);

如果此 Activity 的实例已存在,则它将被移到前面。如果实例不存在,则会创建一个新实例。


1
@David Wasser:我也遇到了同样的问题。这个方法解决了我的问题,谢谢! - AJW
这将仅重新排序活动 - 如果活动存在,它将显示它(但是旧状态,因此如果您有新数据,则不会看到它们!),如果不存在,则将创建它。 - Darksymphony
@Darksymphony 你说的“新数据”是什么意思?如果用户想要更新这个Activity中的View,他可以在onResume()中进行操作,或者如果他想要向Activity发送数据(作为Intent中的“extras”),Activity可以重写onNewIntent()并在那里处理“extras”。当Activity被带到前台时,onNewIntent()将在onResume()之前被调用。 - David Wasser
我有一个带有数据的RecyclerView,用户点击编辑按钮后会进入EditActivity。编辑完成后将重定向回第一个活动 - 目前还没有问题。然后用户再次点击编辑,进入EditActivity,现在他只需按设备上的返回按钮(而不是应用程序中的返回按钮),然后再次按下,旧活动将出现并显示以前的数据。由于您的解决方案没有杀死旧活动,只是将其置于顶部。也许我做错了什么,但我有这种经历。对我来说唯一有帮助的事情是:intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); - Darksymphony
1
@Darksymphony 在这种情况下,您需要在 onResume() 中刷新数据。 - David Wasser

4
您可以将您的活动的 android:launchMode 设置为 singleTop 。在这种情况下,如果该活动已存在,则新意图将被传递到该活动的 onNewIntent() 并将其带到前台。http://developer.android.com/guide/topics/manifest/activity-element.html#lmode 如果您的活动位于堆栈顶部,则这将起作用。
如果您想拥有一个活动的单个实例,那么您可以将 launchMode 设置为 singleTask ,但是这不建议使用,因为它会使您的活动驻留在单独的任务中,这可能会让用户感到困惑。

我认为活动必须在历史堆栈的顶部才能在您给出的条件下正常工作。而我的情况并非如此。如果我错了,请纠正我,@Mina。 - Sagar Nayak
是的,你说得对,它必须在堆栈顶部。 - Mina Wissa
但我的情况不同,请查看修改后的问题。 - Sagar Nayak

0

使用singleTop启动模式(文档):如果在调用方任务的堆栈顶部已经存在相同类型的Activity实例,则不会创建任何新的Activity,而是通过onNewIntent()方法向现有的Activity实例发送一个Intent。

有关启动模式的详细信息,请参见本文


会尝试一下,然后告诉您。 - Sagar Nayak
所以我认为活动必须在历史堆栈的顶部才能在您给出的条件下工作。而我的情况并非如此。如果我错了,请纠正我,@Marcin。 - Sagar Nayak
好的,我稍微理解了你的问题。实际上@david-wasser使用FLAG_ACTIVITY_REORDER_TO_FRONT的答案是可以的,我会给他点赞。 - Marcin Orlowski

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