Activity: forget onPause to handle focus changes

onPause to handle focus changes seems to be a good way, but actually it is not!

Even if, in the lifecycle graph, the onPause method seems to be called when the activity loose the focus, it is not always the case!

I spent one whole afternoon on a very silly issue about the Android activity lifecyle when the focus changes and the device is turned on. I want to share it with you to avoid you some hours of investigation!

Context

In my Stopeen Android app, sometimes I launched an alarm (ringtone and vibrations). When a ringing alarm was ongoing (i.e. the activity AlarmActivity was create), pressing the Home button stopped the alarm (i.e. the activity killed itself). In order to do that, I overrode the onPause method, supposed to be called when the app loose the focus. When onPause was called, the activity killed itself.

On an old device with Android 2.3, it worked perfectly fine, but when I tested on Android 4.4, a strange behavior happened. When my alarm was launched and the device screen was off, the device woke up (expected behavior) but the alarm stopped after half of a second (unexpected behavior). This did not happen if the screen device was already turned, only if it was off.

Hey clever boy! This bug surely came from the PendingIntent you used with the AlarmManager, or from the Wakelock you relied on, or from the way you used the WindowManager to turn on the screen.

Of course I thought that at the beginning, but actually it was none of them: it was the fault of the Activity default lifecycle.

The proof

To detect that, I cleaned almost all my AlarmActivity and added logs in the lifecycle methods:

Do you see the simple log in onPause? Actually I did the same for onStart, onRestart, onResume, onStop and onDestroy.

Here is the result I got on a Samsung Galaxy S5 mini (Android 4.4.2):

When the screen is on When the screen is off
Alarm begins
Alarm Stops

WTF?! Why is the activity started, stopped and then restarted when the screen goes from off to on?

Actually I don’t know, it is not very logical, both cases should be the same. Instead, when the device is turned on, the lifecycle starts very differently. In my case, I was killing the activity when onPause was called, so you can clearly see that when doing that, my activity is creating (onCreate) and killed (onPause) in the same cycle.

Conclusion: alternative to onPause to handle focus loss

After a while I found on this post that the Android default lifecycle has changed between Android 4.0 and Android 4.1.

So instead of using onPause to handle focus loss, now I use onWindowFocusChanged. It works perfectly fine, even if the screen is off.

About Nicolas Form

I'm Nicolas Form, multi-skill programmer, aesthete and joyful French guy. On this blog I share my tips and tutorials about programming and IT in general. I am freelance, so you can also contact me about a website, an Android app or any other software you need. Check my portfolio and drop me a line!
This entry was posted in Android. Bookmark the permalink.

One Response to "Activity: forget onPause to handle focus changes"

Leave a Reply

Your email address will not be published. Required fields are marked *


*


This site uses Akismet to reduce spam. Learn how your comment data is processed.

Activity: forget onPause to handle focus changes

by Nicolas Form time to read: 2 min
1