from:http://developer.android.com/google/play/publishing/multiple-apks.html
Multiple APK support is a feature on Google Play that allows you to publish different APKs for your application that are each targeted to different device configurations. Each APK is a complete and independent version of your application, but they share the same application listing on Google Play and must share the same package name and be signed with the same release key. This feature is useful for cases in which your application cannot reach all desired devices with a single APK.
Android-powered devices may differ in several ways and it’s important to the success of your application that you make it available to as many devices as possible. Android applications usually run on most compatible devices with a single APK, by supplying alternative resources for different configurations (for example, different layouts for different screen sizes) and the Android system selects the appropriate resources for the device at runtime. In a few cases, however, a single APK is unable to support all device configurations, because alternative resources make the APK file too big (greater than 50MB) or other technical challenges prevent a single APK from working on all devices.
Although we encourage you to develop and publish a single APKthat supports as many device configurations as possible, doing so is sometimes not possible. To help you publish your application for as many devices as possible, Google Play allows you to publish multiple APKs under the same application listing. Google Play then supplies each APK to the appropriate devices based on configuration support you’ve declared in the manifest file of each APK.
By publishing your application with multiple APKs, you can:
Currently, these are the only device characteristics that Google Play supports for publishing multiple APKs as the same application.
Note: You should generally use multiple APKs to support different device configurationsonly when your APK is too large (greater than 50MB) due to the alternative resources needed for different device configurations. Using a single APK to support different configurations is always the best practice, because it makes the path for application updates simple and clear for users (and also makes your life simpler by avoiding development and publishing complexity). Read the section below aboutUsing a Single APK Instead to consider your options before publishing multiple APKs.
Before you start publishing multiple APKs on Google Play, you must understand a few concepts regarding how the Google Play Developer Console works.
When editing your application, there are two buttons on the top-right side of the page. The first button is eitherPublish orUnpublish and the second button is always Save (but its behavior changes).
When your application is new or you have unpublished it from Google Play, the first button saysPublish. Clicking it will publish any APKs listed as Active, making them available on Google Play. Also while your application is new or unpublished, clickingSave will save any changes you’ve made, such as information added to the Product details and APKs you’ve uploaded, but nothing is made visible on Google Play—this allows you to save your changes and sign out of the Developer Console before deciding to publish.
Once you’ve published your application, the first button changes toUnpublish. Clicking it in this state unpublishes your application so that none of the APKs are available on Google Play. Also while published, the behavior of theSave button is different. In this state, clicking Savenot only saves all your changes, but also publishes them to Google Play. For example, if you’ve already published your application and then make changes to your product details or activate new APKs, clicking Savemakes all those changes live on Google Play.
Before you can publish your application (whether publishing one or multiple APKs), you must “activate” your APK(s) from theAPK files tab. When you activate an APK, it moves into the list ofActive APKs. This list allows you to preview which APK(s) you’re about to publish.
If there are no errors, any “active” APK will be published to Google Play when you click thePublish button (if the application is unpublished) or when you click theSave button (if the application is already published).
The Google Play Developer Console provides two modes for managing the APKs associated with your application:simple mode and advanced mode. You can switch between these by clicking the link at the top-right corner of theAPK files tab.
Simple mode is the traditional way to publish an application, using one APK at a time. In simple mode, only one APK can be activated at a time. If you upload a new APK to update the application, clicking “Activate” on the new APK deactivates the currently active APK (you must then click Save to publish the new APK).
Advanced mode allows you to activate and publish multiple APKs that are each designed for a specific set of device configurations. However, there are several rules based on the manifest declarations in each APK that determine whether you’re allowed to activate each APK along with others. When you activate an APK and it violates one of the rules, you will receive an error or warning message. If it’s an error, you cannot publish until you resolve the problem; if it’s a warning, you can publish the activated APKs, but there might be unintended consequences as to whether your application is available for different devices. These rules are discussed more below.
The concept for using multiple APKs on Google Play is that you have just one entry in Google Play for your application, but different devices might download a different APK. This means that:
To publish multiple APKs for the same application, you must enable Advanced mode in your application’sAPK files tab (as discussed in the previous section). Once in advanced mode, you can upload, activate, then publish multiple APKs for the same application. The following sections describe more about how it works.
Which devices receive each APK is determined by Google Play filters that are specified by elements in the manifest file of each APK. However, Google Play allows you to publish multiple APKs only when each APK uses filters to support a variation of the following device characteristics:
<supports-gl-texture>
element(s).For example, when developing a game that uses OpenGL ES, you can provide one APK for devices that support ATI texture compression and a separate APK for devices that support PowerVR compression (among many others).<supports-screens>
or <compatible-screens>
element. You should never use both elements and you should use only<supports-screens>
when possible.For example, you can provide one APK that supports small and normal size screens and another APK that supports large and xlarge screens. Note: The Android system provides strong support for applications to support all screen configurations with a single APK. You should avoid creating multiple APKs to support different screens unless absolutely necessary and instead follow the guide to Supporting Multiple Screens so that your application is flexible and can adapt to all screen configurations with a single APK.
Caution: By default, all screen size attributes in the<supports-screens>
element are “true” if you do not declare them otherwise. However, because theandroid:xlargeScreens
attribute was added in Android 2.3 (API level 9), Google Play will assume that it is “false” if your application does not set eitherandroid:minSdkVersion
or android:targetSdkVersion
to “9” or higher.
Caution: You should not combine both <supports-screens>
and <compatible-screens>
elements in your manifest file. Using both increases the chances that you’ll introduce an error due to conflicts between them. For help deciding which to use, readDistributing to Specific Screens. If you can’t avoid using both, be aware that for any conflicts in agreement between a given size, “false” will win.
<uses-feature>
element(s).For example, you can provide one APK for devices that support multitouch and another APK for devices that do not support multitouch. SeeFeatures Reference for a list of features supported by the platform.<uses-sdk>
element. You can use both the android:minSdkVersion
and android:maxSdkVersion
attributes to specify support for different API levels.For example, you can publish your application with one APK that supports API levels 4 – 7 (Android 1.6 – 2.1)—using only APIs available since API level 4 or lower—and another APK that supports API levels 8 and above (Android 2.2+)—using APIs available since API level 8 or lower.
Note:
android:minSdkVersion
value must have a higher android:versionCode
value. This is also true if two APKs overlap their device support based on a different supported filter. This ensures that when a device receives a system update, Google Play can offer the user an update for your application (because updates are based on an increase in the app version code). This requirement is described further in the section below aboutRules for multiple APKs.android:maxSdkVersion
in general, because as long as you’ve properly developed your application with public APIs, it is always compatible with future versions of Android. If you want to publish a different APK for higher API levels, you still do not need to specify the maximum version, because if the android:minSdkVersion
is "4"
in one APK and "8"
in another, devices that support API level 8 or higher will always receive the second APK (because it’s version code is higher, as per the previous note).Application.mk
file) when using the Android NDK.Other manifest elements that enable Google Play filters—but are not listed above—are still applied for each APK as usual. However, Google Play does not allow you to publish separate APKs based on variations of those device characteristics. Thus, you cannot publish multiple APKs if the above listed filters are the same for each APK (but the APKs differ based on other characteristics in the manifest or APK). For example, you cannot provide different APKs that differ purely on the<uses-configuration>
characteristics.
Before you enable advanced mode to publish multiple APKs for your application, you need to understand the following rules that define how publishing multiple APKs works:
android:versionCode
attribute.android:versionCode
).Note: The size of the version code increase is irrelevant; it simply needs to be larger in the version that supports higher API levels.
Here are some examples:
0400
, then an APK for API levels 8 and above (Android 2.2+) must be 0401
or greater. In this case, the API level is the only supported filter used, so the version codesmust increase in correlation with the API level support for each APK, so that users get an update when they receive a system update.Failure to abide by the above rules results in an error on the Google Play Developer Console when you activate your APKs—you will be unable to publish your application until you resolve the error.
There are other conflicts that might occur when you activate your APKs, but which will result in warnings rather than errors. Warnings can be caused by the following:
Note: If you’re creating separate APKs for different CPU architectures, be aware that an APK for ARMv5TE will overlap with an APK for ARMv7. That is, an APK designed for ARMv5TE is compatible with an ARMv7 device, but the reverse is not true (an APK with only the ARMv7 libraries is not compatible with an ARMv5TE device).
When such conflicts occur, you will see a warning message, but you can still publish your application.
Once you decide to publish multiple APKs, you probably need to create separate Android projects for each APK you intend to publish so that you can appropriately develop them separately. You can do this by simply duplicating your existing project and give it a new name. (Alternatively, you might use a build system that can output different resources—such as textures—based on the build configuration.)
Tip: One way to avoid duplicating large portions of your application code is to use alibrary project. A library project holds shared code and resources, which you can include in your actual application projects.
When creating multiple projects for the same application, it’s a good practice to identify each one with a name that indicates the device restrictions to be placed on the APK, so you can easily identify them. For example, “HelloWorld_8″ might be a good name for an application designed for API level 8 and above.
Note: All APKs you publish for the same applicationmust have the same package name and be signed with the same certificate key. Be sure you also understand each of theRules for multiple APKs.
Each APK for the same application must have a unique version code, specified by theandroid:versionCode
attribute. You must be careful about assigning version codes when publishing multiple APKs, because they must each be different, but in some cases, must or should be defined in a specific order, based on the configurations that each APK supports.
An APK that requires a higher API level must usually have a higher version code. For example, if you create two APKs to support different API levels, the APK for the higher API levels must have the higher version code. This ensures that if a device receives a system update that then qualifies it to install the APK for higher API levels, the user receives a notification to update the app. For more information about how this requirement applies, see the section above aboutRules for multiple APKs.
You should also consider how the order of version codes might affect which APK your users receive either due to overlap between coverage of different APKs or future changes you might make to your APKs.
For example, if you have different APKs based on screen size, such as one for small – normal and one for large – xlarge, but foresee a time when you will change the APKs to be one for small and one for normal – xlarge, then you should make the version code for the large – xlarge APK be higher. That way, a normal size device will receive the appropriate update when you make the change, because the version code increases from the existing APK to the new APK that now supports the device.
Also, when creating multiple APKs that differ based on support for different OpenGL texture compression formats, be aware that many devices support multiple formats. Because a device receives the APK with the highest version code when there is an overlap in coverage between two APKs, you should order the version codes among your APKs so that the APK with the preferred compression format has the highest version code. For example, you might want to perform separate builds for your app using PVRTC, ATITC, and ETC1 compression formats. If you prefer these formats in this exact order, then the APK that uses PVRTC should have the highest version code, the APK that uses ATITC has a lower version code, and the version with ETC1 has the lowest. Thus, if a device supports both PVRTC and ETC1, it receives the APK with PVRTC, because it has the highest version code.
In order to allow different APKs to update their version codes independent of others (for example, when you fix a bug in only one APK, so don’t need to update all APKs), you should use a scheme for your version codes that provides sufficient room between each APK so that you can increase the code in one without requiring an increase in others. You should also include your actual version name in the code (that is, the user visible version assigned toandroid:versionName
), so that it’s easy for you to associate the version code and version name.
Note: When you increase the version code for an APK, Google Play will prompt users of the previous version to update the application. Thus, to avoid unnecessary updates, you should not increase the version code for APKs that do not actually include changes.
We suggest using a version code with at least 7 digits: integers that represent the supported configurations are in the higher order bits, and the version name (fromandroid:versionName
) is in the lower order bits. For example, when the application version name is 3.1.0, version codes for an API level 4 APK and an API level 11 APK would be something like 0400310 and 1100310, respectively. The first two digits are reserved for the API Level (4 and 11, respectively), the middle two digits are for either screen sizes or GL texture formats (not used in these examples), and the last three digits are for the application’s version name (3.1.0). Figure 1 shows two examples that split based on both the platform version (API Level) and screen size.
This scheme for version codes is just a suggestion for how you should establish a pattern that is scalable as your application evolves. In particular, this scheme doesn’t demonstrate a solution for identifying different texture compression formats. One option might be to define your own table that specifies a different integer to each of the different compression formats your application supports (for example, 1 might correspond to ETC1 and 2 is ATITC, and so on).
You can use any scheme you want, but you should carefully consider how future versions of your application will need to increase their version codes and how devices can receive updates when either the device configuration changes (for example, due to a system update) or when you modify the configuration support for one or several of the APKs.
Creating multiple APKs for your application is not the normal procedure for publishing an application on Google Play. In most cases, you should be able to publish your application to most users with a single APK and we encourage that you do so. When you encounter a situation in which using a single APK becomes difficult, you should carefully consider all your options before deciding to publish multiple APKs.
First of all, there are a few key benefits to developing a single APK that supports all devices:
The following sections describe some of the other options you should use to support multiple device configurations before deciding to publish multiple APKs.
To support multiple types of GL textures with a single APK, your application should query the GL texture formats supported on the device and then use the appropriate resources or download them from a web server. For example, in order to keep the size of your APK small, you can query the device’s support for different GL texture formats when the application starts for the first time and then download only the textures you need for that device.
For maximum performance and compatibility, your application should use ETC1 textures wherever it doesn’t impact the visual quality. However, because ETC1 cannot deal with images that have drastic chroma changes, such as line art and (most) text, and doesn’t support alpha, it may not the best format for all textures.
With a single APK, you should try to use ETC1 textures and uncompressed textures whenever reasonable, and consider the use of PVRTC, ATITC, or DXTC as a last resort when ETC1 does not suffice.
Here’s an example query for supported texture compression formats from inside aGLSurfaceView.Renderer
:
public void onSurfaceChanged(GL10 gl, int w, int h) { String extensions = gl.glGetString(GL10.GL_EXTENSIONS); Log.d("ExampleActivity", extensions); }
This returns a string that lists each of the supported compression formats.
Unless your APK file exceeds the Google Play size limit of 50MB, supporting multiple screens should always be done with a single APK. Since Android 1.6, the Android system manages most of the work required for your application to run successfully on a variety of screen sizes and densities.
To further optimize your application for different screen sizes and densities, you should providealternative resources such as bitmap drawables at different resolutions and different layout designs for different screen sizes.
For more information about how to support multiple screens with a single APK, readSupporting Multiple Screens.
Additionally, you should consider using a support library from the Compatibility Package so that you can addFragments to your activity designs when running on larger screens such as tablets.
If you want to support as many versions of the Android platform as possible, you should use only APIs available in the lowest reasonable version. For example, your application may not require APIs newer than Android 2.1 (API Level 7), which makes an application available to over 95% of Android-powered devices (as indicated by the Platform Versions dashboard).
By using a support library from the Compatibility Package, you can also use APIs from some of the latest versions (such as Android 3.0) while still supporting versions as low as Android 1.6. The support library includes APIs forFragments, Loaders, and more. Using the fragment APIs is particularly valuable so that you can optimize your user interface for large devices such as tablets.
Alternatively, if you want to use some APIs that are available only in newer versions of Android (which your application can still function without), then you should consider using reflection. By using reflection, you can check whether the current device supports certain APIs. If the APIs are not available, your application can gracefully disable and hide the feature.
Another way to use new APIs only when running on a version that supports them is to check the API level of the current device. That is, you can query the value ofSDK_INT
and create different code paths depending on the API level supported by the device. For example:
if (android.os.Build.VERSION.SDK_INT >= 11) { // Use APIs supported by API level 11 (Android 3.0) and up } else { // Do something different to support older versions }
When using the Android NDK, you can create a single APK that supports multiple CPU architectures by declaring each of the desired architectures with theAPP_ABI
variable in the Application.mk
file.
For example, here’s an Application.mk
file that declares support for three different CPU architectures:
APP_ABI := armeabi armeabi-v7a mips APP_PLATFORM := android-9