本项目演示使用multidex时如何精确控制每个dex文件中所包含的类。
针对方法数超出( 65K Methods Issue )和 Android 2.3 的LinearAlloc问题,其中一个解决方案是使用multidex技术, 并需要控制主dex文件中的方法数(也就是需要控制哪些类出现在主dex文件中)。
Note
|
目前仅支持两个dex文件,即: classes.dex 和 classes2.dex |
Warning
|
最新发布的 Android Gradle v1.5.0 已经移除了dex task( Transform API ),本项目中的技术方案已经失效,需要重新研究并更新。 |
拷贝如下配置到你的app/build.gradle文件中,并做必要的修改:
afterEvaluate {
println "afterEvaluate"
tasks.matching {
it.name.startsWith('dex')
}.each { dx ->
println "dex task found: " + dx.name
dx.doFirst {
def creatorJarFile = 'MultiDexCreator.jar'
def secondaryDexClassesRules = 'secondaryDexClassesRules.txt'
def mainDexClassesListFile = project.buildDir.absolutePath + '/outputs/mainDexClassesList.txt'
def secondaryDexClassesListFile = project.buildDir.absolutePath + '/outputs/secondaryDexClassesList.txt'
def classesProguardJarFile
def proguardMappingFile
if (dx.name.equals('dexDebug')) {
classesProguardJarFile = 'build/intermediates/classes-proguard/debug/classes.jar'
proguardMappingFile = 'build/outputs/mapping/debug/mapping.txt'
} else if (dx.name.equals('dexRelease')) {
classesProguardJarFile = 'build/intermediates/classes-proguard/release/classes.jar'
proguardMappingFile = 'build/outputs/mapping/release/mapping.txt'
} else {
println "skip multi dex for task: " + dx.name
return
}
println "Generating main dex classes list file..."
exec {
executable = 'java'
args = ["-jar", creatorJarFile, classesProguardJarFile, proguardMappingFile,
secondaryDexClassesRules, mainDexClassesListFile, secondaryDexClassesListFile]
}
def file = new File(mainDexClassesListFile)
if (file.exists()) {
println "Add additional parameters for multi dex"
if (additionalParameters == null) {
additionalParameters = []
}
additionalParameters += '--multi-dex'
additionalParameters += '--main-dex-list=' + mainDexClassesListFile
additionalParameters += '--minimal-main-dex'
}
}
}
}
在dex规则文件“app/secondaryDexClassesRules.txt”中, 指定了被放置到第二个dex文件中的类的规则。
当前支持两类规则:
规则 | 问题描述 | 示例 | 说明 |
---|---|---|---|
jar |
jar: <jar path> |
jar: libs/android-lib.jar |
jar文件目录为相对目录 |
class |
class: <class pattern> |
class: android/support/v4/.* |
类的文件路径的Java正规表达式 |
一个规则文件示例:
# This file contains the classes rules for the secondary dex.
# Only one rule should be specified per line.
jar: libs/android-lib.jar
class: android/support/v4/.*
在编译结束后,请检查在生成mainDexClassesList.txt文件时的gradle输出, 查看是否有异常发生。
如果前一步骤没有异常,可进一步通过如下命令检查multidex是否正常工作:
-
ll app/build/intermediates/dex/release/
-
unzip -l app/build/outputs/apk/app-release.apk | grep classes
-
less app/build/outputs/mainDexClassesList.txt(为了便于查看,可以启用-dontobfuscate)
-
less app/build/outputs/secondaryDexClassesList.txt(为了便于查看,可以启用-dontobfuscate)