music: add separator setting dialog
Add a dialog for the new separators setting.
This commit is contained in:
parent
cdd4d5ebcd
commit
780e0dce06
12 changed files with 199 additions and 19 deletions
|
@ -30,7 +30,6 @@ import org.oxycblt.auxio.music.ui.MusicMode
|
|||
import org.oxycblt.auxio.music.ui.Sort
|
||||
import org.oxycblt.auxio.ui.recycler.Item
|
||||
import org.oxycblt.auxio.util.inRangeOrNull
|
||||
import org.oxycblt.auxio.util.logD
|
||||
import org.oxycblt.auxio.util.nonZeroOrNull
|
||||
import org.oxycblt.auxio.util.unlikelyToBeNull
|
||||
import java.security.MessageDigest
|
||||
|
@ -95,6 +94,11 @@ sealed class Music : Item {
|
|||
* external sources, as it can persist across app restarts and does not need to encode useless
|
||||
* information about the relationships between items.
|
||||
*
|
||||
* Note: While the core of a UID is a UUID. The whole is not technically a UUID, with
|
||||
* string representation in particular having multiple extensions to increase uniqueness.
|
||||
* Please don't try to do anything interesting with this and just assume it's a black box
|
||||
* that can only be compared, serialized, and deserialized.
|
||||
*
|
||||
* TODO: MusicBrainz tags
|
||||
*
|
||||
* @author OxygenCobalt
|
||||
|
@ -113,8 +117,6 @@ sealed class Music : Item {
|
|||
result = 31 * result + mode.hashCode()
|
||||
result = 31 * result + uuid.hashCode()
|
||||
hashCode = result
|
||||
|
||||
logD(this)
|
||||
}
|
||||
|
||||
override fun hashCode() = hashCode
|
||||
|
@ -131,8 +133,8 @@ sealed class Music : Item {
|
|||
FORMAT_AUXIO
|
||||
}
|
||||
|
||||
// Instead of making new string values for the mode, just append it's intCode
|
||||
// in front of the UUID. So I guess it's technically not a true UUID, but whatever.
|
||||
// Instead of making new string values for the mode, be lazy and just append it's
|
||||
// intCode in front of the UUID.
|
||||
return "$format:${mode.intCode.toString(16)}-$uuid"
|
||||
}
|
||||
|
||||
|
|
|
@ -24,6 +24,9 @@ class CacheLayer {
|
|||
fun init() {
|
||||
}
|
||||
|
||||
// FIXME: Make the raw datatype use raw values, with most parsing being done in the song
|
||||
// constructor to ensure cache coherency
|
||||
|
||||
/**
|
||||
* Write a list of newly-indexed raw songs to the database.
|
||||
*/
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package org.oxycblt.auxio.music.dirs
|
||||
package org.oxycblt.auxio.music.settings
|
||||
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
|
@ -15,7 +15,7 @@
|
|||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package org.oxycblt.auxio.music.dirs
|
||||
package org.oxycblt.auxio.music.settings
|
||||
|
||||
import org.oxycblt.auxio.music.Directory
|
||||
|
|
@ -15,7 +15,7 @@
|
|||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package org.oxycblt.auxio.music.dirs
|
||||
package org.oxycblt.auxio.music.settings
|
||||
|
||||
import android.net.Uri
|
||||
import android.os.Bundle
|
|
@ -0,0 +1,80 @@
|
|||
/*
|
||||
* Copyright (c) 2022 Auxio Project
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package org.oxycblt.auxio.music.settings
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.core.view.children
|
||||
import com.google.android.material.checkbox.MaterialCheckBox
|
||||
import org.oxycblt.auxio.BuildConfig
|
||||
import org.oxycblt.auxio.R
|
||||
import org.oxycblt.auxio.databinding.DialogSeparatorsBinding
|
||||
import org.oxycblt.auxio.settings.Settings
|
||||
import org.oxycblt.auxio.ui.fragment.ViewBindingDialogFragment
|
||||
import org.oxycblt.auxio.util.context
|
||||
|
||||
class SeparatorsDialog : ViewBindingDialogFragment<DialogSeparatorsBinding>() {
|
||||
private val settings: Settings by lifecycleObject { binding -> Settings(binding.context) }
|
||||
|
||||
override fun onCreateBinding(inflater: LayoutInflater) =
|
||||
DialogSeparatorsBinding.inflate(inflater)
|
||||
|
||||
override fun onConfigDialog(builder: AlertDialog.Builder) {
|
||||
builder
|
||||
.setTitle(R.string.set_separators)
|
||||
.setNegativeButton(R.string.lbl_cancel, null)
|
||||
.setPositiveButton(R.string.lbl_save) { _, _ ->
|
||||
var separators = ""
|
||||
val binding = requireBinding()
|
||||
if (binding.separatorComma.isChecked) separators += SEPARATOR_COMMA
|
||||
if (binding.separatorSemicolon.isChecked) separators += SEPARATOR_SEMICOLON
|
||||
if (binding.separatorSlash.isChecked) separators += SEPARATOR_SLASH
|
||||
if (binding.separatorPlus.isChecked) separators += SEPARATOR_PLUS
|
||||
if (binding.separatorAnd.isChecked) separators += SEPARATOR_AND
|
||||
settings.separators = separators
|
||||
}
|
||||
}
|
||||
|
||||
override fun onBindingCreated(binding: DialogSeparatorsBinding, savedInstanceState: Bundle?) {
|
||||
for (child in binding.separatorGroup.children) {
|
||||
(child as MaterialCheckBox).isChecked = false
|
||||
}
|
||||
|
||||
settings.separators?.forEach {
|
||||
when (it) {
|
||||
SEPARATOR_COMMA -> binding.separatorComma.isChecked = true
|
||||
SEPARATOR_SEMICOLON -> binding.separatorSemicolon.isChecked = true
|
||||
SEPARATOR_SLASH -> binding.separatorSlash.isChecked = true
|
||||
SEPARATOR_PLUS -> binding.separatorPlus.isChecked = true
|
||||
SEPARATOR_AND -> binding.separatorAnd.isChecked = true
|
||||
else -> error("Unexpected separator in settings data")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
const val TAG = BuildConfig.APPLICATION_ID + ".tag.EXCLUDED"
|
||||
|
||||
private const val SEPARATOR_COMMA = ','
|
||||
private const val SEPARATOR_SEMICOLON = ';'
|
||||
private const val SEPARATOR_SLASH = '/'
|
||||
private const val SEPARATOR_PLUS = '+'
|
||||
private const val SEPARATOR_AND = '&'
|
||||
}
|
||||
}
|
|
@ -226,7 +226,8 @@ class IndexerService : Service(), Indexer.Controller, Settings.Callback {
|
|||
override fun onSettingChanged(key: String) {
|
||||
when (key) {
|
||||
getString(R.string.set_key_music_dirs),
|
||||
getString(R.string.set_key_music_dirs_include) -> onStartIndexing()
|
||||
getString(R.string.set_key_music_dirs_include),
|
||||
getString(R.string.set_key_separators) -> onStartIndexing()
|
||||
getString(R.string.set_key_observing) -> {
|
||||
if (!indexer.isIndexing) {
|
||||
updateIdleSession()
|
||||
|
|
|
@ -28,7 +28,7 @@ import org.oxycblt.auxio.IntegerTable
|
|||
import org.oxycblt.auxio.R
|
||||
import org.oxycblt.auxio.home.tabs.Tab
|
||||
import org.oxycblt.auxio.music.Directory
|
||||
import org.oxycblt.auxio.music.dirs.MusicDirs
|
||||
import org.oxycblt.auxio.music.settings.MusicDirs
|
||||
import org.oxycblt.auxio.music.ui.MusicMode
|
||||
import org.oxycblt.auxio.music.ui.Sort
|
||||
import org.oxycblt.auxio.playback.BarAction
|
||||
|
@ -301,7 +301,7 @@ class Settings(private val context: Context, private val callback: Callback? = n
|
|||
inner.getString(context.getString(R.string.set_key_separators), null)?.ifEmpty { null }
|
||||
set(value) {
|
||||
inner.edit {
|
||||
putString(context.getString(R.string.set_key_separators), value)
|
||||
putString(context.getString(R.string.set_key_separators), value?.ifEmpty { null })
|
||||
apply()
|
||||
}
|
||||
}
|
||||
|
|
|
@ -32,7 +32,8 @@ import coil.Coil
|
|||
import org.oxycblt.auxio.R
|
||||
import org.oxycblt.auxio.home.tabs.TabCustomizeDialog
|
||||
import org.oxycblt.auxio.music.MusicViewModel
|
||||
import org.oxycblt.auxio.music.dirs.MusicDirsDialog
|
||||
import org.oxycblt.auxio.music.settings.MusicDirsDialog
|
||||
import org.oxycblt.auxio.music.settings.SeparatorsDialog
|
||||
import org.oxycblt.auxio.playback.PlaybackViewModel
|
||||
import org.oxycblt.auxio.playback.replaygain.PreAmpCustomizeDialog
|
||||
import org.oxycblt.auxio.settings.ui.IntListPreference
|
||||
|
@ -107,6 +108,8 @@ class SettingsListFragment : PreferenceFragmentCompat() {
|
|||
.show(childFragmentManager, PreAmpCustomizeDialog.TAG)
|
||||
context.getString(R.string.set_key_music_dirs) ->
|
||||
MusicDirsDialog().show(childFragmentManager, MusicDirsDialog.TAG)
|
||||
getString(R.string.set_key_separators) ->
|
||||
SeparatorsDialog().show(childFragmentManager, SeparatorsDialog.TAG)
|
||||
else -> error("Unexpected dialog key ${preference.key}")
|
||||
}
|
||||
}
|
||||
|
|
79
app/src/main/res/layout/dialog_separators.xml
Normal file
79
app/src/main/res/layout/dialog_separators.xml
Normal file
|
@ -0,0 +1,79 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.core.widget.NestedScrollView xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
style="@style/Widget.Auxio.Dialog.NestedScrollView"
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/separator_group"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical">
|
||||
|
||||
<com.google.android.material.checkbox.MaterialCheckBox
|
||||
android:id="@+id/separator_comma"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_medium"
|
||||
android:layout_marginEnd="@dimen/spacing_medium"
|
||||
android:paddingStart="@dimen/spacing_medium"
|
||||
android:textAlignment="viewStart"
|
||||
android:text="@string/set_separators_comma"
|
||||
android:textAppearance="@style/TextAppearance.Auxio.BodyLarge"
|
||||
tools:ignore="RtlSymmetry" />
|
||||
|
||||
<com.google.android.material.checkbox.MaterialCheckBox
|
||||
android:id="@+id/separator_semicolon"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_medium"
|
||||
android:layout_marginEnd="@dimen/spacing_medium"
|
||||
android:paddingStart="@dimen/spacing_medium"
|
||||
android:textAlignment="viewStart"
|
||||
android:text="@string/set_separators_and"
|
||||
android:textAppearance="@style/TextAppearance.Auxio.BodyLarge"
|
||||
tools:ignore="RtlSymmetry" />
|
||||
|
||||
<com.google.android.material.checkbox.MaterialCheckBox
|
||||
android:id="@+id/separator_slash"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_medium"
|
||||
android:layout_marginEnd="@dimen/spacing_medium"
|
||||
android:paddingStart="@dimen/spacing_medium"
|
||||
android:textAlignment="viewStart"
|
||||
android:text="@string/set_separators_slash"
|
||||
android:textAppearance="@style/TextAppearance.Auxio.BodyLarge"
|
||||
tools:ignore="RtlSymmetry" />
|
||||
|
||||
<com.google.android.material.checkbox.MaterialCheckBox
|
||||
android:id="@+id/separator_plus"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_medium"
|
||||
android:layout_marginEnd="@dimen/spacing_medium"
|
||||
android:paddingStart="@dimen/spacing_medium"
|
||||
android:textAlignment="viewStart"
|
||||
android:text="@string/set_separators_plus"
|
||||
android:textAppearance="@style/TextAppearance.Auxio.BodyLarge"
|
||||
tools:ignore="RtlSymmetry" />
|
||||
|
||||
<com.google.android.material.checkbox.MaterialCheckBox
|
||||
android:id="@+id/separator_and"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_medium"
|
||||
android:layout_marginEnd="@dimen/spacing_medium"
|
||||
android:paddingStart="@dimen/spacing_medium"
|
||||
android:textAlignment="viewStart"
|
||||
android:text="@string/set_separators_and"
|
||||
android:textAppearance="@style/TextAppearance.Auxio.BodyLarge"
|
||||
tools:ignore="RtlSymmetry" />
|
||||
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
|
||||
</androidx.core.widget.NestedScrollView>
|
|
@ -214,6 +214,8 @@
|
|||
<string name="set_content">Content</string>
|
||||
<string name="set_reindex">Reload music</string>
|
||||
<string name="set_reindex_desc">May wipe playback state</string>
|
||||
<string name="set_observing">Automatic reloading</string>
|
||||
<string name="set_observing_desc">Reload your music library whenever it changes (Experimental)</string>
|
||||
<string name="set_dirs">Music folders</string>
|
||||
<string name="set_dirs_desc">Manage where music should be loaded from</string>
|
||||
<!-- As in the mode to be used with the music folders setting -->
|
||||
|
@ -224,8 +226,13 @@
|
|||
<!-- Restrict music loading to selected folders -->
|
||||
<string name="set_dirs_mode_include">Include</string>
|
||||
<string name="set_dirs_mode_include_desc">Music will <b>only</b> be loaded from the folders you add.</string>
|
||||
<string name="set_observing">Automatic reloading</string>
|
||||
<string name="set_observing_desc">Reload your music library whenever it changes (Experimental)</string>
|
||||
<string name="set_separators">Multi-value separators</string>
|
||||
<string name="set_separators_desc">Configure the characters that denote multiple values in tags</string>
|
||||
<string name="set_separators_comma">Comma (,)</string>
|
||||
<string name="set_separators_semicolon">Semicolon (;)</string>
|
||||
<string name="set_separators_slash">Slash (/)</string>
|
||||
<string name="set_separators_plus">Plus (+)</string>
|
||||
<string name="set_separators_and">Ampersand (&)</string>
|
||||
|
||||
<!-- Error Namespace | Error Labels -->
|
||||
<string name="err_no_music">No music found</string>
|
||||
|
|
|
@ -148,16 +148,21 @@
|
|||
app:summary="@string/set_reindex_desc"
|
||||
app:title="@string/set_reindex" />
|
||||
|
||||
<org.oxycblt.auxio.settings.ui.WrappedDialogPreference
|
||||
app:key="@string/set_key_music_dirs"
|
||||
app:summary="@string/set_dirs_desc"
|
||||
app:title="@string/set_dirs" />
|
||||
|
||||
<SwitchPreferenceCompat
|
||||
app:defaultValue="false"
|
||||
app:key="@string/set_key_observing"
|
||||
app:summary="@string/set_observing_desc"
|
||||
app:title="@string/set_observing" />
|
||||
|
||||
<org.oxycblt.auxio.settings.ui.WrappedDialogPreference
|
||||
app:key="@string/set_key_music_dirs"
|
||||
app:summary="@string/set_dirs_desc"
|
||||
app:title="@string/set_dirs" />
|
||||
|
||||
<org.oxycblt.auxio.settings.ui.WrappedDialogPreference
|
||||
app:key="@string/set_key_separators"
|
||||
app:summary="@string/set_separators_desc"
|
||||
app:title="@string/set_separators" />
|
||||
|
||||
</PreferenceCategory>
|
||||
</PreferenceScreen>
|
Loading…
Reference in a new issue