阅读 160

Activity的启动模式

一、概述

Android提供了四种启动模式,分别是:

标准模式(Standard)

栈顶复用模式(SingleTop)

栈内复用模式(SingleTask)

单例模式(SingleInstance)

下面依次介绍每种模式的特点,首先了解什么是task,task翻译过来就是“任务”,是一组相互有关联的Activity集合,可以理解为Activity是在task里面活动的。task存在于一个称为back stack的数据结构中,也就是说,task是以 栈的形式去管理Activity的,所以也叫可以称为“任务栈”。综上所述:“任务栈”是Activity的管理方式,采用的是“后进先出”的栈结构,每按一次Back键,就会有一个Activity出栈

二、四种启动模式具体特点

(一)Standard

标准模式,也是系统默认的启动模式,该模式特点:

  1. 每启动一次Activity,都会创建一个新的Activity实例在栈顶,不管这个实例在任务栈中是否已经存在。假如 Activity A启动了 Activity B,Activity B则会运行在Activity A所在的任务栈中并处于栈顶位置。

  2. 非Activity类型的context(如ApplicationContext)启动standard模式的Activity时会报错。因为非Activity类型 context 并没有任务栈,故无法采用标准模式启动Activity。解决办法可以为待启动Activity指定 FLAG_ACTIVITY_NEW_TASK标记位,这样启动的时候系统就会为它创建一个新的任务栈。实际上待启动Activity是采用singleTask模式启动的。

(二)SingleTop

栈顶复用模式,该模式特点:

  1. 若需要新建的Activity位于任务栈栈顶,那么此Activity的实例就不会重新创建,而是复用栈顶的实例。调用Activity的onNewIntent()方法不会调用onCreate()和onStart()方法。

  2. 假如Activity A启动Activity B,就会判断A所在的任务栈栈顶是否是B的实例。如果是,则不创建新的Activity B 实例而是直接引用栈顶实例,同时onNewIntent()方法会被回调,通过该方法的参数可以取得当前请求的信息;如果不是,则创建新的Activity B实例。

(三)SingleTask

栈内复用模式,该模式特点:

. 查看Activity想要的任务栈是否存在(通过查找Activity的taskAffinity属性值相匹配的任务栈是否存在),若不存在,则新建一个任务栈并创建该Activity实例压入栈中;若存在,则查看Activity是否在该栈中,若在,则将该Activity实例之上的所有Activity实例出栈,使该Activity实例置于栈顶,执行回调函数onNewIntent()方法。若不在,则创建该Activity实例并压入栈中。

  1. taskAffinity是在Androidmanifest文件中的一个重要属性,这个参数标识了一个Activity所需要的任务栈的名字。默认情况下,所有Activity所需的任务栈的名字为应用的包名。taskAffinity属性主要和singleTask启动模式或者allowTaskReparenting属性配对使用。

(四)SingleInstance

单实例模式,该模式特点:

  1. 这个是singleTas模式的加强版,它除了具有singleTask模式的所有特性外,它还有一点独特的特性,那就是此模式的Activity只能单独地位于一个任务栈,不与其 Activity共存于同一个任务栈。

  2. 直接创建一个新的任务栈并创建该Activity实例压入栈中。

三、启动模式的设置

两种方法能给Activity指定启动模式:

  1. 在AndroidMainifest设置LaunchMode
  2. 通过Intent设置标志位Intent Flag

(一)在AndroidMainifest设置LaunchMode

<activity 
    android:name=".MainActivity"
    android:launchMode="singleTask">
</activity>
复制代码

(二)通过Intent设置标志位Intent Flag

Intent intent = new Intent(MainActivity.this, LoginActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
复制代码

常用Activity的标志位Flags有:

标 志 位 作 用
FLAG_ACTIVITY_SINGLE_TOP 指定启动模式为栈顶复用模式(SingleTop)
FLAG_ACTIVITY_CLEAR_TOP 在同一个任务栈中,所有位于它上面的Activity都要出栈。在下面详细介绍下
FLAG_ACTIVITY_NEW_TASK 指定启动模式为栈内复用模式(SingleTask)
FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS 具有这个标记的Activity不会出现在历史Activity的列表中,即无法通过历史列表回到该Activity中,它等同于在XML中指定Activity 的属性 android:excludeFromRecents="true"

FLAG_ACTIVITY_CLEAR_TOP

如果该Activity已经在存在任务栈中,系统会将同一个任务栈中,该Activity之上的所有Activity都出栈,然后将Intent发给这个已存在的Activity,该Activity收到Intent之后,执行回调onNewIntent()方法或者自行结束然后重新创建自己。

  1. 如果该Activity在AndroidMainifest.xml里将启动模式设置成默认standard模式

  1. 如果该Activity在AndroidMainifest.xml里将启动模式设置成默认singleTop模式

  1. 如果该Activity在AndroidMainifest.xml里将启动模式设置成默认singleTask模式

(三)二者的区别

  1. 优先级不同:Intent设置方式的优先级 > Manifest设置方式,即以前者为准

  2. 限定范围不同Manifest设置方式无法设定FLAG_ACTIVITY_CLEAR_TOP;Intent设置方式无法设置单例模式(SingleInstance)

四、总结

本文介绍了Activity的四种启动模式(standard、singleTop、singleTask、singleNewInstance)和设置启动模式的方法(launchMode、Intent_Flag)