diff --git a/movement.c b/movement.c index f0fb9609..14e8832e 100644 --- a/movement.c +++ b/movement.c @@ -660,6 +660,26 @@ int32_t movement_get_current_timezone_offset(void) { return movement_get_current_timezone_offset_for_zone(movement_state.settings.bit.time_zone); } +int32_t movement_get_timezone_offset_for_date_in_zone(watch_date_time_t date_time, uint8_t zone_index) { + int8_t cached_dst_offset = _movement_dst_offset_cache[zone_index]; + + if (cached_dst_offset == TIMEZONE_DOES_NOT_OBSERVE) { + return (int32_t)zone_defns[zone_index].offset_inc_minutes * OFFSET_INCREMENT * 60; + } + + // Compute the offset for the given date using the zone's DST rules + uzone_t local_zone; + unpack_zone(&zone_defns[zone_index], "", &local_zone); + udatetime_t udt = _movement_convert_date_time_to_udate(date_time); + uoffset_t offset; + get_current_offset(&local_zone, &udt, &offset); + return (int32_t)(offset.hours * 60 + offset.minutes) * 60; +} + +int32_t movement_get_timezone_offset_for_date(watch_date_time_t date_time) { + return movement_get_timezone_offset_for_date_in_zone(date_time, movement_state.settings.bit.time_zone); +} + int32_t movement_get_timezone_index(void) { return movement_state.settings.bit.time_zone; } diff --git a/movement.h b/movement.h index 1bbd9638..7b81e9ec 100644 --- a/movement.h +++ b/movement.h @@ -341,6 +341,8 @@ uint8_t movement_claim_backup_register(void); int32_t movement_get_current_timezone_offset_for_zone(uint8_t zone_index); int32_t movement_get_current_timezone_offset(void); +int32_t movement_get_timezone_offset_for_date_in_zone(watch_date_time_t date_time, uint8_t zone_index); +int32_t movement_get_timezone_offset_for_date(watch_date_time_t date_time); int32_t movement_get_timezone_index(void); void movement_set_timezone_index(uint8_t value); diff --git a/watch-faces/complication/sunrise_sunset_face.c b/watch-faces/complication/sunrise_sunset_face.c index 58514848..5cc5fa3c 100644 --- a/watch-faces/complication/sunrise_sunset_face.c +++ b/watch-faces/complication/sunrise_sunset_face.c @@ -93,13 +93,9 @@ static void _sunrise_sunset_face_update(sunrise_sunset_state_t *state) { double lat = (double)lat_centi / 100.0; double lon = (double)lon_centi / 100.0; - // sunriset returns the rise/set times as signed decimal hours in UTC. - // this can mean hours below 0 or above 31, which won't fit into a watch_date_time_t struct. - // to deal with this, we set aside the offset in hours, and add it back before converting it to a watch_date_time_t. - double hours_from_utc = ((double)movement_get_current_timezone_offset()) / 3600.0; - // we loop twice because if it's after sunset today, we need to recalculate to display values for tomorrow. for(int i = 0; i < 2; i++) { + double hours_from_utc = ((double)movement_get_timezone_offset_for_date(scratch_time)) / 3600.0; uint8_t result = sun_rise_set(scratch_time.unit.year + WATCH_RTC_REFERENCE_YEAR, scratch_time.unit.month, scratch_time.unit.day, lon, lat, &rise, &set); if (result != 0) {