Android之路 - 冷启动解决方案:实现秒开
前言
关于 splash 页面相信每个Android开发者都是非常熟悉的,而且很多人也遇到过需要在splash加个广告图片,然后延迟3秒在进入主页面,splash 应该只是一个启动页面,不应该放广告,但是那又能怎么样呢?又敌不过产品经理。
大多数情况下都会碰到启动白屏和黑屏的情况,那么本文将探讨几种我在开发中用到的几种解决方案。
原理解析
冷启动
什么是冷启动
Android中的冷启动,使用直白的话就是:
- 当手机 重启 ,点击桌面图标启动应用的过程就是冷启动
- 未启动手机,长时 未使用,应用被 kill 后,此时点击桌面图标启动应用的过程
冷启动的表现形式
未做处理的情况
- 点击桌面图标后没有反应,没有瞬间打开应用,也就是没有马上看到应用打开
- 点击桌面图标后会显示 黑屏 或者 白屏 , 没有及时渲染出页面元素
详情可以查看下图:
从上图可以看出,点击图标后出现了短暂的白屏,然后才显示了 splash 页面的内容,在splash页面进行了延迟 1500毫秒再跳转到主页面。虽然白屏的时间很短暂,但给用户的体验感就不是很好了。
冷启动产生的原因
冷启动产生的主要原因要从APP的启动流程说起:
- 用户点击 icon
- 系统开始加载和启动应用
- 应用启动:开启空白(黑色)窗口
- 创建应用进程
- 初始化Application
- 启动 UI 线程
- 创建第一个 Activity
- 解析(Inflater)和加载内容视图
- 布局(Layout)
- 绘制(Draw)
下图是启动的日志信息:
从上面可以看出,从应用启动到布局和绘制,是需要时间的,这也是无法避免的,越是低端的手机上,这一过程耗费的时间。
解决方案
首先要明确的一点就是:冷启动无法避免,我们只能去减少冷启动的时间和适配冷启动。
如何减少冷启动的时间?
其实这个问题等同于如何减少应用初始化的时间,从上面的APP启动流程中,如果我们在应用初始化的操作越多,那么从初始化到绘制的时间越长,用户看到真实界面的时间也就越长,可以从如下几个方面进行:
- 减少在 Application 中的耗时操作(懒加载)
- 减少在 onCreate 的耗时操作
如何适配冷启动?
Android 为我们提供了 android:windowBackground 的解决方案,我们可以专门为 SplashActivity 设置一个背景来避免 创建空白(黑色) 窗口这一步骤的尴尬,而对于 android:windowBackground 又延伸了各种各样的方案。
1. 纯色背景 + 启动图标
这种做法在国产APP上面少见,在国外的APP常见,简单的来说就是用 layer-list 绘制一个纯色的背景加上一个启动图标,layer-list 代码如下:
<?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item android:drawable="@color/colorPrimary" /> <item> <bitmap android:gravity="center" android:src="@mipmap/ic_launcher" /> </item> </layer-list>
然后我们为SplashActivity创建一个主题:
<resources> <!-- 基本主题 --> <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> <item name="colorPrimary">@color/colorPrimary</item> <item name="colorPrimaryDark">@color/colorPrimaryDark</item> <item name="colorAccent">@color/colorAccent</item> </style> <!--纯色加启动图标的方案--> <style name="SplashThemeLayer" parent="AppTheme"> <item name="windowActionBar">false</item> <item name="windowNoTitle">true</item> <item name="android:windowBackground">@drawable/bg_splash_layer_list</item> </style> </resources>
最后为 SplashActivity设置主题为 SplashThemeLayer 在启动看看效果吧。
是不是实现了想要的效果?点击应用图标立即显示了我们的图标。
关于layer-list我们还可以拓展一下:例如加一个45°的线性渐变.
<?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item> <shape android:shape="rectangle"> <gradient android:angle="45" android:endColor="@color/colorPrimary" android:startColor="@color/colorAccent" /> </shape> </item> <item> <bitmap android:gravity="center" android:src="@mipmap/ic_launcher" /> </item> </layer-list>
看看效果:
2. 使用背景图片
前面的第一种方式是使用纯色背景 + 启动图标,这种方式肯定是不满足我们的产品经理的,他们要的是 个性化 的页面。
使用背景图片也是很简单的,只需要在them将我们之前的drawable替换成我们的图片即可:
<!--使用图片的方案--> <style name="SplashThemeImage" parent="AppTheme"> <item name="windowActionBar">false</item> <item name="windowNoTitle">true</item> <item name="android:windowBackground">@mipmap/icon_splish</item> <!--沉浸--> <item name="android:windowTranslucentStatus">true</item> </style>
需要注意的是:Splash页面的背景颜色需要设置为透明 #00000000,不要设置其他背景,否则会导致图片的伸缩变形。
看看启动效果吧:

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。
持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。
转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。
- 上一篇
图书推荐:Kotlin从入门到进阶实战
图片发自简书App 《Kotlin从入门到进阶实战》从Kotlin 语言的基础语法讲起,逐步深入到Kotlin进阶实战,并在最后配合项目实战案例,重点介绍了使用Kotlin+Spring Boot进行服务端开发和使用Kotlin进行Android应用程序开发的内容,让读者不但可以系统地学习Kotlin编程的相关知识,而且还能对Kotlin应用开发有更为深入的理解。 本书分为14章,涵盖的主要内容有Kotlin简介,Kotlin语法基础,类型系统与可空类型,类与面向对象编程,函数与函数式编程,扩展函数与属性,集合类,泛型,文件I/O操作、正则表达式与多线程,使用Kotlin创建DSL,运算符重载与约定,元编程、注解与反射,Kotlin集成Spring Boot服务端开发,使用Kotlin进行Android开发。 本书内容通俗易懂,案例丰富,实用性强,特别适合Kotlin语言的入门读者和进阶读者阅读,也适合Android程序员、Java程序员等其他编程爱好者阅读,还适合作为相关培训机构的教材。 目录 目 录 第1章 Kotlin是什么 1 1.1 初识Kotlin 1 1.2 语言特性 2...
- 下一篇
我要做 Android 之消息机制
Android的消息机制指的是Handler的运行机制,本篇将总结Handler机制的相关知识点: 消息机制概述 消息机制分析 1.消息机制概述 a.作用:跨线程通信。 b.常用场景:当子线程中进行耗时操作后需要更新UI时,通过Handler将有关UI的操作切换到主线程中执行。 系统不建议在子线程访问UI的原因:UI控件非线程安全,在多线程中并发访问可能会导致UI控件处于不可预期的状态。而不对UI控件的访问加上锁机制的原因有: 上锁会让UI控件变得复杂和低效 上锁后会阻塞某些进程的执行 c.四要素: Message(消息):需要被传递的消息,其中包含了消息ID,消息处理对象以及处理的数据等,由MessageQueue统一列队,最终由Handler处理。 MessageQueue(消息队列):用来存放Handler发送过来的消息,内部通过单链表的数据结构来维护消息列表,等待Looper的抽取。 Handler(处理者) :负责Message的发送及处理。 Handler.sendMessage():向消息池发送各种消息事件。 Handler.handleMessage() :处理相应的消...
相关文章
文章评论
共有0条评论来说两句吧...
文章二维码
点击排行
推荐阅读
最新文章
- Windows10,CentOS7,CentOS8安装MongoDB4.0.16
- Windows10,CentOS7,CentOS8安装Nodejs环境
- CentOS8编译安装MySQL8.0.19
- Linux系统CentOS6、CentOS7手动修改IP地址
- CentOS8,CentOS7,CentOS6编译安装Redis5.0.7
- Docker快速安装Oracle11G,搭建oracle11g学习环境
- Red5直播服务器,属于Java语言的直播服务器
- SpringBoot2整合Redis,开启缓存,提高访问速度
- CentOS7,8上快速安装Gitea,搭建Git服务器
- SpringBoot2配置默认Tomcat设置,开启更多高级功能