Android开发者在AndroidManifest文件中一共设计了四种启动模式
栈:先进后出的线性表
一个android应用程序功能通常会被拆分为多个Activity,而各个Activity之间通过Intent进行连接,android系统通过栈结构来保存整个程序的Activity,栈底的元素是整个栈任务的发起者。
正常情况下,当一个Activity启动了另一个Activity的时候,新启动的Activity就会置于任务栈的顶端,而启动它的Activity虽然功成身退,但依然保留在任务栈中,处于停止状态(如果没有finish),当用户按下返回键或者调用finish()方法时,系统会移除顶部的Activity,让后面的Activity恢复活动状态。但是,可以给Activity设置一些“特权”,来打破这种“和谐”的模式。这种特权,就是通过在AndroidManifest.xml文件中的属性android:launchMode来设置或者通过Intent的flag来设置的。
Intent intent = new Intent(this,MainActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);
// intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
默认启动模式,当不指定Activity的启动模式,则使用这种启动方式启动Activity;这种启动方式每次都会创建新的实例,新创建的activity会置于栈顶。
@Override
protected void onCreate(Bundle savedInstanceState) {
Log.e(TAG, "onCreate");
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button = (Button) findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
testLauncherMode();
}
});
}
void testLauncherMode() {
Intent intent = new Intent(this, MainActivity.class);
startActivity(intent);
}
singleTop(栈顶复用模式),如果指定启动模式为singleTop模式,那么在启动时,系统会判断当前栈顶的Activity是不是要启动的Activity,如果是则不创建新的Activity而直接复用这个Activity,同时回掉Activity的onNewIntent方法;如果不是,则创建新的Activity,即使栈内已存在该Activity。
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.e(TAG, "onCreate");
setContentView(R.layout.view_second);
Button button = (Button) findViewById(R.id.button2);
Button btnMySelf = findViewById(R.id.button3);
btnMySelf.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startMySelf();
}
});
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
testSingleTopLauncherMode();
}
});
}
@Override
protected void onNewIntent(Intent intent) {
super.onNewIntent(intent);
Log.e(TAG,"onNewIntent");
}
栈内复用模式:但一个具有singleTask启动模式的Activity请求启动后,比如Activity A,系统首先会寻找是否存在A想要的任务栈,如果不存在,就重新创建一个任务栈,并将A的实例放入栈中。如果存在A所需要的任务栈,这时候要看A是否在栈中有实例存在,如果栈中不存在该实例,创建该Activity的实例并放入占中,如果栈中存在该Activity,复用该Activity,同时将位于该Activity上面的Activity全部销毁。
参考自
作者:JxYoung
链接:https://www.jianshu.com/p/4c8d6e2117ac
來源:简书
这种启动模式的Activity在Android系统中只允许存在一个实例。
如果系统中已经存在了该种启动模式的目标Activity,则系统并不会重新创建一个目标Activity,而是首先将持有目标Activity的整个任务栈都会被置于前台(用户可见),并且通过onNewIntent(
)方法将启动目标Activity的Intent传递给目标Activity,置于目标Activity拿到这个Intent之后要做什么操作,系统就不管了,随便你拿来干什么。但是这里有个问题,就是目标Activity和源Activity是不是来自同一应用。
源Activity和目标Activity来自同一个应用
这种情况还要分两种情况说:
当前系统中还没有目标Activity的实例
这种情况最简单,直接在当前的任务栈中创建SingleTask模式的Activity并置于栈顶即可。当前系统中已经存在目标Activity的实例
这种情况比较特殊,因为系统会把任务栈中目标Activity之上的所有Activity销毁,以让目标Activity处在栈顶的位置。这里还要还要再提醒大家的是,因为目标Activity已经存在,系统不会重新创建,而是通过onNewIntent()的方式把Intent传递过来,这点和singleTop模式有些类似
源Activity和目标Activity来自不同应用 这种情况也要分两种情况说:
当前系统中还没有目标Activity的实例
这时系统首先会看任务管理器中是否有目标Actvity所在应用的任务栈?如果有的话,那就直接在目标Activity所在应用的任务栈的栈顶创建即可。如果任务管理器中没有目标Activity所在应用的任务栈,系统就会创建其所在应用的任务栈和目标Activity,并且把目标Activity作为新建任务栈的根Activity。如下图所示
当前系统中已经存在目标Activity的实例
目标Activity所在任务栈会被置于前台(即用户可见),而且也会把目标Activity之上的所有Actvity全部销毁。
这种启动模式和singleTask几乎一样,它也只允许系统中存在一个目标Activity,包括上面我们所说的SingleTask的一些特性singleInstance都有。singleInstance翻译过来是单例的意思:TA有两层含义:1.告诉系统,我是独一无二的,2.告诉任务栈我是独一无二的,也就是说,任务栈中除了我不能再有其他Activity。
所以,如果要启动singleInstance模式的Activity,那只能新创建一个任务栈用来放它,因为人家说了,“我是独一无二的!”。同样的,如果从这种启动模式的Activity中启动别的Activity,那不好意思,我不管你是不是和我处在同一个应用,我所在的任务栈只能拥有我一个人,您呐,另外让系统给你创建一个任务栈待着去吧。
Intent intent = new Intent(this,MainActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);
// intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
常用的Flag
启动一个Activity,但是启动的每个Activity都将在一个全新的Task中。该Flag通常用来从Service中启动Activity的场景,由于在Service中并不存在Activity栈,所以使用该Flag来创建一个新的Activity栈,并创建新的Activity实例。
等同于android:launchMode=“singleTop”
INTENT.FLAG_ACTIVITY_CLEAR_TOP
等同于android:launchMode=“singleTask”
INTENT.FLAG_ACTIVITY_NO_HISTORY
使用这种模式启动Activity,当该Activity启动其他Activity后,该Activity就消失了,不会保留在Activity栈中,例如A-B,B以这种模式启动C,C在启动D,则当前Activity栈为ABD。
文章写到这,希望对给位有所帮助,谢谢观看。
参考文献:
https://www.jianshu.com/p/4c8d6e2117ac
http://blog.csdn.net/x283930450/article/details/70597555