From bbec7745feec7d98a01eb73fcf5a4ae68afbb6a4 Mon Sep 17 00:00:00 2001 From: davide Date: Mon, 18 Jul 2022 23:25:10 +0200 Subject: [PATCH] Implement multiplatform settings --- androidApp/build.gradle.kts | 3 + .../android/AddSourceActivity.kt | 11 ++- .../android/HomeActivity.kt | 68 ++++++++----------- .../android/LoginActivity.kt | 37 ++++------ .../apps/readerforselfossv2/android/MyApp.kt | 20 +++--- .../android/ReaderActivity.kt | 26 ++----- .../android/SourcesActivity.kt | 10 +-- .../android/adapters/SourcesListAdapter.kt | 2 +- .../android/background/background.kt | 10 ++- .../android/fragments/ArticleFragment.kt | 26 +++---- .../android/settings/SettingsActivity.kt | 15 ++-- .../android/themes/AppColors.kt | 14 ++-- .../android/utils/Config.kt | 22 +++--- .../utils/glide/SelfSignedGlideModule.kt | 6 +- shared/build.gradle.kts | 6 ++ .../service/ApiDetailsServiceImpl.kt | 29 ++++---- 16 files changed, 126 insertions(+), 179 deletions(-) rename androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/service/AndroidApiDetailsService.kt => shared/src/commonMain/kotlin/bou/amine/apps/readerforselfossv2/service/ApiDetailsServiceImpl.kt (50%) diff --git a/androidApp/build.gradle.kts b/androidApp/build.gradle.kts index cabb1c2..d4a17f7 100644 --- a/androidApp/build.gradle.kts +++ b/androidApp/build.gradle.kts @@ -174,6 +174,9 @@ dependencies { implementation("org.kodein.di:kodein-di:7.12.0") implementation("org.kodein.di:kodein-di-framework-android-x:7.12.0") + //Settings + implementation("com.russhwolf:multiplatform-settings-no-arg:0.9") + //PhotoView implementation("com.github.chrisbanes:PhotoView:2.3.0") diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/AddSourceActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/AddSourceActivity.kt index d8908f6..75d1631 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/AddSourceActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/AddSourceActivity.kt @@ -1,9 +1,7 @@ package bou.amine.apps.readerforselfossv2.android -import android.content.Context import android.content.Intent import android.os.Bundle -import androidx.preference.PreferenceManager import androidx.constraintlayout.widget.ConstraintLayout import androidx.appcompat.app.AppCompatActivity import android.view.View @@ -24,6 +22,7 @@ import bou.amine.apps.readerforselfossv2.android.databinding.ActivityAddSourceBi import bou.amine.apps.readerforselfossv2.rest.SelfossApiImpl import bou.amine.apps.readerforselfossv2.rest.SelfossModel import bou.amine.apps.readerforselfossv2.service.ApiDetailsService +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -39,6 +38,7 @@ class AddSourceActivity : AppCompatActivity(), DIAware { private lateinit var appColors: AppColors private lateinit var binding: ActivityAddSourceBinding + private val settings = Settings() override val di by closestDI() private val apiDetailsService : ApiDetailsService by instance() @@ -78,9 +78,6 @@ class AddSourceActivity : AppCompatActivity(), DIAware { supportActionBar?.setDisplayShowHomeEnabled(true) try { - val prefs = PreferenceManager.getDefaultSharedPreferences(this) - val settings = - getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) api = SelfossApiImpl( // this, // this@AddSourceActivity, @@ -103,7 +100,7 @@ class AddSourceActivity : AppCompatActivity(), DIAware { override fun onResume() { super.onResume() - val config = Config(this) + val config = Config() if (config.baseUrl.isEmpty() || !config.baseUrl.isBaseUrlValid(this@AddSourceActivity)) { mustLoginToAddSource() @@ -199,7 +196,7 @@ class AddSourceActivity : AppCompatActivity(), DIAware { mSpoutsValue!!, tags.text.toString(), "", - PreferenceManager.getDefaultSharedPreferences(this@AddSourceActivity).getInt("apiVersionMajor", 0) + settings.getInt("apiVersionMajor", 0) ) if (response != null) { finish() diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/HomeActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/HomeActivity.kt index 24e79f7..b72f211 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/HomeActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/HomeActivity.kt @@ -1,14 +1,11 @@ package bou.amine.apps.readerforselfossv2.android -import android.content.Context import android.content.Intent -import android.content.SharedPreferences import android.graphics.Color import android.graphics.drawable.Drawable import android.graphics.drawable.GradientDrawable import android.net.Uri import android.os.Bundle -import androidx.preference.PreferenceManager import android.view.Menu import android.view.MenuItem import android.view.View @@ -79,6 +76,7 @@ import com.mikepenz.materialdrawer.util.DrawerImageLoader import com.mikepenz.materialdrawer.util.addStickyFooterItem import com.mikepenz.materialdrawer.util.updateBadge import com.mikepenz.materialdrawer.widget.AccountHeaderView +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -132,13 +130,11 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar private lateinit var tabStarredBadge: TextBadgeItem private lateinit var api: SelfossApiImpl private lateinit var customTabActivityHelper: CustomTabActivityHelper - private lateinit var editor: SharedPreferences.Editor - private lateinit var sharedPref: SharedPreferences private lateinit var appColors: AppColors private var offset: Int = 0 private var firstVisible: Int = 0 private lateinit var recyclerViewScrollListener: RecyclerView.OnScrollListener - private lateinit var settings: SharedPreferences + private var settings = Settings() private lateinit var binding: ActivityHomeBinding private var recyclerAdapter: RecyclerView.Adapter<*>? = null @@ -164,7 +160,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar override fun onCreate(savedInstanceState: Bundle?) { appColors = AppColors(this@HomeActivity) - config = Config(this@HomeActivity) + config = Config() super.onCreate(savedInstanceState) binding = ActivityHomeBinding.inflate(layoutInflater) @@ -196,9 +192,6 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar customTabActivityHelper = CustomTabActivityHelper() - sharedPref = PreferenceManager.getDefaultSharedPreferences(this) - settings = getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - api = SelfossApiImpl( // this, // this@HomeActivity, @@ -219,7 +212,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar handleSwipeRefreshLayout() - handleSharedPrefs() + handleSettings() getApiMajorVersion() @@ -358,7 +351,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar val version = api.version() if (version != null) { apiVersionMajor = version.getApiMajorVersion() - sharedPref.edit().putInt("apiVersionMajor", apiVersionMajor).apply() + settings.putInt("apiVersionMajor", apiVersionMajor) } } } @@ -369,10 +362,6 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar // TODO: Make this the only appcolors init appColors = AppColors(this@HomeActivity) - sharedPref = PreferenceManager.getDefaultSharedPreferences(this) - - editor = settings.edit() - handleDrawerItems() handleThemeUpdate() @@ -399,34 +388,34 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar customTabActivityHelper.unbindCustomTabsService(this) } - private fun handleSharedPrefs() { - internalBrowser = sharedPref.getBoolean("prefer_internal_browser", true) - articleViewer = sharedPref.getBoolean("prefer_article_viewer", true) - shouldBeCardView = sharedPref.getBoolean("card_view_active", false) - displayUnreadCount = sharedPref.getBoolean("display_unread_count", true) - displayAllCount = sharedPref.getBoolean("display_other_count", false) - fullHeightCards = sharedPref.getBoolean("full_height_cards", false) - itemsNumber = sharedPref.getString("prefer_api_items_number", "200")!!.toInt() - userIdentifier = sharedPref.getString("unique_id", "")!! - displayAccountHeader = sharedPref.getBoolean("account_header_displaying", false) - infiniteScroll = sharedPref.getBoolean("infinite_loading", false) - searchService.itemsCaching = sharedPref.getBoolean("items_caching", false) - updateSources = sharedPref.getBoolean("update_sources", true) - markOnScroll = sharedPref.getBoolean("mark_on_scroll", false) - hiddenTags = if (sharedPref.getString("hidden_tags", "")!!.isNotEmpty()) { - sharedPref.getString("hidden_tags", "")!!.replace("\\s".toRegex(), "").split(",") + private fun handleSettings() { + internalBrowser = settings.getBoolean("prefer_internal_browser", true) + articleViewer = settings.getBoolean("prefer_article_viewer", true) + shouldBeCardView = settings.getBoolean("card_view_active", false) + displayUnreadCount = settings.getBoolean("display_unread_count", true) + displayAllCount = settings.getBoolean("display_other_count", false) + fullHeightCards = settings.getBoolean("full_height_cards", false) + itemsNumber = settings.getString("prefer_api_items_number", "200").toInt() + userIdentifier = settings.getString("unique_id", "") + displayAccountHeader = settings.getBoolean("account_header_displaying", false) + infiniteScroll = settings.getBoolean("infinite_loading", false) + searchService.itemsCaching = settings.getBoolean("items_caching", false) + updateSources = settings.getBoolean("update_sources", true) + markOnScroll = settings.getBoolean("mark_on_scroll", false) + hiddenTags = if (settings.getString("hidden_tags", "").isNotEmpty()) { + settings.getString("hidden_tags", "").replace("\\s".toRegex(), "").split(",") } else { emptyList() } - periodicRefresh = sharedPref.getBoolean("periodic_refresh", false) - refreshWhenChargingOnly = sharedPref.getBoolean("refresh_when_charging", false) - refreshMinutes = sharedPref.getString("periodic_refresh_minutes", "360")!!.toLong() + periodicRefresh = settings.getBoolean("periodic_refresh", false) + refreshWhenChargingOnly = settings.getBoolean("refresh_when_charging", false) + refreshMinutes = settings.getString("periodic_refresh_minutes", "360").toLong() if (refreshMinutes <= 15) { refreshMinutes = 15 } - apiVersionMajor = sharedPref.getInt("apiVersionMajor", 0) + apiVersionMajor = settings.getInt("apiVersionMajor", 0) } private fun handleThemeBinding() { @@ -481,8 +470,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar binding.drawerContainer.addDrawerListener(drawerListener) displayAccountHeader = - PreferenceManager.getDefaultSharedPreferences(this) - .getBoolean("account_header_displaying", false) + settings.getBoolean("account_header_displaying", false) binding.mainDrawer.addStickyFooterItem( PrimaryDrawerItem().apply { @@ -512,7 +500,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar attachToSliderView(binding.mainDrawer) addProfiles( ProfileDrawerItem().apply { - nameText = settings.getString("url", "").toString() + nameText = settings.getString("url", "") setBackgroundResource(R.drawable.bg) iconRes = R.mipmap.ic_launcher selectionListEnabledForSingleProfile = false @@ -1211,7 +1199,7 @@ class HomeActivity : AppCompatActivity(), SearchView.OnQueryTextListener, DIAwar return true } R.id.action_disconnect -> { - return Config.logoutAndRedirect(this, this@HomeActivity, editor) + return Config.logoutAndRedirect(this, this@HomeActivity) } else -> return super.onOptionsItemSelected(item) } diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/LoginActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/LoginActivity.kt index b4d7b22..519b758 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/LoginActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/LoginActivity.kt @@ -3,7 +3,6 @@ package bou.amine.apps.readerforselfossv2.android import android.animation.Animator import android.animation.AnimatorListenerAdapter import android.content.Intent -import android.content.SharedPreferences import android.os.Bundle import androidx.appcompat.app.AlertDialog import androidx.appcompat.app.AppCompatActivity @@ -14,7 +13,6 @@ import android.view.MenuItem import android.view.View import android.view.inputmethod.EditorInfo import android.widget.TextView -import androidx.preference.PreferenceManager import bou.amine.apps.readerforselfossv2.android.databinding.ActivityLoginBinding import bou.amine.apps.readerforselfossv2.android.themes.AppColors import bou.amine.apps.readerforselfossv2.android.utils.isBaseUrlValid @@ -22,6 +20,7 @@ import bou.amine.apps.readerforselfossv2.android.utils.network.isNetworkAvailabl import bou.amine.apps.readerforselfossv2.rest.SelfossApiImpl import bou.amine.apps.readerforselfossv2.service.ApiDetailsService import com.mikepenz.aboutlibraries.LibsBuilder +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -35,8 +34,7 @@ class LoginActivity() : AppCompatActivity(), DIAware { private var isWithLogin = false private var isWithHTTPLogin = false - private lateinit var settings: SharedPreferences - private lateinit var editor: SharedPreferences.Editor + private val settings = Settings() private lateinit var userIdentifier: String private lateinit var appColors: AppColors private lateinit var binding: ActivityLoginBinding @@ -57,12 +55,9 @@ class LoginActivity() : AppCompatActivity(), DIAware { handleBaseUrlFail() - settings = PreferenceManager.getDefaultSharedPreferences(applicationContext) - userIdentifier = settings.getString("unique_id", "")!! + userIdentifier = settings.getString("unique_id", "") - editor = settings.edit() - - if (settings.getString("url", "")!!.isNotEmpty()) { + if (settings.getString("url", "").isNotEmpty()) { goToMain() } @@ -127,12 +122,11 @@ class LoginActivity() : AppCompatActivity(), DIAware { } private fun preferenceError(t: Throwable) { - editor.remove("url") - editor.remove("login") - editor.remove("httpUserName") - editor.remove("password") - editor.remove("httpPassword") - editor.apply() + settings.remove("url") + settings.remove("login") + settings.remove("httpUserName") + settings.remove("password") + settings.remove("httpPassword") binding.urlView.error = getString(R.string.wrong_infos) binding.loginView.error = getString(R.string.wrong_infos) binding.passwordView.error = getString(R.string.wrong_infos) @@ -210,13 +204,12 @@ class LoginActivity() : AppCompatActivity(), DIAware { } else { showProgress(true) - editor.putString("url", url) - editor.putString("login", login) - editor.putString("httpUserName", httpLogin) - editor.putString("password", password) - editor.putString("httpPassword", httpPassword) - editor.putBoolean("isSelfSignedCert", isWithSelfSignedCert) - editor.apply() + settings.putString("url", url) + settings.putString("login", login) + settings.putString("httpUserName", httpLogin) + settings.putString("password", password) + settings.putString("httpPassword", httpPassword) + settings.putBoolean("isSelfSignedCert", isWithSelfSignedCert) apiDetailsService.refresh() val api = SelfossApiImpl( diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/MyApp.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/MyApp.kt index b18a683..65bc23b 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/MyApp.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/MyApp.kt @@ -6,40 +6,38 @@ import android.content.Context import android.graphics.drawable.Drawable import android.net.Uri import android.os.Build -import androidx.preference.PreferenceManager import android.widget.ImageView import androidx.multidex.MultiDexApplication -import bou.amine.apps.readerforselfossv2.android.service.AndroidApiDetailsService +import androidx.preference.PreferenceManager import bou.amine.apps.readerforselfossv2.android.utils.Config import bou.amine.apps.readerforselfossv2.android.utils.glide.loadMaybeBasicAuth import bou.amine.apps.readerforselfossv2.service.ApiDetailsService +import bou.amine.apps.readerforselfossv2.service.ApiDetailsServiceImpl import com.bumptech.glide.Glide import com.bumptech.glide.request.RequestOptions import com.ftinc.scoop.Scoop import com.mikepenz.materialdrawer.util.AbstractDrawerImageLoader import com.mikepenz.materialdrawer.util.DrawerImageLoader +import com.russhwolf.settings.Settings import org.kodein.di.* import java.util.UUID.randomUUID class MyApp : MultiDexApplication(), DIAware { override val di by DI.lazy { - bind() with instance(this@MyApp.applicationContext) - - bind() with singleton { AndroidApiDetailsService(instance()) } + bind() with singleton { ApiDetailsServiceImpl() } } private lateinit var config: Config + private lateinit var settings : Settings override fun onCreate() { super.onCreate() - config = Config(baseContext) + config = Config() + settings = Settings() - val prefs = getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - if (prefs.getString("unique_id", "")!!.isEmpty()) { - val editor = prefs.edit() - editor.putString("unique_id", randomUUID().toString()) - editor.apply() + if (settings.getString("unique_id", "").isEmpty()) { + settings.putString("unique_id", randomUUID().toString()) } initDrawerImageLoader() diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/ReaderActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/ReaderActivity.kt index 2b490d5..2da8e05 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/ReaderActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/ReaderActivity.kt @@ -1,7 +1,5 @@ package bou.amine.apps.readerforselfossv2.android -import android.content.Context -import android.content.SharedPreferences import android.graphics.Color import android.os.Bundle import android.view.KeyEvent @@ -10,7 +8,6 @@ import android.view.MenuItem import androidx.appcompat.app.AppCompatActivity import androidx.fragment.app.Fragment import androidx.fragment.app.FragmentActivity -import androidx.preference.PreferenceManager import androidx.room.Room import androidx.viewpager2.adapter.FragmentStateAdapter import androidx.viewpager2.widget.ViewPager2 @@ -22,12 +19,12 @@ import bou.amine.apps.readerforselfossv2.android.persistence.migrations.MIGRATIO import bou.amine.apps.readerforselfossv2.android.persistence.migrations.MIGRATION_3_4 import bou.amine.apps.readerforselfossv2.android.themes.AppColors import bou.amine.apps.readerforselfossv2.android.themes.Toppings -import bou.amine.apps.readerforselfossv2.android.utils.Config import bou.amine.apps.readerforselfossv2.android.utils.toggleStar import bou.amine.apps.readerforselfossv2.rest.SelfossApiImpl import bou.amine.apps.readerforselfossv2.rest.SelfossModel import bou.amine.apps.readerforselfossv2.service.ApiDetailsService import com.ftinc.scoop.Scoop +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -47,7 +44,6 @@ class ReaderActivity : AppCompatActivity(), DIAware { private lateinit var toolbarMenu: Menu private lateinit var db: AppDatabase - private lateinit var prefs: SharedPreferences private lateinit var binding: ActivityReaderBinding private var activeAlignment: Int = 1 @@ -73,7 +69,7 @@ class ReaderActivity : AppCompatActivity(), DIAware { showMenuItem(false) } - private lateinit var editor: SharedPreferences.Editor + private var settings = Settings() override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) @@ -96,15 +92,9 @@ class ReaderActivity : AppCompatActivity(), DIAware { supportActionBar?.setDisplayHomeAsUpEnabled(true) supportActionBar?.setDisplayShowHomeEnabled(true) - val settings = - getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - - prefs = PreferenceManager.getDefaultSharedPreferences(this) - editor = prefs.edit() - - userIdentifier = prefs.getString("unique_id", "")!! - markOnScroll = prefs.getBoolean("mark_on_scroll", false) - activeAlignment = prefs.getInt("text_align", JUSTIFY) + userIdentifier = settings.getString("unique_id", "") + markOnScroll = settings.getBoolean("mark_on_scroll", false) + activeAlignment = settings.getInt("text_align", JUSTIFY) api = SelfossApiImpl( // this, @@ -246,14 +236,12 @@ class ReaderActivity : AppCompatActivity(), DIAware { } } R.id.align_left -> { - editor.putInt("text_align", ALIGN_LEFT) - editor.apply() + settings.putInt("text_align", ALIGN_LEFT) alignmentMenu(true) refreshFragment() } R.id.align_justify -> { - editor.putInt("text_align", JUSTIFY) - editor.apply() + settings.putInt("text_align", JUSTIFY) alignmentMenu(false) refreshFragment() } diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/SourcesActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/SourcesActivity.kt index e2217ed..22869df 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/SourcesActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/SourcesActivity.kt @@ -1,18 +1,15 @@ package bou.amine.apps.readerforselfossv2.android -import android.content.Context import android.content.Intent import android.content.res.ColorStateList import android.os.Bundle -import androidx.preference.PreferenceManager +import android.widget.Toast import androidx.appcompat.app.AppCompatActivity import androidx.recyclerview.widget.LinearLayoutManager -import android.widget.Toast import bou.amine.apps.readerforselfossv2.android.adapters.SourcesListAdapter import bou.amine.apps.readerforselfossv2.android.databinding.ActivitySourcesBinding import bou.amine.apps.readerforselfossv2.android.themes.AppColors import bou.amine.apps.readerforselfossv2.android.themes.Toppings -import bou.amine.apps.readerforselfossv2.android.utils.Config import bou.amine.apps.readerforselfossv2.android.utils.network.isNetworkAvailable import bou.amine.apps.readerforselfossv2.rest.SelfossApiImpl import bou.amine.apps.readerforselfossv2.rest.SelfossModel @@ -24,7 +21,6 @@ import kotlinx.coroutines.launch import org.kodein.di.DIAware import org.kodein.di.android.closestDI import org.kodein.di.instance -import java.util.ArrayList class SourcesActivity : AppCompatActivity(), DIAware { @@ -64,10 +60,6 @@ class SourcesActivity : AppCompatActivity(), DIAware { super.onResume() val mLayoutManager = LinearLayoutManager(this) - val settings = - getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - val prefs = PreferenceManager.getDefaultSharedPreferences(this) - val api = SelfossApiImpl( // this, // this@SourcesActivity, diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/adapters/SourcesListAdapter.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/adapters/SourcesListAdapter.kt index aaff569..6357863 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/adapters/SourcesListAdapter.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/adapters/SourcesListAdapter.kt @@ -43,7 +43,7 @@ class SourcesListAdapter( override fun onBindViewHolder(holder: ViewHolder, position: Int) { val itm = items[position] - config = Config(c) + config = Config() if (itm.getIcon(apiDetailsService.getBaseUrl()).isEmpty()) { val color = generator.getColor(itm.getTitleDecoded()) diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/background/background.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/background/background.kt index 0b97ffb..ad502e9 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/background/background.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/background/background.kt @@ -5,7 +5,6 @@ import android.app.PendingIntent import android.content.Context import android.content.Intent import android.os.Build -import androidx.preference.PreferenceManager import androidx.core.app.NotificationCompat import androidx.core.app.NotificationCompat.PRIORITY_DEFAULT import androidx.core.app.NotificationCompat.PRIORITY_LOW @@ -32,6 +31,7 @@ import bou.amine.apps.readerforselfossv2.service.ApiDetailsService import bou.amine.apps.readerforselfossv2.service.SearchService import bou.amine.apps.readerforselfossv2.service.SelfossService import bou.amine.apps.readerforselfossv2.utils.DateUtils +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -48,10 +48,8 @@ class LoadingWorker(val context: Context, params: WorkerParameters) : Worker(con private val apiDetailsService : ApiDetailsService by instance() override fun doWork(): Result { - val settings = - this.context.getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - val sharedPref = PreferenceManager.getDefaultSharedPreferences(this.context) - val periodicRefresh = sharedPref.getBoolean("periodic_refresh", false) + val settings = Settings() + val periodicRefresh = settings.getBoolean("periodic_refresh", false) if (periodicRefresh) { val api = SelfossApiImpl( // this.context, @@ -82,7 +80,7 @@ override fun doWork(): Result { notificationManager.notify(1, notification.build()) - val notifyNewItems = sharedPref.getBoolean("notify_new_items", false) + val notifyNewItems = settings.getBoolean("notify_new_items", false) db = Room.databaseBuilder( applicationContext, diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/fragments/ArticleFragment.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/fragments/ArticleFragment.kt index 66f987c..518c59f 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/fragments/ArticleFragment.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/fragments/ArticleFragment.kt @@ -1,8 +1,6 @@ package bou.amine.apps.readerforselfossv2.android.fragments -import android.content.Context import android.content.Intent -import android.content.SharedPreferences import android.content.res.ColorStateList import android.content.res.TypedArray import android.graphics.Bitmap @@ -18,7 +16,6 @@ import androidx.browser.customtabs.CustomTabsIntent import androidx.core.content.res.ResourcesCompat import androidx.core.widget.NestedScrollView import androidx.fragment.app.Fragment -import androidx.preference.PreferenceManager import androidx.room.Room import bou.amine.apps.readerforselfossv2.android.ImageActivity import bou.amine.apps.readerforselfossv2.android.R @@ -51,6 +48,7 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.request.RequestOptions import com.github.rubensousa.floatingtoolbar.FloatingToolbar import com.google.android.material.floatingactionbutton.FloatingActionButton +import com.russhwolf.settings.Settings import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch @@ -76,7 +74,6 @@ class ArticleFragment : Fragment(), DIAware { private lateinit var contentImage: String private lateinit var contentTitle: String private lateinit var allImages : ArrayList - private lateinit var editor: SharedPreferences.Editor private lateinit var fab: FloatingActionButton private lateinit var appColors: AppColors private lateinit var db: AppDatabase @@ -88,7 +85,7 @@ class ArticleFragment : Fragment(), DIAware { override val di : DI by closestDI() private val apiDetailsService : ApiDetailsService by instance() - private lateinit var prefs: SharedPreferences + private var settings = Settings() private var typeface: Typeface? = null private var resId: Int = 0 @@ -104,7 +101,7 @@ class ArticleFragment : Fragment(), DIAware { override fun onCreate(savedInstanceState: Bundle?) { appColors = AppColors(requireActivity()) - config = Config(requireActivity()) + config = Config() super.onCreate(savedInstanceState) @@ -137,12 +134,10 @@ class ArticleFragment : Fragment(), DIAware { contentSource = item.sourceAndDateText(DateUtils(apiDetailsService)) allImages = item.getImages() - prefs = PreferenceManager.getDefaultSharedPreferences(activity) - editor = prefs.edit() - fontSize = prefs.getString("reader_font_size", "16")!!.toInt() - staticBar = prefs.getBoolean("reader_static_bar", false) + fontSize = settings.getString("reader_font_size", "16").toInt() + staticBar = settings.getBoolean("reader_static_bar", false) - font = prefs.getString("reader_font", "")!! + font = settings.getString("reader_font", "") if (font.isNotEmpty()) { resId = requireContext().resources.getIdentifier(font, "font", requireContext().packageName) typeface = try { @@ -156,8 +151,6 @@ class ArticleFragment : Fragment(), DIAware { refreshAlignment() - val settings = requireActivity().getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - val api = SelfossApiImpl( // requireContext(), // requireActivity(), @@ -277,10 +270,7 @@ class ArticleFragment : Fragment(), DIAware { .setTitle(requireContext().getString(R.string.webview_dialog_issue_title)) .setPositiveButton(android.R.string.ok ) { _, _ -> - val sharedPref = PreferenceManager.getDefaultSharedPreferences(requireContext()) - val editor = sharedPref.edit() - editor.putBoolean("prefer_article_viewer", false) - editor.apply() + settings.putBoolean("prefer_article_viewer", false) requireActivity().finish() } .create() @@ -296,7 +286,7 @@ class ArticleFragment : Fragment(), DIAware { } private fun refreshAlignment() { - textAlignment = when (prefs.getInt("text_align", 1)) { + textAlignment = when (settings.getInt("text_align", 1)) { 1 -> "justify" 2 -> "left" else -> "justify" diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/settings/SettingsActivity.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/settings/SettingsActivity.kt index aa708e7..f4382ce 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/settings/SettingsActivity.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/settings/SettingsActivity.kt @@ -17,6 +17,7 @@ import bou.amine.apps.readerforselfossv2.android.databinding.ActivitySettingsBin import bou.amine.apps.readerforselfossv2.android.themes.Toppings import bou.amine.apps.readerforselfossv2.android.utils.Config import com.ftinc.scoop.Scoop +import com.russhwolf.settings.Settings import java.lang.NumberFormatException private const val TITLE_TAG = "settingsActivityTitle" @@ -173,14 +174,12 @@ class SettingsActivity : AppCompatActivity(), override fun onOptionsItemSelected(item: MenuItem): Boolean { val id = item.itemId if (id == R.id.clear) { - val pref = PreferenceManager.getDefaultSharedPreferences(activity) - val editor = pref.edit() - editor.remove("color_primary") - editor.remove("color_primary_dark") - editor.remove("color_accent") - editor.remove("color_accent_dark") - editor.remove("dark_theme") - editor.apply() + val settings = Settings() + settings.remove("color_primary") + settings.remove("color_primary_dark") + settings.remove("color_accent") + settings.remove("color_accent_dark") + settings.remove("dark_theme") requireActivity().recreate() } return super.onOptionsItemSelected(item) diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/themes/AppColors.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/themes/AppColors.kt index 321c400..9c10e52 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/themes/AppColors.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/themes/AppColors.kt @@ -2,8 +2,8 @@ package bou.amine.apps.readerforselfossv2.android.themes import android.app.Activity import androidx.annotation.ColorInt -import androidx.preference.PreferenceManager import bou.amine.apps.readerforselfossv2.android.R +import com.russhwolf.settings.Settings class AppColors(a: Activity) { @@ -16,30 +16,30 @@ class AppColors(a: Activity) { val isDarkTheme: Boolean init { - val sharedPref = PreferenceManager.getDefaultSharedPreferences(a) + val settings = Settings() colorPrimary = - sharedPref.getInt( + settings.getInt( "color_primary", a.resources.getColor(R.color.colorPrimary) ) colorPrimaryDark = - sharedPref.getInt( + settings.getInt( "color_primary_dark", a.resources.getColor(R.color.colorPrimaryDark) ) colorAccent = - sharedPref.getInt( + settings.getInt( "color_accent", a.resources.getColor(R.color.colorAccent) ) colorAccentDark = - sharedPref.getInt( + settings.getInt( "color_accent_dark", a.resources.getColor(R.color.colorAccentDark) ) isDarkTheme = - sharedPref.getBoolean( + settings.getBoolean( "dark_theme", false ) diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/Config.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/Config.kt index 849c261..ba81e76 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/Config.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/Config.kt @@ -3,28 +3,27 @@ package bou.amine.apps.readerforselfossv2.android.utils import android.app.Activity import android.content.Context import android.content.Intent -import android.content.SharedPreferences -import androidx.preference.PreferenceManager import bou.amine.apps.readerforselfossv2.android.LoginActivity +import com.russhwolf.settings.Settings -class Config(c: Context) { +class Config { - val settings: SharedPreferences = PreferenceManager.getDefaultSharedPreferences(c) + val settings = Settings() val baseUrl: String - get() = settings.getString("url", "")!! + get() = settings.getString("url", "") val userLogin: String - get() = settings.getString("login", "")!! + get() = settings.getString("login", "") val userPassword: String - get() = settings.getString("password", "")!! + get() = settings.getString("password", "") val httpUserLogin: String - get() = settings.getString("httpUserName", "")!! + get() = settings.getString("httpUserName", "") val httpUserPassword: String - get() = settings.getString("httpPassword", "")!! + get() = settings.getString("httpPassword", "") companion object { const val settingsName = "paramsselfoss" @@ -47,11 +46,10 @@ class Config(c: Context) { fun logoutAndRedirect( c: Context, callingActivity: Activity, - editor: SharedPreferences.Editor, baseUrlFail: Boolean = false ): Boolean { - val settings = PreferenceManager.getDefaultSharedPreferences(c) - settings.edit().clear().commit() + val settings = Settings() + settings.clear() val intent = Intent(c, LoginActivity::class.java) if (baseUrlFail) { intent.putExtra("baseUrlFail", baseUrlFail) diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/glide/SelfSignedGlideModule.kt b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/glide/SelfSignedGlideModule.kt index 8449013..999a130 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/glide/SelfSignedGlideModule.kt +++ b/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/utils/glide/SelfSignedGlideModule.kt @@ -1,13 +1,13 @@ package bou.amine.apps.readerforselfossv2.android.utils.glide import android.content.Context -import bou.amine.apps.readerforselfossv2.android.utils.Config import bou.amine.apps.readerforselfossv2.android.utils.getUnsafeHttpClient import com.bumptech.glide.Glide import com.bumptech.glide.GlideBuilder import com.bumptech.glide.Registry import com.bumptech.glide.load.model.GlideUrl import com.bumptech.glide.module.GlideModule +import com.russhwolf.settings.Settings import java.io.InputStream class SelfSignedGlideModule : GlideModule { @@ -18,8 +18,8 @@ class SelfSignedGlideModule : GlideModule { override fun registerComponents(context: Context?, glide: Glide?, registry: Registry?) { if (context != null) { - val pref = context?.getSharedPreferences(Config.settingsName, Context.MODE_PRIVATE) - if (pref.getBoolean("isSelfSignedCert", false)) { + val settings = Settings() + if (settings.getBoolean("isSelfSignedCert", false)) { val client = getUnsafeHttpClient().build() registry?.append( diff --git a/shared/build.gradle.kts b/shared/build.gradle.kts index 4eaed04..d5062d4 100644 --- a/shared/build.gradle.kts +++ b/shared/build.gradle.kts @@ -30,6 +30,12 @@ kotlin { //Dependency Injection implementation("org.kodein.di:kodein-di:7.12.0") + + //Settings + implementation("com.russhwolf:multiplatform-settings-no-arg:0.9") + + //Logging + implementation("io.github.aakira:napier:2.6.1") } } val commonTest by getting { diff --git a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/service/AndroidApiDetailsService.kt b/shared/src/commonMain/kotlin/bou/amine/apps/readerforselfossv2/service/ApiDetailsServiceImpl.kt similarity index 50% rename from androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/service/AndroidApiDetailsService.kt rename to shared/src/commonMain/kotlin/bou/amine/apps/readerforselfossv2/service/ApiDetailsServiceImpl.kt index 8e64e10..a09a8dc 100644 --- a/androidApp/src/main/java/bou/amine/apps/readerforselfossv2/android/service/AndroidApiDetailsService.kt +++ b/shared/src/commonMain/kotlin/bou/amine/apps/readerforselfossv2/service/ApiDetailsServiceImpl.kt @@ -1,19 +1,16 @@ -package bou.amine.apps.readerforselfossv2.android.service +package bou.amine.apps.readerforselfossv2.service -import android.content.Context -import android.content.SharedPreferences -import android.util.Log -import androidx.preference.PreferenceManager -import bou.amine.apps.readerforselfossv2.service.ApiDetailsService +import com.russhwolf.settings.Settings +import io.github.aakira.napier.Napier -class AndroidApiDetailsService(c: Context) : ApiDetailsService { - val settings: SharedPreferences = PreferenceManager.getDefaultSharedPreferences(c) +class ApiDetailsServiceImpl : ApiDetailsService { + val settings: Settings = Settings() private var _apiVersion: Int = -1 private var _baseUrl: String = "" private var _userName: String = "" private var _password: String = "" override fun logApiCalls(message: String) { - Log.d("LogApiCalls", message) + Napier.d(message, tag = "LogApiCalls") } @@ -27,30 +24,30 @@ class AndroidApiDetailsService(c: Context) : ApiDetailsService { override fun getBaseUrl(): String { if (_baseUrl.isEmpty()) { - _baseUrl = settings.getString("url", "")!! + _baseUrl = settings.getString("url", "") } return _baseUrl } override fun getUserName(): String { if (_userName.isEmpty()) { - _userName = settings.getString("login", "")!! + _userName = settings.getString("login", "") } return _userName } override fun getPassword(): String { if (_password.isEmpty()) { - _password = settings.getString("password", "")!! + _password = settings.getString("password", "") } return _password } override fun refresh() { - _password = settings.getString("password", "")!! - _userName = settings.getString("login", "")!! - _baseUrl = settings.getString("url", "")!! - _baseUrl = settings.getString("url", "")!! + _password = settings.getString("password", "") + _userName = settings.getString("login", "") + _baseUrl = settings.getString("url", "") + _baseUrl = settings.getString("url", "") _apiVersion = settings.getInt("apiVersionMajor", -1) } } \ No newline at end of file