APK拆分配置

虽然你应该尽可能建立一个单一的APK来支持所有的目标设备,这可能会导致用一个非常大的APK处理支持多个屏幕密度应用二进制接口(ABIs)。 减少APK大小的一种方法是创建多个APK,其中包含特定屏幕密度或ABI的文件。

Gradle使用APK拆分来创建单独的APK,这些APK仅包含特定于每个密度或ABI的代码和资源。 本页介绍如何配置构建来完成APK拆分。 如果您需要创建不基于屏幕密度或ABI的不同版本的应用程序,您可以改用构建变体

APK拆分配置


要启用APK拆分,请在模块级build.gradle文件中添加一个splits {}块。 在split {}块中,提供一个density {}指定Gradle应如何生成每个密度的APK,或者一个 abi {}指定Gradle应如何生成每个ABI的APK。 您可以提供密度和ABI块,构建系统将为每个密度和ABI组合创建一个拆分APK。

配置APK拆分的密度

要为不同的屏幕密度创建单独的APK,请在split {}块中添加density {}块。 在您的density {}块中,提供所需的屏幕密度和兼容的屏幕尺寸的列表。 只有在每个APK的清单中需要特定的<compatible-screens>元素时,才能使用兼容的屏幕尺寸列表。

以下Gradle DSL选项用于配置密度APK拆分:

enable

如果将此元素设置为true,Gradle会根据您定义的屏幕密度生成APK分割。 默认值为false。

exclude

指定一个逗号分隔的密度列表,Gradle不应为其生成单独的APK。 如果您想为大多数密度生成APK,但需要排除应用不支持的几个密度,请使用exclude。

reset()

清除默认的屏幕密度列表。 仅当与include元素组合使用时才能指定要添加的密度。 以下代码片段将密度列表设置为ldpixxhdpi,方法是调用reset()清除列表,然后使用include

reset()  // clear the default list from all densities to no densities
include "ldpi", "xxhdpi" // specify the two densities we want to generate APKs for
  • 1
  • 2

include

指定Gradle应生成APK的密度的逗号分隔列表。 只能与reset()结合使用以指定密度的精确列表。

compatibleScreens

指定兼容的屏幕尺寸用逗号分隔的列表。 这将在每个拆分APK的清单中注入匹配的<compatible-screens>节点。 这个可选设置提供了在同一个build.gradle部分管理屏幕密度和屏幕大小的方便方法,但是使用<compatible-screens> 将限制您的应用程序将使用的设备类型。 有关支持不同屏幕大小的其他方法,请参阅支持多个屏幕


因为基于屏幕密度的拆分的每个APK都包含一个<compatible-screens>标签,其中包含APK支持的屏幕类型的具体限制,即使您发布了多个APK,一些新设备也不会与您的多个APK过滤器匹配。 因此,Gradle总是生成一个额外的通用APK,包含所有屏幕密度的资源,并且不包括<compatible-screens>标记。 您应该发布此通用APK以及拆分APK,以便为与APK不匹配的设备提供后备方案(使用<compatible-screens>标记)。

以下示例为支持的屏幕范围中列出的每个屏幕密度生成单独的APK,除了ldpixxhdpixxxhdpi。 这是通过使用exclude从所有密度的默认列表中删除三个密度来完成的:

android {
  ...
  splits {

    // Configures screen density split settings
    density {

      // Enables density APK splits
      enable true

      // Specifies a list of screen densities Gradle should not create APK splits for
      exclude "ldpi", "xxhdpi", "xxxhdpi"

      // Specifies a list of compatible screen size settings for the manifest
      compatibleScreens 'small', 'normal', 'large', 'xlarge'
    }
  }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

有关密度名称和屏幕尺寸名称的列表,请参阅如何支持多屏幕。 有关将应用程序分发到特定屏幕类型和设备的详细信息,请参阅分发到特定屏幕

配置APK拆分的ABI

要为不同的ABI创建单独的APK,请在您的split {}块中添加一个abi {}块。 在您的abi {}块中,提供所需ABI的列表。

以下Gradle DSL选项用于配置每ABI APK拆分:

enable

如果将此元素设置为true,Gradle会根据您定义的ABI生成APK拆分。 默认值为false

exclude

指定一个逗号分隔的ABI列表,Gradle不应为其生成单独的APK。 如果您想为大多数ABI生成APK,但需要排除应用程序不支持的几个ABI,请使用exclude

reset()

清除ABI的默认列表。 仅当与include元素组合使用时才指定要添加的ABI。 以下代码片段通过调用reset()将ABI列表设置为x86mips,以清除列表,然后使用include

reset()  // clear the default list from all ABIs to no ABIs
include "x86", "mips" // specify the two ABIs we want to generate APKs for
  • 1
  • 2

include

指定Gradle应为其生成APK的ABI的逗号分隔列表。 只能与reset()结合使用以指定ABI的精确列表。

universalApk

如果为true,Gradle会生成一个通用APK以及拆分APK。 通用APK包含单个APK中所有ABI的代码和资源。 默认值为false。 请注意,此选项仅适用于ABI APK拆分。 密度APK分裂总是生成一个通用的APK,包含所有屏幕密度的代码和资源。


以下示例为每个ABI生成单独的APK:x86,armeabi-v7a和mips。 这是通过使用reset()开始一个空列表的ABI,然后是包含三个ABI列表,每个都将获得一个APK:

android {
  ...
  splits {

    // Configures screen ABI split settings
    abi {

      // Enable ABI APK splits
      enable true

      // By default all ABIs are included, so use reset() and include to specify that we only
      // want APKs for x86, armeabi-v7a, and mips

      // Resets the list of ABIs that Gradle should create APKs for to none
      reset()

      // Specifies a list of ABIs that Gradle should create APKs for
      include "x86", "armeabi-v7a", "mips"

      // Specify that we do not want to also generate a universal APK that includes all ABIs
      universalApk false
    }
  }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24

有关支持的ABI的列表,请参阅支持的ABI

配置APK拆分的版本控制

默认情况下,当Gradle生成APK拆分时,每个APK将具有相同的版本信息,如模块级build.gradle文件中指定的。 由于Google Play商店不允许具有相同版本信息的同一应用程序使用多个APK,因此您需要确保每个split APK都有自己独特的versionCode,然后才能上传到Play商店。

您可以配置模块级build.gradle文件以覆盖每个拆分APK的versionCode。 为APK拆分中使用的每个ABI和密度分配唯一的数值,然后使用将·defaultConfig.versionCode·与分配给密度或ABI的数值组合的值覆盖输出版本代码。

以下示例创建一个映射,为每个用于APK拆分的ABI分配唯一的数值。 使用此映射,创建一个每拆分APK版本代码,其将映射的ABI值与defaultConfig.versionCode组合。 在此示例中,x86 ABI的split APK将获得304的versionCode。如果defaultConfig.versionCode重复为5,Gradle将为x86拆分APK分配一个versionCode为305。

android {
  ...
  defaultConfig {
    ...
    versionCode 4
  }
  splits {
    ...
  }
}

// map for the version code that gives each ABI a value
ext.versionCodes = ['armeabi-v7a':1, mips:2, x86:3]

// For each APK output variant, override versionCode with a combination of
// ABI APK value * 100 + defaultConfig.versionCode
android.applicationVariants.all { variant ->
    // assign different version code for each output
    variant.outputs.each { output ->
        output.versionCodeOverride =
                project.versionCodes.get(output.getFilter(OutputFile.ABI)) * 100
                + android.defaultConfig.versionCode
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24

有关备用版本代码方案的更多示例,请参阅分配版本代码

构建APK拆分


配置模块级build.gradle文件以构建APK拆分后,请在Project 窗格单击Build > Build APK为当前选定的模块构建所有APK。 Gradle为每个密度或ABI创建APK在项目的build/outputs/apk/目录下。

Gradle为每个配置的密度或ABI拆分构建一个APK。 如果您为密度和ABI启用了分割,Gradle将为每个密度和ABI组合创建一个APK。 例如,以下build.gradle代码段允许构建mdpi和hdpi密度的APK拆分,以及x86和mips ABI:

...
  splits {
    density {
      enable true
      reset()
      include "mdpi", "hdpi"
    }
    abi {
      enable true
      reset()
      include "x86", "mips"
    }
  }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

示例配置的输出将包括以下4个拆分APK: 
app-hdpiX86-release.apk: 仅包含hdpi density和x86 ABI的代码和资源。 
app-hdpiMips-release.apk: 仅包含hdpi密度和mips ABI的代码和资源。 
app-mdpiX86-release.apk: 仅包含mdpi密度和x86 ABI的代码和资源。 
app-mdpiMips-release.apk: 仅包含mdpi密度和mips ABI的代码和资源。

根据您如何配置APK拆分,Gradle还将生成一个通用APK,包含所有密度或ABI的代码和资源。 对于密度APK的拆分,Gradle将始终生成一个通用APK,包括所有密度的代码和资源,除了每个密度的APK。 对于ABI拆分,如果在build.gradle文件中的splits {}块的abi部分中指定universalApk true,Gradle只会生成包含所有ABI的代码和资源的APK。

APK文件名格式

对于APK拆分,Gradle使用APK文件名使用以下方案: 
modulename-screendensityABI-buildvariant.apk

方案组件是:

modulename

指定正在构建的模块名称。

screendensity

如果启用屏幕密度APK拆分,则指定APK的屏幕密度,例如“mdpi”。

ABI

如果启用ABI APK拆分,则指定APK的ABI,例如“x86”。 如果屏幕密度和ABI APK拆分都启用,Gradle将密度名称与ABI名称连接,例如“mdpiX86”。 如果为ABI APK分裂启用universalApk,Gradle使用“通用”作为通用APK文件名的ABI部分。

buildvariant

指定正在构建的构建变量,例如“debug”。


例如,对于mdpi屏幕密度启用APK拆分的“myApp”的调试版本将使用APK文件名myApp-mdpi-debug.apk。 发布版本的“myApp”的APK分裂已启用mdpi屏幕密度和x86 ABI将使用APK文件名myApp-mdpiX86-release.apk

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值