Jan Schejbal
Jan Schejbal

Reputation: 4033

Is there an easier way to use AlarmManager or to set real-time based alarms?

It seems that the only way to time actions based on the actual elapsed time (as opposed to uptime, which stops when the device sleeps) is the AlarmManager.

Is there an an easy way to do "wallclock"-based delayed exectuion, for example through an open-source wrapper around AlarmManager?

For normal timing operations, you can use a handler, which is as easy as such a simple task should be:

However, Handler only supports uptime-based delays, which sometimes are not sufficient (e.g. if you want to check the server for new messages every 15 minutes).

If you want those, it seems that you have to use the AlarmManager, which is not very comfortable:

Upvotes: 0

Views: 567

Answers (1)

CommonsWare
CommonsWare

Reputation: 1006744

For normal timing operations, you can use a handler

Only from a foreground activity. Any other use of Handler for long-term polling is unreliable at best, even ignoring your concerns regarding uptime calculations.

Define an action for your alarm

This is not necessary. It is not even a good idea.

Create a receiver (either by creating a dedicated receiver class and declaring it the manifest, or implementing the interface, registering the receiver using registerReciever, and unregistering it when done)

If you want the event to occur when you are not in the foreground and the alarm to go off while the device is asleep (_WAKEUP alarms), the manifest-registered receiver is required. If _WAKEUP is not needed, a service will suffice. If you only need to be in the foreground and receive the event in an activity, use createPendingResult() to give you a PendingIntent that will trigger onActivityResult() of your activity. Though, in this latter case, it would make more sense to use postDelayed() on a View or Handler.

and store the pending intent if you want to cancel the alarm

If storing a PendingIntent is an option, then Handler is all you need, and AlarmManager is unsuitable. To cancel an alarm, you need an equivalent PendingIntent (one where the underlying Intent objects match based on filterEquals() and where the PendingIntent operation [activity, service, broadcast] is the same).

When you want to cancel the alarm, cancel it using the stored pendingIntent

No, you cancel it by creating an equivalent PendingIntent.

Should you decide to have multiple intents or intents with changing data, you will have to save them all to clean up the alarm manager afterwards

No, you cancel them by creating an equivalent PendingIntent.

Is there an an easy way to do "wallclock"-based delayed exectuion, for example through an open-source wrapper around AlarmManager?

Creating wrapper code for this that covers 80% of the work would have taken you less time than it did to write your question. I am not aware of a dedicated library for this, partly because there wouldn't be all that much to it.

Or, use ScheduledExecutorService and a WakeLock, for short-term things. This is unsuitable for "every 15 minutes" scenarios, as it keeps the device awake all of the time.

Upvotes: 0

Related Questions