Using Gradle flavors on vlc-android-sdk - android

In my app I'm using "de.mrmaffen:vlc-android-sdk:2.0.6" library and it's taking much storage but I can't find a smaller alternative.
So I decided as CommonsWare mentioned to use splits or product flavors but I can't get it to work.
I tried to follow the docs with no luck.
Any help appreciated.

Building the LibVLC Android SDK yourself
If you are using "de.mrmaffen:vlc-android-sdk:2.0.6", buid the LibVLC Android SDK yourself
As explained here, afterwards simply run this Gradle command: ./gradlew buildLibVlc
Building a specific version of the LibVLC Android SDK
cd vlc-android // if this folder doesn't exist yet, simply run ./gradlew cloneVlcAndroid
git tag // to list all release versions
git checkout {tag-name} // to checkout the git repo at the given tag
cd ..
./gradlew buildLibVlc // build it
Make sure you followed the Android compile instructions in terms of dependencies and check this:
git clone repo.
open up a command prompt in this repo. "cd" or change directory into
it.
git clone .
change directory into the vlc-android directory.
git tag
git checkout <tag_version>. In this case, 2.1.2.
cd ..
comment out both the compile/build of the build.gradle script that
you don't need.
./gradlew buildLibVlc
you should have a successful build with both the Java sources and
shared object (*.so) files in the jniLibs folder.
create a libs folder right next to the jniLibs folder if you
updated the gradle version.
Get it via Maven CentralJCenter
Just add this dependency to your project and you're good to go.
dependencies {
implementation 'de.mrmaffen:libvlc-android:2.1.12#aar'
}
I'm using this version. Remember to add JCenter to your project's build.gradle file:
allprojects {
repositories {
jcenter()
}
}
VLC Android SDK via JCenter supports the next ABIs: armeabi-v7a, arm64-v8a, x86 and x86_64.
You can filter specific ABIs in your app's build.gradle file (x86_64 and arm64-v8a are excluded):
android {
ndk {
abiFilters "armeabi-v7a", "x86"
}
}
It's possible to check included files in mrmaffen's repository and via recent Android Studio versions:
Configure multiple APKs for ABIs
Add an abi block inside
your splits block. In your abi block, provide a list of desired ABIs. Source
android {
...
splits {
// Configures multiple APKs based on ABI.
abi {
// Enables building multiple APKs per ABI.
enable true
// By default all ABIs are included, so use reset() and include to specify that we only
// want APKs for x86 and armeabi-v7a.
// 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"
// Specifies that we do not want to also generate a universal APK that includes all ABIs.
universalApk false
}
}
}
Build multiple APKs
Click Build > Build APK to build all APKs for the currently selected
module in the Project pane.
Gradle creates the APKs for each ABI
into the project's build/outputs/apk/ directory.
Configure Build Variants
This page builds on the Configure Your Build Overview to show you how you can configure build variants to create different versions of your app.
Combine abi filters and build variants
Exclude abi from apk
android {
productFlavors {
x86 {
ndk {
abiFilter "x86"
}
}
arm {
ndk {
abiFilters "armeabi-v7a", "armeabi"
}
}
}
}
Multi-APK through ABI and density splits
How to reduce the number of APKs with ABI splits
Here’s
a code snippet that you can use to set version codes for ABI splits.
Give the x86_64 and x86 higher version numbers than ARM, as many x86
devices can run ARM code through an emulation layer, although with
lower performance.
If you don’t wish to manage too many APKs, target the most popular
ones (usually ARM and maybe x86) with a split APK and serve a
universal APK to everyone else.
It’s vital that you publish the universal APK on the Play Store with a lower
version number than all other ABI-specific packages.
If you need more flexibility for your Multi-APK setup, check out
Multi-APK through product
flavors.
Recommended Medium post to choose supported ABIs
In this
post
we will understand what is ABI, problems with the ABI split, and
alternative way to avoid those problems... For instance, Android supports the following ABIs :
mips, mips64, X86, X86–64, arm64-v8a, armeabi, armeabi-v7a
So you have to take a call on supporting 64-bit libraries based on
size vs performance criteria but mips, mips-64, and armeabi should be
removed without any hesitation.
Solve UnsatisfiedLinkError Problem on some devices
As explained here, 64-bit processors generate and check arm64 folder to load native libraries.
If your project does not have arm64 folder. Here is the solution:
build.gradle
defaultConfig {
...
ndk {
abiFilters "armeabi-v7a", "x86"
}
}
You need to add this filters(abiFilters) to your app module’s
build.gradle files. So when your device try to run your app, it will
check gradle file and understands that it should not generate any
folder and use existing native library resources. Boom. Almost solved.
But still there is one more thing. Add this line to your gradle.properties to use deprecated Ndk.
gradle.properties
android.useDeprecatedNdk=true

You can use app bundle so you don't need to handle multiple apks. Google Play will handle it for you automatically. Plus this approach can provide additional benefits. For more details: https://developer.android.com/guide/app-bundle

Related

How to install a specific APK on my device

I do not use Android Studio but I do everything from the command line. I am building different APKs for different architectures so my build.gradle looks like this:
...
splits {
// Configures multiple APKs based on ABI.
abi {
// Enables building multiple APKs per ABI.
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 "armeabi", "armeabi-v7a", "arm64-v8a"
// Specifies that we do not want to also generate a universal APK that includes all ABIs.
universalApk false
}
}
I then use the method described here to assign different version codes to the individual APKs.
This all works fine except that when I say
./gradlew tasks
there is only one task named installRelease. Running this task will then automatically choose an appropriate APK and install it.
However, I'd like to test the individual APKs separately, i.e. on my 64-bit Android device I'd first like to test armeabi, then armeabi-v7a, and finally arm64-v8a. When running installRelease, however, gradle will always automatically install arm64-v8a. So how can I force gradle to install a specific architecture?
Previously, I was using this code in build.gradle instead of the splits code shown above:
productFlavors {
arm7 {
// in the future, ndk.abiFilter might also work
ndk {
abiFilter 'armeabi-v7a'
}
}
arm8 {
ndk {
abiFilters 'arm64-v8a'
}
}
arm {
ndk {
abiFilter 'armeabi'
}
}
}
When using this code, gradle offered individual tasks named installArmRelease, installArm7Release, and installArm8Release which was exactly what I was looking for but I had to drop this code because I didn't find a way to use it alongside the code that generates different version codes for the individual APKs as described here.

Get the running gradle task name

I use gradle splits to generate different apks for different architectures. However, based on the running "assemble(ABI)" I'd like to disable building some native libraries.
My question is, if I run:
gradle assembleMipsDebug
how can I get "assembleMipsDebug" or preferably "mips" from build.gradle script?
Even if you have splits enabled, there is no separate gradle task for each ABI. Still, you can provide different options for different splits.
You can choose the list of built libraries in your Android.mk or CMakeLists.txt script, or you can list the explicit targets in the externalNativeBuild block.

How to remove extra native dependencies from app?

I am using arcgis in my app and it bundles native dependencies that are large in size. I don't want to include the x86 dependency if it means reducing the size of the apk. How do I tell gradle to automatically exclude the x86 native library.
I tried removing it manually during the build. but it shows up again after rebuild.
how do I tell gradle to automatically exclude the x86 native library
Use splits:
android {
// other good stuff here
splits {
abi {
enable true
reset()
include 'armeabi-v7a'
universalApk false
}
}
}
This tells Android to build only an ARMv7 version of your APK. You would need to adjust the include line to list what APKs you want.
However, you may be better served using splits to just build a separate x86 APK file (have include 'x86', 'armeabi-v7a') and ship both, so you better support x86 but still have smaller files.

How to import only selected native library ABIs from AAR?

I have a bit unusual problem - my Android app contains native libs and I build native libs for armeabi-v7a and x86. However, now I need to integrate a third party library into my app which also contains native libraries (third party library is Crashlytics which I included via Maven from my build.gradle.). The problem is that third party library's AAR provides all arhitectures (armeabi, arm64-v8a, armeabi-v7a, mips, mips64, x86 and x86_64) and my app only supports armeabi-v7a and x86 (arm64-v8a is planned for near future), so when final apk is built it contains 3rd party library's all ABI's and only x86 and armeabi-v7a ABI's of my native code. This causes my app to crash when launched on arm64 device like Galaxy S6.
My question is: is it possible to include only selected ABI's from 3rd party AAR?
Please note that I am aware of APK splits, but this only solves my problem partially, i.e. it works only if I distribute my app via Play Store. Although Play Store supports beta test distribution, the propagation of updated APK is rather slow, so prior pushing an update to app's PlayStore beta channel, we push an update via Crashlytics' beta distribution system, which is much faster. The problem is that Crashlytics' distibution system does not support APK splits (or am I wrong?). Therefore, I actually need to build an "universal" APK that will contain only selected ABIs. How to achieve that?
Although I would be satisfied even with Crashlytics'-specific answers (like for example, how to distribute APK splits via their beta channel), I would be much more satisfied with solution for building "universal" APK that contains only selected ABIs, because at our company we also provide SDKs to our clients as AAR archives that contain only supported architectures and we would like to instruct them how to handle case when they integrate our SDK with other SDKs that have different ABI's supported.
I am using latest stable Android studio (1.2.1.1), gradle 2.4 and android gradle plugin version 1.2.3.
packagingOptions {
exclude 'lib/arm64-v8a/libcrashlytics-envelope.so'
exclude 'lib/arm64-v8a/libcrashlytics.so'
exclude 'lib/armeabi/libcrashlytics-envelope.so'
exclude 'lib/armeabi/libcrashlytics.so'
exclude 'lib/mips64/libcrashlytics-envelope.so'
exclude 'lib/mips64/libcrashlytics.so'
exclude 'lib/mips/libcrashlytics-envelope.so'
exclude 'lib/mips/libcrashlytics.so'
exclude 'lib/x86_64/libcrashlytics-envelope.so'
exclude 'lib/x86_64/libcrashlytics.so'
}
This works for me:
(e.g: only armeabi & armeabi-v7a)
build.gradle
android{
defaultConfig{
ndk{
abiFilters "armeabi", "armeabi-v7a"
}
}
}
Mike from Fabric and Crashlytics here. With Splits, currently, we don't know in advance which density to provide the tester, so just add this line to your specific flavor or variant, to use the universal APK that is generated.
ext.betaDistributionApkFilePath = "path to the universal split APK"
Also, if you're using NDK crash reporting, in case it matches the crash you're seeing, check out this link.
I had the same problem as you, but you actually helped me with the link you posted about APK Splits!
In your case, try to add the following to your build.gradle inside the android closure:
splits {
abi {
enable true
reset()
include 'armeabi-v7a', 'x86'
universalApk true
}
}
The trick in there is to set the universalApk to true in order to generate only one APK with all the defined architectures, instead of splitting them up in several APKs.
Also don't forget the reset() which removes all the default values.

Android Studio: How to run a single test on x86

I am using two different flavors for two different architectures, because I have very large native libraries, and I want smaller binaries.
When I click on the "Run" icon, Android Studio ALWAYS builds and deploys the "Arm" flavor of our product. If I run this on an x86 emulator it fails because it doesn't have the libraries for x86.
Anybody know how to convince Android Studio to deploy the right version for a particular emulator?
Try using the abiFilter property in your build.gradle.
This post explains how to use native libraries in different architectures:
In Chapter Building one APK per architecture, and doing it well! it says:
Use flavors to build one APK per architecture really easily, by using abiFilter property.
Try adding this to your gradle.build:
android{
...
productFlavors {
x86 {
ndk {
abiFilter "x86"
}
}
mips {
ndk {
abiFilter "mips"
}
}
armv7 {
ndk {
abiFilter "armeabi-v7a"
}
}
arm {
ndk {
abiFilter "armeabi"
}
}
fat
}
}
You might just need the arm & x86.
After this, synchronize the project with the gradle file using
Tools > Android > Sync Project with Gradle Files
Now you should be able to switch between build variants and one APK by architecture should be generated.
Select Build Variants in the lower left corner. You should be able to switch between the different architectures in the Build Variant dropdown.
Hope this helps.
First of all, there's now an easier way to distribute to different ABI's without using flavours - This is new to Android gradle 0.13.0 (2014/09/18) - http://tools.android.com/tech-docs/new-build-system/user-guide/apk-splits
There it says: Using the new Split mechanism, building a hdpi, and an mdpi version of the same app will share a lot of the tasks (like javac, dx, proguard). Additionally, it will be considered a single variant and the same test app will be used to test every multi-apk.
Maybe that will help you manage the tests easier

Categories

Resources