From 9727dac3c34b918b8ba3a5de2ce34474ffee61a6 Mon Sep 17 00:00:00 2001 From: David Volovskiy Date: Mon, 29 Jul 2024 20:28:10 -0400 Subject: [PATCH] Revert "Leaving sleep with alarm button up doesn't trigger alarm button" This reverts commit 7d5aaf60caa943a248a7f635111ddfd50c230389. --- movement/movement.c | 114 ++++++++++++++------------------------------ movement/movement.h | 7 +-- 2 files changed, 37 insertions(+), 84 deletions(-) diff --git a/movement/movement.c b/movement/movement.c index f665792..a9ff2fa 100644 --- a/movement/movement.c +++ b/movement/movement.c @@ -99,8 +99,6 @@ #include #endif -#define DEBOUNCE_TICKS 2 // In terms of *7.8125ms - movement_state_t movement_state; void * watch_face_contexts[MOVEMENT_NUM_FACES]; watch_date_time scheduled_tasks[MOVEMENT_NUM_FACES]; @@ -171,9 +169,6 @@ static inline void _movement_reset_inactivity_countdown(void) { static inline void _movement_enable_fast_tick_if_needed(void) { if (!movement_state.fast_tick_enabled) { movement_state.fast_ticks = 0; - movement_state.debounce_ticks_light = 0; - movement_state.debounce_ticks_alarm = 0; - movement_state.debounce_ticks_mode = 0; watch_rtc_register_periodic_callback(cb_fast_tick, 128); movement_state.fast_tick_enabled = true; } @@ -188,6 +183,16 @@ static inline void _movement_disable_fast_tick_if_possible(void) { } } +static void cb_debounce(void) { + movement_state.debounce_occurring = false; + watch_rtc_disable_periodic_callback(64); // 64 HZ is 15.625ms +} + +static inline void _movement_enable_debounce_tick(void) { + movement_state.debounce_occurring = true; + watch_rtc_register_periodic_callback(cb_debounce, 64); +} + static void _movement_handle_background_tasks(void) { for(uint8_t i = 0; i < MOVEMENT_NUM_FACES; i++) { // For each face, if the watch face wants a background task... @@ -228,15 +233,15 @@ static void _movement_handle_scheduled_tasks(void) { } void movement_request_tick_frequency(uint8_t freq) { - // Movement uses the 128 Hz tick internally - if (freq == 128) return; + // Movement uses the 128 Hz tick internally; 64 is th edebounce frequency + if (freq == 128 || freq == 64 ) return; // Movement requires at least a 1 Hz tick. // If we are asked for an invalid frequency, default back to 1 Hz. if (freq == 0 || __builtin_popcount(freq) != 1) freq = 1; // disable all callbacks except the 128 Hz one - watch_rtc_disable_matching_periodic_callbacks(0xFE); + watch_rtc_disable_matching_periodic_callbacks(0xFC); movement_state.subsecond = 0; movement_state.tick_frequency = freq; @@ -620,6 +625,8 @@ bool app_loop(void) { static movement_event_type_t _figure_out_button_event(bool pin_level, movement_event_type_t button_down_event_type, uint16_t *down_timestamp) { // force alarm off if the user pressed a button. if (movement_state.alarm_ticks) movement_state.alarm_ticks = 0; + if ( movement_state.debounce_occurring) + return EVENT_NONE; if (pin_level) { // handle rising edge @@ -634,49 +641,36 @@ static movement_event_type_t _figure_out_button_event(bool pin_level, movement_e uint16_t diff = movement_state.fast_ticks - *down_timestamp; *down_timestamp = 0; _movement_disable_fast_tick_if_possible(); + _movement_enable_debounce_tick(); // any press over a half second is considered a long press. Fire the long-up event if (diff > MOVEMENT_LONG_PRESS_TICKS) return button_down_event_type + 3; else return button_down_event_type + 1; } } -static void light_btn_action(void) { +void cb_light_btn_interrupt(void) { bool pin_level = watch_get_pin_level(BTN_LIGHT); _movement_reset_inactivity_countdown(); event.event_type = _figure_out_button_event(pin_level, EVENT_LIGHT_BUTTON_DOWN, &movement_state.light_down_timestamp); } -static void mode_btn_action(void) { +void cb_mode_btn_interrupt(void) { bool pin_level = watch_get_pin_level(BTN_MODE); _movement_reset_inactivity_countdown(); event.event_type = _figure_out_button_event(pin_level, EVENT_MODE_BUTTON_DOWN, &movement_state.mode_down_timestamp); } -static void alarm_btn_action(void) { +void cb_alarm_btn_interrupt(void) { bool pin_level = watch_get_pin_level(BTN_ALARM); _movement_reset_inactivity_countdown(); uint8_t event_type = _figure_out_button_event(pin_level, EVENT_ALARM_BUTTON_DOWN, &movement_state.alarm_down_timestamp); if (movement_state.ignore_alarm_btn_after_sleep){ - if (event_type == EVENT_ALARM_BUTTON_UP || event_type == EVENT_ALARM_LONG_UP) movement_state.ignore_alarm_btn_after_sleep = false; + if (event_type == EVENT_ALARM_BUTTON_UP) movement_state.ignore_alarm_btn_after_sleep = false; return; } event.event_type = event_type; } -void cb_light_btn_interrupt(void) { - movement_state.debounce_btn_trig_light = true; - _movement_enable_fast_tick_if_needed(); -} - -void cb_mode_btn_interrupt(void) { - movement_state.debounce_btn_trig_mode = true; - _movement_enable_fast_tick_if_needed(); -} - -void cb_alarm_btn_interrupt(void) { - movement_state.debounce_btn_trig_alarm = true; - _movement_enable_fast_tick_if_needed(); -} void cb_alarm_btn_extwake(void) { // wake up! @@ -688,59 +682,23 @@ void cb_alarm_fired(void) { } void cb_fast_tick(void) { - // printf("%d \r\n", movement_state.fast_ticks); - if (movement_state.debounce_ticks_light > 0) movement_state.debounce_ticks_light--; - if (movement_state.debounce_ticks_alarm > 0) movement_state.debounce_ticks_alarm--; - if (movement_state.debounce_ticks_mode > 0) movement_state.debounce_ticks_mode--; - if (movement_state.debounce_btn_trig_light) { - movement_state.debounce_btn_trig_light = false; - if (movement_state.debounce_ticks_light == 0) { - light_btn_action(); - movement_state.debounce_ticks_light = DEBOUNCE_TICKS; - } - else { - movement_state.light_down_timestamp = 0; - _movement_disable_fast_tick_if_possible(); - } + movement_state.fast_ticks++; + if (!movement_state.debounce_occurring) { + if (movement_state.light_ticks > 0) movement_state.light_ticks--; + if (movement_state.alarm_ticks > 0) movement_state.alarm_ticks--; + // check timestamps and auto-fire the long-press events + // Notice: is it possible that two or more buttons have an identical timestamp? In this case + // only one of these buttons would receive the long press event. Don't bother for now... + if (movement_state.light_down_timestamp > 0) + if (movement_state.fast_ticks - movement_state.light_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) + event.event_type = EVENT_LIGHT_LONG_PRESS; + if (movement_state.mode_down_timestamp > 0) + if (movement_state.fast_ticks - movement_state.mode_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) + event.event_type = EVENT_MODE_LONG_PRESS; + if (movement_state.alarm_down_timestamp > 0) + if (movement_state.fast_ticks - movement_state.alarm_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) + event.event_type = EVENT_ALARM_LONG_PRESS; } - if (movement_state.debounce_btn_trig_alarm) { - movement_state.debounce_btn_trig_alarm = false; - if (movement_state.debounce_ticks_alarm == 0) { - alarm_btn_action(); - movement_state.debounce_ticks_alarm = DEBOUNCE_TICKS; - } - else { - movement_state.alarm_down_timestamp = 0; - _movement_disable_fast_tick_if_possible(); - } - } - if (movement_state.debounce_btn_trig_mode) { - movement_state.debounce_btn_trig_mode = false; - if (movement_state.debounce_ticks_mode == 0) { - mode_btn_action(); - movement_state.debounce_ticks_mode = DEBOUNCE_TICKS; - } - else { - movement_state.mode_down_timestamp = 0; - _movement_disable_fast_tick_if_possible(); - } - } - if (movement_state.debounce_ticks_light + movement_state.debounce_ticks_mode + movement_state.debounce_ticks_alarm == 0) - movement_state.fast_ticks++; - if (movement_state.light_ticks > 0) movement_state.light_ticks--; - if (movement_state.alarm_ticks > 0) movement_state.alarm_ticks--; - // check timestamps and auto-fire the long-press events - // Notice: is it possible that two or more buttons have an identical timestamp? In this case - // only one of these buttons would receive the long press event. Don't bother for now... - if (movement_state.light_down_timestamp > 0) - if (movement_state.fast_ticks - movement_state.light_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) - event.event_type = EVENT_LIGHT_LONG_PRESS; - if (movement_state.mode_down_timestamp > 0) - if (movement_state.fast_ticks - movement_state.mode_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) - event.event_type = EVENT_MODE_LONG_PRESS; - if (movement_state.alarm_down_timestamp > 0) - if (movement_state.fast_ticks - movement_state.alarm_down_timestamp == MOVEMENT_LONG_PRESS_TICKS + 1) - event.event_type = EVENT_ALARM_LONG_PRESS; // this is just a fail-safe; fast tick should be disabled as soon as the button is up, the LED times out, and/or the alarm finishes. // but if for whatever reason it isn't, this forces the fast tick off after 20 seconds. if (movement_state.fast_ticks >= 128 * 20) { diff --git a/movement/movement.h b/movement/movement.h index 81e55ab..5829ba8 100644 --- a/movement/movement.h +++ b/movement/movement.h @@ -267,15 +267,10 @@ typedef struct { bool needs_background_tasks_handled; bool has_scheduled_background_task; bool needs_wake; + bool debounce_occurring; // low energy mode countdown int32_t le_mode_ticks; - uint8_t debounce_ticks_light; - uint8_t debounce_ticks_alarm; - uint8_t debounce_ticks_mode; - bool debounce_btn_trig_light; - bool debounce_btn_trig_alarm; - bool debounce_btn_trig_mode; bool ignore_alarm_btn_after_sleep; // app resignation countdown (TODO: consolidate with LE countdown?)