mirror of
https://github.com/taigrr/arduinolibs
synced 2025-01-18 04:33:12 -08:00
Add a snooze feature to the alarm clock
This commit is contained in:
parent
dce1ede576
commit
a872972c9d
@ -50,6 +50,7 @@
|
||||
// Offsets of settings in the realtime clock's NVRAM.
|
||||
#define SETTING_24HOUR 0 // 0: 12 hour, 1: 24 hour
|
||||
#define SETTING_ALARM_TIMEOUT 1 // Timeout in minutes for the alarm
|
||||
#define SETTING_SNOOZE 2 // 0: no snooze, 1: snooze
|
||||
|
||||
// Initialize the LCD
|
||||
FreetronicsLCD lcd;
|
||||
@ -75,6 +76,7 @@ SetAlarm alarm2(mainForm, "Alarm 2", 1);
|
||||
SetAlarm alarm3(mainForm, "Alarm 3", 2);
|
||||
SetAlarm alarm4(mainForm, "Alarm 4", 3);
|
||||
IntField alarmTimeout(mainForm, "Alarm timeout", 2, 10, 1, 2, " minutes");
|
||||
BoolField snooze(mainForm, "Snooze alarm", "On", "Off", false);
|
||||
SetTime setTime(mainForm, "Set current time");
|
||||
SetDate setDate(mainForm, "Set current date");
|
||||
BoolField hourMode(mainForm, "Hour display", "24 hour clock", "12 hour clock", false);
|
||||
@ -112,6 +114,7 @@ void setup() {
|
||||
frontScreen.set24HourMode(is24HourClock);
|
||||
alarmTimeout.setValue(rtc.readByte(SETTING_ALARM_TIMEOUT));
|
||||
alarmMelody.setLoopDuration(60000UL * alarmTimeout.value());
|
||||
snooze.setValue(rtc.readByte(SETTING_SNOOZE) != 0);
|
||||
|
||||
// Set the initial time and date and find the next alarm to be triggered.
|
||||
RTCTime time;
|
||||
@ -171,6 +174,8 @@ void loop() {
|
||||
} else if (alarmTimeout.isCurrent()) {
|
||||
rtc.writeByte(SETTING_ALARM_TIMEOUT, (byte)alarmTimeout.value());
|
||||
alarmMelody.setLoopDuration(60000UL * alarmTimeout.value());
|
||||
} else if (snooze.isCurrent()) {
|
||||
rtc.writeByte(SETTING_SNOOZE, (byte)snooze.value());
|
||||
}
|
||||
prevHour = 24; // Force an update of the main screen.
|
||||
findNextAlarm(); // Update the time of the next alarm event.
|
||||
@ -191,12 +196,28 @@ inline int timeToAlarm(const RTCTime ¤tTime, const RTCAlarm &alarm)
|
||||
{
|
||||
int mins1 = currentTime.hour * 60 + currentTime.minute;
|
||||
int mins2 = alarm.hour * 60 + alarm.minute;
|
||||
if (mins1 < mins2)
|
||||
if (mins1 <= mins2)
|
||||
return mins2 - mins1;
|
||||
else
|
||||
return 24 * 60 + mins2 - mins1;
|
||||
}
|
||||
|
||||
// Add 9 minutes to an alarm to get its snooze time.
|
||||
RTCAlarm adjustForSnooze(const RTCAlarm &alarm)
|
||||
{
|
||||
if (!alarm.flags)
|
||||
return alarm;
|
||||
RTCAlarm snooze;
|
||||
snooze.hour = alarm.hour;
|
||||
snooze.minute = alarm.minute + 9;
|
||||
if (snooze.minute >= 60) {
|
||||
snooze.hour = (snooze.hour + 1) % 24;
|
||||
snooze.minute %= 60;
|
||||
}
|
||||
snooze.flags = alarm.flags;
|
||||
return snooze;
|
||||
}
|
||||
|
||||
// Find the time of the next alarm to be triggered.
|
||||
void findNextAlarm()
|
||||
{
|
||||
@ -215,9 +236,22 @@ void findNextAlarm()
|
||||
findNextAlarm(currentTime, alarm2.alarmValue());
|
||||
findNextAlarm(currentTime, alarm3.alarmValue());
|
||||
findNextAlarm(currentTime, alarm4.alarmValue());
|
||||
if (snooze.value()) {
|
||||
findNextAlarm(currentTime, adjustForSnooze(alarm1.alarmValue()));
|
||||
findNextAlarm(currentTime, adjustForSnooze(alarm2.alarmValue()));
|
||||
findNextAlarm(currentTime, adjustForSnooze(alarm3.alarmValue()));
|
||||
findNextAlarm(currentTime, adjustForSnooze(alarm4.alarmValue()));
|
||||
}
|
||||
|
||||
// Set the alarm indicator on the front screen.
|
||||
frontScreen.setAlarmActive(nextAlarm.flags != 0);
|
||||
if (nextAlarm.flags) {
|
||||
if (snooze.value())
|
||||
frontScreen.setAlarmMode(FrontScreenField::Snooze);
|
||||
else
|
||||
frontScreen.setAlarmMode(FrontScreenField::AlarmOn);
|
||||
} else {
|
||||
frontScreen.setAlarmMode(FrontScreenField::AlarmOff);
|
||||
}
|
||||
}
|
||||
void findNextAlarm(const RTCTime ¤tTime, const RTCAlarm &alarm)
|
||||
{
|
||||
|
@ -40,7 +40,7 @@ FrontScreenField::FrontScreenField(Form &form)
|
||||
, _voltageTrunc(36)
|
||||
, _batteryBars(IND_BATTERY_FULL)
|
||||
#endif
|
||||
, _alarmActive(false)
|
||||
, _alarmMode(FrontScreenField::AlarmOff)
|
||||
, _hourMode(false)
|
||||
{
|
||||
_date.day = 1;
|
||||
@ -124,10 +124,45 @@ void FrontScreenField::setVoltage(int voltage)
|
||||
|
||||
#endif
|
||||
|
||||
void FrontScreenField::setAlarmActive(bool active)
|
||||
static uint8_t alarmActive1[8] = {
|
||||
B00100,
|
||||
B01001,
|
||||
B10010,
|
||||
B00000,
|
||||
B10010,
|
||||
B01001,
|
||||
B00100,
|
||||
B00000
|
||||
};
|
||||
static uint8_t alarmActive2[8] = {
|
||||
B11000,
|
||||
B10100,
|
||||
B10011,
|
||||
B10011,
|
||||
B10011,
|
||||
B10100,
|
||||
B11000,
|
||||
B00000
|
||||
};
|
||||
static uint8_t alarmSnooze[8] = {
|
||||
B11110,
|
||||
B00100,
|
||||
B01000,
|
||||
B11110,
|
||||
B00000,
|
||||
B00000,
|
||||
B00000,
|
||||
B00000
|
||||
};
|
||||
|
||||
void FrontScreenField::setAlarmMode(AlarmMode mode)
|
||||
{
|
||||
if (_alarmActive != active) {
|
||||
_alarmActive = active;
|
||||
if (_alarmMode != mode) {
|
||||
_alarmMode = mode;
|
||||
if (mode == Snooze)
|
||||
lcd()->createChar(IND_ALARM_ACTIVE1, alarmSnooze);
|
||||
else
|
||||
lcd()->createChar(IND_ALARM_ACTIVE1, alarmActive1);
|
||||
if (isCurrent())
|
||||
updateAlarm();
|
||||
}
|
||||
@ -211,8 +246,8 @@ void FrontScreenField::updateAlarm()
|
||||
#else
|
||||
lcd()->setCursor(14, 0);
|
||||
#endif
|
||||
lcd()->write(_alarmActive ? IND_ALARM_ACTIVE1 : ' ');
|
||||
lcd()->write(_alarmActive ? IND_ALARM_ACTIVE2 : ' ');
|
||||
lcd()->write(_alarmMode != AlarmOff ? IND_ALARM_ACTIVE1 : ' ');
|
||||
lcd()->write(_alarmMode != AlarmOff ? IND_ALARM_ACTIVE2 : ' ');
|
||||
}
|
||||
|
||||
#ifdef USE_VOLTAGE_MONITOR
|
||||
@ -277,26 +312,6 @@ static uint8_t batteryFull[8] = {
|
||||
B00000
|
||||
};
|
||||
#endif
|
||||
static uint8_t alarmActive1[8] = {
|
||||
B00100,
|
||||
B01001,
|
||||
B10010,
|
||||
B00000,
|
||||
B10010,
|
||||
B01001,
|
||||
B00100,
|
||||
B00000
|
||||
};
|
||||
static uint8_t alarmActive2[8] = {
|
||||
B11000,
|
||||
B10100,
|
||||
B10011,
|
||||
B10011,
|
||||
B10011,
|
||||
B10100,
|
||||
B11000,
|
||||
B00000
|
||||
};
|
||||
|
||||
void FrontScreenField::registerIndicators()
|
||||
{
|
||||
|
@ -47,8 +47,15 @@ public:
|
||||
void setVoltage(int voltage);
|
||||
#endif
|
||||
|
||||
bool isAlarmActive() const { return _alarmActive; }
|
||||
void setAlarmActive(bool active);
|
||||
enum AlarmMode
|
||||
{
|
||||
AlarmOff,
|
||||
AlarmOn,
|
||||
Snooze
|
||||
};
|
||||
|
||||
AlarmMode isAlarmMode() const { return _alarmMode; }
|
||||
void setAlarmMode(AlarmMode mode);
|
||||
|
||||
bool is24HourMode() const { return _hourMode; }
|
||||
void set24HourMode(bool value);
|
||||
@ -61,7 +68,7 @@ private:
|
||||
int _voltageTrunc;
|
||||
int _batteryBars;
|
||||
#endif
|
||||
bool _alarmActive;
|
||||
AlarmMode _alarmMode;
|
||||
bool _hourMode;
|
||||
|
||||
void updateDate();
|
||||
|
Loading…
x
Reference in New Issue
Block a user