StartingWindow

// frameworks/base/services/core/java/com/android/server/wm/ActivityRecord.java
boolean createStartingWindow(...) {
    ...
    mWmService.mStartingSurfaceController.addStartingWindow(this);
}

这段代码是系统在启动 Activity 过程中插入启动窗口(包括 SplashScreen)的关键路径。我们来详细剖析这段代码的实现背景、调用链和最终效果

1. 背景

当 Android 应用启动时(冷启动或首次启动某个 Activity),为了避免用户看到黑屏,系统会在应用真正绘制前插入一个“占位窗口”,通常是:

SplashScreen(Android 12+)

• 或老版本的 StartingWindow(如 preview window)

🔍 2. 核心调用链梳理

你提到的是:

// ActivityRecord.java
boolean createStartingWindow(...) {
    ...
    mWmService.mStartingSurfaceController.addStartingWindow(this);
}

这段代码的调用链如下:

ActivityTaskManagerService.startActivity()
  ↳ ActivityStackSupervisor.realStartActivityLocked()
      ↳ ActivityRecord.attach() -> 创建 WindowToken
      ↳ ActivityRecord.createStartingWindow()
          ↳ StartingSurfaceController.addStartingWindow()

也就是说:当系统即将启动某个 Activity 时,会判断是否要添加一个“起始窗口”

3. addStartingWindow() 做了什么?

这个函数负责:

创建 SplashScreenView 或 legacy StartingWindow

// frameworks/base/services/core/java/com/android/server/wm/StartingSurfaceController.java

boolean addStartingWindow(ActivityRecord activity) {
    // 判断是否启用 SplashScreen(API 31+)
    if (mSplashScreenController != null && activity.shouldUseSplashScreen()) {
        return mSplashScreenController.addSplashScreenStartingWindow(activity, ...);
    } else {
        // fallback: 使用老版 StartingWindow(TextView + 背景色)
        return createLegacyStartingWindow(activity);
    }
}

系统在这里判断当前 Activity 是否应该使用 SplashScreenView,如果不行则回退到老方案(白底+app icon+label)

4. SplashScreenController.addSplashScreenStartingWindow(…)

该方法最终构造了:

// 创建 SplashScreenView
SplashScreenView view = new SplashScreenView(...);

// 将 View 添加到应用窗口
WindowState.addChild(view);

SplashScreenView 是一个系统级的 View,由 android:windowSplashScreenAnimatedIcon 和 windowSplashScreenBackground 控制内容。

** 5. 为什么叫 “StartingWindow”?和 Splash 有何关系?**

• 在 Android 12+ 中,“起始窗口”就是 SplashScreen;

• 在旧版本中,“起始窗口”是通过 TextView + 背景色手动构建的 preview 窗口;

• 系统使用 相同的接口 addStartingWindow() 注入起始界面,内部根据条件决定是否创建 SplashScreen。

6. 关键点总结

关键点 说明
createStartingWindow() ActivityRecord 启动前构建占位窗口
mWmService.mStartingSurfaceController 控制 Splash 的插入逻辑
addStartingWindow() 自动判断是否构建 SplashScreen
SplashScreenController Android 12+ 新引入的系统类,用于统一展示启动画面
SplashScreenView 系统实际展示在屏幕上的 View(背景 + 图标 + 动画)

相关源码文件(AOSP)

类名 作用 文件路径
ActivityRecord.java 管理单个 Activity 启动状态 services/core/java/com/android/server/wm/
StartingSurfaceController.java 控制启动窗口的创建 同上
SplashScreenController.java Android 12+ 专用于管理 SplashScreen 同上
SplashScreenView.java 实际展示的 View core/java/com/android/internal/policy/

当前网速较慢或者你使用的浏览器不支持博客特定功能,请尝试刷新或换用Chrome、Firefox等现代浏览器