活动的启动模式
活动的启动模式一共有四种分别是standard、singleTop、singleTask和singleInstance,可以在AndroidManifest中通过给<activity>标签指定android:launchMode属性来选择启动模式。
- standard(标准模式)
standard是活动的默认启动模式,在不进行显示指定的情况下,所有的活动都会自动使用这种启动模式,在standard模式下,每当启动一个新的活动,他就会在返回栈中入栈,并处于栈顶的位置。对于standard模式的活动,系统不会在乎这个活动是否已经在栈中存在,每次启动都会创建该活动的一个新的实例,一个任务栈可以有多个实例,,每个实例也可以属于不同的任务栈,在这种模式下,谁启动了这个Activity,那么这个Activity就在启动它的那个Activity所在的栈中。所以我们用ApplicationContext去启动standard模式的活动的时候就会报错,原因是非Activity类型的Context(如ApplicationContext)并没有所谓的任务栈,解决这个问题就是为待启动的活动指定FLAG_ACTIVITY_NEW_TASK标记位,这样启动的时候就会为它创建一个新的任务栈,这个时候待启动的Activiy就是以singleTask模式启动的 - singleTop(栈顶复用模式)
当活动的启动模式指定为singleTop时,在启动活动时如果发现返回栈的栈顶已经是该活动,则认为可以直接使用它,不会再创建新的活动实例,所以该活动的onCreate和onStart方法不会被系统调用,因为它并未发生改变,但同时它的onNewIntent方法会被回调,使用singleTop模式可以很好地解决重复创建栈顶活动的问题,但是如果该活动没有处于栈顶,还是可能会重复创建多个同一个活动的实例,下面讲singleTask - singleTask(栈内复用模式)
当活动模式指定为singleTask时,每次启动该活动时系统首先会在返回栈中检查是否存在该活动的实例,如果发现已经存在则直接使用该实例,并把这个活动之上的所有活动统统出栈,和singleTop一样,系统也会回调onNewIntent方法,如果没有发现就会创建一个新的活动实例。具体一点,当一个具有singleTask模式的Activity A要请求启动的时候,系统首先会去找是否存在A想要的任务栈,如果不存在就去创建一个,将A压入栈,如果存在A所需的任务栈,这时要看该任务栈例是否有A的实例存在,如果不存在就创建一个A的实例并压入栈顶,如果存在,系统就会把A调到栈顶并调用它的onNewIntent方法。 - singleInstance(单实例模式)
这时一种加强的singleTask模式,它除了具有singleTask模式的所有特性外,还加强了一点,那就是具有此种模式的Activity只能单独地位于一个任务栈中,比如Activity A是这种模式,当A启动后,系统会为它创建一个任务栈,然后A单独在这个任务栈中,由于栈内复用的特性,后续的请求都不会创建新的Activity,除非这个任务栈被销毁了。这样做有什么意义呢?假设我们的程序中有一个活动是允许其他程序调用的,如果想实现其他程序和这个程序共享这个活动的实例该如何实现呢?其他三个模式肯定是做不到的,因为每个应用程序都有它自己的任务栈,同一个活动在不同的返回栈中入栈是必然会创建新的实例,所以这时候我们用singleInstance模式就可以很好地解决这个问题,不管是哪个应用程序来访问这个活动,都共用同一个返回栈,也就解决了共享活动实例的问题。
怎样指定启动模式
方法一:
通过AndroidManifest指定
<activity
...
android :launchMode="singleTask"
...
/>
方法二:
通过在Intent中设置标记位来为Activity指定启动模式
Intent intent =new Intent(this,SecondActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
需要注意的是第二种方式的优先级高于第一种,当两种指定模式同时存在的情况下,以第二种为准;其次两种方式在限定范围上有所不同,比如第一种方式无法直接为Activity设定FLAG_ACTIVITY_CLEAR_TOP标识,而第二种无法为Activity指定singleInstance模式。
Activity常用的Flags
- FLAG_ACTIVITY_NEW_TASK:指定singleTask(栈内复用)启动模式,其效果和在XML中指定该启动模式相同
- FLAG_ACTIVITY_SINGLE_TOP:指定singleTop(栈顶复用)启动模式,其效果和在XML中指定该启动模式相同
- FLAG_ACTIVITY_CLEAR_TOP:当启动这个Activity时,在同一个任务栈中所有位于它上面的Activity都要出栈,这个标记为一般和singleTask启动模式一起出现,在这种情况下,如果被启动的Activity的实例在任务栈中已经存在,,那么系统就会调用它的onNewIntent,如果被启动的Activity采用standard模式启动