Users often avoid downloading apps that seem too large, particularly in emerging markets where devices connect to often-spotty 2G and 3G networks or work on pay-by-the-byte plans. This article describes how to reduce your app's APK size, which enables more users to download your app.
Understand the APK Structure
Before discussing how to reduce the size of your app, it's helpful to understand the structure of an app's APK. An APK file consists of a ZIP archive that contains all the files that comprise your app. These files include Java class files, resource files, and a file containing compiled resources.
An APK contains the following directories:
- META-INF/: Contains the CERT.SF and CERT.RSA signature files, as well as the MANIFEST.MF manifest file.
- assets/: Contains the app's assets, which the app can retrieve using an AssetManager object.
- res/: Contains resources that aren't compiled into resources.arsc.
- lib/: Contains the compiled code that is specific to the software layer of a processor. This directory contains a subdirectory for each platform type, like armeabi, armeabi-v7a, arm64-v8a, x86, x86_64, and mips.
An APK also contains the following files. Among them, only AndroidManifest.xml is mandatory.
resources.arsc: Contains compiled resources. This file contains the XML content from all configurations of the res/values/ folder. The packaging tool extracts this XML content, compiles it to binary form, and archives the content. This content includes language strings and styles, as well as paths to content that is not included directly in the resources.arsc file, such as layout files and images.
classes.dex: Contains the classes compiled in the DEX file format understood by the Dalvik/ART virtual machine.
AndroidManifest.xml: Contains the core Android manifest file. This file lists the name, version, access rights, and referenced library files of the app. The file uses Android's binary XML format.
1. Reuse resources as much as possible :
Its first thing to keep in mind that you reuse resources like icons, backgrounds, button backgrounds as much as possible. Suppose you want same icon in different colours, then instead of having different .png file for different color of same icon you can use only one and you can change color using android:tint and android:tintMode attribute on Android 5.0 (API level 21) or above, for bellow Android versions ColorFilter can be used to change icon color dynamically.
<?xml version="1.0" encoding="utf-8"?>
<bitmap
xmlns:android="http://schemas.android.com/apk/res/android"
android:src="@drawable/ic_back"
android:tint="@color/white_tint"/>
or
ImageView imageView = (ImageView)convertView.findViewById(R.id.ic_home_black);
int color = Color.parseColor("#AE6118"); //The color u want
imageView.setColorFilter(color);
Also we can reuse some icon like if you want plus icon and also you need close icon you can rotate plus icon by 45% and reuse it as close icon, similarly you can do with arrows on arrow you can use as up, down, back, forward etc both statically or dynamically.
<?xml version="1.0" encoding="utf-8"?>
<rotate xmlns:android="http://schemas.android.com/apk/res/android"
android:drawable="@drawable/ic_arrow_expand"
android:fromDegrees="45"
android:pivotX="50%"
android:pivotY="50%"
android:toDegrees="45" />
Although layout files doesn't matters more but yes its good practice to extracts common part of layout and create layout and reuse it in other layouts using include. Its helps in maintaining consistency and also reduces no of lines in your code.
Define app_bar.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.AppBarLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:theme="@style/AppTheme.AppBarOverlay">
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="?attr/colorPrimary"
app:popupTheme="@style/AppTheme.PopupOverlay" />
</android.support.design.widget.AppBarLayout>
Reuse it in activities layout like
<include layout="@layout/app_bar" />
2. By Using vector Drawables :
Vector drawables are based on vector graphics, as opposed to raster graphics which is a grid of x and y coordinates on a display space are also known as Bitmap Images, vector images are made of geometrical shapes. It is similar to SVG file which are used in web applications. In Android Vector Drawable are created with XML files. Before the Addition of Vector Drawable in Android SDK, developer had to create multiple version of images for different display resolutions. This take more time to create extra assets and consume more space that increases the Apk size.
Now there is no need to design different size image for mdpi, hdpi,xhdpi and etc. With Vector Drawable you need to create image only once as an xml file and you can scale it for all dpi and for different devices. This also not only saves space but also simplifies maintenance.
3. Optimize .png images :
There are many tools offline and online tools available to optimize the .png images without compromizing the quality ImageOptim, OptiPNG or PNGCrush, TinyPng. If you can reduce the size images your app size will obviously become low.
4. Using 9-patch Images :
A 9patch png is a specialy designed format for PNG that can be used for backgrounds of buttons, drawing shadow, re-sizing logo etc. Instead of defining a regular bitmap to be used as a background, a 9patch defines nine segments — for each of the four corners, the four edges, and the centre. You can use very small 9-patch image and stretch it for any size of background instead of using heavy images for background.
5. Optimum code reusability and modularisation :
Whenever you are developing any application try to develop reusable component which can be reused throughout your application. It will reduce your app size as well as save your time. If required create different different modules for different purposes.
7. Use Media formats wisely :
Image : For example we have two common media formats for images .png and .jpg. .png files are heavier than .jpg files but .png files can be strech without losing quality but .jpg files not so we have to use high pixcel .jpg files for larger background. So depending on the requirement we should selcect which file format is best. Generally .png files are recomended.
Audio : Same ways for audio .mp3, .ogg files are not good choice, AAC Audio is recommended for all audio resources. AAC achieves better compression at a given quality, compared to mp3 or Ogg Vorbis. Raw formats such as WAV should never be used.
Video: Use H264 AVC. Encode the video to a resolution no larger than the screen resolution of the target device
8. Reduce Animation Frames :
Frame-by-frame animations can drastically increase the size of your APK. frame-by-frame animation get separated into multiple PNG files within a directory. Each image is one frame in the animation.
For each frame that you add to the animation, you increase the number of images stored in the APK. In Figure 1, the image animates at 30 FPS within the app. If the image animated at only 15 FPS instead, the animation would require only half the number of needed frames.
9. Use Code shringking tools like Proguard :
Code shrinking tools like proguard helps to significantly reduce the code foot prints. After applying proguard to the code, test the app properly as it replaces the symbols. You can learn more about proguard from sourceforge. Its also make difficult to reverse engineering of your code. After applying proguard Java and Android applications becomes up to 90% littler and up to 20% quicker.
10. Google Play Services :
Select the compiling APIs extensively. In versions of Google Play services prior to 6.5, you had to compile the entire package of APIs into your app. In some cases, doing so made it more difficult to keep the number of methods in your app (including framework APIs, library methods, and your own code) under the 65,536 limit.
From version 6.5, you can instead selectively compile Google Play service APIs into your app. For example, to include only the Google Fit and Android Wear APIs, replace the following line in your
build.gradle file:
compile 'com.google.android.gms:play-services:8.4.0'
with these lines:
compile 'com.google.android.gms:play-services-gcm:8.4.0'
compile 'com.google.android.gms:play-services-wearable:8.4.0'
11. Remove unused resources :
You can make use of android-resource-remover is utility that removes unused resources reported by Android Lint from your project.
12. Reduce the Size of Native Binaries :
If your app uses native code and the Android NDK, you can also reduce the size of your app by optimizing your code. Two useful techniques are removing debug symbols and not extracting native libraries.
13. Remove Debug Symbols :
Using debug symbols makes sense if your application is in development and still requires debugging. Use the arm-eabi-strip tool, provided in the Android NDK, to remove unnecessary debug symbols from native libraries. After that, you can compile your release build.
Store .so files uncompressed in the APK, and set the android:extractNativeLibs flag to false in the <application> element of your app manifest. This will prevent PackageManager from copying out .so files from the APK to the filesystem during installation and will have the added benefit of making delta updates of your app smaller.
14. Maintain Multiple Lean APKs :
Your APK can contain content that users download but never use, like regional or language information. To create a minimal download for your users, you can segment your app into several APKs, differentiated by factors such as screen size or GPU texture support.
When a user downloads your app, their device receives the correct APK based on the device's features and settings. This way, devices don't receive assets for features that the devices don't have. For example, if a user has a hdpi device, they don’t need xxxhdpi resources that you might include for devices with higher density displays.
For more information, see Configure APK Splits and Maintaining Multiple APKs.
15. Remove Enumerations :
A single enum can add about 1.0 to 1.4 KB of size to your app's classes.dex file. These additions can quickly accumulate for complex systems or shared libraries. If possible, consider using the @IntDef annotation and ProGuard to strip enumerations out and convert them to integers. This type conversion preserves all of the type safety benefits of enums.
With the technology improves, many industries has to be update to beat their competitors. Mobile Application Development Company India is increasing massively due to the immense development and android mobile phone users. This is some extra points to be added from my point of view.
ReplyDeleteRegards:
Android Training
Android Training in Chennai
thanks for your sharing. i think this article must be share to other people. i like it. android app development in USA
ReplyDelete