2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

お題は不問!Qiita Engineer Festa 2024で記事投稿!
Qiita Engineer Festa20242024年7月17日まで開催中!

Android12以降でスプラッシュ画面のアイコンが表示されない場合がある

Posted at

SplashScreen API (androidx.core.splashscreen) を利用したスプラッシュ画面の実装を前提とします

Android 12 以降において startActivity() + Intent.FLAG_ACTIVITY_NEW_TASKで Activity を新たに起動する場合、スプラッシュ画面のアイコンが表示されません。

before after
splash_demo_before.gif splash_demo_after.gif

TL;DR

Activity の起動方法によらず常にスプラッシュ画面でアイコンを表示させるには以下の対応が必要です。

Android 13 以降

themes で静的に指定できます

themes.xml
 <?xml version="1.0" encoding="utf-8"?>
 <resources xmlns:tools="http://schemas.android.com/tools">
     <!-- 対象のActivityに適用するテーマ -->
     <style name="MySplash" parent="Theme.SplashScreen">
         <item name="windowSplashScreenBackground">@color/splash_background</item>
         <item name="windowSplashScreenAnimatedIcon">@drawable/splash_icon</item>
+        <item name="android:windowSplashScreenBehavior" tools:targetApi="33">icon_preferred</item>
     </style>
 </resources>

Android 12

Activityを起動するコードからオプション指定が必要です。ただし AndroidStudio から起動する場合にアイコンが表示されない問題は解決できません。

    val intent = Intent(context, MyActivity::class.java)
-   startActivity(intent)
+   if (Build.VERSION.SDK_INT in listOf(31, 32)) {
+       val options = bundleOf("android.activity.splashScreenStyle" to 1)
+       startActivity(intent, options)
+   } else {
+       startActivity(intent)
+   }

詳説

検証に使用したソースはこちら

AndroidX ライブラリ

Android 12 においてOS側のスプラッシュ画面の挙動が大幅に変更され、同時に従来のスプラッシュ画面をAndroid 12 以降も一貫的に実装できるライブラリが提供されました。 SplashScreen API の詳細はここでは割愛します。

Android 12 以降の問題

SplashScreen API によるスプラッシュ画面が表示されるのは、

  • コールドスタート
    (例) アプリが完全に終了している状態でランチャーアプリから起動したとき
  • ウォームスタート
    (例) システムによりbackgroundのアプリが破棄された状態からforegroundに復帰したとき

一方で起動済み&表示中のアプリから新たにActivityを起動すると、Android 12 以降に限りスプラッシュ画面自体は表示されますがアイコンが表示されません。具体的には以下のようなコードが該当します。

fun onRestartClicked() {
    val intent = Intent(context, MyActivity::class.java).apply {
        flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
    }
    startActivity(intent)
}    

windowSplashScreenBehavior属性

API 33 (Android 13) 以降でのみ使用できます

スプラッシュ画面を設定するthemes.xmlにおいてwindowSplashScreenBehavior属性でアイコン表示有無を制御できます。Activityの起動方法によらず常に表示させるにはicon_preferredを指定します。

res/values-v33/themes.xml
 <?xml version="1.0" encoding="utf-8"?>
 <resources xmlns:tools="http://schemas.android.com/tools">
     <!-- MyActivityに適用するテーマ -->
     <style name="MySplash" parent="Theme.SplashScreen">
         <item name="windowSplashScreenBackground">@color/splash_background</item>
         <item name="windowSplashScreenAnimatedIcon">@drawable/splash_icon</item>
         <item name="android:windowSplashScreenBehavior">icon_preferred</item>
     </style>
 </resources>

コードから指定する場合は、

    val intent = Intent(context, MyActivity::class.java).apply {
        flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
    }
-   startActivity(intent)
+   if (Build.VERSION.SDK_INT >= 33) {
+       val options = ActivityOptions.makeBasic().apply {
+           splashScreenStyle = SplashScreen.SPLASH_SCREEN_STYLE_ICON
+       }.toBundle()
+       startActivity(intent, options)
+   } else {
+       startActivity(intent)
+   }

Android 12 対応

windowSplashScreenBehavior属性はAndroid 13 で導入されたため、Android 12 では使用できません。スマートな方法が見つからず、みんな同じ問題で困っているようでした....

開発側の回答にて以下のようなワークアラウンドが提案されています。Bundleだったら文字列でkeyを直接指定できるって発想ですね。

    val intent = Intent(context, MyActivity::class.java).apply {
        flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
    }
+   if (Build.VERSION.SDK_INT in listOf(31, 32)) {
+       val options = bundleOf("android.activity.splashScreenStyle" to 1)
+       context.startActivity(intent, options)
    } else if (Build.VERSION.SDK_INT >= 33) {

AndroidStudio から Run ボタンでアプリ起動する場合、Android 12 でアイコンが表示されない問題はこの方法でも回避できません。

2
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?