Fixed bug where a recurring alarm dismissed in its upcoming state is rescheduled immediately for its normal ring time
This commit is contained in:
parent
c37e9438cf
commit
22973eb262
@ -20,9 +20,9 @@
|
||||
</activity>
|
||||
<activity
|
||||
android:name=".ringtone.RingtoneActivity"
|
||||
android:excludeFromRecents="true"
|
||||
android:label="@string/title_activity_ringtone"
|
||||
android:launchMode="singleTask"
|
||||
android:excludeFromRecents="true"
|
||||
android:taskAffinity="com.philliphsu.clock2.RingtoneActivity">
|
||||
</activity>
|
||||
|
||||
@ -47,7 +47,6 @@
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value="com.philliphsu.clock2.MainActivity"/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".settings.SettingsActivity"
|
||||
android:label="@string/title_activity_settings"
|
||||
@ -56,6 +55,12 @@
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value="com.philliphsu.clock2.MainActivity"/>
|
||||
</activity>
|
||||
|
||||
<receiver
|
||||
android:name=".PendingAlarmScheduler"
|
||||
android:enabled="true"
|
||||
android:exported="false">
|
||||
</receiver>
|
||||
</application>
|
||||
|
||||
</manifest>
|
||||
@ -0,0 +1,32 @@
|
||||
package com.philliphsu.clock2;
|
||||
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
|
||||
import com.philliphsu.clock2.model.AlarmsRepository;
|
||||
import com.philliphsu.clock2.util.AlarmUtils;
|
||||
|
||||
import static com.philliphsu.clock2.util.Preconditions.checkNotNull;
|
||||
|
||||
/**
|
||||
* Used to reschedule recurring alarms that were dismissed in their upcoming state, so {@link Alarm#ringsAt()}
|
||||
* still refers to the time it rings today. This class receives
|
||||
* your intent at the Alarm instance's normal ring time, so by the time you make a subsequent call
|
||||
* to {@link Alarm#ringsAt()}, the value returned refers to the next time the alarm will recur.
|
||||
*/
|
||||
public class PendingAlarmScheduler extends BroadcastReceiver {
|
||||
// We include the class name in the string to distinguish this constant from the one defined
|
||||
// in UpcomingAlarmReceiver.
|
||||
public static final String EXTRA_ALARM_ID = "com.philliphsu.clock2.PendingAlarmScheduler.extra.ALARM_ID";
|
||||
|
||||
@Override
|
||||
public void onReceive(Context context, Intent intent) {
|
||||
long id = intent.getLongExtra(EXTRA_ALARM_ID, -1);
|
||||
if (id < 0) {
|
||||
throw new IllegalStateException("No alarm id received");
|
||||
}
|
||||
Alarm alarm = checkNotNull(AlarmsRepository.getInstance(context).getItem(id));
|
||||
AlarmUtils.scheduleAlarm(context, alarm, false);
|
||||
}
|
||||
}
|
||||
@ -37,7 +37,7 @@ public class UpcomingAlarmReceiver extends BroadcastReceiver {
|
||||
} else {
|
||||
Alarm alarm = checkNotNull(AlarmsRepository.getInstance(context).getItem(id));
|
||||
if (ACTION_DISMISS_NOW.equals(intent.getAction())) {
|
||||
AlarmUtils.cancelAlarm(context, alarm, true);
|
||||
AlarmUtils.cancelAlarm(context, alarm, true); // TODO: Cancel only, do not reschedule.
|
||||
} else {
|
||||
// Prepare notification
|
||||
String title;
|
||||
|
||||
@ -433,7 +433,7 @@ public class EditAlarmActivity extends BaseActivity implements AlarmNumpad.KeyLi
|
||||
|
||||
@Override
|
||||
public void cancelAlarm(Alarm alarm, boolean showToast) {
|
||||
AlarmUtils.cancelAlarm(this, alarm, showToast);
|
||||
AlarmUtils.cancelAlarm(this, alarm, showToast); // TODO: Cancel only?
|
||||
if (RingtoneActivity.isAlive()) {
|
||||
Intent intent = new Intent(this, RingtoneActivity.class)
|
||||
.setAction(RingtoneActivity.ACTION_UNBIND);
|
||||
|
||||
@ -158,12 +158,6 @@ public class RingtoneActivity extends AppCompatActivity implements RingtoneServi
|
||||
|
||||
private void dismiss() {
|
||||
AlarmUtils.cancelAlarm(this, mAlarm, false);
|
||||
// As of API 19, alarms scheduled with AlarmManager.setRepeating() are inexact. The recommended
|
||||
// workaround is to schedule one-time exact alarms, and reschedule each time after handling
|
||||
// an alarm delivery.
|
||||
if (mAlarm.hasRecurrence()) {
|
||||
AlarmUtils.scheduleAlarm(this, mAlarm, false /*show toast?*/);
|
||||
}
|
||||
unbindAndFinish();
|
||||
}
|
||||
|
||||
|
||||
@ -10,6 +10,7 @@ import android.util.Log;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.philliphsu.clock2.Alarm;
|
||||
import com.philliphsu.clock2.PendingAlarmScheduler;
|
||||
import com.philliphsu.clock2.R;
|
||||
import com.philliphsu.clock2.UpcomingAlarmReceiver;
|
||||
import com.philliphsu.clock2.model.AlarmsRepository;
|
||||
@ -84,7 +85,7 @@ public final class AlarmUtils {
|
||||
removeUpcomingAlarmNotification(c, a);
|
||||
|
||||
// TOneverDO: Place block after making value changes to the alarm.
|
||||
if (showToast && (a.ringsIn() <= HOURS.toMillis(hoursBeforeUpcoming(c)) || a.isSnoozed())) {
|
||||
if (showToast && (a.ringsWithinHours(hoursBeforeUpcoming(c)) || a.isSnoozed())) {
|
||||
String time = formatTime(c, a.isSnoozed() ? a.snoozingUntil() : a.ringsAt());
|
||||
String text = c.getString(R.string.upcoming_alarm_dismissed, time);
|
||||
Toast.makeText(c, text, Toast.LENGTH_LONG).show();
|
||||
@ -96,6 +97,19 @@ public final class AlarmUtils {
|
||||
|
||||
if (!a.hasRecurrence()) {
|
||||
a.setEnabled(false);
|
||||
} else {
|
||||
if (a.isEnabled()) {
|
||||
if (a.ringsWithinHours(hoursBeforeUpcoming(c))) {
|
||||
// Still upcoming today, so wait until the normal ring time passes before
|
||||
// rescheduling the alarm.
|
||||
Intent intent = new Intent(c, PendingAlarmScheduler.class)
|
||||
.putExtra(PendingAlarmScheduler.EXTRA_ALARM_ID, a.id());
|
||||
pi = PendingIntent.getBroadcast(c, a.intId(), intent, PendingIntent.FLAG_ONE_SHOT);
|
||||
am.set(AlarmManager.RTC_WAKEUP, a.ringsAt(), pi);
|
||||
} else {
|
||||
scheduleAlarm(c, a, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
save(c); // Save any changes
|
||||
@ -108,8 +122,8 @@ public final class AlarmUtils {
|
||||
}
|
||||
|
||||
public static void snoozeAlarm(Context c, Alarm a) {
|
||||
a.snooze(AlarmUtils.snoozeDuration(c));
|
||||
AlarmUtils.scheduleAlarm(c, a, true);
|
||||
a.snooze(snoozeDuration(c));
|
||||
scheduleAlarm(c, a, true);
|
||||
save(c);
|
||||
}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user