Ravindra
Ravindra

Reputation: 289

Android repeat alarm manager in not triggering immediately

My code:

Calendar calSet = Calendar.getInstance();
calSet.set(Calendar.HOUR_OF_DAY, 11);
calSet.set(Calendar.MINUTE, 20);
calSet.set(Calendar.SECOND, 0);
calSet.set(Calendar.MILLISECOND, 0);

PendingIntent pi=PendingIntent.getBroadcast(context,0,myIntent,PendingIntent.FLAG_UPDATE_CURRENT);
AlarmManager alarmManager = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
alarmManager.set(AlarmManager.RTC_WAKEUP,calSet.getTimeInMillis(),pi);

and say, I'm executing at 11:30. Alarm triggers immediately (which is expected). But, for the same when I use

alarmManager.setRepeating(AlarmManager.RTC_WAKEUP,calSet.getTimeInMillis(),24*60*60*1000,pi);

alarm is not triggered immediately. There is a delay up to 1 minute (which is not expected). I want repeating alarm to trigger immediately without any delay.

Could someone please help me with this?

Upvotes: 1

Views: 2323

Answers (1)

hqt
hqt

Reputation: 30284

You should change your code to :

PendingIntent pi=PendingIntent.getBroadcast(context,0,myIntent,PendingIntent.FLAG_UPDATE_CURRENT);
AlarmManager alarmManager = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT) {
      alarmManager.setExact(AlarmManager.RTC_WAKEUP, calSet.getTimeInMillis(), pi);
} else {
      alarmManager.set(AlarmManager.RTC_WAKEUP, calSet.getTimeInMillis(), pi);
}

@Edit Above code will work for set exactly time. But this section will explain about repeating for alarm manager.

For api below 19, we use AlarmManager.setRepeating() will make alarms trigger exactly at specified time periodically. But from 19 and newer, this method won't work again and there aren't any apis support this behavior. I think this api change make developers thinking more carefully when they create a timer. Because a timer trigger at exactly time periodically will drain battery so much.

If you want you must do on your own. Firstly, you set AlarmManager.setExact() and when alarm trigger, you will make alarm trigger again next time manually

Here is the code:

PendingIntent pi=PendingIntent.getBroadcast(context,0,myIntent,PendingIntent.FLAG_UPDATE_CURRENT);
AlarmManager alarmManager = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT) {
     alarmManager. setExact(AlarmManager.RTC_WAKEUP, calSet.getTimeInMillis(), pi);
} else {
     alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calSet.getTimeInMillis(), pi);
}

And in your intent, where you put handle code, you should check if android api >= 19, application will create new alarm for the next event.

if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT) {
         doSomething();
         // calculate time for next event
         Calendar nextEvent = calcNextEvent();
         // and set alarm again
         alarmManager. setExact(AlarmManager.RTC_WAKEUP, nextEvent.getTimeInMillis(), pi);
 } else {
         doSomething();
 }

I think this is problem in android api design. Old code should work on newer version. Anyway, this new api design make everything clearer for developer, better for system(save battery). Of course, when you use new api :)

Hope this help :)

Upvotes: 2

Related Questions