From 9f47d626a9972734bb52457ece4d386923bb5f29 Mon Sep 17 00:00:00 2001
From: azuo <azuo.lee@sohu.com>
Date: Mon, 13 Sep 2021 23:24:58 +0800
Subject: [PATCH] setExact is more reliable than setRepeating on some ROMs
 (e.g., MIUI).

---
 .../receivers/UpdatesReceiver.kt              | 21 +++++++++++--------
 .../receivers/WeatherReceiver.kt              | 17 +++++++--------
 .../services/UpdateCalendarService.kt         |  1 +
 .../ui/activities/MainActivity.kt             |  1 +
 .../ui/fragments/tabs/CalendarFragment.kt     |  5 +++--
 .../ui/fragments/tabs/PreferencesFragment.kt  |  2 ++
 6 files changed, 26 insertions(+), 21 deletions(-)

diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/UpdatesReceiver.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/UpdatesReceiver.kt
index c9faa40..2997b1b 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/UpdatesReceiver.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/UpdatesReceiver.kt
@@ -65,6 +65,8 @@ class UpdatesReceiver : BroadcastReceiver() {
         const val EVENT_ID = "EVENT_ID"
 
         fun setUpdates(context: Context, eventId: Long? = null) {
+            if (!Preferences.showEvents)
+                return
             val eventRepository = EventRepository(context)
             if (eventId == null) {
                 // schedule ACTION_CALENDAR_UPDATE at midnight (ACTION_DATE_CHANGED no longer works)
@@ -84,7 +86,8 @@ class UpdatesReceiver : BroadcastReceiver() {
                             Intent(context, UpdatesReceiver::class.java).apply {
                                 action = Actions.ACTION_CALENDAR_UPDATE
                             },
-                            0)
+                            0
+                        )
                     )
                 }
 
@@ -149,14 +152,14 @@ class UpdatesReceiver : BroadcastReceiver() {
                         else -> 0
                     }
             }
-            // avoid redundant updates at midnight
-            if (Calendar.getInstance().run {
-                timeInMillis = fireTime
-                get(Calendar.MILLISECOND) == 0 &&
-                get(Calendar.SECOND) == 0 &&
-                get(Calendar.MINUTE) == 0 &&
-                get(Calendar.HOUR_OF_DAY) == 0
-            }) return
+            // no need to schedule updates after the next ACTION_CALENDAR_UPDATE
+            if (Calendar.getInstance().apply {
+                set(Calendar.MILLISECOND, 0)
+                set(Calendar.SECOND, 0)
+                set(Calendar.MINUTE, 0)
+                set(Calendar.HOUR_OF_DAY, 0)
+                add(Calendar.DATE, 1)
+            }.timeInMillis <= fireTime) return
             with(context.getSystemService(Context.ALARM_SERVICE) as AlarmManager) {
                 setExact(
                     AlarmManager.RTC,
diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/WeatherReceiver.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/WeatherReceiver.kt
index 92f068b..f352b28 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/WeatherReceiver.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/receivers/WeatherReceiver.kt
@@ -22,13 +22,8 @@ class WeatherReceiver : BroadcastReceiver() {
             Intent.ACTION_MY_PACKAGE_REPLACED,
             Intent.ACTION_TIMEZONE_CHANGED,
             Intent.ACTION_LOCALE_CHANGED,
-            Intent.ACTION_TIME_CHANGED -> setUpdates(context)
-
-            Actions.ACTION_WEATHER_UPDATE -> {
-                GlobalScope.launch(Dispatchers.IO) {
-                    WeatherHelper.updateWeather(context)
-                }
-            }
+            Intent.ACTION_TIME_CHANGED,
+            Actions.ACTION_WEATHER_UPDATE -> setUpdates(context)
         }
     }
 
@@ -46,13 +41,15 @@ class WeatherReceiver : BroadcastReceiver() {
                     else -> 60
                 }
                 with(context.getSystemService(Context.ALARM_SERVICE) as AlarmManager) {
-                    setRepeating(
+                    setExact(
                         AlarmManager.RTC,
-                        Calendar.getInstance().timeInMillis,
-                        interval,
+                        System.currentTimeMillis() + interval,
                         PendingIntent.getBroadcast(context, 0, Intent(context, WeatherReceiver::class.java).apply { action = Actions.ACTION_WEATHER_UPDATE }, 0)
                     )
                 }
+                GlobalScope.launch(Dispatchers.IO) {
+                    WeatherHelper.updateWeather(context)
+                }
             }
         }
 
diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/services/UpdateCalendarService.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/services/UpdateCalendarService.kt
index b69f0b9..cef9fe0 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/services/UpdateCalendarService.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/services/UpdateCalendarService.kt
@@ -88,6 +88,7 @@ class UpdateCalendarService : Service() {
                 ) {
                     eventRepository.resetNextEventData()
                     eventRepository.clearEvents()
+                    Preferences.showEvents = false
                 } else {
                     try {
                         val provider = CalendarProvider(this@UpdateCalendarService)
diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/activities/MainActivity.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/activities/MainActivity.kt
index 6435d89..0e080df 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/activities/MainActivity.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/activities/MainActivity.kt
@@ -140,6 +140,7 @@ class MainActivity : AppCompatActivity(), SharedPreferences.OnSharedPreferenceCh
 
         if (Preferences.showEvents && !checkGrantedPermission(Manifest.permission.READ_CALENDAR)) {
             Preferences.showEvents = false
+            com.tommasoberlose.anotherwidget.receivers.UpdatesReceiver.removeUpdates(this)
         }
     }
 
diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/CalendarFragment.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/CalendarFragment.kt
index d6d3018..b6b7034 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/CalendarFragment.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/CalendarFragment.kt
@@ -182,7 +182,7 @@ class CalendarFragment : Fragment() {
 
         binding.showAllDayToggle.setOnCheckedChangeListener { _, isChecked ->
             Preferences.calendarAllDay = isChecked
-            MainWidget.updateWidget(requireContext())
+            updateCalendar()
         }
 
         binding.actionChangeAttendeeFilter.setOnClickListener {
@@ -227,7 +227,7 @@ class CalendarFragment : Fragment() {
 
         binding.showOnlyBusyEventsToggle.setOnCheckedChangeListener { _, isChecked ->
             Preferences.showOnlyBusyEvents = isChecked
-            MainWidget.updateWidget(requireContext())
+            updateCalendar()
         }
 
         binding.actionShowDiffTime.setOnClickListener {
@@ -254,6 +254,7 @@ class CalendarFragment : Fragment() {
                     .addItem(getString(R.string.settings_widget_update_frequency_low), Constants.WidgetUpdateFrequency.LOW.rawValue)
                     .addOnSelectItemListener { value ->
                         Preferences.widgetUpdateFrequency = value
+                        updateCalendar()
                     }.show()
             }
         }
diff --git a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/PreferencesFragment.kt b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/PreferencesFragment.kt
index 74a4c97..c531a40 100644
--- a/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/PreferencesFragment.kt
+++ b/app/src/main/java/com/tommasoberlose/anotherwidget/ui/fragments/tabs/PreferencesFragment.kt
@@ -135,6 +135,8 @@ class PreferencesFragment : Fragment() {
         binding.showWeatherSwitch.setOnCheckedChangeListener { _, enabled: Boolean ->
             Preferences.showWeather = enabled
             if (enabled) {
+                Preferences.weatherProviderError = ""
+                Preferences.weatherProviderLocationError = ""
                 WeatherReceiver.setUpdates(requireContext())
             } else {
                 WeatherReceiver.removeUpdates(requireContext())