From 813c1f54a0d6052ece7257553bedfb4f1276c39a Mon Sep 17 00:00:00 2001 From: Roman Tsisyk Date: Tue, 31 Oct 2023 11:21:06 +0200 Subject: [PATCH] [android] Disable the screen wake lock by default Organic Maps drains the battery like crazy with default settings. **Steps to reproduce:** 1. Install and run the app. 2. Lock your device and put it on a flat surface, with the screen facing up. 3. Pick up the device OR just tap on the screen. 4. The screen will automatically turn on, this is an Android feature. 5. Organic Maps will never allow the screen to go off after that. Now, imaging this case happens while the phone is in a pocket. The battery may The battery will completely drain before the user even notice that screen is on. I see Organic Maps draining battery and burning screens on my devices regulary. The problem is caused by two options which are enabled by default - "Show on the lock screen" and "Allow the screen to sleep". The first option adds the app to the lock screen (which is weird on its own). The second option doesn't allow the phone's screen to go off. This patch does the following: - Inverts "Allow the screen to sleep" option to "Keep the screen on". - Sets the default value of the option to OFF (=allow screen to sleep). - Applies the option only in FOLLOW & FOLLOW_ROTATE location modes. - Forces the screen to keep on during navigation no matter of the option. To summarize, with enabled "Keep the screen on" the screen will be kept on in the following cases: - During navigation. - FOLLOW and FOLLOW_ROTATE location modes. Without the option, the screen will be kept on only during navigation. Signed-off-by: Roman Tsisyk --- .../main/cpp/app/organicmaps/util/Config.cpp | 13 ++ .../DownloadResourcesLegacyActivity.java | 3 +- .../java/app/organicmaps/MwmActivity.java | 11 +- .../java/app/organicmaps/MwmApplication.java | 2 + .../java/app/organicmaps/SplashActivity.java | 1 - .../settings/SettingsPrefsFragment.java | 12 +- .../java/app/organicmaps/util/Config.java | 24 ++- .../main/java/app/organicmaps/util/Utils.java | 2 + .../src/main/res/values/donottranslate.xml | 2 +- android/app/src/main/res/values/strings.xml | 4 +- android/app/src/main/res/xml/prefs_main.xml | 6 +- data/strings/strings.txt | 162 +++++++++--------- 12 files changed, 140 insertions(+), 102 deletions(-) diff --git a/android/app/src/main/cpp/app/organicmaps/util/Config.cpp b/android/app/src/main/cpp/app/organicmaps/util/Config.cpp index e754985f77..3794f74349 100644 --- a/android/app/src/main/cpp/app/organicmaps/util/Config.cpp +++ b/android/app/src/main/cpp/app/organicmaps/util/Config.cpp @@ -4,6 +4,19 @@ extern "C" { + JNIEXPORT jboolean JNICALL + Java_app_organicmaps_util_Config_nativeHasConfigValue(JNIEnv * env, jclass thiz, jstring name) + { + std::string value; + return settings::Get(jni::ToNativeString(env, name), value); + } + + JNIEXPORT void JNICALL + Java_app_organicmaps_util_Config_nativeDeleteConfigValue(JNIEnv * env, jclass thiz, jstring name) + { + settings::Delete(jni::ToNativeString(env, name)); + } + JNIEXPORT jboolean JNICALL Java_app_organicmaps_util_Config_nativeGetBoolean(JNIEnv * env, jclass thiz, jstring name, jboolean defaultVal) { diff --git a/android/app/src/main/java/app/organicmaps/DownloadResourcesLegacyActivity.java b/android/app/src/main/java/app/organicmaps/DownloadResourcesLegacyActivity.java index d0e16add7b..52eeaf0b3c 100644 --- a/android/app/src/main/java/app/organicmaps/DownloadResourcesLegacyActivity.java +++ b/android/app/src/main/java/app/organicmaps/DownloadResourcesLegacyActivity.java @@ -30,6 +30,7 @@ import app.organicmaps.intent.IntentProcessor; import app.organicmaps.intent.MapTask; import app.organicmaps.location.LocationHelper; import app.organicmaps.location.LocationListener; +import app.organicmaps.util.Config; import app.organicmaps.util.ConnectionState; import app.organicmaps.util.StringUtils; import app.organicmaps.util.UiUtils; @@ -231,7 +232,7 @@ public class DownloadResourcesLegacyActivity extends BaseMwmFragmentActivity super.onSafeDestroy(); mApiRequest.unregister(); mApiRequest = null; - Utils.keepScreenOn(false, getWindow()); + Utils.keepScreenOn(Config.isKeepScreenOnEnabled(), getWindow()); if (mCountryDownloadListenerSlot != 0) { MapManager.nativeUnsubscribe(mCountryDownloadListenerSlot); diff --git a/android/app/src/main/java/app/organicmaps/MwmActivity.java b/android/app/src/main/java/app/organicmaps/MwmActivity.java index 4ae15c8234..06f8608a6f 100644 --- a/android/app/src/main/java/app/organicmaps/MwmActivity.java +++ b/android/app/src/main/java/app/organicmaps/MwmActivity.java @@ -117,7 +117,10 @@ import static android.Manifest.permission.ACCESS_COARSE_LOCATION; import static android.Manifest.permission.ACCESS_FINE_LOCATION; import static android.Manifest.permission.POST_NOTIFICATIONS; import static android.content.pm.PackageManager.PERMISSION_GRANTED; +import static app.organicmaps.location.LocationState.FOLLOW; +import static app.organicmaps.location.LocationState.FOLLOW_AND_ROTATE; import static app.organicmaps.location.LocationState.LOCATION_TAG; +import static app.organicmaps.location.LocationState.PENDING_POSITION; public class MwmActivity extends BaseMwmFragmentActivity implements PlacePageActivationListener, @@ -1089,8 +1092,6 @@ public class MwmActivity extends BaseMwmFragmentActivity LocationHelper.from(this).addListener(this); onMyPositionModeChanged(LocationState.nativeGetMode()); mSearchController.attach(this); - if (!Config.isScreenSleepEnabled()) - Utils.keepScreenOn(true, getWindow()); } @Override @@ -1523,6 +1524,7 @@ public class MwmActivity extends BaseMwmFragmentActivity mMapButtonsViewModel.setSearchOption(null); mMapButtonsViewModel.setLayoutMode(MapButtonsController.LayoutMode.regular); refreshLightStatusBar(); + Utils.keepScreenOn(Config.isKeepScreenOnEnabled(), getWindow()); } @Override @@ -1542,6 +1544,7 @@ public class MwmActivity extends BaseMwmFragmentActivity requestPostNotificationsPermission(); NavigationService.startForegroundService(this); + Utils.keepScreenOn(true, getWindow()); } @Override @@ -1693,6 +1696,10 @@ public class MwmActivity extends BaseMwmFragmentActivity if (controller.isPlanning()) showAddStartOrFinishFrame(controller, true); LocationHelper.from(this).restartWithNewMode(); + if (newMode == FOLLOW || newMode == FOLLOW_AND_ROTATE) + Utils.keepScreenOn(Config.isKeepScreenOnEnabled() || RoutingController.get().isNavigating(), getWindow()); + else + Utils.keepScreenOn(RoutingController.get().isNavigating(), getWindow()); } /** diff --git a/android/app/src/main/java/app/organicmaps/MwmApplication.java b/android/app/src/main/java/app/organicmaps/MwmApplication.java index f9f86bd051..3e20a87850 100644 --- a/android/app/src/main/java/app/organicmaps/MwmApplication.java +++ b/android/app/src/main/java/app/organicmaps/MwmApplication.java @@ -149,6 +149,8 @@ public class MwmApplication extends Application implements Application.ActivityL Logger.d(TAG, "Settings path = " + settingsPath); nativeSetSettingsDir(settingsPath); + Config.init(this); + mMainLoopHandler = new Handler(getMainLooper()); ConnectionState.INSTANCE.initialize(this); diff --git a/android/app/src/main/java/app/organicmaps/SplashActivity.java b/android/app/src/main/java/app/organicmaps/SplashActivity.java index 2ecec89d3d..a6fc6267f2 100644 --- a/android/app/src/main/java/app/organicmaps/SplashActivity.java +++ b/android/app/src/main/java/app/organicmaps/SplashActivity.java @@ -81,7 +81,6 @@ public class SplashActivity extends AppCompatActivity throw new IllegalArgumentException("Attempt to apply unsupported theme: " + theme); UiThread.cancelDelayedTasks(mInitCoreDelayedTask); - Config.updateCounters(this); setContentView(R.layout.activity_splash); mPermissionRequest = registerForActivityResult(new ActivityResultContracts.RequestMultiplePermissions(), result -> Config.setLocationRequested()); diff --git a/android/app/src/main/java/app/organicmaps/settings/SettingsPrefsFragment.java b/android/app/src/main/java/app/organicmaps/settings/SettingsPrefsFragment.java index f68a8af251..e40df225bb 100644 --- a/android/app/src/main/java/app/organicmaps/settings/SettingsPrefsFragment.java +++ b/android/app/src/main/java/app/organicmaps/settings/SettingsPrefsFragment.java @@ -731,18 +731,18 @@ public class SettingsPrefsFragment extends BaseXmlSettingsFragment private void initScreenSleepEnabledPrefsCallbacks() { - final Preference pref = getPreference(getString(R.string.pref_screen_sleep)); + final Preference pref = getPreference(getString(R.string.pref_keep_screen_on)); - final boolean isScreenSleepEnabled = Config.isScreenSleepEnabled(); - ((TwoStatePreference) pref).setChecked(isScreenSleepEnabled); + final boolean isKeepScreenOnEnabled = Config.isKeepScreenOnEnabled(); + ((TwoStatePreference) pref).setChecked(isKeepScreenOnEnabled); pref.setOnPreferenceChangeListener( (preference, newValue) -> { boolean newVal = (Boolean) newValue; - if (isScreenSleepEnabled != newVal) + if (isKeepScreenOnEnabled != newVal) { - Config.setScreenSleepEnabled(newVal); - Utils.keepScreenOn(!newVal, requireActivity().getWindow()); + Config.setKeepScreenOnEnabled(newVal); + Utils.keepScreenOn(newVal, requireActivity().getWindow()); } return true; }); diff --git a/android/app/src/main/java/app/organicmaps/util/Config.java b/android/app/src/main/java/app/organicmaps/util/Config.java index 7870d7fbfc..bfa04a50c2 100644 --- a/android/app/src/main/java/app/organicmaps/util/Config.java +++ b/android/app/src/main/java/app/organicmaps/util/Config.java @@ -30,7 +30,8 @@ public final class Config private static final String KEY_MISC_USE_MOBILE_DATA = "UseMobileData"; private static final String KEY_MISC_USE_MOBILE_DATA_TIMESTAMP = "UseMobileDataTimestamp"; private static final String KEY_MISC_USE_MOBILE_DATA_ROAMING = "UseMobileDataRoaming"; - private static final String KEY_MISC_ENABLE_SCREEN_SLEEP = "EnableScreenSleep"; + private static final String KEY_MISC_KEEP_SCREEN_ON = "KeepScreenOn"; + private static final String KEY_MISC_SHOW_ON_LOCK_SCREEN = "ShowOnLockScreen"; private static final String KEY_MISC_AGPS_TIMESTAMP = "AGPSTimestamp"; private static final String KEY_DONATE_URL = "DonateUrl"; @@ -170,14 +171,14 @@ public final class Config setBool(KEY_PREF_STATISTICS, enabled); } - public static boolean isScreenSleepEnabled() + public static boolean isKeepScreenOnEnabled() { - return getBool(KEY_MISC_ENABLE_SCREEN_SLEEP, false); + return getBool(KEY_MISC_KEEP_SCREEN_ON, false); } - public static void setScreenSleepEnabled(boolean enabled) + public static void setKeepScreenOnEnabled(boolean enabled) { - setBool(KEY_MISC_ENABLE_SCREEN_SLEEP, enabled); + setBool(KEY_MISC_KEEP_SCREEN_ON, enabled); } public static boolean isShowOnLockScreenEnabled() @@ -333,13 +334,14 @@ public final class Config return getString(KEY_DONATE_URL); } - public static void updateCounters(@NonNull Context context) + public static void init(@NonNull Context context) { PreferenceManager.setDefaultValues(context, R.xml.prefs_main, false); final SharedPreferences prefs = MwmApplication.prefs(context); final SharedPreferences.Editor editor = prefs.edit(); + // Update counters. final int launchNumber = prefs.getInt(KEY_APP_LAUNCH_NUMBER, 0); editor.putInt(KEY_APP_LAUNCH_NUMBER, launchNumber + 1); editor.putLong(KEY_APP_LAST_SESSION_TIMESTAMP, System.currentTimeMillis()); @@ -354,6 +356,14 @@ public final class Config editor.remove("LastRatedSession"); editor.remove("RatedDialog"); + // Migrate ENABLE_SCREEN_SLEEP to KEEP_SCREEN_ON. + final String KEY_MISC_ENABLE_SCREEN_SLEEP = "EnableScreenSleep"; + if (nativeHasConfigValue(KEY_MISC_ENABLE_SCREEN_SLEEP)) + { + nativeSetBoolean(KEY_MISC_KEEP_SCREEN_ON, !getBool(KEY_MISC_ENABLE_SCREEN_SLEEP, false)); + nativeDeleteConfigValue(KEY_MISC_ENABLE_SCREEN_SLEEP); + } + editor.apply(); } @@ -370,6 +380,8 @@ public final class Config .apply(); } + private static native boolean nativeHasConfigValue(String name); + private static native boolean nativeDeleteConfigValue(String name); private static native boolean nativeGetBoolean(String name, boolean defaultValue); private static native void nativeSetBoolean(String name, boolean value); private static native int nativeGetInt(String name, int defaultValue); diff --git a/android/app/src/main/java/app/organicmaps/util/Utils.java b/android/app/src/main/java/app/organicmaps/util/Utils.java index 69b954f226..677eb2ad26 100644 --- a/android/app/src/main/java/app/organicmaps/util/Utils.java +++ b/android/app/src/main/java/app/organicmaps/util/Utils.java @@ -74,6 +74,7 @@ public class Utils */ public static void keepScreenOn(boolean enable, Window w) { + Logger.i(TAG, "enabled = " + enable + " window = " + w); if (enable) w.addFlags(android.view.WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); else @@ -90,6 +91,7 @@ public class Utils public static void showOnLockScreen(boolean enable, Activity activity) { + Logger.i(TAG, "enabled = " + enable + " window = " + activity.getWindow()); if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O_MR1) showOnLockScreenOld(enable, activity); else diff --git a/android/app/src/main/res/values/donottranslate.xml b/android/app/src/main/res/values/donottranslate.xml index 527150dca9..f515beb367 100644 --- a/android/app/src/main/res/values/donottranslate.xml +++ b/android/app/src/main/res/values/donottranslate.xml @@ -37,7 +37,7 @@ Information Transliteration PowerManagment - ScreenSleep + KeepScreenOn ShowOnLockScreen %1$s: %2$s diff --git a/android/app/src/main/res/values/strings.xml b/android/app/src/main/res/values/strings.xml index 5ca04fd5c1..9e0e0a7c18 100644 --- a/android/app/src/main/res/values/strings.xml +++ b/android/app/src/main/res/values/strings.xml @@ -753,9 +753,9 @@ Connection failure Disconnect USB cable - Allow the screen to sleep + Keep the screen on - When enabled, the screen will be allowed to sleep after a period of inactivity. + When enabled, the screen will always be on when displaying the map. Show on the lock screen diff --git a/android/app/src/main/res/xml/prefs_main.xml b/android/app/src/main/res/xml/prefs_main.xml index 7bb06f87d1..983f8c3f40 100644 --- a/android/app/src/main/res/xml/prefs_main.xml +++ b/android/app/src/main/res/xml/prefs_main.xml @@ -84,10 +84,10 @@ android:entryValues="@array/power_management_scheme_values" android:order="15"/>