Make better choices while coding
-
Use OkHttp over HttpUrlConnect
HttpUrlConnect suffers from quite some bugs. Okhttp solves them in a more elegant manner. [Reference Link]
-
Use Pidcat for a better log reading experience
-
Use some Version Control System(VCS) like Git
-
Use ClassyShark
It is a standalone tool for Android Devs used to browse any Android executable and show important info such as class interfaces and members, dex counts and dependencies
-
Use Stetho
Debug your android apps using Chrome Dev Tools. Includes tools like Network Monitor, Shared Preference explorer etc.
-
A tool to analyze battery consumers using Android "bugreport" files.
-
Always use a constant version value like "1.2.0"
Avoid using
+
when specifying the version of dependencies.- Keeps one secured from unexpected API changes in the dependency.
- Avoids doing an extra network call for the checking latest version of each dependency on every build.
-
Do not use your own personal email for Google Play Developer Account
-
Use Vectors instead of PNG
If you do have to use png, compress them. Take a look at TinyPNG.
-
Learn about some architecture such as MVP or Clean
-
Try to understand and follow TDD (Test Driven Development)
-
Follow the DRY principle DRY = Do not Repeat Yourself
-
Learn about Dependency Resolution
With the speed android dependencies update, sooner or later you are going to encounter some sort of dependency conflict. The solution is making use of Dependency Resolution. Official Reference
-
Use a proper .gitignore in your Android Projects, Check it here
-
Use LeakCanary to detect memory leaks in your app - Its a memory leak detection library for Android and Java.
-
Enable gradle to automatically download missing platforms in android sdk
Set the below property in your global
gradle.properties
fileandroid.builder.sdkDownload=true
This is an experimental option and it only downloads build tools and platforms, but doesn't actually update Google or Support repository [Bug Ref]
-
Clear your gradle cache if you think that bundled support and google play services lib in android sdk are inconsistent
- Goto
~/.gradle/caches/
and delete everything inside thecache
folder. - Open SDK Manager and resync all support libs and google play services
- Next re-sync your project
- Everything should become consistent and functional.
- Goto
-
Use
alfi
to find the gradle dependency statement for a libraryIts basically the command line version of Gradle, Please which is a web hosted.
-
Run
alfi name_of_library
-
Copy the desired library
-
Paste in your build.gradle
-
-
Use
dryrun
to test a library directly-
Just Run
dryrun REMOTE_GIT_URL
-
-
Use an abtracted Logger class
-
If you want to automatically initialize your library, use a Content Provider [Read how Firebase does it - Ref Link]
-
Reduce installed app size with
"android:extractNativeLibs:false"
in<application>
[Ref Link]This will essentially prevent the system from creating a second copy of the .so files and fix the System.loadLibrary call so it’s able to find and open native libs straight from the APK, no code changes on your part required.
-
Selectivily execute a specific method in Android Studio [Ref Link]
-
Did you get one of these Google Play Developer Policy Violation Emails? Worry not, generate a Privacy Policy for your android app [Ref ink]
- Take a look at App Privacy Policy Generator, a web app to generate a generic privacy policy for your app.
-
Activity LifeCycle [Ref Link]
-
Tip about
onSaveInstanceState()
onSaveInstanceState()
is called only when the OS decides to kill theActivity
instance. It will not be called when Activity is explicitly killed i.e User pressed back button orfinish()
is called from code. -
If you are into building Android Libraries, then read here for more tips
-
Input some text in an editfield in a running emulator from your keyboard
adb shell input text "keyboard text"
-
Use
areNotificationsEnabled()
fromNotificationManagerCompat
to detect whether your users blocked your Notifications [Ref Link] -
Don't hard-code encryption keys, a simple grep for
"Ljavax/crypto"
reveals them in bytecode [Ref Link] -
Intents have a limited payload size (1Mb), don't serialize and attach entire file to it [Ref Link]
-
Always copy a file before sending it as intent URI. Receiving app could edit it & send a canceled result [Ref Link]
-
Use
http://
as scheme for app deeplinks, they are more universal & when app not installed drive users to a domain you own [Ref Link] -
Use below to display your app launch time [Ref Link]
adb shell am start -W <packagename>/. <activityname>
-
Use activity-alias or your launcher icons will disappear when renaming/moving your MainActivity
-
To enable
aapt2
set below in gradle propertiesandroid.enableaapt2=true
-
To testout doze mode, trigger it using
adb
[Ref Linkadb shell dumpsys deviceidle force-idle
-
Thumb rule regarding setting
compileSdkVersion
,minSdkVersion
andtargetSdkVersion
minSdkVersion
(lowest possible) <=targetSdkVersion
==compileSdkVersion
(latest SDK)
-
Google released an option to include OSS license activity in your app, use that to attribute credits to the OSS libs in your app [Ref Link]
-
Make Android Studio render
<merge>
layouts correctly by specifying the layout type with the tools:parentTag attribute [Ref Link] -
Checkout the Background Execution Limits on Android Oreo and update your app to work with the restrictions [Ref Link]
-
To take good screenshots with clean status bar use the Demo Mode in Android [Ref Link]
-
Steps
-
Enable Demo Mode
adb shell settings put global sysui_demo_allowed 1
-
Enable/disable icons by running the right command
// display time 12:00 adb shell am broadcast -a com.android.systemui.demo -e command clock -e hhmm 1200 // Display full mobile data without type adb shell am broadcast -a com.android.systemui.demo -e command network -e mobile show -e level 4 -e datatype false // Hide notifications adb shell am broadcast -a com.android.systemui.demo -e command notifications -e visible false // Show full battery but not in charging state adb shell am broadcast -a com.android.systemui.demo -e command battery -e plugged false -e level 100
-
Run app and take screenshots
-
Exit demo mode once you are done
adb shell am broadcast -a com.android.systemui.demo -e command exit
-
-
-
To record video of your android device [Ref Link]
adb shell && screenrecord /sdcard/download/fileName.mp4
Hit
Ctrl+C
to exit/stop recordingRecorded video file is saved at the location mentioned in the command on the device itself.
-
Use Dao inheritance to reduce the amount of boilerplate code [Ref Link]
-
Instead of using
getActivity()
in fragment, keep a habit of getting context fromonAttach()
. [Ref Link] -
Avoid setting a background in every view/fragment as it likely causes overdraw. [Ref Link]
-
View.getWidth() = 0?
That's because your view hasn't been layout yet, use globallayoutListener to know layout done. [Ref Link] -
Android never kills activities, it only kills processes. When low memory the lowest priority ranked will be killed.[Ref Link]
-
Use
-whyareyoukeeping class com.jeroenmols.MyClass
to figure out why certain a class wasn't removed.[Ref Link] -
Use certificate pinning to resist impersonation by attackers using mis-issued or otherwise fraudulent certificates, when making requests from your app. [Ref Link]
-
Do download the latest emulator using CLI
cd <android_sdk>/tools/bin ./sdkmanager --channel=3 emulator
To check the version of emulator, use
./sdkmanager --channel=3 emulator
-
Cleanup your Gradle caches by deleting files not accessed within the last month [Ref Link]
find ~/.gradle -type f -atime +30 -delete find ~/.gradle -type d -mindepth 1 -empty -delete
To check the size of your gradle cache, run:
du -sh ~/.gradle
-
Remove all debug log statements from the release build using the below proguard rules. (app's build.gradle should have
minifyEnabled true
set for this to work)# Remove all debug logs -assumenosideeffects class android.util.Log { public static *** d(...); }
The above snippet is usually appended to contents of app/proguard-rules.pro file
-
Should I use Enums in Android?
tl;dr
-
If you need code to be very performant integer constants may be the way to go
public class Operator { public static final int ADD = 1; public static final int SUBTRACT = 2; public static final int MULTIPLY = 3; public static final int DIVIDE = 4; }
-
Use Enums because
- Are type-safe, so you can only use valid enum types
- Provide better code readability
- Can implement interfaces
- Support polymorphic behavior
- In some really trivial cases, Proguard can optimize Enums into integer constants for you [Ref Link]
- Performance difference rarely makes a difference.
public enum Operators { Add, Subtract, Multiply, Divide }
-
-
The string resource
android.R.string.yes
doesnot yield string "Yes" instead it yields "Ok". Similarly the string resourceandroid.R.string.no
doesnot yield string "No" instead it yields "Cancel" [Ref Link] -
Don’t want generated files in your AS search results? Go to
Preferences -> File Types -> Ignore files and folders
and add the pattern to ignore - e.g.*.dex;*.class;
[Ref Link] -
If you uncheck “Suspend” and check “Evaluate and Log” in breakpoint menu, the breakpoint will print evaluated statement into the uncluttered “Console” window. No need for recompile due to added Log.d statements anymore [Ref Link]
-
To measure how long a method took to execute, you can use
TimingLogger
class. [Ref Link]- Typical Usage
TimingLogger timings = new TimingLogger(TAG, "methodA"); // ... do some work A ... timings.addSplit("work A"); // ... do some work B ... timings.addSplit("work B"); // ... do some work C ... timings.addSplit("work C"); timings.dumpToLog();
- Output
D/TAG ( 3459): methodA: begin D/TAG ( 3459): methodA: 9 ms, work A D/TAG ( 3459): methodA: 1 ms, work B D/TAG ( 3459): methodA: 6 ms, work C D/TAG ( 3459): methodA: end, 16 ms
- Typical Usage
-
If you're working with Android Things and you don't have an extrenal screen for your device, install scrcpy and use it to see what's going on your Android IoT device. It works a charm over wireless adb. [Ref Link]
-
Android Studio has this weird behaviour that it allows to edit its default code style, which leads to a weird side-effect. If you open your pre-setup project(with set codestyle and copyright configs) in Android Studio it will delete all pre-setup codestyle and copyright profile in this project. This is every much evident if you checked in your configs into git for sharing purpose, which is lost immediately as soon as you open the project
deleted: .idea/codeStyles/Project.xml deleted: .idea/codeStyles/codeStyleConfig.xml deleted: .idea/copyright/profiles_settings.xml deleted: .idea/copyright/copyright.xml
To fix that please follow along as below: [All thanks to Said Tahsin Dane for the solution]
-
We first need to verify that your
Default
codestyle isn't modified. To check that please open Android Studio with any project except your pre-setup(with set codestyle and copyright configs) project. Then navigate toPreferences>Edior>Codestyle
and check if your code scheme hasDefault
in BLUE color (this means it is modified). -
However if it is not colored BLUE, you are good and you can go ahead to open your pre-setup(with set codestyle and copyright configs) project and everything should be pre-setup for you.
-
If it is modified (colored BLUE), then click on the cog icon and select
Restore Default
-
After you hit that option, simply accept the change
-
Once done, you will see your Default is no more colored BLUE or modified, which means you are good
-
Now simply go ahead and open your pre-setup(with set codestyle and copyright configs) project and everything should be pre-setup for you.
-
-
If you add
android:sharedUserId
to an already published app, the app data will be cleared for all users that install your upgrade (because Android changes the process). So if you ever intend to use it, you must add it before publishing your app [Ref Link] -
When opening up methods for testing, use otherwise to still hide it from code complete.[Tweet Link, Ref Link]
-
You can group your recent Android Studio projects, and add icons to them [Ref Link]
-
Only build a single configuration to speed up debug builds. [Ref Link]
-
Avoid the annoying jump to Design tab while editing XML. Prefer XML editor under Settings [Ref Link]
-
Reduce installed app size with
android:extractNativeLibs="false"
in[Tweet Link, Ref Link] -
Improve Android Studio code inspections with Thread annotations [Tweet Link, Ref Link]
-
Use
adb
to put a phone into doze mode for testing [Tweet Link, Ref Link] -
Use
areNotificationsEnabled()
fromNotificationManagerCompat
to detect whether your users blocked your Notifications [Tweet Link, Ref Link] -
Activity.runOnUiThread
is just a convenient wrapper ofHandler.post
; don't pass aroundActivity
just so you can use it. [Ref Link] -
Define your interfaces with the highest possible option that will suffice. Don't use an
Activity
when a Context will do. [Ref Link] -
If you're not building a replacement for the dialer, use
ACTION_DIAL
notACTION_CALL
to initiate a call. [Ref Link] -
Requesting updates from a system service may drain battery, so register for updates in onResume and unregister in onPause. [Ref Link]
-
Hierarchy Viewer won’t run on prod devices, if however u want to run it then follow below steps [Tweet Link, Ref Link]
-
Variable and
init
block declaration order in Kotlin, actually matters :) if you want to use a variable inside init {} initialize it before it. -
When comparing intents it does not compare any extra data included in the intents [Tweet Link, Ref Link]
-
To show a ringtone picker to the user, use the
ACTION_RINGTONE_PICKER
intent to launch the picker as a subactivity. [Ref Link] -
Want to remove focusState on an item in GridView? Try:
android:listSelector="#00000000"
[Ref Link] -
You can generate the proguard keep rules via the APK Analyzer inside Android Studio. [Ref Link]
-
When viewing an Android Manifest, there is a tab at the bottom that allows you to see the merged manifest. Use this to inspect the merged manifest and find conflicts. [Ref Link]
-
In the APK analyzer in Android Studio, classes/members listed in italic are only references, not definitions. If it's in italics, it's defined in another DEX file (or the SDK). [Ref Link]
-
To be able to write multiline Todo comments, simply indent by 1 tab from second line onwards. [Ref Link]
-
You can get rid of a lot of noise in the Logcat, by Right Clicking a selected text > "Fold lines like this" option!. [Ref Link]
-
You know how you can group ur code inside IDEs such as Android Studio and IntelliJ IDEA by using the
region
andendregion
comment blocks. Turns out you can use the same trick to group inside XML files such as for layout, strings, styles, colors xml files [Ref Tweet] -
How many of you have had issue with special characters (&,<, >, etc) in your strings.xml file? Did you know there is an action called "Encode XML/HTML Special Characters" inside Android Studio that can escape those characters for you! [Ref Tweet]
-
The option is also avaliable under Edit menu drop down
-
In case the issue is in just one line, you can also just
ALT+ENTER
to get contextual fix.
-