1. 程式人生 > >如何快速啟動android app

如何快速啟動android app

近日在開發過程中,發現每次點選app從桌面啟動都有一個在桌面明顯的等待時間,機型越低端的越明顯,冷啟動優化看來已經勢在必行。

1.冷啟動相關優化點:

生命週期內減少耗時操作

Application:attachBaseContext():

這個方法中一般雷區主要都在這句程式碼上,因為在Android 5.0(API 21) 以下會存在65535方法數分包的問題,當dex過大時會導致Application啟動慢, ANR或者ClassNotFound等異常,關於分包解決和優化方案網上一堆就不在做贅述了。

Application:onCreate()

這個方法是需要重點優化的,因為大家的第三方外掛初始化一般都會放在這裡,在Application初始化做繁重的東西會嚴重阻塞app啟動(DiskIO,網路請求等)。以下是我們第三方外掛初始化的耗時:
針對於解決第三方外掛初始化耗時方案一般是:
1.SDK分優先順序載入,非必要SDK由懶載入實現。
2.可以多執行緒初始化的sdk由多執行緒方式來進行初始化。
MainActiviity:onCreate()
同上一樣,儘量不要在此佈局做一些耗時的操作或者呈現一些過於複雜的佈局。在具體分析自己的app時發現onCreate中有這樣一行程式碼:
其作用是希望使用者在開啟時,一定能看見Splash的畫面,主動延遲了1s載入。這裡其實有更好的解決辦法處理,則是把跳轉MainPage的方法放在onResume中而不是放在onCreate中。因為Android系統中onResume一定是處於可見可互動的狀態,使用者一定能看見SplashActivity再去跳轉,由系統生命週期決定,而不是固定的等待1s,此處優化後啟動速度又提升了500ms。所以建議大家以後還是遵循生命週期去做一些事情,儘量別進行人為延遲阻塞。

2. 避免冷啟動

App啟動方式一般有3種:

  • ColdStart ——冷啟動:

此種方式最為耗時,一般是因為程序被幹掉,系統需要重新fork程序進行一系列初始化。

  • WarmStart ——暖啟動

比ColdStart稍快,因為app的所有Activities還常駐在記憶體中,並沒有被殺掉,所做的只是把app從後臺提到前臺來展示,並不需要重走初始化一系列行為,減少了物件初始化、佈局載入等工作。但其行為表現與冷啟動一致,是會displays a blank screen直到App渲染activity。這個blank screen後面會解釋。

  • LukeWarm Start——熱啟動

啟動方式最快,類似於返回鍵退出應用又立即進入的那種行為。
優化方案:
既然冷啟動那麼慢,我們就在非使用者主動kill程序或系統通知kill程序的其他情況下不再主動退出程序。那答案很簡單了,就是在位於Activity棧底activity中Hook其返回鍵行為,保證使用者點選返回鍵後不再退出app。在我們App裡位於我們棧底的一定是我們的MainActivity,因為一系統行為都是由其向下衍生的。所以只需在onBackPressed()方法中加入以下幾句話:moveTaskToBack(true);
moveTaskToBack:作用是不再Finish到此Activity,僅僅是把它放到後臺隱藏。類似於使用者主動觸發系統Home鍵的效果。

3.WindowBackGround——脫下秒開的最後一層薄絲襪

經過上面一頓操作後,我發現然並卵!!!啟動速度是提升了,但是App一點選還是會在桌面停頓一下。哇呀~很難受~細細思考了一下,一個APP啟動無論如何都是會新Fork程序,難道就是這個問題導致其在桌面上停頓一會兒?那其他app又是怎麼做到秒開的呢?在AndroidDeveloper的Launch-Time Performance有這麼一句話:
這裡寫圖片描述

其實在建立App程序時,android系統會為你立即顯示一個background window,然後再去建立app程序,當app完成first draw時,會立即由你的MainActivity(即預設啟動的Activity)替換掉它。這裡的background window就是上文WarmStart中提到的blank screen。謎底到此解開所謂的秒開原來就是視覺欺騙。。。所以說有人給你說他只是僅僅是優化生命週期內初始化程式碼達到秒開都是扯淡。但不得不承認這樣使用者體驗大大的提升了,一點選launcher就渲染好一個背景圖片,給使用者一種已經啟動的感覺,前面做的一系列優化,不過為了讓使用者少看一會兒系統給渲染的black window。

那為什麼我們的APP會出現在系統桌面上停留一會,而不是渲染背景圖呢?原來在專案建立時,系統會為launcherActivity默認了一個LightTheme,這樣就會導致App點選啟動後會白屏一段時間然後展示自己的Activity,為了解決白屏的問題把theme主題換成透明的就像下面
這裡寫圖片描述
但其實這樣雖然解決了白屏的問題,但是就會出現上文所說的,點選後停留在桌面一會兒,直至MainActivity渲染出來。這是大部分App的做法,但並不是最佳解決方案。

WindowBackground最佳解決方案:

應該由windowBackground此屬性作為你的品牌推廣頁或者logo頁,如果你的SplashActivity完全不需要做任何初始化,只是希望有個閃屏頁,完全可以由windowBackground來滿足。

a.設定自定義帶windowBackground的Theme

這裡寫圖片描述
前兩行程式碼是設定Theme不透明並且預設渲染的背景圖是我們必看影視閃屏頁的圖片。

windowBackground:關鍵,主要設定你想要的背景圖或者是動態自繪的drawable皆行,這個檢視會在你冷啟動時渲染給使用者過渡看。

windowFullscreen:全屏展示,免得頂部狀態列顯現顏色不一致過於脫節和突兀

b. 為你的launcher Activity設定你的啟動Theme

這裡寫圖片描述

c.在Launch Activity啟動後再把主題設定回自己的AppTheme

這裡寫圖片描述
此時你的App就能完成秒開了!

4.如果用到SharePreference,儘量在非同步執行緒中操作

5.減少佈局的層次,並且生命週期回撥的方法中儘量減少耗時的操作