Android 12 SplashScreen API适配后singleTask启动模式的回退栈问题
为什么官方推荐singleTask却会重置导航?
官方推荐主Activity用singleTask,核心是确保应用始终只有一个主Activity实例,避免深层链接、重复启动时创建多份实例,这对内存管理和状态一致性很重要。但singleTask的固有特性就是:当从启动器启动应用时,如果任务栈里已经存在该Activity实例,系统会把它上方的所有Activity全部出栈,让主Activity回到栈顶——这就是你看到导航重置的原因,不是你漏了配置,是该模式本身的设计逻辑。
如何兼顾「不重复显示闪屏」和「保留回退栈」?
直接用standard模式会重复创建MainActivity导致闪屏,用singleTask会清栈,这里给你两个可行的解决方案:
方案一:用默认standard模式,加启动判断逻辑
在MainActivity的onCreate方法里加入以下判断,当从启动器打开时,如果当前任务栈里已经存在MainActivity实例,直接finish掉新创建的实例,既不会触发闪屏,又能保留原来的回退栈:@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // 处理重复启动的情况 if (!isTaskRoot()) { Intent intent = getIntent(); String action = intent.getAction(); if (intent.hasCategory(Intent.CATEGORY_LAUNCHER) && Intent.ACTION_MAIN.equals(action)) { finish(); return; } } // 原有初始化逻辑 setContentView(R.layout.activity_main); }方案二:改用singleTop模式(适合主Activity不会被多次压栈的场景)
把主Activity的launchMode设为singleTop,同时确保所有启动主Activity的Intent都加上FLAG_ACTIVITY_REORDER_TO_FRONT标记。这样从启动器打开时,如果主Activity已经在栈中,会直接把它移到栈顶,不会清掉上方的Activity,也不会重新创建实例,自然不会触发闪屏。不过这个方案需要注意其他启动主Activity的场景(比如通知跳转)也要统一处理Intent标记。
补充说明
官方推荐singleTask是从「应用启动唯一性」的通用场景出发,但保留回退栈属于个性化需求,系统没有默认适配,需要开发者根据自己的业务场景选择合适的启动模式+自定义逻辑来平衡。
内容的提问来源于stack exchange,提问作者Papps

