Merge PR #470 - implement automatic DST toggling

Implements logic to automatically offset daylight saving time settings
when calculating timezone offsets. This should make the DST functions
work automatically with no need for user input in most cases.

Reviewed-by: Matheus Afonso Martins Moreira <matheus@matheusmoreira.com>
GitHub-Pull-Request: https://github.com/joeycastillo/Sensor-Watch/pull/470
This commit is contained in:
Matheus Afonso Martins Moreira
2024-09-08 13:41:52 -03:00
32 changed files with 295 additions and 165 deletions

View File

@@ -61,7 +61,7 @@ bool beats_face_loop(movement_event_t event, movement_settings_t *settings, void
case EVENT_ACTIVATE:
case EVENT_TICK:
date_time = watch_rtc_get_date_time();
centibeats = clock2beats(date_time.unit.hour, date_time.unit.minute, date_time.unit.second, event.subsecond, movement_timezone_offsets[settings->bit.time_zone]);
centibeats = clock2beats(date_time.unit.hour, date_time.unit.minute, date_time.unit.second, event.subsecond, get_timezone_offset(settings->bit.time_zone, date_time));
if (centibeats == state->last_centibeat_displayed) {
// we missed this update, try again next subsecond
state->next_subsecond_update = (event.subsecond + 1) % BEAT_REFRESH_FREQUENCY;
@@ -76,7 +76,7 @@ bool beats_face_loop(movement_event_t event, movement_settings_t *settings, void
case EVENT_LOW_ENERGY_UPDATE:
if (!watch_tick_animation_is_running()) watch_start_tick_animation(432);
date_time = watch_rtc_get_date_time();
centibeats = clock2beats(date_time.unit.hour, date_time.unit.minute, date_time.unit.second, event.subsecond, movement_timezone_offsets[settings->bit.time_zone]);
centibeats = clock2beats(date_time.unit.hour, date_time.unit.minute, date_time.unit.second, event.subsecond, get_timezone_offset(settings->bit.time_zone, date_time));
sprintf(buf, "bt %4lu ", centibeats / 100);
watch_display_string(buf, 0);

View File

@@ -62,7 +62,8 @@ void day_night_percentage_face_setup(movement_settings_t *settings, uint8_t watc
if (*context_ptr == NULL) {
*context_ptr = malloc(sizeof(day_night_percentage_state_t));
day_night_percentage_state_t *state = (day_night_percentage_state_t *)*context_ptr;
watch_date_time utc_now = watch_utility_date_time_convert_zone(watch_rtc_get_date_time(), movement_timezone_offsets[settings->bit.time_zone] * 60, 0);
watch_date_time date_time = watch_rtc_get_date_time();
watch_date_time utc_now = watch_utility_date_time_convert_zone(date_time, get_timezone_offset(settings->bit.time_zone, date_time) * 60, 0);
recalculate(utc_now, state);
}
}
@@ -77,7 +78,7 @@ bool day_night_percentage_face_loop(movement_event_t event, movement_settings_t
char buf[12];
watch_date_time date_time = watch_rtc_get_date_time();
watch_date_time utc_now = watch_utility_date_time_convert_zone(date_time, movement_timezone_offsets[settings->bit.time_zone] * 60, 0);
watch_date_time utc_now = watch_utility_date_time_convert_zone(date_time, get_timezone_offset(settings->bit.time_zone, date_time) * 60, 0);
switch (event.event_type) {
case EVENT_ACTIVATE:

View File

@@ -70,7 +70,7 @@ static void _h_to_hms(mars_clock_hms_t *date_time, double h) {
static void _update(movement_settings_t *settings, mars_time_state_t *state) {
char buf[11];
watch_date_time date_time = watch_rtc_get_date_time();
uint32_t now = watch_utility_date_time_to_unix_time(date_time, movement_timezone_offsets[settings->bit.time_zone] * 60);
uint32_t now = watch_utility_date_time_to_unix_time(date_time, get_timezone_offset(settings->bit.time_zone, date_time) * 60);
// TODO: I'm skipping over some steps here.
// https://www.giss.nasa.gov/tools/mars24/help/algorithm.html
double jdut = 2440587.5 + ((double)now / 86400.0);

View File

@@ -154,6 +154,7 @@ void world_clock2_face_activate(movement_settings_t *settings, void *context)
movement_request_tick_frequency(4);
break;
}
state->tz = get_timezone_offset(settings->bit.time_zone, watch_rtc_get_date_time());
refresh_face = true;
}
@@ -183,8 +184,8 @@ static bool mode_display(movement_event_t event, movement_settings_t *settings,
/* Determine current time at time zone and store date/time */
date_time = watch_rtc_get_date_time();
timestamp = watch_utility_date_time_to_unix_time(date_time, movement_timezone_offsets[settings->bit.time_zone] * 60);
date_time = watch_utility_date_time_from_unix_time(timestamp, movement_timezone_offsets[state->current_zone] * 60);
timestamp = watch_utility_date_time_to_unix_time(date_time, state->tz * 60);
date_time = watch_utility_date_time_from_unix_time(timestamp, state->tz * 60);
previous_date_time = state->previous_date_time;
state->previous_date_time = date_time.reg;
@@ -289,7 +290,7 @@ static bool mode_settings(movement_event_t event, movement_settings_t *settings,
watch_clear_indicator(WATCH_INDICATOR_PM);
refresh_face = false;
}
result = div(movement_timezone_offsets[state->current_zone], 60);
result = div(state->tz, 60);
hours = result.quot;
minutes = result.rem;

View File

@@ -104,6 +104,7 @@ typedef struct {
world_clock2_mode_t current_mode;
uint8_t current_zone;
uint32_t previous_date_time;
int16_t tz;
} world_clock2_state_t;
void world_clock2_face_setup(movement_settings_t *settings, uint8_t watch_face_index, void **context_ptr);

View File

@@ -60,15 +60,16 @@ static bool world_clock_face_do_display_mode(movement_event_t event, movement_se
watch_date_time date_time;
switch (event.event_type) {
case EVENT_ACTIVATE:
if (settings->bit.clock_mode_24h && !settings->bit.clock_24h_leading_zero) watch_set_indicator(WATCH_INDICATOR_24H);
state->tz = get_timezone_offset(settings->bit.time_zone, watch_rtc_get_date_time());
if (settings->bit.clock_mode_24h) watch_set_indicator(WATCH_INDICATOR_24H);
watch_set_colon();
state->previous_date_time = 0xFFFFFFFF;
// fall through
case EVENT_TICK:
case EVENT_LOW_ENERGY_UPDATE:
date_time = watch_rtc_get_date_time();
timestamp = watch_utility_date_time_to_unix_time(date_time, movement_timezone_offsets[settings->bit.time_zone] * 60);
date_time = watch_utility_date_time_from_unix_time(timestamp, movement_timezone_offsets[state->settings.bit.timezone_index] * 60);
timestamp = watch_utility_date_time_to_unix_time(date_time, state->tz * 60);
date_time = watch_utility_date_time_from_unix_time(timestamp, state->tz * 60);
previous_date_time = state->previous_date_time;
state->previous_date_time = date_time.reg;
@@ -176,8 +177,8 @@ static bool _world_clock_face_do_settings_mode(movement_event_t event, movement_
sprintf(buf, "%c%c %3d%02d ",
movement_valid_position_0_chars[state->settings.bit.char_0],
movement_valid_position_1_chars[state->settings.bit.char_1],
(int8_t) (movement_timezone_offsets[state->settings.bit.timezone_index] / 60),
(int8_t) (movement_timezone_offsets[state->settings.bit.timezone_index] % 60) * (movement_timezone_offsets[state->settings.bit.timezone_index] < 0 ? -1 : 1));
(int8_t) (state->tz / 60),
(int8_t) (state->tz % 60) * (state->tz < 0 ? -1 : 1));
watch_set_colon();
watch_clear_indicator(WATCH_INDICATOR_PM);

View File

@@ -62,6 +62,7 @@ typedef struct {
uint8_t backup_register;
uint8_t current_screen;
uint32_t previous_date_time;
int16_t tz;
} world_clock_state_t;
void world_clock_face_setup(movement_settings_t *settings, uint8_t watch_face_index, void ** context_ptr);