Android AlarmManager 无法正常工作
Android AlarmManager doesn´t work properly
我在我的应用程序上使用警报管理器,我需要在 2:00 AM 重置一些 DefaultSharedPreferences 值(设置为 0)。
我的主 activity 上有一个函数,只要打开应用程序就会调用该函数:
protected void setUpAlarmManager(){ //To delete the data of each day and pass it to Records database
AlarmManager alarmManager = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(this, AlarmReceiver.class);
PendingIntent pIntent = PendingIntent.getBroadcast(this, 1, intent, PendingIntent.FLAG_CANCEL_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 02);
calendar.set(Calendar.MINUTE, 00);
calendar.set(Calendar.SECOND, 00);
alarmManager.setInexactRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY , pIntent); //set repeating every 24 hours
Log.i("Set", "Alarm set");
}
然后我使用 BroadcastReceiver 重置值。
package com.javierd.iifym;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.util.Log;
import com.javierd.iifym.sqlite.RecordsDataSource;
//To delete the data of each day and pass it to Records database
public class AlarmReceiver extends android.content.BroadcastReceiver {
private RecordsDataSource dataSource;
private Utils utils;
@Override
public void onReceive(Context context, Intent intent) {
Log.i("Time", "TIMEEEE!!!!");
SharedPreferences macros = context.getSharedPreferences(context.getPackageName() + "_preferences", Context.MODE_PRIVATE); //As we store data using DefaultSharedPreferences, not SharedPreferences
SharedPreferences.Editor editor = macros.edit();
editor.putString("eaten_carbs", "0");
editor.putString("eaten_proteins", "0");
editor.putString("eaten_fats", "0");
editor.apply();
}
}
接收器正常工作,问题是 AlarmManager 随机工作。虽然它应该是在 2:00 上午,也许你在 16:00 进入应用程序,保存一些值,在下次你在 17:30 进入时,这些值被删除,或者可能没有,这是随机的,我不明白。
这样的效果我相信是使用AlarmManager.setInexectRepeating(int, long, long, PendingIntent)
造成的。
根据documentation
Your alarm's first trigger will not be before the requested time, but
it might not occur for almost a full interval after that time.
当您使用此方法时,Android 同步多个不精确重复的警报并同时触发它们。考虑到间隔是一天,警报可能会在 17:30.
触发
如果闹钟需要在上午 2:00 准时触发,那么我建议改用 AlarmManager.setRepeating(int, long, long, PendingIntent) 方法。
请注意,建议尽可能避免使用精确警报,以减少电池电量消耗。
已更新。
我建议检查触发时间是否在过去。
你能试试吗
protected void setUpAlarmManager(){ //To delete the data of each day and pass it to Records database
AlarmManager alarmManager = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(this, AlarmReceiver.class);
PendingIntent pIntent = PendingIntent.getBroadcast(this, 1, intent, PendingIntent.FLAG_CANCEL_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 2);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.SECOND, 0);
if (Calendar.getInstance().after(calendar)) {
calendar.add(Calendar.DAY_OF_MONTH, 1);
}
alarmManager.setInexactRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY , pIntent); //set repeating every 24 hours
Log.i("Set", "Alarm set");
}
我在我的应用程序上使用警报管理器,我需要在 2:00 AM 重置一些 DefaultSharedPreferences 值(设置为 0)。 我的主 activity 上有一个函数,只要打开应用程序就会调用该函数:
protected void setUpAlarmManager(){ //To delete the data of each day and pass it to Records database
AlarmManager alarmManager = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(this, AlarmReceiver.class);
PendingIntent pIntent = PendingIntent.getBroadcast(this, 1, intent, PendingIntent.FLAG_CANCEL_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 02);
calendar.set(Calendar.MINUTE, 00);
calendar.set(Calendar.SECOND, 00);
alarmManager.setInexactRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY , pIntent); //set repeating every 24 hours
Log.i("Set", "Alarm set");
}
然后我使用 BroadcastReceiver 重置值。
package com.javierd.iifym;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.util.Log;
import com.javierd.iifym.sqlite.RecordsDataSource;
//To delete the data of each day and pass it to Records database
public class AlarmReceiver extends android.content.BroadcastReceiver {
private RecordsDataSource dataSource;
private Utils utils;
@Override
public void onReceive(Context context, Intent intent) {
Log.i("Time", "TIMEEEE!!!!");
SharedPreferences macros = context.getSharedPreferences(context.getPackageName() + "_preferences", Context.MODE_PRIVATE); //As we store data using DefaultSharedPreferences, not SharedPreferences
SharedPreferences.Editor editor = macros.edit();
editor.putString("eaten_carbs", "0");
editor.putString("eaten_proteins", "0");
editor.putString("eaten_fats", "0");
editor.apply();
}
}
接收器正常工作,问题是 AlarmManager 随机工作。虽然它应该是在 2:00 上午,也许你在 16:00 进入应用程序,保存一些值,在下次你在 17:30 进入时,这些值被删除,或者可能没有,这是随机的,我不明白。
这样的效果我相信是使用AlarmManager.setInexectRepeating(int, long, long, PendingIntent)
造成的。
根据documentation
Your alarm's first trigger will not be before the requested time, but it might not occur for almost a full interval after that time.
当您使用此方法时,Android 同步多个不精确重复的警报并同时触发它们。考虑到间隔是一天,警报可能会在 17:30.
触发如果闹钟需要在上午 2:00 准时触发,那么我建议改用 AlarmManager.setRepeating(int, long, long, PendingIntent) 方法。
请注意,建议尽可能避免使用精确警报,以减少电池电量消耗。
已更新。
我建议检查触发时间是否在过去。
你能试试吗
protected void setUpAlarmManager(){ //To delete the data of each day and pass it to Records database
AlarmManager alarmManager = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(this, AlarmReceiver.class);
PendingIntent pIntent = PendingIntent.getBroadcast(this, 1, intent, PendingIntent.FLAG_CANCEL_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 2);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.SECOND, 0);
if (Calendar.getInstance().after(calendar)) {
calendar.add(Calendar.DAY_OF_MONTH, 1);
}
alarmManager.setInexactRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY , pIntent); //set repeating every 24 hours
Log.i("Set", "Alarm set");
}