diff --git a/app/build.gradle.kts b/app/build.gradle.kts
index 7c6a032..d435c27 100644
--- a/app/build.gradle.kts
+++ b/app/build.gradle.kts
@@ -30,6 +30,7 @@ android {
applicationIdSuffix = ".debug"
proguardFiles (getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
resValue("string", "app_name", "Easy Launcher (Debug)")
+ resValue("string", "settings_backups_file", "autoBackup.debug.ini")
}
getByName("release") {
@@ -37,6 +38,7 @@ android {
isShrinkResources = true
proguardFiles (getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
resValue("string", "app_name", "Easy Launcher")
+ resValue("string", "settings_backups_file", "autoBackup.ini")
}
}
@@ -87,6 +89,7 @@ dependencies {
implementation("androidx.work:work-runtime-ktx:2.9.0")
implementation("androidx.recyclerview:recyclerview:1.3.2")
implementation("androidx.viewpager2:viewpager2:1.1.0")
+ implementation("androidx.preference:preference-ktx:1.2.1")
debugImplementation("junit:junit:4.13.2")
androidTestImplementation("androidx.test.ext:junit:1.1.5")
androidTestImplementation("androidx.test.espresso:espresso-core:3.5.1")
diff --git a/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppExtensions.kt b/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppExtensions.kt
index 447c1a0..69e4922 100644
--- a/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppExtensions.kt
+++ b/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppExtensions.kt
@@ -3,6 +3,7 @@ package com.github.droidworksstudio.launcher.helper
import android.app.SearchManager
import android.content.Context
import android.content.Intent
+import android.content.SharedPreferences
import android.content.pm.LauncherApps
import android.net.Uri
import android.os.UserHandle
@@ -10,7 +11,11 @@ import android.util.Log
import android.view.View
import android.view.inputmethod.InputMethodManager
import android.widget.EditText
+import android.widget.Toast
+import androidx.fragment.app.Fragment
import com.github.droidworksstudio.launcher.Constants
+import java.io.File
+import java.io.IOException
fun View.hideKeyboard() {
this.clearFocus()
@@ -74,6 +79,86 @@ fun Context.searchCustomSearchEngine(searchQuery: String? = null): Boolean {
return true
}
+fun Context.backupSharedPreferences(backupFileName: String) {
+ val sharedPreferences: SharedPreferences = this.getSharedPreferences(Constants.PREFS_FILENAME, 0)
+ val allPrefs = sharedPreferences.all
+ val backupFile = File(filesDir, backupFileName)
+
+ println("Backup SharedPreferences to: ${backupFile.absolutePath}")
+
+ try {
+ backupFile.bufferedWriter().use { writer ->
+ for ((key, value) in allPrefs) {
+ if (value != null) {
+ val line = when (value) {
+ is Boolean -> "$key=${value}\n"
+ is Int -> "$key=${value}\n"
+ is Float -> "$key=${value}\n"
+ is Long -> "$key=${value}\n"
+ is String -> "$key=${value}\n"
+ is Set<*> -> "$key=${value.joinToString(",")}\n"
+ else -> null
+ }
+ if (line != null) {
+ writer.write(line)
+ println("Writing: $line")
+ } else {
+ println("Skipping unsupported type for key: $key")
+ }
+ } else {
+ println("Null value for key: $key")
+ }
+ }
+ }
+ println("Backup completed successfully.")
+ } catch (e: IOException) {
+ e.printStackTrace()
+ println("Failed to backup SharedPreferences: ${e.message}")
+ }
+}
+
+fun Context.restoreSharedPreferences(backupFileName: String) {
+ val sharedPreferences: SharedPreferences = this.getSharedPreferences(Constants.PREFS_FILENAME, 0)
+ val editor = sharedPreferences.edit()
+ val backupFile = File(filesDir, backupFileName)
+
+ println("Restoring SharedPreferences from: ${backupFile.absolutePath}")
+
+ if (backupFile.exists()) {
+ try {
+ backupFile.forEachLine { line ->
+ val (key, value) = line.split("=", limit = 2)
+ when {
+ value.toBooleanStrictOrNull() != null -> editor.putBoolean(key, value.toBoolean())
+ value.toIntOrNull() != null -> editor.putInt(key, value.toInt())
+ value.toFloatOrNull() != null -> editor.putFloat(key, value.toFloat())
+ value.toLongOrNull() != null -> editor.putLong(key, value.toLong())
+ value.contains(",") -> editor.putStringSet(key, value.split(",").toSet())
+ else -> editor.putString(key, value)
+ }
+ println("Restoring: $key=$value")
+ }
+ editor.apply()
+ println("Restore completed successfully.")
+ } catch (e: IOException) {
+ e.printStackTrace()
+ println("Failed to restore SharedPreferences: ${e.message}")
+ }
+ } else {
+ println("Backup file does not exist.")
+ }
+}
+
+fun Fragment.restartApp() {
+ val packageManager = requireContext().packageManager
+ val intent = packageManager.getLaunchIntentForPackage(requireContext().packageName)
+ intent?.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
+ if (intent != null) {
+ startActivity(intent)
+ }
+ requireActivity().finish()
+}
+
fun Context.isPackageInstalled(packageName: String, userHandle: UserHandle = android.os.Process.myUserHandle()): Boolean {
val launcher = getSystemService(Context.LAUNCHER_APPS_SERVICE) as LauncherApps
val activityInfo = launcher.getActivityList(packageName, userHandle)
diff --git a/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppHelper.kt b/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppHelper.kt
index 5e7ec83..7e8be3b 100644
--- a/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppHelper.kt
+++ b/app/src/main/java/com/github/droidworksstudio/launcher/helper/AppHelper.kt
@@ -267,7 +267,7 @@ class AppHelper @Inject constructor() {
return dailyWordsArray[wordIndex]
}
- fun shareApp(context: Context){
+ fun shareAppButton(context: Context){
val shareIntent = Intent(Intent.ACTION_SEND)
shareIntent.type = "text/plain"
shareIntent.putExtra(Intent.EXTRA_SUBJECT, "Share Application")
@@ -275,19 +275,27 @@ class AppHelper @Inject constructor() {
context.startActivity(Intent.createChooser(shareIntent, "Share Application"))
}
- fun github(context: Context){
+ fun githubButton(context: Context){
val uri = Uri.parse("https://github.com/DroidWorksStudio/EasyLauncher")
val intent = Intent(Intent.ACTION_VIEW, uri)
context.startActivity(intent)
}
- fun feedback(context: Context){
+ fun feedbackButton(context: Context){
val emailIntent = Intent(Intent.ACTION_SENDTO)
emailIntent.data = Uri.parse("mailto:droidworksstuido@063240.xyz")
emailIntent.putExtra(Intent.EXTRA_SUBJECT, "Easy Launcher")
context.startActivity(Intent.createChooser(emailIntent, "Choose Mail Application"))
}
+ fun backupSharedPreferences(context: Context) {
+ context.backupSharedPreferences(context.getString(R.string.settings_backups_file))
+ }
+
+ fun restoreSharedPreferences(context: Context) {
+ context.restoreSharedPreferences(context.getString(R.string.settings_backups_file))
+ }
+
fun enableAppAsAccessibilityService(context: Context, accessibilityState: Boolean) {
val state: String = if (accessibilityState) {
context.getString(R.string.accessibility_settings_disable)
diff --git a/app/src/main/java/com/github/droidworksstudio/launcher/ui/settings/SettingsFragment.kt b/app/src/main/java/com/github/droidworksstudio/launcher/ui/settings/SettingsFragment.kt
index 49c00e1..6f85f53 100644
--- a/app/src/main/java/com/github/droidworksstudio/launcher/ui/settings/SettingsFragment.kt
+++ b/app/src/main/java/com/github/droidworksstudio/launcher/ui/settings/SettingsFragment.kt
@@ -7,6 +7,7 @@ import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
+import android.widget.Toast
import androidx.fragment.app.Fragment
import androidx.fragment.app.viewModels
import androidx.navigation.NavController
@@ -15,6 +16,7 @@ import com.github.droidworksstudio.launcher.R
import com.github.droidworksstudio.launcher.databinding.FragmentSettingsBinding
import com.github.droidworksstudio.launcher.helper.AppHelper
import com.github.droidworksstudio.launcher.helper.PreferenceHelper
+import com.github.droidworksstudio.launcher.helper.restartApp
import com.github.droidworksstudio.launcher.listener.ScrollEventListener
import com.github.droidworksstudio.launcher.ui.bottomsheetdialog.AlignmentBottomSheetDialogFragment
import com.github.droidworksstudio.launcher.ui.bottomsheetdialog.ColorBottomSheetDialogFragment
@@ -30,7 +32,6 @@ class SettingsFragment : Fragment(), ScrollEventListener {
private var _binding: FragmentSettingsBinding? = null
private val binding get() = _binding!!
- //private val viewModel: AppViewModel by viewModels()
private val preferenceViewModel: PreferenceViewModel by viewModels()
@Inject
@@ -127,15 +128,27 @@ class SettingsFragment : Fragment(), ScrollEventListener {
}
binding.shareView.setOnClickListener {
- appHelper.shareApp(requireContext())
+ appHelper.shareAppButton(requireContext())
}
binding.githubView.setOnClickListener {
- appHelper.github(requireContext())
+ appHelper.githubButton(requireContext())
+
}
binding.feedbackView.setOnClickListener {
- appHelper.feedback(requireContext())
+ appHelper.feedbackButton(requireContext())
+ }
+
+ binding.backupView.setOnClickListener {
+ appHelper.backupSharedPreferences(requireContext())
+ Toast.makeText(requireContext(), getString(R.string.settings_reload_app_backup), Toast.LENGTH_SHORT).show()
+ }
+
+ binding.restoreView.setOnClickListener {
+ appHelper.restoreSharedPreferences(requireContext())
+ Toast.makeText(requireContext(), getString(R.string.settings_reload_app_restore), Toast.LENGTH_SHORT).show()
+ restartApp()
}
}
diff --git a/app/src/main/res/layout/fragment_settings.xml b/app/src/main/res/layout/fragment_settings.xml
index f538ba4..073df8e 100644
--- a/app/src/main/res/layout/fragment_settings.xml
+++ b/app/src/main/res/layout/fragment_settings.xml
@@ -673,6 +673,49 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Time Style
App Manage
Gestures
+ Backups
Others
Show Status Bar
@@ -75,6 +76,12 @@
Feedback
Github
+ Backup Preferences
+ Restore Preferences
+
+ Preferences backed up.
+ Preferences restored. Restarting.
+
Authentication
Log in using your biometric credentials.
Authentication Cancel