Add library sort mode preference

Save the library sort mode to a SharedPreferences object, soon to be extended with other prefs.
This commit is contained in:
OxygenCobalt 2020-11-27 20:11:24 -07:00
parent 6a5084beb1
commit 76c1fe1d75
6 changed files with 128 additions and 8 deletions

View file

@ -5,8 +5,8 @@ import android.content.Intent
import android.util.AttributeSet import android.util.AttributeSet
import android.view.View import android.view.View
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.app.AppCompatDelegate
import org.oxycblt.auxio.playback.PlaybackService import org.oxycblt.auxio.playback.PlaybackService
import org.oxycblt.auxio.prefs.PrefsManager
import org.oxycblt.auxio.ui.accent import org.oxycblt.auxio.ui.accent
// FIXME: Fix bug where fast navigation will break the animations and // FIXME: Fix bug where fast navigation will break the animations and
@ -16,7 +16,8 @@ import org.oxycblt.auxio.ui.accent
class MainActivity : AppCompatActivity(R.layout.activity_main) { class MainActivity : AppCompatActivity(R.layout.activity_main) {
override fun onCreateView(name: String, context: Context, attrs: AttributeSet): View? { override fun onCreateView(name: String, context: Context, attrs: AttributeSet): View? {
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES) val prefsManager = PrefsManager.init(this)
// Apply the theme // Apply the theme
setTheme(accent.second) setTheme(accent.second)

View file

@ -6,11 +6,14 @@ import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.ViewModel import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import org.oxycblt.auxio.R import org.oxycblt.auxio.R
import org.oxycblt.auxio.music.BaseModel import org.oxycblt.auxio.music.BaseModel
import org.oxycblt.auxio.music.Header import org.oxycblt.auxio.music.Header
import org.oxycblt.auxio.music.MusicStore import org.oxycblt.auxio.music.MusicStore
import org.oxycblt.auxio.prefs.PrefsManager
import org.oxycblt.auxio.recycler.ShowMode import org.oxycblt.auxio.recycler.ShowMode
import org.oxycblt.auxio.recycler.SortMode import org.oxycblt.auxio.recycler.SortMode
@ -36,6 +39,16 @@ class LibraryViewModel : ViewModel() {
private var mSearchHasFocus = false private var mSearchHasFocus = false
val searchHasFocus: Boolean get() = mSearchHasFocus val searchHasFocus: Boolean get() = mSearchHasFocus
init {
val prefsManager = PrefsManager.getInstance()
viewModelScope.launch {
mSortMode.value = withContext(Dispatchers.IO) {
prefsManager.getLibrarySortMode()
}
}
}
/** /**
* Perform a search of the music library, given a query. * Perform a search of the music library, given a query.
* Results are pushed to [searchResults]. * Results are pushed to [searchResults].
@ -119,6 +132,14 @@ class LibraryViewModel : ViewModel() {
if (mode != mSortMode.value) { if (mode != mSortMode.value) {
mSortMode.value = mode mSortMode.value = mode
viewModelScope.launch {
withContext(Dispatchers.IO) {
val prefsManager = PrefsManager.getInstance()
prefsManager.setLibrarySortMode(mSortMode.value!!)
}
}
} }
} }
} }

View file

@ -271,6 +271,7 @@ class PlaybackStateManager private constructor() {
/** /**
* Go to the previous song, doing any checks that are needed. * Go to the previous song, doing any checks that are needed.
* TODO: Implement option to rewind before skipping back
*/ */
fun prev() { fun prev() {
if (mIndex > 0 && !mIsInUserQueue) { if (mIndex > 0 && !mIsInUserQueue) {

View file

@ -0,0 +1,71 @@
package org.oxycblt.auxio.prefs
import android.content.Context
import android.content.SharedPreferences
import org.oxycblt.auxio.recycler.SortMode
/**
* Wrapper around the [SharedPreferences] class that writes & reads values.
* Please run any getter/setter in a coroutine. Its not required, but it prevents slowdowns
* on older devices.
* @author OxygenCobalt
*/
class PrefsManager private constructor(context: Context) {
private val sharedPrefs = context.getSharedPreferences(
"auxio_prefs", Context.MODE_PRIVATE
)
private lateinit var mLibrarySortMode: SortMode
fun setLibrarySortMode(sortMode: SortMode) {
mLibrarySortMode = sortMode
sharedPrefs.edit()
.putInt(Keys.KEY_LIBRARY_SORT_MODE, sortMode.toConstant())
.apply()
}
fun getLibrarySortMode(): SortMode {
if (!::mLibrarySortMode.isInitialized) {
mLibrarySortMode = SortMode.fromConstant(
sharedPrefs.getInt(
Keys.KEY_LIBRARY_SORT_MODE,
SortMode.CONSTANT_ALPHA_DOWN
)
) ?: SortMode.ALPHA_DOWN
}
return mLibrarySortMode
}
companion object {
@Volatile
private lateinit var INSTANCE: PrefsManager
/**
* Init the single instance of [PrefsManager]. Done so that every object
* can have access to it regardless of if it has a context.
*/
fun init(context: Context): PrefsManager {
synchronized(this) {
INSTANCE = PrefsManager(context)
return getInstance()
}
}
/**
* Get the single instance of [PrefsManager].
*/
fun getInstance(): PrefsManager {
check(::INSTANCE.isInitialized) {
"PrefsManager must be initialized with init() before getting its instance."
}
return INSTANCE
}
}
object Keys {
const val KEY_LIBRARY_SORT_MODE = "KEY_LIBRARY_SORT_MODE"
}
}

View file

@ -36,11 +36,7 @@ class NoLeakThumbView @JvmOverloads constructor(
context: Context, context: Context,
attrs: AttributeSet? = null, attrs: AttributeSet? = null,
defStyleAttr: Int = R.attr.indicatorFastScrollerThumbStyle defStyleAttr: Int = R.attr.indicatorFastScrollerThumbStyle
) : ConstraintLayout( ) : ConstraintLayout(context, attrs, defStyleAttr),
context,
attrs,
defStyleAttr
),
FastScrollerView.ItemIndicatorSelectedCallback { FastScrollerView.ItemIndicatorSelectedCallback {
private var thumbColor = ColorStateList.valueOf(accent.first.toColor(context)) private var thumbColor = ColorStateList.valueOf(accent.first.toColor(context))
@ -98,7 +94,7 @@ class NoLeakThumbView @JvmOverloads constructor(
/** /**
* Hack so that I can detect when the pointer is off the FastScrollerView's items * Hack so that I can detect when the pointer is off the FastScrollerView's items
* without using onItemIndicatorTouched [Which is internal] * without using onItemIndicatorTouched (Which is internal)
* @author OxygenCobalt * @author OxygenCobalt
*/ */
private fun isPointerOnItem(fastScrollerView: FastScrollerView, touchY: Int): Boolean { private fun isPointerOnItem(fastScrollerView: FastScrollerView, touchY: Int): Boolean {

View file

@ -94,4 +94,34 @@ enum class SortMode(val iconRes: Int) {
else -> R.id.option_sort_none else -> R.id.option_sort_none
} }
} }
fun toConstant(): Int {
return when (this) {
NONE -> CONSTANT_NONE
ALPHA_UP -> CONSTANT_ALPHA_UP
ALPHA_DOWN -> CONSTANT_ALPHA_DOWN
NUMERIC_UP -> CONSTANT_NUMERIC_UP
NUMERIC_DOWN -> CONSTANT_NUMERIC_DOWN
}
}
companion object {
const val CONSTANT_NONE = 0xA060
const val CONSTANT_ALPHA_UP = 0xA061
const val CONSTANT_ALPHA_DOWN = 0xA062
const val CONSTANT_NUMERIC_UP = 0xA063
const val CONSTANT_NUMERIC_DOWN = 0xA065
fun fromConstant(constant: Int): SortMode? {
return when (constant) {
CONSTANT_NONE -> NONE
CONSTANT_ALPHA_UP -> ALPHA_UP
CONSTANT_ALPHA_DOWN -> ALPHA_DOWN
CONSTANT_NUMERIC_UP -> NUMERIC_UP
CONSTANT_NUMERIC_DOWN -> NUMERIC_DOWN
else -> null
}
}
}
} }