From e914da4bd15790edeabd82151ae8574180bf1e23 Mon Sep 17 00:00:00 2001 From: OxygenCobalt Date: Mon, 13 Jun 2022 09:41:52 -0600 Subject: [PATCH] music: default to codecs in format Only show codecs in the "format" field, if we are able to extract them. This is primarily for consistency, as there is no way for us to determine the container format outside of an extension (which could not be sane). --- app/src/main/AndroidManifest.xml | 7 ++ .../org/oxycblt/auxio/home/HomeFragment.kt | 4 +- .../auxio/music/FileSystemFramework.kt | 82 ++++++++++++------- .../java/org/oxycblt/auxio/music/Indexer.kt | 6 +- .../org/oxycblt/auxio/music/IndexerService.kt | 5 +- .../playback/system/MediaButtonReceiver.kt | 3 +- app/src/main/res/values/donottranslate.xml | 4 +- app/src/main/res/values/strings.xml | 2 + 8 files changed, 76 insertions(+), 37 deletions(-) diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 2e189db2d..8b0313ec5 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -14,6 +14,8 @@ + + + + + diff --git a/app/src/main/java/org/oxycblt/auxio/home/HomeFragment.kt b/app/src/main/java/org/oxycblt/auxio/home/HomeFragment.kt index 70e9e7dae..9035c5d7c 100644 --- a/app/src/main/java/org/oxycblt/auxio/home/HomeFragment.kt +++ b/app/src/main/java/org/oxycblt/auxio/home/HomeFragment.kt @@ -34,7 +34,6 @@ import androidx.navigation.fragment.findNavController import androidx.recyclerview.widget.RecyclerView import androidx.viewpager2.adapter.FragmentStateAdapter import androidx.viewpager2.widget.ViewPager2 -import com.google.android.material.appbar.AppBarLayout import com.google.android.material.tabs.TabLayoutMediator import kotlin.math.abs import org.oxycblt.auxio.R @@ -95,8 +94,7 @@ class HomeFragment : ViewBindingFragment(), Toolbar.OnMenuI binding.homeToolbar.alpha = 1f - (abs(offset.toFloat()) / (range.toFloat() / 2)) binding.homeContent.updatePadding( - bottom = binding.homeAppbar.totalScrollRange + offset - ) + bottom = binding.homeAppbar.totalScrollRange + offset) } } diff --git a/app/src/main/java/org/oxycblt/auxio/music/FileSystemFramework.kt b/app/src/main/java/org/oxycblt/auxio/music/FileSystemFramework.kt index 45fb81e8d..3381e420f 100644 --- a/app/src/main/java/org/oxycblt/auxio/music/FileSystemFramework.kt +++ b/app/src/main/java/org/oxycblt/auxio/music/FileSystemFramework.kt @@ -75,37 +75,61 @@ sealed class Dir { */ data class MimeType(val fromExtension: String, val fromFormat: String?) { fun resolveName(context: Context): String { - // While it would be nice to have more refined mime type names (Layer I/II/III, containers, - // etc.), it's not exactly practical with ExoPlayer. So, we go for the next best thing - // and try to find a good enough readable name to use. - val readableStringRes = - if (fromFormat != null && fromFormat != MimeTypes.AUDIO_RAW) { - // Prefer the extracted mime type, as it properly handles container formats and - // is agnostic to the file extension - when (fromFormat) { - MimeTypes.AUDIO_MPEG, - MimeTypes.AUDIO_MPEG_L1, - MimeTypes.AUDIO_MPEG_L2 -> R.string.cdc_mp3 - MimeTypes.AUDIO_AAC -> R.string.cdc_mp4 - MimeTypes.AUDIO_VORBIS -> R.string.cdc_ogg_vorbis - MimeTypes.AUDIO_OPUS -> R.string.cdc_ogg_opus - MimeTypes.AUDIO_WAV -> R.string.cdc_wav - else -> -1 - } - } else { - // Fall back to the file extension in the case that we have a useless - when (fromExtension) { - "audio/mpeg" -> R.string.cdc_mp3 - "audio/mp4" -> R.string.cdc_mp4 - "audio/ogg" -> R.string.cdc_ogg - "audio/x-wav" -> R.string.cdc_wav - "audio/x-matroska" -> R.string.cdc_mka - else -> -1 - } + // We try our best to produce a more readable name for the common audio formats. + val formatName = + when (fromFormat) { + // We start with the extracted mime types, as they are more consistent. Note that + // we do not include container formats at all with these names. It is only the + // inner codec that we show. + MimeTypes.AUDIO_MPEG, + MimeTypes.AUDIO_MPEG_L1, + MimeTypes.AUDIO_MPEG_L2 -> R.string.cdc_mp3 + MimeTypes.AUDIO_AAC -> R.string.cdc_aac + MimeTypes.AUDIO_VORBIS -> R.string.cdc_vorbis + MimeTypes.AUDIO_OPUS -> R.string.cdc_opus + MimeTypes.AUDIO_FLAC -> R.string.cdc_flac + MimeTypes.AUDIO_WAV -> R.string.cdc_wav + + // We don't give a name to more unpopular formats. + + else -> -1 } - return if (readableStringRes > -1) { - context.getString(readableStringRes) + if (formatName > -1) { + return context.getString(formatName) + } + + // Fall back to the file extension in the case that we have no mime type or + // a useless "audio/raw" mime type. Here: + // - We return names for container formats instead of the inner format, as we + // cannot parse the file. + // - We are at the mercy of the Android OS, hence we check for every possible mime + // type for a particular format. + val extensionName = + when (fromExtension) { + "audio/mpeg", + "audio/mp3" -> R.string.cdc_mp3 + "audio/mp4", + "audio/mp4a-latm", + "audio/mpeg4-generic" -> R.string.cdc_mp4 + "audio/aac", + "audio/aacp", + "audio/3gpp", + "audio/3gpp2" -> R.string.cdc_aac + "audio/ogg", + "application/ogg", + "application/x-ogg" -> R.string.cdc_ogg + "audio/flac" -> R.string.cdc_flac + "audio/wav", + "audio/x-wav", + "audio/wave", + "audio/vnd.wave" -> R.string.cdc_wav + "audio/x-matroska" -> R.string.cdc_mka + else -> -1 + } + + return if (extensionName > -1) { + context.getString(extensionName) } else { // Fall back to the extension if we can't find a special name for this format. MimeTypeMap.getSingleton().getExtensionFromMimeType(fromExtension)?.uppercase() diff --git a/app/src/main/java/org/oxycblt/auxio/music/Indexer.kt b/app/src/main/java/org/oxycblt/auxio/music/Indexer.kt index 7152c70e6..bcddeeb3a 100644 --- a/app/src/main/java/org/oxycblt/auxio/music/Indexer.kt +++ b/app/src/main/java/org/oxycblt/auxio/music/Indexer.kt @@ -179,7 +179,11 @@ class Indexer { private fun indexImpl(context: Context, generation: Long): MusicStore.Library? { emitIndexing(Indexing.Indeterminate, generation) - // Establish the backend to use when initially loading songs. + // Since we have different needs for each version, we determine a "Backend" to use + // when loading music and then leverage that to create the initial song list. + // This is technically dependency injection. Except it doesn't increase your compile + // times by 3x. Isn't that nice. + val mediaStoreBackend = when { Build.VERSION.SDK_INT >= Build.VERSION_CODES.R -> Api30MediaStoreBackend() diff --git a/app/src/main/java/org/oxycblt/auxio/music/IndexerService.kt b/app/src/main/java/org/oxycblt/auxio/music/IndexerService.kt index e5441fa64..8dff997c0 100644 --- a/app/src/main/java/org/oxycblt/auxio/music/IndexerService.kt +++ b/app/src/main/java/org/oxycblt/auxio/music/IndexerService.kt @@ -40,7 +40,10 @@ import org.oxycblt.auxio.util.newMainPendingIntent * A [Service] that handles the music loading process. * * Loading music is actually somewhat time-consuming, to the point where it's likely better suited - * to a service that is less likely to be + * to a service that is less likely to be killed by the OS. + * + * You could probably do the same using WorkManager and the GooberQueue library or whatever, but the + * boilerplate you skip is not worth the insanity of androidx. * * @author OxygenCobalt */ diff --git a/app/src/main/java/org/oxycblt/auxio/playback/system/MediaButtonReceiver.kt b/app/src/main/java/org/oxycblt/auxio/playback/system/MediaButtonReceiver.kt index 5fa05b885..0b3e2950e 100644 --- a/app/src/main/java/org/oxycblt/auxio/playback/system/MediaButtonReceiver.kt +++ b/app/src/main/java/org/oxycblt/auxio/playback/system/MediaButtonReceiver.kt @@ -37,7 +37,8 @@ class MediaButtonReceiver : BroadcastReceiver() { val playbackManager = PlaybackStateManager.getInstance() if (playbackManager.song != null) { // We have a song, so we can assume that the service will start a foreground state. - // At least, I hope. + // At least, I hope. Again, *this is why we don't do this, I cannot describe how + // stupid this is with the state of foreground services on modern android* intent.component = ComponentName(context, PlaybackService::class.java) ContextCompat.startForegroundService(context, intent) } diff --git a/app/src/main/res/values/donottranslate.xml b/app/src/main/res/values/donottranslate.xml index 9f8cb8e66..2832c3934 100644 --- a/app/src/main/res/values/donottranslate.xml +++ b/app/src/main/res/values/donottranslate.xml @@ -9,8 +9,8 @@ %d - Ogg Vorbis - Ogg Opus + Vorbis + Opus Microsoft WAVE diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index fd0a23593..b367be498 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -185,6 +185,8 @@ MPEG-4 Audio Ogg Audio Matroska Audio + Advanced Audio Coding (AAC) + Free Lossless Audio Codec (FLAC) Red