Android green figure, next to its original packaging

Android: Determine when App is Opened or Closed

The Problem

Inevitably when developing an Android application there will come a time when you need to detect when it comes into the foreground, and when the user leaves.  Surprisingly, there is no easy way to do this! It isn’t hard to detect when the application is first opened, but its not so simple to determine when it is re-opened or closed.

This post will lay out a technique that can be used to detect when an application has been opened, re-opened, or closed.

Lets Get Started

At the core of determining if an application is opened or closed is if any of its activities are currently being displayed. So lets take a very simple example; an application that has exactly one Activity, and does not support landscape mode. All it would take to determine when the application opened or closed would be the Activity’s onStart and onStop methods.

protected void onStart() {
    // The Application has been opened!

protected void onStop() {
    // The Application has been closed!

The problem is this approach quickly breaks down as soon as you add landscape support.  If we rotate the device then this Activity will be re-created and onStart will run a second time resulting in incorrectly detecting the app was opened a second time.

In order to handle device rotation we need to add a validation step. This validation needs to launch a timer whenever the Activity stops in order to detect if we quickly see another Activity in the app start. If we do not, then the user has really exited the app, if we do then we know that the user is still within the app.

This validation also allows supporting an application with multiple Activities. Since transitioning from one Activity to another is handled by this validation as well.

So using this technique I created a manager class that all Activities report to when they become visible and are no longer visible. This manager class handles the validation step for each Activity to avoid accidental detection. It also utilizes a publisher-subscriber (Observer) pattern to allow any interested parties to be notified when the application opens or closes.

To use this manager there are three steps:

1) Add it to your codebase

import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.text.format.DateUtils;

import java.lang.ref.Reference;
import java.lang.ref.WeakReference;
import java.util.HashSet;
import java.util.Set;

 * This class is responsible for tracking all currently open activities.
 * By doing so this class can detect when the application is in the foreground
 * and when it is running in the background.
public class AppForegroundStateManager {
    private static final String TAG = AppForegroundStateManager.class.getSimpleName();
    private static final int MESSAGE_NOTIFY_LISTENERS = 1;
    public static final long APP_CLOSED_VALIDATION_TIME_IN_MS = 30 * DateUtils.SECOND_IN_MILLIS; // 30 Seconds
    private Reference<Activity> mForegroundActivity;
    private Set<OnAppForegroundStateChangeListener> mListeners = new HashSet<>();
    private AppForegroundState mAppForegroundState = AppForegroundState.NOT_IN_FOREGROUND;
    private NotifyListenersHandler mHandler;

    // Make this class a thread safe singleton
    private static class SingletonHolder {
        public static final AppForegroundStateManager INSTANCE = new AppForegroundStateManager();

    public static AppForegroundStateManager getInstance() {
        return SingletonHolder.INSTANCE;

    private AppForegroundStateManager() {
        // Create the handler on the main thread
        mHandler = new NotifyListenersHandler(Looper.getMainLooper());

    public enum AppForegroundState {

    public interface OnAppForegroundStateChangeListener {
        /** Called when the foreground state of the app changes */
        public void onAppForegroundStateChange(AppForegroundState newState);

    /** An activity should call this when it becomes visible */
    public void onActivityVisible(Activity activity) {
        if (mForegroundActivity != null) mForegroundActivity.clear();
        mForegroundActivity = new WeakReference<>(activity);

    /** An activity should call this when it is no longer visible */
    public void onActivityNotVisible(Activity activity) {
         * The foreground activity may have been replaced with a new foreground activity in our app.
         * So only clear the foregroundActivity if the new activity matches the foreground activity.
        if (mForegroundActivity != null) {
            Activity ref = mForegroundActivity.get();

            if (activity == ref) {
                // This is the activity that is going away, clear the reference
                mForegroundActivity = null;


    /** Use to determine if this app is in the foreground */
    public Boolean isAppInForeground() {
        return mAppForegroundState == AppForegroundState.IN_FOREGROUND;

     * Call to determine the current state, update the tracking global, and notify subscribers if the state has changed.
    private void determineAppForegroundState() {
        /* Get the current state */
        AppForegroundState oldState = mAppForegroundState;

        /* Determine what the new state should be */
        final boolean isInForeground = mForegroundActivity != null && mForegroundActivity.get() != null;
        mAppForegroundState = isInForeground ? AppForegroundState.IN_FOREGROUND : AppForegroundState.NOT_IN_FOREGROUND;

        /* If the new state is different then the old state the notify subscribers of the state change */
        if (mAppForegroundState != oldState) {

     * Add a listener to be notified of app foreground state change events.
     * @param listener
    public void addListener(@NonNull OnAppForegroundStateChangeListener listener) {

     * Remove a listener from being notified of app foreground state change events.
     * @param listener
    public void removeListener(OnAppForegroundStateChangeListener listener) {

    /** Notify all listeners the app foreground state has changed */
    private void notifyListeners(AppForegroundState newState) {
        android.util.Log.i(TAG, "Notifying subscribers that app just entered state: " + newState);

        for (OnAppForegroundStateChangeListener listener : mListeners) {

     * This method will notify subscribes that the foreground state has changed when and if appropriate.
     * <br><br>
     * We do not want to just notify listeners right away when the app enters of leaves the foreground. When changing orientations or opening and
     * closing the app quickly we briefly pass through a NOT_IN_FOREGROUND state that must be ignored. To accomplish this a delayed message will be
     * Sent when we detect a change. We will not notify that a foreground change happened until the delay time has been reached. If a second
     * foreground change is detected during the delay period then the notification will be canceled.
    private void validateThenNotifyListeners() {
        // If the app has any pending notifications then throw out the event as the state change has failed validation
        if (mHandler.hasMessages(MESSAGE_NOTIFY_LISTENERS)) {
            android.util.Log.v(TAG, "Validation Failed: Throwing out app foreground state change notification");
        } else {
            if (mAppForegroundState == AppForegroundState.IN_FOREGROUND) {
                // If the app entered the foreground then notify listeners right away; there is no validation time for this
            } else {
                // We need to validate that the app entered the background. A delay is used to allow for time when the application went into the
                // background but we do not want to consider the app being backgrounded such as for in app purchasing flow and full screen ads.
                mHandler.sendEmptyMessageDelayed(MESSAGE_NOTIFY_LISTENERS, APP_CLOSED_VALIDATION_TIME_IN_MS);

    private class NotifyListenersHandler extends Handler {
        private NotifyListenersHandler(Looper looper) {

        public void handleMessage(Message inputMessage) {
            switch (inputMessage.what) {
                // The decoding is done
                case MESSAGE_NOTIFY_LISTENERS:
                    /* Notify subscribers of the state change */
                    android.util.Log.v(TAG, "App just changed foreground state to: " + mAppForegroundState);

2) Activities Must Notify of Visibility Changes

Have all of your Activities implement the following code to notify the manager when they become visible and when they are no longer visible. This is best achieved by adding this code to your base Activity class.

protected void onStart() {

protected void onStop() {

3) Subscribe to Be Notified of Foreground Changes

Subscribe to be notified of app foreground state changes from somewhere of interest. The application class onCreate method is a prime placement to ensure that you get notified every time the app enters or leaves the foreground.

public class MyApplication extends Application {
    public void onCreate() {

    public void onAppForegroundStateChange(AppForegroundStateManager.AppForegroundState newState) {
        if (AppForegroundStateManager.AppForegroundState.IN_FOREGROUND == newState) {
            // App just entered the foreground. Do something here!
        } else {
            // App just entered the background. Do something here!

Further thought

There are a few details that need further discussion.  These changes may need to be made in order to calibrate this for your particular application.

Validation Time

How long should this validation timer be that is used to detect that your app has really entered the background? In the code above it set to 30 seconds for a few reasons.

There are third party Activities that can appear full screen when the application is running. A few common examples of these are in Google In App Purchasing or Facebook signup. Both of these essentially send the application into the background since none of you applications Activities are in the foreground when those are displaying. It is not desirable for those to count as the user “leaving the app” since they really haven’t. The 30 second timeout helps to catch this case. For example if a user completes an in app purchase in under 30 seconds, which the vast majority of users will, then they will not be counted accidentally as “leaving the app”.

If this situation doesn’t apply to you, then I recommend setting your validation time to around four seconds. That is enough of a safety margin for slow devices to create the next Activity when rotating.

CPU Sleep

A potential issue is there is no guarantee that the CPU will still be running long enough for the background detection to occur if the user locks their phone quickly after exiting the app (or locks the phone with the app still open).  In order to guarantee this always works as expected you would need to take a wake lock until the app closed event can be validated to prevent the CPU from sleeping. In practice however this did not seem to be a big enough issue to warrant use of a wake lock.

Determining How The App Was Launched

Great so now we know how to detect when the application was opened or closed, but we don’t know how the application was opened. Did the user click on a notification? Did they click on a link? Or did they just launch the app from the icon or recents tray?

Tracking Launch Mechanism

First we need somewhere to track how the application was opened. In this code I have added an enum to the application class to track how the application was opened. This builds upon the last example so we can print a log when the application is opened, along with how the application was opened.

public class MyApplication extends Application {
    public final String TAG = MyApplication.class.getSimpleName();

    public enum LaunchMechanism {

    private LaunchMechanism mLaunchMechanism = LaunchMechanism.DIRECT;

    public void setLaunchMechanism(LaunchMechanism launchMechanism) {
        mLaunchMechanism = launchMechanism;

    public void onCreate() {

    public void onAppForegroundStateChange(AppForegroundStateManager.AppForegroundState newState) {
        if (AppForegroundStateManager.AppForegroundState.IN_FOREGROUND.equals(newState)) {
            // App just entered the foreground.
            Log.i(TAG, "App Just Entered the Foreground with launch mechanism of: " + mLaunchMechanism);
        } else {
            // App just entered the background. Set our launch mode back to the default of direct.
            mLaunchMechanism = LaunchMechanism.DIRECT;

Setting the Launch Mechanism

Great so now we can print off the launch mechanism when the app is opened, but we never actually set it! So the next step is to set it when the user opens the app via a link or a notification. If its not set to one of those two, then the user must have opened the app directly.

Tracking Link Clicks

To track the user clicking a link that caused the app to open find the place in your code where you intercept your links and place the following code to track the launch mechanism. Make sure this is called before your Activity’s onStart(). This could be needed in many places or just one common link intercepter depending on your architecture.


Tracking Notifications

Unfortunately tracking notifications is a bit trickier. Notifications are shown and when clicked a PendingIntent that you previously bound to them is opened. The trick here is to add a flag to all PendingIntents that you make for a notification that indicates that this Intent is an Intent from a Notification. In other words, when the intent eventually opens some Activity, we need to be able to detect that this intent was created from a Notification.

So for example when creating any PendingIntent for a notification add the following to each intent:


// Put an extra so we know when an activity launches if it is a from a notification

Now all we need to do is check for that flag in every single Activity (add to your base Activity class). If we detect the flag then we know this Activity was launched via a notification and we can set the launch mechanism to notification. This must be done in onCreate so that it is set prior to the application coming into the foreground (which will trigger the printing of the launch mechanism).

public void onCreate(Bundle savedInstanceState) {

    Intent intent = getIntent();
    if (intent != null && intent.getExtras() != null) {
        // Detect if the activity was launched by the user clicking on a notification
        if (intent.getExtras().getBoolean(EXTRA_HANDLING_NOTIFICATION, false)) {
            // Notify that the activity was opened by the user clicking on a notification.

And there you have it! You can now detect not only when the app is opened or closed, but how it was opened as well.


Do you find this sort of work interesting? Do you love quaint Bucks County Pennsylvania? Are you an amazing Android Developer? Then we would love to hear from you!

Featured image by Dsimic – license via CC BY-SA 3.0

Some Time with Android Watches

Watching Android

In late June, Google announced Android Wear, a solution to the age-old problem of how to augment and interact with your smartphone via jewelry. Like all things Android, Wear presents us gadget-lovers with the impossible task of explaining what it is, what it does, and how an OS differs from hardware, without boring or confusing the listener. The inaccurate but socially-appropriate description is, “Android Wear is watches with screens that show you stuff from your phone and take simple voice commands.” To date, there are just two Wear devices on the market: The LG G Watch, and the Samsung Gear Live. Several of us at MeetMe, including our entire Android team, have adopted the timepieces into our lives for the last couple weeks. What follows are some of our individual thoughts, first on the LG model, then the Samsung (scroll down a bit).

LG G Watch


Bryan Emmanuel,  Android Developer

I like the watch so far, but it’s not quite what I thought it would be. I was expecting to be actively navigating around apps and content, but instead it’s more like remote notifications for my phone. That’s not a bad thing though, as it’s more convenient, and extends the battery life on my phone as I’m checking it less. I do occasionally respond to Hangouts from the watch, or ask “How far to home/work”, which is nice as well. Even when using navigation on the watch for over 2 hours of daily commuting, the battery on the watch easily exceeds 24hrs. As far as comfort goes, I’m still getting use to wearing a watch again after using a phone as my clock for the past 15 years. It’s light and not as bulky as I expected, so the transition has been easy enough.

John Spivak,  Mobile QA

Used the LG Watch for a few days.


  • Weather Alerts, with all the recent thunderstorm activity, was great.  A good enhancement for either a weather app or just the builtin weather alert functionality would be working with municipalities to provide options for flood/tornado shelter nav directions.
  • Betterer notifications on the wrist.  Pebble has it, but it’s a much better experience on the Wear, making use of the notification icons and full text.  Wish it had more granular controls, though.  I’d like to get email notifications for Wear for my personal Gmail’s Primary category, but no notifications at all from my work Gmail, while still getting work Gmail notifications on my phone.
  • Search from wrist is handy, and will be getting better the more stuff Google adds to Google Now.


  • No off/lock button on the LG watch to force it into “dim” mode or prevent accidental touches.  I know there’s an app for that, but it seems like something that should be part of the device.
  • Solid plastic/rubber straps don’t breathe very well in the summer, or at all.
  • Lots of apps don’t have any significant support for it, if anything at all.  I feel that most developers aren’t going to leverage it fully, since the goal here is to know when the user is going to need your app before the user does, and get out of the way otherwise.
  • It’s ugly as sin.  I bought the Pebble with knowledge that it would be dorky as hell, but the Wear watch is even worse.  This is basically the “Apple wins on design, every time” thing that a theoretical iWatch will beat everyone out of.  Hopefully the Moto 360 is better.
  • It’s very difficult to tell the time in the sun until the display automatically un-dims.  This is kind of a pain for something that should be immediate; those milliseconds add up.
Brian Herbert,  Android Developer

After a week of use, I still find the watch to be uncomfortable. The curved Samsung form-factor feels better than the flat LG unit, and the stock wristband isn’t arm-hair friendly. The charging dock is really nice, though, and I been averaging about 24 hours of battery life. I really want a reason to keep using it, but if it weren’t for the opportunity to write Wear software, I think I’d go back to bare wrists. The whole philosophy of Android Wear is passivity: it’ll tell you what it thinks is relevant when it wants to. For me, that’s annoying on two fronts. First, I can’t easily approach the device with an intent to DO something, and second, I don’t like to be randomly interrupted by notifications on my phone, let alone my wrist. When trying to demo the watch to my friends, I either have to dig awkwardly through the menus to find an interesting utility (or try to launch it with voice commands), or flip through my notification cards, which display the same thing as my phone, only with a fraction of the information. It’s occasionally nice when play controls show up after you launch Netflix, or you get a really short text message that you can read at a glance, but as far as convenience, I haven’t found any use that isn’t better and just as culturally acceptable to do on my phone. So if this were a closed-platform devices with no hardware options, I’d say it’s not for me.

But this is Android, in an era of customizable peripherals, so regardless of the implied uses for this watch, I still have a device on my wrist that can do a ton of cool stuff, given the right software. I installed an app launcher, accessible like a menu drawer, and now it feels like I control the watch, rather than the other way around. The play store also has a couple calculator watch apps, so you can go retro with your geekery. After a tiny bit of hacking, I was able to port one of my old games over. It ran smoothly at almost 60 fps, so decent gaming is possible. As a developer, I’m almost overwhelmed with grandiose ideas, and I think we’re gonna see a lot of cool apps soon enough. I wish there were a camera and speaker, but the screen, accelerometers, haptic feedback, and connectivity through the phone still allow for some great creativity.

In short, I think this is a device purely for hackers and early-adopters. It needs another generation or two before there are enough apps and use cases for Apple to sift out the marketable features.

 Kenny Campagna,  Android Developer


  1. Google Now Integration. Easily one of the best features as I use this daily, whether it is weather/traffic updates, setting reminders/alarms or the dozens of other things it does.
  2. Notifications. I have a Nexus 5 and for some reason it has a very low vibration so I can never feel it when its in my pocket. The watch takes care of the need to have to feel that, or even look at it for a notification. It is also useful when I am at home. I can leave my phone plugged in charging and not go over and look at it whenever I get a notification.
  3. Battery Life. I’ve read reports of battery life not being spectacular, but in my experience the watch last 2+ days before needing a charge.


  1. It’s A Watch. This really isn’t a knock against the functionality of the watch but I’m not a watch person. I’m still getting used to it so it sometimes is awkward.
  2. No Speaker. When I google something I got used to hearing it spoken back to me, I have been spoiled, I now have to Gasp Read!
David Weinstein,  Senior UI Designer

For nearly ten days I’ve been wearing my new LG G watch and unlike Glass it’s not even there. I will preface this by saying that I wear watches frequently and own about a dozen different ones for many occasions. When I saw the sub $250 price tag on the first two watches I was elated. I’ve spent more on a watch that does less. Throughout my childhood to present day I have always been enamored with the idea of a computer as a watch. From classic Dick Tracy, Penny on Inspector Gadget, to Zordon calling the Power Rangers, a watch that could act as a communication tool has always seemed very logical.

To my dismay when I strapped on the LG G I did not get the call from Zordon, but I did get the weather. Having Google Now feed me information to my watch is very useful. While I work, I generally keep my phone silenced with vibration off since its usually on my desk. Having an extension of my phone on my wrist is quite fantastic. Getting a Hangout or Hipchat notification directly on my watch have made missed text messages pretty infrequent. The ability to reply to a Hangout with quick replies or voice is also fantastic. So far I’ve found most of the quick replies to be sufficient enough at least to let the other person know I saw and understood their message without having to take out my phone.

I have found some physical detractors for the LG G though. It’s poor battery life is the most disappointing. If I forget to charge it at night I’m likely to run out of battery before I hit work. On the plus side since the battery is so small, it charges very quickly. The second annoying factor is terrible direct sun viewing. Add polarized sunglasses to the mix and it’s impossible to read making its usefulness during the summer lacking a bit depending on the shades I have on that day. One thing I had not considered was how distracting it would be in a dark movie theater. While you can dim the watch it still puts out significant light in a dark room. I didn’t want to be ‘that guy’ so I made sure to slip the watch off during the film. An option to make the watch go completely dark via a gesture would be very useful.

On the software side of things, with most applications currently not supporting Android Wear the phone mostly acts as a notification center, which I already knew going in. This does make the current generation of watches more for early adopters than for the masses. The general public’s expectations of what a smart watch is capable of is tempered by science fiction and mass media. What it’s actually capable of is much less. For example my dreams of being Dick Tracy, answering a call on my wrist, is a mixed bag. While phone calls do forward to my wrist; answering them leaves me awkwardly reaching for my phone in my back pocket. The watch has no speaker therefore can not act as a headset, unless I am already paired with a bluetooth headset, which I am not. The call functionality is reserved more for dismissing a call or sending a quick response via text to the person ringing me. One feature that seems to be a horrible oversight is lack of call status on the watch. I have no ability to hang up or see who I am talking to on the watch.

Where science fiction does meet reality is with GPS navigation and Wear integrated apps. Walking directions are even better on my wrist than they were with Glass. With Glass I was constantly calling attention to myself and many people would ask me about it, making actually getting anywhere quite the challenge. With the LG G no one thinks twice about a man checking his watch making walking navigation a breeze. And while the list of integrated apps is currently slim, fitness apps shine showing off just how useful the watch can be. By providing me with minimalist controls for starting and stopping a workout it makes my progress tracking that much more accurate since I no longer have to fumble around with my arm band or zipped pocket where I awkwardly carry my phone during a run or workout.

Overall my experience has been a pleasant one. Android Wear does what Glass did not. It provides information at a glance without getting in the way or calling attention to itself. Making wearable computers innocuous is the crutch that is required for them to succeed. Having an obvious computer strapped somewhere on your body defeats the purpose of wearables and makes breaking into the mass market that much more difficult. When you make the item a fashion accessory you’ve succeeded. Wear is on the right track and now it’s in the hands of the developers to make it killer.

Samsung Gear Live


Joe Hansche,  Android Architect


  • It didn’t take as long as I was fearing to get used to wearing a watch again, after not having worn one for about 7 years.  The last watch I wore got lost at some point after I moved here, most likely due to the fact that I used to hate wearing it while working at a keyboard, so it would come off as soon as I sat down (which hasn’t been much of an issue with the Gear, thus far)
  • I like getting quick-glance previews of what is going on on my phone without having to look at the phone.  This is important especially when I’m at work, because my phone sits in its charging dock, so I don’t actually see or pay attention to notifications that come up on the phone.
  • I like the gentle buzz on an incoming notification;  something that my phone typically doesn’t do very well.  It’s enough to get my attention if I’m interested, but unintrusive enough to allow me to easily ignore it if I’m not.
  • Step count has been an interesting one, since I haven’t had a device that counts steps for me (and I walk to/from work every day).  An app on my phone to do that would be a no-go, since that requires the accelerometer sensor, and that would drain my battery.
  • Speaking of battery, the battery on the Gear has been great, usually getting down to somewhere between 50-70% after a full day of using itand then I take it off and put it on the charger before I go to bed.  After dealing with sub-par phone batteries that often can’t even last a full day, it’s nice to see that this gets a good 24+ hour charge.
    But that’s kinda sad if you think about it:  we are all infatuated with the idea that it can last over a day without being charged.  Our phones are such battery hogs, that we are ecstatic to see something that doesn’t yell at us at the end of the day because it’s on its last breath.
  • I like the fact that the wristbands are replaceable [1] [2], because while I am hesitantly in favor of the Samsung wristband as of now, I fear the day that the holes wear out from the band snapping on/off multiple times a day, and the pegs will no longer hold the band properly.  Or I’ve had visions of walking across the bridge and the band catches the inside of my pants pocket, ripping the band completely off my wrist as the gadget goes for a swim in the Delaware River ¬_¬
    Again, I do still prefer the Samsung band over the LG one, but I think a more traditional strap will be better in the long run.


  • Speaking of chargers:  the Samsung Gear charger is absolutely terrible…  it’s a tiny, odd-shaped chunk of plastic that snaps onto the back of the watch (after about 2-3 attempts, anyway, if you’re lucky), and then forces you to leave the watch laying on its side with the charger cable sticking up.  I’m just waiting for the day that one of those tiny clips breaks off and then I’m totally screwed (since it won’t even lay flat in order to hold against the contacts while charging).  The LG G charger/cradle was a much better design, and I wish Samsung had taken a similarly simplistic route when designing their charger.
  • I seem to get multiple Now cards for daily agenda, each containing the same set of 2-3 events that I am not interested in (two separate weather forecasts for the day and a 10am meeting I don’t attend).  Weather forecast is great, but I don’t need to get the notification from my calendar (I use Google’s weather calendar, so it shows today’s temperature as an agenda item, and that’s not really where it belongs).  I do like having the weather forecast as its own card, including a weekly view.  I just don’t want to see it in my agenda.
  • The heart rate monitor doesn’t work well at all..  About 80% of the times I have tried it, it says “tighten band and try again.”  Sometimes it’ll work if I hold the watch face tightly against my wrist, but I feel like if you’re going to add something like that as a core selling point of the device, it should Just Work™.  I’ve also noticed it works much more often when I’m inside, as it virtually never works outside in the daylight:  probably because it uses a small green LED to detect the pulses, and the daylight entering from the side of the watch is just too bright for the sensor to detect the variance properly.  One time I did get it to work outside (on the 2nd attempt) while playing company softball, and it registered my heart rate at 63bpm, which is 100% incorrect (I had just hit a homerun!).  My heart rate had to be over 120bpm, and it just couldn’t seem to figure that out.
  • Speaking of the heart rate monitor:  I think it would also be a nicer feature (assuming it actually worked reliably!) if it took regular heart rate samples without me having to ask for it.  It counts my steps without me asking it to, so I should also be able to look at the history and see an hourly (or whatever) history of my heart rate throughout the day.
  • Sensitivity…  This is an issue on a couple different fronts.  As John mentioned, holding the watch in the “I’m looking at you, please turn on now” pose is not as reactive as I would like.  In fact, as I’m writing this, I can’t even get it to turn on at all without touching it.  That makes it difficult to see the time, because now I have to waste a couple seconds starting at a black screen before finally deciding to tap the screen to turn it on.
  • Related to why that previous item annoys me so much:  I disabled the screen-always-on feature, because at night, that small amount of ambient glow is actually super distracting.  I’d like to be able to keep the screen always on (dim) during the day, and have it automatically switch to turning off the screen entirely either based on time-of-day or ambient light (I don’t think it has an ambient light sensor, so that is probably not possible).
  • Also tying into the annoyance of turning the screen on is the touch sensitivity and/or lag issues…  Sometimes when I get impatient in my “I’m looking at you, please turn on now” pose, I’ll tap the screen preemptively to turn it onBUT if it’s one of those rare times that it actually recognized my pose, it might actually turn on just before I tap (or more likely, it happens after my tap, but the tap recognition is so lagged that it doesn’t register a touch event until after it’s on), and then it brings up the google voice search screen… not what I wanted.  So now I have to try to swipe it away.  I’m used to being able to do pretty sloppy touch gestures on the phone, but in using the watch, it seems to be far less forgiving of slop.  So now not only does it incorrectly think I want to search for something, it is also incorrectly ignoring my swipe gesture to get rid of the search screen (or incorrectly interprets it as a swipe-up to see the menu options)!  Sometimes when I tap to get the menu options, the lag issue makes it incorrectly think I’m long-pressing, and that causes the “choose a watch face” screen to appear, which makes me choose a sad face 🙁  Swipes are interpreted as taps, taps interpreted as long-press, etc…  All adds up to being mildly annoying.

In the end, I’m still wearing itfor now, at least.  I think part of that is I’m just anxious to start playing around with the development aspect of it, since I have unfortunately not had a chance yet to play with developing anything for it.



 James O’Brien,  Android Developer

The Samsung Gear Live is the first watch I’ve worn in maybe 8 years, and I’m happy to report that it tells the time successfully. Personally this feels like what the next step in personal computing should have been, rather than Google Glass, as the smart watch is a pre-existing medium and is far from a distraction for those who wear it or those who the wearers interact with. At first I was disappointed with the lack of functionality, but over time I found that I liked that it isn’t a standalone device, rather an extension to your phone.

If I were to critic the Gear Live, my first port of call would be the strap. I do not feel comfortable with its fastening mechanism. I now take my watch off while riding my bike, which is unfortunate because riding is almost the perfect use case for the wear. While the watch has never unbuckled accidentally yet, there is something uncomforting about a $200 watch that could pop off at any moment.

Charging is the next issue I found with the Gear Live. The charger is a small block which clips to the back of the device and then connects via micro-usb. At first this was very stiff and difficult to click into place and then remove; I wasn’t surprised by the number of complaints from owners of this breaking. The strap also makes it impossible to charge the device face up because of the slight curvature where it is joined to the watch face. I was able to combat this by fastening my watch to a glasses case, or alternatively by forcefully bending the bottom strap inside.

The battery life has been very impressive. I turn the device off at night, and I have managed to easily have two days of constant use. The device doesn’t feel sluggish while navigating the cards and when the heart rate monitor works, its a nice novelty feature. Those around me will be happy to hear that I now leave my phone on silent, because the incoming buzz on my wrist means I no longer have to reach for my pocket.

Android Wear as a concept is a great. These two devices are not quite the finished product, but neither was my G1 and just like the G1, the more I use it the more I like it.

I think I’m going to get a Motorola 360.

 Bill Donahue,  Android Developer

Android Wear took one of the most annoying aspects of the Android OS, constant notifications of largely unwanted or irrelevant data, and made an entire experience around it. With a lot of work I think it has the potential to be useful, but as it stands today it feels like a product just for tech enthusiasts and hackers.

Android and Gradle : migrating to the new project structure

Recently, I decided to sit down and restructure an app the Gradle way. I had previously migrated the project to Gradle, and made the switch to Android Studio, but I had kept the legacy project structure:


This app has 2 flavors: free and paid. To support them, all of the common code was in a library project, which was used by free and paid projects, for a total of 3 projects. There was a lot of duplicated code with the multiple manifests, and wrapper classes, as well as code interrogating the package name to determine which features should be enabled. Gradle solves all of that mess quite nicely.

To start, I moved all of the library project code into the default Gradle structure, which looked something like this:

mv src/com/myapp/*.aidl src/main/aidl/com/myapp/
mv src/* src/main/java/
mv AndroidManifest.xml src/main/
mv res src/main/
mv assets src/main/

This puts everything under the src directory, where Gradle expects to find its source sets. Since this code was common to both the free and paid flavors of the app, everything went into the main source set.

As those files were now in the default locations, I removed all of these custom locations from build.gradle.

# don't need these anymore :)
java.srcDirs = ['src']
aidl.srcDirs = ['src']
res.srcDirs = ['res']
assets.srcDirs = ['assets']

I also switched the plugin in build.gradle from android-library to, since this would become my single project for building both flavors of the app.

At this point, based on the buildTypes in build.gradle, I could assemble debug and release apps. Since I have 2 flavors, I defined them alongside the buildTypes in build.gradle as productFlavors.

buildTypes {
productFlavors {
    free {
        applicationId = "com.myapp"
    paid {
        applicationId = "com.myapppro"

With Ant, I had multiple AndroidManifest.xml files which had unique package names, but with Gradle a single file can be used with the package name injected while building. This is done using applicationId, which is built into the plugin. Custom variables are also supported. For example, this app uses the Backup API, which requires a key unique to the app. For each productFlavor, I added a variable in the custom set manifestPlaceholders.

free {
    applicationId = "com.myapp"
    manifestPlaceholders = [
        backupApiKey: "myFreeBackupApiKeyValue"
paid {
    applicationId = "com.myapppro"
    manifestPlaceholders = [
        backupApiKey: "myPaidBackupApiKeyValue"

Custom variables can then be referenced in the AndroidManifest.xml like this:

    android:value="${backupApiKey}" />

If  you’re running into build errors when injecting values, you may need to specify the new manifest merger in build.gradle:

android {
    useOldManifestMerger false

The new manifest merger has been the default since version 11 of the gradle plugin.

The free flavor of the app has Ads in it, which requires defining an activity in the manifest. That definition isn’t need in the paid flavor. This is where the source sets come in. I have an AndroidManifest.xml in the main source set. Alongside the main directory, I added directories for free and paid.


In the free directory, I only need a slimmed down manifest with the differences:

<manifest xmlns:android="">
    android:configChanges="keyboard|keyboardHidden|orientation|screenLayout|uiMode|screenSize|smallestScreenSize" />

Gradle, through the plugin, merges the manifests together, so that the free flavor has everything it needs, without effecting the paid flavor.

The last difference between flavors was the app name. As with the manifest for the free flavor, I created a strings.xml in the paid source set with only the changed strings, as they will be merged with all of the common strings in the main source set.

The result was the only differences to maintain between the two flavors are the manifest and strings files, rather than two entire projects.


Those Backup API keys can be loaded from an external file, so that they’re not necessary shared along with the build.gradle file. For example, a file in the root of the project might contain:


Those variables would then be accessed in the build.gradle file like this:

manifestPlaceholders = [

Quick Tip: How to install or uninstall APKs on multiple Android devices with just one command

Recently, while working on a mobile project, I found myself spending a lot of time connecting a device, uninstalling the previous version of the Application Under Test (AUT), installing the new one, and then disconnecting the device, just to do it again on another 6 or 7 devices (I would like to talk about why it is better to test on actual devices than in a simulator, but that topic deserves its own blog post).

For this post, I want to describe a solution I found to manage all of the attached devices with a single command. First I obtained this device, (you can get it thru Amazon here)which is just one of many different options available, depending on the arrangement, number of ports, shape, etc. I picked this one because it was cheap and the switches come in handy because we can exclude devices just by switching OFF that specific device and there’s no need to connect/disconnect any device.

usb hub

Just adding ports to your computer helps, but we need to get the most of them. When working with Android devices and we want, for example, to install an app, we have to type the following command in the terminal:

adb install -r path/to/the/app/to/install.apk

 This works fine when you have a single device attached because adb is designed for a single device, but when you have multiple devices attached, you get an error,  like so:

- waiting for device -

error: more than one device and emulator

- waiting for device -

error: more than one device and emulator

- waiting for device -


 We need to specify to adb the device we want to send the command to. To do so, we need to first get the device ID of every device connected by typing:

adb devices

This command will return something like:

List of devices attached

04544fawebf0b595dc device

13928weff7c device

 Then to install on each device, we would need to copy each of these ids, and include them in the following command.

adb -s (deviceID) install -r path/to/the/app/to/install.apk

If I were to do this, I would need to copy each deviceID, type the above command seven times, pasting a different deviceID each time. Although this is better than connecting and disconnecting each device, this is still not the most productive way.

Searching the web for a solution, I found on Stackoverflow a script that solves this problem nicely.


First, copy and paste the following code in a new file called adb+

# Script adb+
# Usage
# You can run any command adb provides on all your currently connected devices
# ./adb+ <command> is the equivalent of ./adb -s <serial number> <command>
# Examples
# ./adb+ version
# ./adb+ install apidemo.apk
# ./adb+ uninstall
adb devices | while read line
  if [ ! "$line" = "" ] && [ `echo $line | awk '{print $2}'` = "device" ]
      device=`echo $line | awk '{print $1}'`
      echo "adb -s $device $@ ..."
      adb -s $device $@

Then store this new file in the folder containing adb within your Android SDK installation folder. This should most likely be the  platform-tools folder.


Using the script is very simple. When we have more than one device connected (always use adb devices first, just to make sure all your devices are connected) we just need to work as if we were using adb, with any “adb” command replaced with “adb+”. For example, if we want to install an app:

adb+ install -r path/to/the/app/to/install.apk

This gives us something like:

04544fabs23f0b595dc install -r /path/to/your/app/name_of_the_app.apk ...

4619 KB/s (13249277 bytes in 2.800s)

    pkg: /data/local/tmp/name_of_the_app.apk


1399834vskj28f7c install -r/path/to/your/app/name_of_the_app.apk ...

3608 KB/s (13249277 bytes in 3.585s)

    pkg: /data/local/tmp/name_of_the_app.apk



If you find that you get the following when you attempt to run adb+

-bash: adb+: Permission denied

Your bash script simply isn’t executable. This is very easy to fix, run this command from the directory containing the script:

chmod 755 ./adb+

Now try it, you should see what you were expecting.

That’s it. The new script will go thru each device, performing the same command.  The app will install on all devices connected, and you will save a few minutes. What do you think? Is this going to help you with your mobile testing? Let us know!

Web Developer Screenshot

The Best Browser Add-Ons for Quality Assurance

Recently, Firefox 29 was rolled out with a new redesign and, while downloading and installing it, I realized all the history Firefox and I have together. I believe the first version I installed was 2.7; since then we’ve been BFFs.

I’ve seen some browsers rise, grow, and die, like Flock (based on Firefox) and Rockmelt (based on Chrome). I have also seen others that always have been there, like Opera and Internet Explorer, but they have never been good enough.

As a Quality Assurance Tester, Chrome became a necessity to test because of its dominance in the market and, while I have grown accustomed to it, I still prefer Firefox.We testers need tools to help replicate user errors on the websites we’re testing, but the browsers alone are not enough for in-depth needs. This is when we can get help from some add-ons that can extend our browsers’ capabilities.

Below are some of the add-ons I use frequently and that all testers should utilize. This list is mostly focused on Firefox, but most of these add-ons (or similar ones) are also available for Chrome.


One of the most common tasks of a tester is taking screenshots. We need to take screenshots to back up our findings and sometimes we need to show the error to the developer. There are many of apps for this task, but my favorite is Fireshot. It has two killer features.

First, it is capable of taking screenshots of a complete page, even when the page is not showing completely in the browser. The second is the ability to add annotations within the app with some other great tools in it. These are important to us as testers because we can point out to our dev/design teams, stuff that is out of place, or bigger/smaller that it should, we can annotate steps to follow in the current page, to replicate some issue, etc. That helps or dev team to visualize what we are reporting and helps them realize faster where in the code that could be fixed.

fireshot screenshot

Another interesting feature is that once we install it in Firefox, it will prompt for installing it on Chrome and Internet Explorer. Unfortunately, this add-on is not available on Mac for any browser, but there are some other pretty good options for this OS. I’ve been using for my Firefox on Mac, and although is not as complete as Fireshot, it has been working pretty well for me. It can also take screenshots of a complete page, even when the page is not displaying completely on the browser. Fireshot is available for Free and there’s a PRO (paid) version for about $40  for a Lifetime License.


This is an add-on that has been around for a while with Firefox. Although now all browsers have their own debugger tools, I still consider this one a must-have. I keep liking it because I’m used to it, and its interface, in my opinion, is more friendly. If we compare it to Chrome’s native tool for example, Firebug is easier to use because everything is one or maybe two clicks away, in Chrome’s native tool there’s some cases we have to navigate through some three-like menus to get some kind of info., like cookies.

Firebug Screenshot

By using it we can edit the cookies, delete any specific cookie to replicate certain behavior, we can navigate through the HTML code of the current website and its CSS, we can even modify it and see the changes on the fly, for example, to fix some little CSS issue, we can give a suggestion on how to fix it, or actually find the part of the code that is causing the problem and that will save some time to our dev to fix the problem. We can also see errors from the console, copy and paste the response of a call and report back to our dev with that information, that would help them debug the issue and a lot of more stuff. This is, if not the most, one of the most important tools for a Tester. It is also expandable, we can install addons on it like Yslow or Firepath (more on this one later).

Every web tester should know how to use Firebug or any of the native alternatives for all the browsers. Firebug is available for Firefox in Mac and Windows and it is also available in a pretty light version for Safari in Mac.

Measure It

Lets say that we want to make sure that the measures of that textbox or that other button meet the requirements described in the specs. We could use Firebug to search through the CSS of the application. However, sometimes the code is not that clean or we can have problems finding an specific item. Measure It is a pretty good tool for this situation. This add-on adds a button into our browser that when clicked will let us draw an area and tell us the measurements on pixels of it. Easy and quick.

MeasureIt Screenshot

It is currently available for free in Firefox and Chrome, in both Mac and Windows.


AdBlock Plus is a tool that can be very useful if we are not currently working with ads testing or our app doesn’t need them to work. This add-on blocks all the ads from a website based on specific filters we choose. With this add-on, our app can work faster because it doesn’t load them, bringing better performance to our app and less distraction to us.

ABP Screenshot

However, we have to be careful with this add-on as it can hide some bugs that our users are experiencing. For example, when an ad is broken, it can cause a bug in our app and we won’t be aware of it if we have this add-on active. Or, worse, it can cause us a momentary panic if it inadvertently shows us a bug that is not happening when the ads are present in our app. When the layout of an app depends on the ads, if the ads are not present, the layout might break. I’ve always find it useful to get my Application Under Test (AUT) better performance for my tests. This add-on is available for free in Firefox and Chrome for both Mac and Windows.

Link Evaluator

As its name implies, this add-on evaluates all the links in a given page and it colors them green, yellow, or red depending on their response. It colors them green when it receives a 200 or 400 response, and red if it gets a 404, 500, or some other error response. It is very useful to check all the links in a page quickly and to avoid missing any of them. In this way, the tester doesn’t need to click on each one to see if there are any dead ends or some other bad user experience.

Link Evaluator Meetme

It is available for free in Firefox on Mac or Windows, and, although it is not available for Chrome, there are other options for this one. The most similar is Link Checker that is available for free on Mac and Windows.

Dummy Lipsum

This add-on helps us by generating dummy text. Suppose we want to fill a form or see how some text looks in a page. After installing this add-on, we would have a button on our browser’s toolbar that, on click, will bring us a dialog where we can pick between some options, like how much paragraphs or words, if we want to include punctuation or html tags, etc.

Dummy Lipsum Screenshot

After selecting all our options, we just need to click Generate button, then Copy to Clipboard button and then we can paste it anywhere.

This add-on is available for free only for Firefox on Mac and Windows. There are similar tools available there for Chrome or any other browser, like YALIG (Yet Another Lorem Ipsum Generator) that is available for free in Chrome in both Mac and Windows. There are other fun Lorem Ipsum Generators that are not add-ons, but are useful and will add a touch of creativity to our tests. We can add them to our bookmarks for easy access.

  • Fillerama generates dialogs from shows like Futurama, Dexter, Arrested Development and more.
  • Pirate Ipsum  generates random pirate like sentences.
  • Obama Ipsum generates random President Obama quotes.
  • Trollen Ipsum generates trolling phrases between, for example,  Apple Fans to Android Fans and viceversa.
  • Quote Ipsum generates random famous quotes.
  • Picksum Ipsum generates phrases from movie dialogs from characters of Michael Caine, Jim Carrey, Clint Eastwood and Morgan Freeman.

Web Developer

This tool adds a menu to our browser with a whole world of options that can help us to make our day-to-day work a little bit easier. What I’ve used it for is the cookies menu, which lets us clear cookies completely. Sounds like nothing special, right?. Where this is useful and different is that it lets us clear just the cookies from our current session or just current domain cookies. This is a major help for when we have login credentials for various sites and we want to clear cookies for just one of them. With this tool we can also play with the CSS, disabling it, changing it, adding stylesheets to the current page.

Web Developer Screenshot

We can also disable the cache, disable cookies, disable javascript. All that can help us to test certain conditions in an application. It can help us to work with Forms, clearing all fields, with just one click, auto-filling forms, etc. It can also work with images, for example it can display image sizes, disable all images, display alt texts and tons of other features. This one is a must have!

This add-on is available for free in Firefox, Internet Explorer, Chrome, and Opera for Windows and Firefox and Chrome in  Mac OSX.

URL to QR code

Not talking about a specific add-on here, there’s a bunch of them out there for all browsers and OS combinations. What does they do? Very simple, they generate a QR Code using the URL for the current viewing web page. Something like:

When we use a mobile device like a phone or a tablet and we scan this QR Code, it will open the browser in the device and navigate to that URL. In that way, we can easily type our URL in our desktop browser, then take a picture with the device with a QR Code reader. In this way, we would not need to type in those tricky small touchscreen keyboards. This saves some time and hassle from typing if we are working on a browser-based mobile app or website.

URLToQRCode Screenshot

I have tried URLtoQRcode on my Firefox + Mac environment. On my Chrome in both, Mac and Windows I have QR Image from URL. But in my Firefox + Windows I use Etao QR Code, all them are practically the same thing and all they are free.


The first automation tool in this post, iMacros allows us to record steps that we are doing manually and while recording it saves those steps as code. Once recorded, we can edit, add, or remove steps on it’s own IDE. And finally we can play them over and over again. While not the most popular app available for this, I find it as good or better than Selenium, the most popular tool out there.

iMacros Screenshot

iMacros has its own versions free for Firefox, Chrome, and Internet Explorer in both Mac and Windows. In that way, we can create our script in Chrome and play it there, but also in Firefox and Internet Explorer.

There are a few caveats preventing it from being perfect. This free add-on has some command restrictions on its Chrome and IE versions, compared with its Firefox free version. And the Firefox free version has some other restrictions that the PRO version doesn’t have. The PRO version is more complete, allowing us to use their own browser, and code scripts in almost all well-known programming languages. However, it is very expensive. For the frugal-minded, the Firefox version is pretty capable–we can build pretty complex scripts there.

Selenium IDE

Who hasn’t used or heard about this tool? It’s free, compatible with all major browsers and OS (including Linux), and programming languages. What else we can ask for, right?

Selenium IDE Screenshot

This IDE is pretty much the same thing as iMacros, letting us record steps made manually and play them back later. All steps are recorded in Selenesse, the Selenium language. This tool has other add-ons that let us export our scripts to other languages as python, ruby, php, java, etc. It also has its own add-ons created by the community that further expand the capabilities of this IDE.


Last but not least, now that we are talking about automation, I would like to talk about Firepath. Who hasn’t had problems with the way Selenium’s playback functions from time to time? Firepath is an add-on for Firebug. It lets us select an element from the web page we are on and it will tell us its Xpath or CSS selector. It also works backwards–we can specify an Xpath or CSS selector in the box and it will mark for us the element that meets that selector. We can then use that information in our scripts.

FirePath Screenshot

So, what do you think about these tools? Do you like them? Are you already using any of them? Which ones have I missed? Give us a shout and let us know!