diff --git a/app/src/main/java/com/termux/app/settings/preferences/SharedPreferenceUtils.java b/app/src/main/java/com/termux/app/settings/preferences/SharedPreferenceUtils.java index 3f2a9b17..389ba9ba 100644 --- a/app/src/main/java/com/termux/app/settings/preferences/SharedPreferenceUtils.java +++ b/app/src/main/java/com/termux/app/settings/preferences/SharedPreferenceUtils.java @@ -1,13 +1,47 @@ package com.termux.app.settings.preferences; +import android.annotation.SuppressLint; +import android.content.Context; import android.content.SharedPreferences; import com.termux.app.utils.Logger; +import java.util.Set; + public class SharedPreferenceUtils { private static final String LOG_TAG = "SharedPreferenceUtils"; + /** + * Get {@link SharedPreferences} instance of the preferences file 'name' with the operating mode + * {@link Context#MODE_PRIVATE}. This file will be created in the app package's default + * shared preferences directory. + * + * @param context The {@link Context} to get the {@link SharedPreferences} instance. + * @param name The preferences file basename without extension. + * @return The single {@link SharedPreferences} instance that can be used to retrieve and + * modify the preference values. + */ + public static SharedPreferences getPrivateSharedPreferences(Context context, String name) { + return context.getSharedPreferences(name, Context.MODE_PRIVATE); + } + + /** + * Get {@link SharedPreferences} instance of the preferences file 'name' with the operating mode + * {@link Context#MODE_PRIVATE} and {@link Context#MODE_MULTI_PROCESS}. This file will be + * created in the app package's default shared preferences directory. + * + * @param context The {@link Context} to get the {@link SharedPreferences} instance. + * @param name The preferences file basename without extension. + * @return The single {@link SharedPreferences} instance that can be used to retrieve and + * modify the preference values. + */ + public static SharedPreferences getPrivateAndMultiProcessSharedPreferences(Context context, String name) { + return context.getSharedPreferences(name, Context.MODE_PRIVATE | Context.MODE_MULTI_PROCESS); + } + + + /** * Get a {@code boolean} from {@link SharedPreferences}. * @@ -38,14 +72,71 @@ public class SharedPreferenceUtils { * @param sharedPreferences The {@link SharedPreferences} to set the value in. * @param key The key for the value. * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. */ - public static void setBoolean(SharedPreferences sharedPreferences, String key, boolean value) { + @SuppressLint("ApplySharedPref") + public static void setBoolean(SharedPreferences sharedPreferences, String key, boolean value, boolean commitToFile) { if(sharedPreferences == null) { Logger.logError(LOG_TAG, "Ignoring setting boolean value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); return; } - sharedPreferences.edit().putBoolean(key, value).apply(); + if(commitToFile) + sharedPreferences.edit().putBoolean(key, value).commit(); + else + sharedPreferences.edit().putBoolean(key, value).apply(); + + } + + + + /** + * Get a {@code float} from {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to get the value from. + * @param key The key for the value. + * @param def The default value if failed to read a valid value. + * @return Returns the {@code float} value stored in {@link SharedPreferences}, otherwise returns + * default if failed to read a valid value, like in case of an exception. + */ + public static float getFloat(SharedPreferences sharedPreferences, String key, float def) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Error getting float value for the \"" + key + "\" key from null shared preferences. Returning default value \"" + def + "\"."); + return def; + } + + try { + return sharedPreferences.getFloat(key, def); + } + catch (ClassCastException e) { + Logger.logStackTraceWithMessage(LOG_TAG, "Error getting float value for the \"" + key + "\" key from shared preferences. Returning default value \"" + def + "\".", e); + return def; + } + } + + /** + * Set a {@code float} in {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to set the value in. + * @param key The key for the value. + * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. + */ + @SuppressLint("ApplySharedPref") + public static void setFloat(SharedPreferences sharedPreferences, String key, float value, boolean commitToFile) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Ignoring setting float value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); + return; + } + + if(commitToFile) + sharedPreferences.edit().putFloat(key, value).commit(); + else + sharedPreferences.edit().putFloat(key, value).apply(); } @@ -80,14 +171,70 @@ public class SharedPreferenceUtils { * @param sharedPreferences The {@link SharedPreferences} to set the value in. * @param key The key for the value. * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. */ - public static void setInt(SharedPreferences sharedPreferences, String key, int value) { + @SuppressLint("ApplySharedPref") + public static void setInt(SharedPreferences sharedPreferences, String key, int value, boolean commitToFile) { if(sharedPreferences == null) { Logger.logError(LOG_TAG, "Ignoring setting int value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); return; } - sharedPreferences.edit().putInt(key, value).apply(); + if(commitToFile) + sharedPreferences.edit().putInt(key, value).commit(); + else + sharedPreferences.edit().putInt(key, value).apply(); + } + + + + /** + * Get a {@code long} from {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to get the value from. + * @param key The key for the value. + * @param def The default value if failed to read a valid value. + * @return Returns the {@code long} value stored in {@link SharedPreferences}, otherwise returns + * default if failed to read a valid value, like in case of an exception. + */ + public static long getLong(SharedPreferences sharedPreferences, String key, long def) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Error getting long value for the \"" + key + "\" key from null shared preferences. Returning default value \"" + def + "\"."); + return def; + } + + try { + return sharedPreferences.getLong(key, def); + } + catch (ClassCastException e) { + Logger.logStackTraceWithMessage(LOG_TAG, "Error getting long value for the \"" + key + "\" key from shared preferences. Returning default value \"" + def + "\".", e); + return def; + } + } + + /** + * Set a {@code long} in {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to set the value in. + * @param key The key for the value. + * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. + */ + @SuppressLint("ApplySharedPref") + public static void setLong(SharedPreferences sharedPreferences, String key, long value, boolean commitToFile) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Ignoring setting long value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); + return; + } + + if(commitToFile) + sharedPreferences.edit().putLong(key, value).commit(); + else + sharedPreferences.edit().putLong(key, value).apply(); } @@ -122,14 +269,70 @@ public class SharedPreferenceUtils { * @param sharedPreferences The {@link SharedPreferences} to set the value in. * @param key The key for the value. * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. */ - public static void setString(SharedPreferences sharedPreferences, String key, String value) { + @SuppressLint("ApplySharedPref") + public static void setString(SharedPreferences sharedPreferences, String key, String value, boolean commitToFile) { if(sharedPreferences == null) { Logger.logError(LOG_TAG, "Ignoring setting String value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); return; } - sharedPreferences.edit().putString(key, value).apply(); + if(commitToFile) + sharedPreferences.edit().putString(key, value).commit(); + else + sharedPreferences.edit().putString(key, value).apply(); + } + + + + /** + * Get a {@code Set} from {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to get the value from. + * @param key The key for the value. + * @param def The default value if failed to read a valid value. + * @return Returns the {@code Set} value stored in {@link SharedPreferences}, otherwise returns + * default if failed to read a valid value, like in case of an exception. + */ + public static Set getStringSet(SharedPreferences sharedPreferences, String key, Set def) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Error getting Set value for the \"" + key + "\" key from null shared preferences. Returning default value \"" + def + "\"."); + return def; + } + + try { + return sharedPreferences.getStringSet(key, def); + } + catch (ClassCastException e) { + Logger.logStackTraceWithMessage(LOG_TAG, "Error getting Set value for the \"" + key + "\" key from shared preferences. Returning default value \"" + def + "\".", e); + return def; + } + } + + /** + * Set a {@code Set} in {@link SharedPreferences}. + * + * @param sharedPreferences The {@link SharedPreferences} to set the value in. + * @param key The key for the value. + * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. + */ + @SuppressLint("ApplySharedPref") + public static void setStringSet(SharedPreferences sharedPreferences, String key, Set value, boolean commitToFile) { + if(sharedPreferences == null) { + Logger.logError(LOG_TAG, "Ignoring setting Set value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); + return; + } + + if(commitToFile) + sharedPreferences.edit().putStringSet(key, value).commit(); + else + sharedPreferences.edit().putStringSet(key, value).apply(); } @@ -172,14 +375,21 @@ public class SharedPreferenceUtils { * @param sharedPreferences The {@link SharedPreferences} to set the value in. * @param key The key for the value. * @param value The value to store. + * @param commitToFile If set to {@code true}, then value will be set to shared preferences + * in-memory cache and the file synchronously. Ideally, only to be used for + * multi-process use-cases. */ - public static void setIntStoredAsString(SharedPreferences sharedPreferences, String key, int value) { + @SuppressLint("ApplySharedPref") + public static void setIntStoredAsString(SharedPreferences sharedPreferences, String key, int value, boolean commitToFile) { if(sharedPreferences == null) { Logger.logError(LOG_TAG, "Ignoring setting int value \"" + value + "\" for the \"" + key + "\" key into null shared preferences."); return; } - sharedPreferences.edit().putString(key, Integer.toString(value)).apply(); + if(commitToFile) + sharedPreferences.edit().putString(key, Integer.toString(value)).commit(); + else + sharedPreferences.edit().putString(key, Integer.toString(value)).apply(); } } diff --git a/app/src/main/java/com/termux/app/settings/preferences/TermuxAppSharedPreferences.java b/app/src/main/java/com/termux/app/settings/preferences/TermuxAppSharedPreferences.java index 3dbbdeb6..18be3803 100644 --- a/app/src/main/java/com/termux/app/settings/preferences/TermuxAppSharedPreferences.java +++ b/app/src/main/java/com/termux/app/settings/preferences/TermuxAppSharedPreferences.java @@ -26,13 +26,13 @@ public class TermuxAppSharedPreferences { public TermuxAppSharedPreferences(@Nonnull Context context) { mContext = TermuxUtils.getTermuxPackageContext(context); - mSharedPreferences = getSharedPreferences(mContext); + mSharedPreferences = getPrivateSharedPreferences(mContext); setFontVariables(context); } - private static SharedPreferences getSharedPreferences(Context context) { - return context.getSharedPreferences(TermuxConstants.TERMUX_DEFAULT_PREFERENCES_FILE_BASENAME_WITHOUT_EXTENSION, Context.MODE_PRIVATE); + private static SharedPreferences getPrivateSharedPreferences(Context context) { + return SharedPreferenceUtils.getPrivateSharedPreferences(context, TermuxConstants.TERMUX_DEFAULT_PREFERENCES_FILE_BASENAME_WITHOUT_EXTENSION); } @@ -42,7 +42,7 @@ public class TermuxAppSharedPreferences { } public void setShowTerminalToolbar(boolean value) { - SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_SHOW_TERMINAL_TOOLBAR, value); + SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_SHOW_TERMINAL_TOOLBAR, value, false); } public boolean toogleShowTerminalToolbar() { @@ -58,7 +58,7 @@ public class TermuxAppSharedPreferences { } public void setKeepScreenOn(boolean value) { - SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_KEEP_SCREEN_ON, value); + SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_KEEP_SCREEN_ON, value, false); } @@ -86,7 +86,7 @@ public class TermuxAppSharedPreferences { } public void setFontSize(int value) { - SharedPreferenceUtils.setIntStoredAsString(mSharedPreferences, TERMUX_APP.KEY_FONTSIZE, value); + SharedPreferenceUtils.setIntStoredAsString(mSharedPreferences, TERMUX_APP.KEY_FONTSIZE, value, false); } public void changeFontSize(boolean increase) { @@ -106,7 +106,7 @@ public class TermuxAppSharedPreferences { } public void setCurrentSession(String value) { - SharedPreferenceUtils.setString(mSharedPreferences, TERMUX_APP.KEY_CURRENT_SESSION, value); + SharedPreferenceUtils.setString(mSharedPreferences, TERMUX_APP.KEY_CURRENT_SESSION, value, false); } @@ -117,7 +117,7 @@ public class TermuxAppSharedPreferences { public void setLogLevel(Context context, int logLevel) { logLevel = Logger.setLogLevel(context, logLevel); - SharedPreferenceUtils.setInt(mSharedPreferences, TERMUX_APP.KEY_LOG_LEVEL, logLevel); + SharedPreferenceUtils.setInt(mSharedPreferences, TERMUX_APP.KEY_LOG_LEVEL, logLevel, false); } @@ -127,7 +127,7 @@ public class TermuxAppSharedPreferences { } public void setTerminalViewKeyLoggingEnabled(boolean value) { - SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_TERMINAL_VIEW_KEY_LOGGING_ENABLED, value); + SharedPreferenceUtils.setBoolean(mSharedPreferences, TERMUX_APP.KEY_TERMINAL_VIEW_KEY_LOGGING_ENABLED, value, false); } }