相关文章推荐
活泼的蚂蚁  ·  新闻动态-中央民族大学附属中学·  9 月前    · 
玩命的青蛙  ·  常州市新北区人民政府征收土地公告〔2022〕 ...·  1 年前    · 
很拉风的红酒  ·  Microsoft Word: ...·  1 年前    · 
威武的豌豆  ·  摆脱多巴胺,追逐内啡肽,这才应该是每个人的人 ...·  2 年前    · 
深情的麻辣香锅  ·  3家股份行“补降”存款利率,大行进一步下调利 ...·  2 年前    · 
Code  ›  Android 12 新功能:SplashScreen优化启动体验开发者社区
https://cloud.tencent.com/developer/article/1946216
安静的墨镜
2 年前
作者头像
BennuCTech
0 篇文章

Android 12 新功能:SplashScreen优化启动体验

前往专栏
腾讯云
开发者社区
文档 意见反馈 控制台
首页
学习
活动
专区
工具
TVP
文章/答案/技术大牛
发布
首页
学习
活动
专区
工具
TVP
返回腾讯云官网
社区首页 > 专栏 > BennuCTech > Android 12 新功能:SplashScreen优化启动体验

Android 12 新功能:SplashScreen优化启动体验

作者头像
BennuCTech
发布 于 2022-02-24 07:54:50
2.4K 0
发布 于 2022-02-24 07:54:50
举报

前言

由于很多应用在启动时需要进行一些初始化事务,导致在启动应用时有一定的空白延迟,在之前我们一般的做法是通过替换 android:windowBackground 的自定义主题,使应用启动时及时显示一张默认图片来改善启动体验。

在Android 12中,官方添加了SplashScreen API(https://developer.android.google.cn/about/versions/12/features/splash-screen),它可为所有应用启用新的应用启动界面。新的启动界面是瞬时显示的,所以就不必再自定义 android:windowBackground 了。新启动页面的样式默认是正中显示应用图标,但是允许我们自定义,以便应用能够保持其独特的品牌。下面我们来看看如何使用它。

启动画面实现

其实在Android 12上已经默认使用了SplashScreen,如果没有任何配置,会自动使用App图标。

当然也允许自定义启动画面,在value-v31中的style.xml中,可以在App的主Theme中通过如下属性来进行配置:

<style name="AppTheme" parent="android:Theme.Holo.Light.DarkActionBar">
    <item name="android:windowSplashScreenBackground">@android:color/white</item>
    <item name="android:windowSplashScreenAnimatedIcon">@drawable/anim_ai_loading</item>
    <item name="android:windowSplashScreenAnimationDuration">1000</item>
    <item name="android:windowSplashScreenBrandingImage">@mipmap/brand</item>
</style>
  • windowSplashScreenBackground 设置启动画面的背景色
  • windowSplashScreenAnimatedIcon 启动图标。就是显示在启动界面中间的图片,也可以是动画
  • windowSplashScreenAnimationDuration 设置动画的长度。注意这里最大只能1000ms,如果需要动画时间更长,则需要通过代码的手段让启动画面在屏幕上显示更长时间(下面会讲到)
  • windowSplashScreenIconBackground 设置启动图标的背景色
  • windowSplashScreenBrandingImage 设置要显示在启动画面底部的图片。官方设计准则建议不要使用品牌图片。

运行启动应用就可以看到新的启动画面了,如下:

动画的元素

在Android 12上,显示在启动界面中间的图片会有一个圆形遮罩,所以在设计图片或动画的时候一定要注意,比如上面我的例子,动画其实就没有显示完整。对此官方给了详细的设计指导,如下:

  • 应用图标 (1) 应该是矢量可绘制对象,它可以是静态或动画形式。虽然动画的时长可以不受限制,但我们建议让其不超过 1000 毫秒。默认情况下,使用启动器图标。
  • 图标背景 (2) 是可选的,在图标与窗口背景之间需要更高的对比度时很有用。如果您使用一个自适应图标,当该图标与窗口背景之间的对比度足够高时,就会显示其背景。
  • 与自适应图标一样,前景的 ⅓ 被遮盖 (3)。
  • 窗口背景 (4) 由不透明的单色组成。如果窗口背景已设置且为纯色,则未设置相应的属性时默认使用该背景。

启动时长

默认当应用绘制第一帧后,启动画面会立即关闭。但是在我们实际使用中,一般在启动时进行一些初始化操作,另外大部分应用会请求启动广告,这样其实需要一些耗时的。通常情况下,这些耗时操作我们会进行异步处理,那么是否可以让启动画面等待这些初始化完成后才关闭?

我们可以使用 ViewTreeObserver.OnPreDrawListener 让应用暂停绘制第一帧,直到一切准备就绪才开始,这样就会让启动画面停留更长的时间,如下:

...
var isReady = false
override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.main_activity)
    val content: View = findViewById(android.R.id.content)
    content.viewTreeObserver.addOnPreDrawListener(
        object : ViewTreeObserver.OnPreDrawListener {
            override fun onPreDraw(): Boolean {
                return if (isReady) {
                    content.viewTreeObserver.removeOnPreDrawListener(this)
                } else {
                    false

这样当初始化等耗时操作完成后,将isReady置为true即可关闭启动画面进入应用。

上面我们提到配置启动动画的时长最多只能是1000ms,但是通过上面的代码可以让启动画面停留更长时间,所以动画的展示时间也就更长了。

关闭动画

启动画面关闭时默认直接消失,当然我们也可以对其进行自定义。

在Activity中可以通过 getSplashScreen 来获取(注意判断版本,低版本中没有这个函数,会crash),然后通过它的 setOnExitAnimationListener 来定义关闭动画,如下:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
    splashScreen.setOnExitAnimationListener { splashScreenView ->
        val slideUp = ObjectAnimator.ofFloat(
            splashScreenView,
            View.TRANSLATION_Y,
            -splashScreenView.height.toFloat()
        slideUp.interpolator = AnticipateInterpolator()
        slideUp.duration = 200L
        //这里doOnEnd需要Android KTX库,即androidx.core:core-ktx:1.7.0
        slideUp.doOnEnd { splashScreenView.remove() }
        slideUp.start()

加上如上代码后,本来直接消失的启动画面就变成了向上退出了。

这里可以通过 splashScreenView 可以获取到启动动画的时长和开始时间,如下:

val animationDuration = splashScreenView.iconAnimationDurationMillis
val animationStart = splashScreenView.getIconAnimationStartMillis

这样就可以计算出启动动画的剩余时长。

顺便吐槽一下官网这里代码错了,开始时间也用了 iconAnimationDurationMillis 来获取,实际上应该是 getIconAnimationStartMillis

低版本使用SplashScreen

只能在Android 12上体验官方的启动动画,显然不能够啊!官方提供了Androidx SplashScreen compat库,能够向后兼容,并可在所有 Android 版本上显示外观和风格一致的启动画面(这点我保留意见)。

首先要升级compileSdkVersion,并依赖SplashScreen库,如下:

android {
   compileSdkVersion 31
dependencies {
   implementation 'androidx.core:core-splashscreen:1.0.0-alpha01'

然后在style.xml添加代码如下:

<style name="Theme.App.Starting" parent="Theme.SplashScreen">
    // Set the splash screen background, animated icon, and animation duration.
    <item name="windowSplashScreenBackground">@android:color/white</item>
    // Use windowSplashScreenAnimatedIcon to add either a drawable or an
    // animated drawable. One of these is required.
    <item name="windowSplashScreenAnimatedIcon">@drawable/anim_ai_loading</item>
    <item name="windowSplashScreenAnimationDuration">1000</item>  # Required for
    # animated icons
    // Set the theme of the Activity that directly follows your splash screen.
    <item name="postSplashScreenTheme">@style/AppTheme</item>  # Required.
</style>

前三个我们上面都介绍过了,这里新增了一个 postSplashScreenTheme ,它应该设置为应用的原主题,这样会将这个主题设置给启动画面之后的Activity,这样就可以保持样式的不变。

注意上面提到的 windowSplashScreenIconBackground 和 windowSplashScreenBrandingImage 没有,这是与Android12的不同之一。

然后我们将这个style设置给Application或Activity即可:

<manifest>
   <application android:theme="@style/Theme.App.Starting">
    <!-- or -->
        <activity android:theme="@style/Theme.App.Starting">

最后需要在启动activity中,先调用 installSplashScreen ,然后才能调用 setContentView ,如下

class MainActivity : ComponentActivity() {
 
推荐文章
活泼的蚂蚁  ·  新闻动态-中央民族大学附属中学
9 月前
玩命的青蛙  ·  常州市新北区人民政府征收土地公告〔2022〕第42号
1 年前
很拉风的红酒  ·  Microsoft Word: Document Translation Failed/Unable to reach - Microsoft Q&A
1 年前
威武的豌豆  ·  摆脱多巴胺,追逐内啡肽,这才应该是每个人的人生目标|心流|脑内啡_网易订阅
2 年前
深情的麻辣香锅  ·  3家股份行“补降”存款利率,大行进一步下调利率的可能性几何?_手机新浪网
2 年前
今天看啥   ·   Py中国   ·   codingpro   ·   小百科   ·   link之家   ·   卧龙AI搜索
删除内容请联系邮箱 2879853325@qq.com
Code - 代码工具平台
© 2024 ~ 沪ICP备11025650号