APK瘦身方向:
-
代碼方面
除必要的封裝外铲敛,還可以通過混淆壓縮release { minifyEnabled true // 是否混淆 //去除無效的文件,但目前還不支持移除app和libray中的values目錄下的資源文件(strings,dimensions,styles,colors)会钝,這些我//們可以使用Splits解決 shrinkResources true // 混淆的配置文件 proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' }
lib
輕量級(jí)lib是首選伐蒋;so本地庫
主流的架構(gòu)都是arm的;-
資源文件(圖片迁酸,音頻先鱼,字體等)
a. 通過Lint工具掃描代碼中沒有使用到的靜態(tài)資源,但不包括assets中的文件奸鬓,方法:在As的 Analyze –>Inspect Code,并合理刪除無用代碼型型;b. 圖片處理及優(yōu)化方面
- 必要時(shí)可采用圖片旋轉(zhuǎn)方式代替添加新的圖片:
<rotate xmlns:android="http://schemas.android.com/apk/res/android" android:drawable="@drawable/blue_btn_icon" android:fromDegrees="180" android:pivotX="50%" android:pivotY="50%" android:toDegrees="180" />
- 在某些時(shí)候jpeg可以減少圖片的體積(無alpha屬性);
- 9.png的圖片全蝶,特點(diǎn)是可拉伸闹蒜;
- 在不降低圖片效果、保證APK顯示效果的前提下縮小圖片-如使用tinypng優(yōu)化大部分圖片資源(缺點(diǎn):對(duì)有過渡效果(帶alpha值)的圖片不能使用抑淫,會(huì)造成圖片失真绷落,這種圖片可以將png圖片轉(zhuǎn)換為webP格式(軟件:iSparta));
- 用svg替換原來圖片能立刻將圖片減少始苇,而且不用考慮分辨率適配的問題砌烁。但在As中需要vectorDrawable配合。
d. 清除你的無用的代碼以及資源
查詢到的都是對(duì)當(dāng)前項(xiàng)目無貢獻(xiàn)的資源: Analyze –>Run Inspection by name –> unused resources
-
分析得到?jīng)]有用的類及方法: Analyze –>Run Inspection by name –> unused declaration
注意:上述兩個(gè)方法站宗,查詢到的文件中也包括了一些需要保留的資源佩抹,手動(dòng)刪除前還是需要分析下的(資源使用查詢:alt+F7,刪除文件:alt+Del)
-
指定資源配置
android { ...... productFlavors { cs { resConfigs "zh","xxhdpi" //指定資源配置 ext.dexOptions = false //調(diào)試構(gòu)建停用 Crashlytics ext.alwaysUpdateBuildId = false //阻止 Crashlytics 不斷更新其構(gòu)建 ID } } }
注意:
無論時(shí)尺寸適配還是語言適配,都需要有values這個(gè)文件夾笨奠,并且values-zh或values-400x320中的所有文件管呵,在values中也"必須也要有"梳毙,否則會(huì)報(bào)錯(cuò)
e. 混淆配置參考:http://www.reibang.com/writer#/notebooks/9538856/notes/28822848
- 必要時(shí)可采用圖片旋轉(zhuǎn)方式代替添加新的圖片:
apk打包
-
配置產(chǎn)品風(fēng)味實(shí)現(xiàn)多個(gè)變體:
變體可以理解為apk變體,多少種變體就是多少種apk類型捐下;公式:
變體數(shù) = 被標(biāo)記為不同種維度的產(chǎn)品風(fēng)味個(gè)數(shù)的乘積 * 構(gòu)建類型個(gè)數(shù) - 過濾變體構(gòu)建類型個(gè)數(shù)
(如下邊例子的 變體數(shù) = 232 - 12 = 10)flavorDimensions "mode","suffix" //產(chǎn)品風(fēng)味組(也稱風(fēng)味維度账锹,其中有兩種維度,優(yōu)先級(jí)前高后低,不同維度的產(chǎn)品風(fēng)味會(huì)自由組合) productFlavors { //產(chǎn)品風(fēng)味配置標(biāo)志 cancell{ //產(chǎn)品風(fēng)味名 dimension "suffix" versionNameSuffix "-csss" } dess{ //產(chǎn)品風(fēng)味名 dimension "suffix" versionNameSuffix "-devss" } cs { //產(chǎn)品風(fēng)味名 dimension "mode" resConfigs "zh","en","xxhdpi" ext.dexOptions = false //調(diào)試構(gòu)建停用 Crashlytics ext.alwaysUpdateBuildId = false //阻止 Crashlytics 不斷更新其構(gòu)建 ID buildConfigField 'String', 'API_URL', "\"https://cs.XXX\"" buildConfigField 'String', 'WETCHAT_ID', "\"XXX\"" buildConfigField 'String', 'PAY_URL', "\"https://XXX\"" manifestPlaceholders = [JPUSH_APPKEY: "XXX", JPUSH_PKGNAME: "com.XXX.app", JPUSH_CHANNEL: "developer-default",UMENG_CHANNEL_VALUE: "cs"] } dev { //產(chǎn)品風(fēng)味名 dimension "mode" buildConfigField 'String', 'API_URL', "\"https://cs.XXX\"" buildConfigField 'String', 'WETCHAT_ID', "\"XXX\"" buildConfigField 'String', 'PAY_URL', "\"https://XXX\"" manifestPlaceholders = [JPUSH_APPKEY: "XXX", JPUSH_PKGNAME: "com.XXX.app", JPUSH_CHANNEL: "developer-default",UMENG_CHANNEL_VALUE: "dev"] } prod { //產(chǎn)品風(fēng)味名 dimension "mode" buildConfigField 'String', 'API_URL', "\"https://cs.XXX\"" buildConfigField 'String', 'WETCHAT_ID', "\"XXX\"" buildConfigField 'String', 'PAY_URL', "\"https://XXX\"" manifestPlaceholders = [JPUSH_APPKEY: "XXX", JPUSH_PKGNAME: "com.XXX.app", JPUSH_CHANNEL: "developer-default",UMENG_CHANNEL_VALUE: "prod"] } } //變體過濾器,可以過濾掉種變體,配置后在Build > Select Build Variant(或工具窗口欄中的 Build Variants)中坷襟,這些構(gòu)建變體將不會(huì)再顯示在下拉菜單中奸柬。 variantFilter { variant -> def names = variant.flavors*.name if (names.contains("cancell") && names.contains("cs")) { setIgnore(true) } } buildTypes { //構(gòu)建類型 debug { //構(gòu)建類型名 signingConfig signingConfigs.debug minifyEnabled false //混淆 zipAlignEnabled true //zipalign優(yōu)化 shrinkResources false //移除無用resources } release { //構(gòu)建類型名 signingConfig signingConfigs.release zipAlignEnabled true //zipalign優(yōu)化 minifyEnabled false shrinkResources false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } }
-
Splits構(gòu)建不同density和ABI 的APK:
android { ... splits { density { enable true exclude "ldpi", "tvdpi", "xxxhdpi" //不能與reset()一起使用 compatibleScreens 'small', 'normal', 'large', 'xlarge' } } android { ... splits { abi { enable true reset() include 'x86', 'armeabi-v7a', 'mips' //必須與reset()一起使用 universalApk true } } } 參數(shù)解析: enable: 啟用屏幕密度拆分機(jī)制 exclude: 默認(rèn)情況下所有屏幕密度都包括在內(nèi),你可以移除一些密度婴程。 include: 表示要包括哪些屏幕密度 reset(): 重置屏幕密度列表為只包含一個(gè)空字符串 (這能夠?qū)崿F(xiàn)廓奕,在與include一起使用時(shí)可以表示使用哪一個(gè)屏幕密度,而不是要忽略哪一些屏幕密度) compatibleScreens:表示兼容屏幕的列表档叔。這將會(huì)注入到manifest中匹配的 節(jié)點(diǎn)桌粉。這個(gè)設(shè)置是可選的。 universalApk:指示是否打包一個(gè)通用版本(包含所有的ABI)蹲蒲。默認(rèn)值為 false番甩。
-
其他
查看生產(chǎn)的apk各個(gè)資源占用情況:
a. 先要用As生產(chǎn)一個(gè)apk;
b. build-Analyze Apk(或者在生產(chǎn)apk時(shí)會(huì)有analyze提示);當(dāng)apk安裝不上問題解決:
如錯(cuò)誤信息:It is possible that this issue is resolved by uninstalling an existing version of the apk if it is present, and then re-installing.時(shí)侵贵,在手機(jī)上有沒有找到此應(yīng)用的應(yīng)用圖標(biāo)届搁,這也有可能是該應(yīng)用的某個(gè)模塊在手機(jī)上隱式安裝了,我們可以先查看工程中都有那些模塊(android庫模塊),記下這些模塊名稱窍育,再到手機(jī)的程序管理中去找卡睦,若是有則卸載即可;