Michael Evans

A bunch of technobabble.

Using Build Types With the Google Services Gradle Plugin

| Comments

If you want to integrate your Android app with most of Google Play Services nowadays, you’ll find that you are instructed to set up the Google Services Gradle plugin to handle configuring dependencies. The plugin allows you to drop a JSON file into your project, and then the plugin will do a bunch of the configuration for your project, such as handling the API keys.

This is all well and good—unless you’re like me (and countless others) and want to use a different configuration for your debug and release builds. This would be useful, as an example, if you use Google Play Services for GCM and would like to have development builds recieve pushes from non-production systems.

It seems that the plugin is configured in such a way that it supports build flavors, but it does not yet support build types. However, with a little Gradle magic, we can hack that support in.

Changelog for N Support Libraries

| Comments

Pssst! If you’re an Android developer, you might not have heard yet…the N Preview started today! As part of the festivities, a new alpha version of the support libraries was released. There was no changelog that I could find, so I decided to make one. Here’s what has changed (so far) in the public API of a few of these libraries:

Testing Intents With Espresso Intents

| Comments

A few weeks ago, I wrote a basic introduction on how to use Espresso to test the UI of an Android application. However, when I went to write instrumentation tests for Aftermath, I ran into trouble testing things that exist outside my application’s process. For example, what do you do when your app needs to use the Android Intent system to call upon the dialer or the browser, or pick a contact with the contact picker? What about testing a share action? Because these apps run outside your application itself, you can’t use Espresso to interact with them. So how can you test your app’s behavior? You can either use Espresso-Intents or UI Automator (but that’s another show).

Using Espresso for Easy UI Testing

| Comments

One thing that I notice when I talk to Android developers is that a lot of them don’t put an emphasis on testing. They say that it’s too hard to write them or that they are too hard to integrate and set up, or give a bunch of other reasons why they don’t. But it’s actually pretty simple to write Espresso tests, and they really aren’t that hard to integrate with your code base.

Improving Your Code With Android Support Annotations

| Comments

If you haven’t heard of the Android Support Annotations library yet, you’re missing out on a neat new package that will help you catch bugs in your apps. Included in the library is a number of Java annotations, that will help Android Studio check your code for possible errors and report them to you. There are quite a few of them, so I only plan to go over a few of them here, but you should definitely check out the docs for more info about the rest.

@NonNull / @Nullable

@NonNull and @Nullable are probably the most basic of the support annotations, but also some of the most helpful! Annotate a parameter or method with either of these to denote if the parameter or method’s return value can be null or not, and voila, now Android Studio can give us a nice warning that we’re doing something unsafe.

Android Ripples With Rounded Corners

| Comments

So recently I was trying to add a ripple to a view that had rounded corners. Simple enough right? Let’s just say I have a FrameLayout with the background similar to this one:

1
2
3
4
5
6
7
8
9
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <solid android:color="@android:color/transparent"/>
    <corners android:radius="15dp" />
    <stroke
        android:width="1px"
        android:color="#000000" />
</shape>

It’s not quite as simple as setting the foreground to ?attr/selectableItemBackground, or else you’ll see the ripple surpasses the corners (which doesn’t look so bad when your border radius is small, but this would look terrible with a circlular view):

The solution for this lies in the special mask layer of the RippleDrawable. You specify the mask layer via the android:id value set to @android:id/mask. For the example above, you can set the mask to the same size/shape as the view you’re masking, and then the ripple will only show for that area. For something like our example above, you’d use something like this:

1
2
3
4
5
6
7
8
9
10
11
<?xml version="1.0" encoding="utf-8"?>
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="?android:attr/colorControlHighlight">
    <item android:id="@android:id/mask">
        <shape android:shape="rectangle">
            <solid android:color="#000000" />
            <corners android:radius="15dp" />
        </shape>
    </item>
    <item android:drawable="@drawable/rounded_corners" />
</ripple>

Now when you tap on the view, you’ll see something like this:

Huzzah!

Another tip: if you don’t set a click listener for a FrameLayout (like we used in this example), the pressed state will never be used!

Blurred Background Effect for Android

| Comments

A few months ago, the Android design team reviewed apps that they thought were good-looking, and were referred to as the “Beautiful Design Collection”, as part of their Android Design in Action series.

One of these apps was Etsy, which had a very cool fading blur background effect, which you can see here:

As a learning experiment, I set off to replicate this behavior. I had seen a library by Manuel Peinado called GlassActionBar which demonstrated a similar glass-like blur effect on the ActionBar, so I decided to use that code for blurring my background.

The code itself is pretty interesting, specifically the bit for versions on Jelly Bean or higher. If you’re using API version 16 and up, you can use Renderscript Intrinsics, which are a set of built-in functions that require very little code to use, but are optimized for high-performance.

In my sample tests, using Renderscript to blur the image took on average about ~175ms, vs ~2 seconds doing the blur using Java code. (The required code is also only a tiny fraction of the length of the Renderscript one).

Renderscript is extremely easy to add to your project, just throw

1
2
    renderscriptTargetApi 19
    renderscriptSupportMode true

in your build.gradle and you should be ready to roll.

Once you have the blurring, the rest of the process is fairly straight forward. When you plan to leave an activity, create a bitmap of the current view and write it to disk. When you start your new activity (which should have a transparent background), you override the transition (otherwise you’ll get the default zoom), and set the background to the blurred image you saved earlier. Add a fade in for the alpha and you get a nice little effect!

If you’d like to see how this looks in a sample project, you can find it on Github here.