Calendar calendars = Calendar.getInstance();
calendars.set(Calendar.HOUR_OF_DAY, hour);
calendars.set(Calendar.MINUTE, min);
calendars.set(Calendar.SECOND, 0);
calendars.set(Calendar.MILLISECOND, 0);
calendars.set(Calendar.AM_PM, timezone);
PendingIntent pendingIntent = PendingIntent.getBroadcast(getBaseContext(), currentTime, intent, PendingIntent.FLAG_UPDATE_CURRENT);
if (Build.VERSION.SDK_INT < 23) {
if (Build.VERSION.SDK_INT >= 19) {
alarmManager.setExact(AlarmManager.RTC_WAKEUP, calendars.getTimeInMillis(), pendingIntent);
} else {
alarmManager.set(AlarmManager.RTC_WAKEUP, calendars.getTimeInMillis(), pendingIntent);
}
} else { alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, calendars.getTimeInMillis(), pendingIntent);
}
In my App if I set Alarm within an hour then it is working fine but for long duration it is not working.
I have searched a lot regarding the alarm issue we are facing and found out that in latest android updates android OS is killing the broadcast receivers if memory needed for other task OR in low battery state OR without a reason.
In some cases if mobile is in idle / doze mode that time also alarm is not working.
Related
I've searched around but did not found the solution. My application is required to show daily notifications on different times decided by user but alarmmanager is not working properly, If I set time for next few minute it will show notification but most of the time when I'm not using device it do not works.
this is what i've been trying to set repeating alarm.
Intent intent = new Intent(Reminder.this, AlarmReceiverDaily.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(Reminder.this, 100, intent, PendingIntent.FLAG_UPDATE_CURRENT);
AlarmManager alarmManager = (AlarmManager) Reminder.this.getSystemService(ALARM_SERVICE);
alarmManager.setInexactRepeating(AlarmManager.RTC_WAKEUP, targetCal.getTimeInMillis(), 24 * 60 * 60 * 1000, pendingIntent);
How I can set repeating alarm even if my device is in Doze mode from the following code?
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
alarmManager.setAlarmClock(new AlarmManager.AlarmClockInfo(targetCal.getTimeInMillis(),pendingIntent),pendingIntent);
else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
alarmManager.setExact(AlarmManager.RTC, targetCal.getTimeInMillis(), pendingIntent);
else
alarmManager.set(AlarmManager.RTC, targetCal.getTimeInMillis(), pendingIntent);
If I can not use setAlarmClock() with repeating alarm then what solution you prefer to make repeating alarm and it must work.
You have to use:
if( Build.VERSION.SDK_INT >= 23 ){
alarmManager.setExactAndAllowWhileIdle( ... );
}
I have implemented AlaramManager with background service, It works fine on devices below Oreo. But doesn't work on android Oreo and above as Google stopped background services from working on Oreo and Above.
Is there any source code or any kind resource which will help me to set alarms on android Oreo or above devices?
After searching for a while I found out about JobsIntentService, but couldn't found enough information about it. And I don't know if it is the way to go. Basically, I want to show notifications on particular dates and times.
Thanks in Advance.
Please try bellow method it will work for you.
/**
* Method for start Alarm on defined minute
* #param minutes Minute when you want to start after current time
* #param context
*/
public static void startAlarm(Context context, int minutes) {
Logger.print("AlarmReceiver startAlarm called");
Intent alarmIntent = new Intent(context, WakefulBroadcastReceiverService.class);
alarmIntent.setAction("testAPP");
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 123451, alarmIntent, PendingIntent.FLAG_CANCEL_CURRENT);
AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
manager.cancel(pendingIntent);
long alarmPeriodicTime = System.currentTimeMillis() + Utils.getTimeInMilliSec(Constant.TimeType.MINUTE, minutes);
if (Build.VERSION.SDK_INT >= 23) {
manager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
} else if (Build.VERSION.SDK_INT >= 19) {
manager.setExact(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
} else {
manager.set(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
}
}
I want to set alarm at particular time with hour and minute.
I am trying to do it this way:
AlarmManager alarm = (AlarmManager) getSystemService(ALARM_SERVICE);
Calendar cal = Calendar.getInstance();
cal.set(Calendar.HOUR_OF_DAY, 11);
cal.set(Calendar.MINUTE, 30);
Intent intent = new Intent(this, AlarmService.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, intent, 0);
alarm (AlarmManager.RTC_WAKEUP, calAlarm.getTimeInMillis(), pendingIntent);
But alarm is not fired at particular hour and minute.
I have seen many example on stackoverflow and other blogs, but that also didn't work for me.
Starting from Android 6.0 (API level 23), Android introduces Doze feature that extend battery life for users by managing how apps behave when a device is not connected to a power source.
Doze is particularly likely to affect activities that AlarmManager alarms and timers manage, because alarms in Android 5.1 (API level 22) or lower do not fire when the system is in Doze.
To help with scheduling alarms, Android 6.0 (API level 23) introduces two new AlarmManager methods: setAndAllowWhileIdle() and setExactAndAllowWhileIdle(). With these methods, you can set alarms that will fire even if the device is in Doze.
Note: Neither setAndAllowWhileIdle() nor setExactAndAllowWhileIdle() can fire alarms more than once per 9 minutes, per app.
AlarmManager alarmManager = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(this, AlarmService.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, intent, 0);
if (Build.VERSION.SDK_INT >= 23) {
alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
} else if (Build.VERSION.SDK_INT >= 19) {
alarmManager.setExact(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
} else {
alarmManager.set(AlarmManager.RTC_WAKEUP, alarmPeriodicTime, pendingIntent);
}
More info:
https://developer.android.com/training/monitoring-device-state/doze-standby.html
You can use:
AlarmManagerCompat.setAlarmClock(alarmManager, time, triggerIntent, showIntent)
You can find the docs here.
Below is my code
public static void startAlarmManager(Context context, Date date) {
Intent alarmIntent = new Intent(context, AlarmReceiver.class);
alarmIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
PendingIntent recurringAlarm = PendingIntent.getBroadcast(context.getApplicationContext(), NOTIFY_ME_ID,
alarmIntent, PendingIntent.FLAG_UPDATE_CURRENT);
AlarmManager alarms = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarms.cancel(recurringAlarm);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
alarms.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, date.getTime(), recurringAlarm);
} else if (Build.VERSION.SDK_INT >= 19) {
alarms.setExact(AlarmManager.RTC_WAKEUP, date.getTime(), recurringAlarm);
} else {
alarms.set(AlarmManager.RTC_WAKEUP, date.getTime(), recurringAlarm);
}
}
This code works correctly in all device on which I have tested. But I am facing issue with Wiko Jerry mt6580.
In this device alarm is triggered after five minutes, of the intended time.
Note: The tests made with the devices connected to charger, to not
active o doze mode.
Any suggestions why I am getting this problem, or how to solve it would be of great help.
-Thanks!
I have this method which should schedule alarms but when the time arrives it doesn't start the pendingintent ??
public void setAlarm(String name, long time) {
AlarmManager am = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
Intent dialog = new Intent(this, SubActivity.class);
dialog.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
PendingIntent pi = PendingIntent.getActivity(this, 0, dialog, 0);
if (Build.VERSION.SDK_INT >= 19) {
if (System.currentTimeMillis() < time) {
am.setExact(AlarmManager.ELAPSED_REALTIME_WAKEUP, time, pi);
}else{
time+=(AlarmManager.INTERVAL_DAY*7);
am.setExact(AlarmManager.RTC_WAKEUP, time, pi);
}
} else {
am.setRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP, time, AlarmManager.INTERVAL_DAY * 7, pi);
}
}
The problem is you are using a PendingIntent for an Activity, which will not necessarily keep the device awake long enough for the Activity to get started. You'll have to use a PendingIntent for a BroadcastReceiver which leverages a wake lock to keep the device awake until your app code can run. WakefulBrodcastReceiver is a good choice, or you can roll your own as needed. See this article for an explanation and sample of how to use alarms to wake the device: http://po.st/7UpipA