首页 > 解决方案 > AlarmManager 警报在错误的时间响起

问题描述

我正在尝试使用 AlarmManager 创建示例警报应用程序。但是,即使我设置了触发它的特定时间,警报也会在不同的时间响起。

设置闹钟:

        Calendar calendar = Calendar.getInstance();
        calendar.setTimeInMillis(System.currentTimeMillis());
        calendar.set(Calendar.HOUR_OF_DAY, 18); // trigger at 6 PM

        Intent notifyIntent = new Intent(context, CheckupAlarmReceiver.class);
        PendingIntent pendingIntent = PendingIntent.getBroadcast
                (context, 100, notifyIntent, PendingIntent.FLAG_UPDATE_CURRENT);
        android.app.AlarmManager alarmManager = (android.app.AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
        if (alarmManager != null) {
            alarmManager.setInexactRepeating(android.app.AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(),
                    android.app.AlarmManager.INTERVAL_DAY, pendingIntent);
        }

显现:

<receiver
      android:name=".notifications.CheckupAlarmReceiver"
      android:enabled="true"
      android:exported="false" />

要重新迭代,警报工作正常。它只是在错误的时间触发。日历实例是否没有考虑时区?我在这里做错了什么?

标签: androidbroadcastreceiveralarmmanager

解决方案


setInexactRepeating()顾名思义,您的设置无法在您指定的确切时间触发。这是一种优化,因此操作系统会尝试获取多个警报,这些警报应该在相似的时间触发以同时触发所有警报。

相反,您可以使用void setExactAndAllowWhileIdle(int type, long triggerAtMillis, PendingIntent operation). 请参阅文档

例子:

 alarmManager.setExactAndAllowWhileIdle(android.app.AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pendingIntent);

正如其建议的那样,您不应使用具有准确时间的重复警报。相反,您可以等到确切的警报响起,然后为第二天安排另一个警报。

对于低于 23 的 API,您可以使用void setExact(int type, long triggerAtMillis, PendingIntent operation). 对于低于 19 的 API,您可以void setRepeating(int type, long triggerAtMillis, long intervalMillis, PendingIntent operation)像往常一样使用预期的精确触发。


推荐阅读