У меня следующие требования. Пользователь должен иметь возможность запланировать повторяющееся напоминание в моем приложении, которое будет запускать push-уведомление в точное время каждый день.
Это один из тех вопросов, которые, как я надеялся, я в конечном итоге не отправлю, поскольку при его написании были рекомендованы аналогичные вопросы. Однако несколько членов команды часами просматривали документацию для разработчиков Android и Stackoverflow, и мы, похоже, не приблизились к ответу, так что вот и мы.
Если я создам напоминание и настрою запускать уведомление через 5 минут в будущем, уведомление сработает нормально.
Я подозреваю, что это может быть проблема, вызванная изменениями в энергосбережении, блокировке пробуждения и т. Д., Введенными в Android P, поскольку у нас не было этой проблемы до обновления нашего целевого SDK до 28. При этом я не уверен, что это Единственная проблема, но я могу постоянно воспроизводить проблему на Pixel и Pixel 3 XL под управлением Android P.
Пример, когда уведомление не запускается, происходит, когда, например, пользователь устанавливает напоминание на какое-то время посреди ночи (предположительно, когда пользователь спит и, следовательно, не будет использовать телефон в течение нескольких часов). Эти напоминания не срабатывают никогда.
В настоящее время я пытаюсь сделать это с помощью диспетчера аварийных сигналов.
Эта проблема похожа на другой вопрос, в котором используется setRepeating Метод, который мы нашли, не работает. Вместо этого мы используем метод setExactAndAllowWhileIdle диспетчера сигналов тревоги. Мы также попробовали ту же реализацию с менеджерами тревог setAlarmClock, который, согласно документации Android," будет разрешен запускаться, даже если система находится в режиме ожидания с низким энергопотреблением (также известный как дремота) ", однако это также не увенчалось успехом.
Я подозреваю, что причина, по которой это не работает, заключается в том, что setExactAndAllowWhileIdle не срабатывает, когда телефон находится в режиме ожидания, аналогично проблемам, выраженным в этот вопрос. В этом вопросе рекомендуется использовать Firebase JobDispatcher, но поскольку это внутреннее уведомление, я должен запускать уведомление с сетевым подключением или без него, что, похоже, исключает Firebase JobDispatcher в качестве опции. Этот вопрос также указывает на то, что как только телефон выходит из спящего режима, пользователь получает уведомление, однако мы никогда не получаем уведомление, они, похоже, потеряны из-за отсутствия лучшего термина.
Я добавил разрешение блокировки пробуждения в свой AndroidManifest.xml:
<uses-permission android:name="android.permission.WAKE_LOCK" />
Вот как мой приемник регистрируется в AndroidManifest.xml
<receiver android:name="com.myapp.receiver.AlarmReceiver">
</receiver>
Вот моя текущая реализация:
Ожидающее намерение обработки уведомлений
Intent i = new Intent(context, ScheduleAllReceiver.class);
PendingIntent scheduleAllPendingIntent = PendingIntent.getBroadcast(context, SCHEDULER_DAILY_ALL, i, PendingIntent.FLAG_UPDATE_CURRENT);
Впоследствии я вызываю метод createAlarm следующим образом
createAlarm(context, scheduleAllPendingIntent, calendar.getTimeInMillis());
Создание будильников
public static void createAlarm(Context context, PendingIntent pendingIntent, long timeinMilli) {
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
if(alarmManager != null) {
if (Build.VERSION.SDK_INT >= 23) {
alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP, timeinMilli, pendingIntent);
} else {
alarmManager.setExact(AlarmManager.RTC_WAKEUP, timeinMilli, pendingIntent);
}
}
}