除了一个方面之外,我有一个功能完全正常的闹钟功能:我为触发闹钟设置的时间并不总是它触发的时间。
我想了一会儿警报可能会在几秒钟内完成,而不是毫秒。在重新阅读文档之后,这个想法被驳回了。
在我再解释一下之前,我现在要发布重要的代码:
BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
startAlarm(findViewById(R.id.reset));
Log.d("test", "reseting");
}
};
public void startAlarm(View view) {
//setup
EditText nameInput = (EditText) this.findViewById(R.id.nameInput);
EditText firstAlertInput = (EditText) this.findViewById(R.id.firstAlertInput);
EditText intervalInput = (EditText) this.findViewById(R.id.intervalInput);
EditText descriptionInput = (EditText) this.findViewById(R.id.descriptionInput);
SharedPreferences sp = PreferenceManager.getDefaultSharedPreferences(this);
SharedPreferences.Editor editor = sp.edit();
AlarmManager alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
//Need to parse and format the offset now, before intent is created, then attach it to the intent.
//HERE I NEED TO GET THE OFFSET AND CONVERT INTO MILLISECONDS
EditText hoursInput = (EditText) this.findViewById(R.id.hoursInput);
EditText minutesInput = (EditText) this.findViewById(R.id.minutesInput);
EditText secondsInput = (EditText) this.findViewById(R.id.secondsInput);
int hours = 0;
int minutes = 0;
int seconds = 0;
try {
hours = Integer.parseInt(hoursInput.getText().toString()) * 3600000;
minutes = Integer.parseInt(minutesInput.getText().toString()) * 60000;
seconds = Integer.parseInt(secondsInput.getText().toString()) * 1000;
} catch(NumberFormatException e) {
}
int offsetMillis = hours + minutes + seconds;
//HERE: Randomly Generate the offset, add or subtract it when alarm is set. Make sure to attach the opposite to the PI so that the next alarm will trigger at te correct default time
int offsetRandomMillis = 0;
if(offsetMillis != 0){
Random offsetRandom = new Random();
int oneOrNegativeOne = (offsetRandom.nextBoolean()) ? 1 : -1;
offsetRandomMillis = offsetRandom.nextInt(offsetMillis) * oneOrNegativeOne;
}
//Creates new offset alarm structure
Intent intent = new Intent(this, AlarmReciever.class);
intent.putExtra("name", nameInput.getText().toString());
intent.putExtra("description", descriptionInput.getText().toString());
PendingIntent pendingIntent = PendingIntent.getBroadcast(this.getApplicationContext(), 234324243, intent, PendingIntent.FLAG_UPDATE_CURRENT);
//Creates new recursion alarm structure
Intent intent2 = new Intent("RESET_ALARM");
PendingIntent pendingIntent2 = PendingIntent.getBroadcast(this.getApplicationContext(), 000, intent2, PendingIntent.FLAG_UPDATE_CURRENT);
//Stores old offset alarm details
editor.putString("oldName", nameInput.getText().toString());
editor.putString("oldDescription", descriptionInput.getText().toString());
editor.apply();
//Finishes new offset alarm details
int[] times = parseTime(firstAlertInput.getText().toString());
times[0] = times[0] * 3600000;
times[1] = times[1] * 60000;
long millis = times[0] + times[1];
int[] intervalTimes = parseTime(intervalInput.getText().toString());
intervalTimes[0] = intervalTimes[0] * 3600000;
intervalTimes[1] = intervalTimes[1] * 60000;
long intervalMillis = intervalTimes[0] + intervalTimes[1];
//New offset alarm set
alarmManager.set(AlarmManager.RTC_WAKEUP, System.currentTimeMillis() + millis + intervalMillis + offsetRandomMillis, pendingIntent);
//New Recursion alarm set
alarmManager.set(AlarmManager.RTC_WAKEUP, System.currentTimeMillis() + millis + intervalMillis, pendingIntent2);
Log.d("test", "OFFSET: " + String.valueOf((System.currentTimeMillis() + millis + intervalMillis + offsetRandomMillis) / 1000));
Log.d("test", "NOOFFSET: " + String.valueOf((System.currentTimeMillis() + millis + intervalMillis) / 1000));
}
private int[] parseTime(String input){
int[] times = new int[2];
String[] split = input.split(":");
for(int i = 0; i < times.length; i++){
times[i] = Integer.parseInt(split[i]);
}
return times;
}
注意:这些都属于同一类,我排除同一类的不相关部分。
所以这就是发生的事情:清除所有警报并设置新警报后,这些警报会在正确的时间触发。当broadcastReceiver设置新警报时,这些警报会延迟5-20秒。它设置的所有后续警报也会触发较晚,但它们会比之前的警报触发5-20秒。正如您所看到的,警报最终触发的次数远少于应该的次数。
另外,请注意,此测试的间隔值为1分钟,这意味着每个警报应在设置后一分钟触发。我知道还有一些代码可以确定和解析偏移量,但我没有为此设置值,所以它不会影响时间。我在许多其他值中打印了这个值,所以我知道这很有用。
我很沮丧因为我没有理由认为这会失败。我发布的代码中的当前log.d语句只是为了显示何时设置新警报以及两个警报应该关闭的时间(一个警报是为了触发通知,这个警报会添加偏移量。没有偏移的其他触发器并设置新的警报。抱歉,如果我困惑你。)。这些值是正确的,因此这不是问题。
此刻我的怀疑来自于我所进行的另一项实验。我不断点击首先运行startAlarm方法的按钮。这显示了应该触发设置的警报的时间(以毫秒为单位)。我预计这个数字会不断上升,因为1000毫秒必须在一秒钟内通过。但事实并非如此。这个数字缓慢上升,每隔几个就会增加10个。这是一个非常意外的行为。有人可以在他们的答案中解释这个原因吗?感谢。
我目前的怀疑是我未能将某些内容转换为毫秒或秒。但是,查看代码和记录变量,我不知道这是问题所在。通过的毫秒似乎很时髦,所以我不知道是什么。