在项目开发过程中遇到的一个问题,现在将其记录下来:
问题描述:
点击App图标启动时,会由SplashActivity跳转至MainActivity,相信大多数App都是这样的吧。但是从最近任务列表点击时直接白屏,大概3秒之后会直接显示MainActivity,也就是说SplashActivity被跳过了(在这之前也已经确认App被彻底关掉了),我需要的是点击最近任务列表中的App时,要先显示SplashActivity,然后再跳转到MainActivity。
解决方案:
经过排查,发现AndroidManifest.xml中关于MainActivity的声明是这样的:
<activity
android:name="com.example.MainActivity"
android:label="@string/app_name"
android:launchMode="singleTask"
android:screenOrientation="portrait" />
所以想到可能是因为launchMode设定导致的,将launchMode设置为默认值之后(直接将android:launchMode="singleTask"
删掉),问题就得到了解决。
但是这样会导致MainActivity在来回切换过程中生成多个实例,所以在跳转到MainActivity时需要设置Intent的Flag:
// MainActivity.java
public static void startActivity(Activity activity) {
Intent intent = new Intent();
intent.setClass(activity, MainActivity.class);
/*
* Intent.FLAG_ACTIVITY_CLEAR_TOP
* 如果设置这个属性,跳转至该Activity时,如果这个Activity已经在当前的Task中运行,
* 那将会清除该Activity之上所有的Activity,并将该Activity置于栈顶;
*
* Intent.FLAG_ACTIVITY_SINGLE_TOP
* 如果不设置这个属性,那跳转至Activity时,将会执行onCreate方法
* 设置这个属性的话,跳转至Activity时,将会执行onNewIntent方法
*/
int flag = Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP;
intent.setFlags(flag);
activity.startActivity(intent);
}
上面这个方法只能用于MainActivity已经在栈中存在时,如果栈中不存在MainActivity,也就是刚运行时(由SplashActivity跳转至MainActivity),这时就不需要设置flag, 直接跳转即可。
至于Activity的四种启动模式,网上有太多的讲解了,这里就不再阐述了。
总结一下四种模式:
standard 默认模式,每start一次就会创建一个实例(与Task无关)
singleTop 跟standard模式很类似,但是当前实例如果在栈顶,就不会创建新的实例,会调用该实例的onNewIntent方法;如不在栈顶,则创建新的实例(与Task无关)
singleTask 如果该实例已经存在于其他的Task中,则直接调用该Task中的实例,如果没有的话,新建一个Task(只有一个Task中存在该实例)
singleInstance 新建一个Task,且在该Task中只能存在该Activity的实例(只有一个Task会有,并且该Task中只有这个实例)