Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ data class AudioMetadata(
val albumArtist: String?,
val album: String?,
val genre: String?,
val composer: String?,
val lyrics: String?,
val durationMs: Long?,
val trackNumber: Int?,
Expand Down Expand Up @@ -77,6 +78,8 @@ object AudioMetadataReader {
?: propertyMap["BAND"]?.firstOrNull()?.takeIf { it.isNotBlank() }
val album = propertyMap["ALBUM"]?.firstOrNull()?.takeIf { it.isNotBlank() }
val genre = propertyMap["GENRE"]?.firstOrNull()?.takeIf { it.isNotBlank() }
val composer = propertyMap["COMPOSER"]?.firstOrNull()?.takeIf { it.isNotBlank() }
?: propertyMap["TCOM"]?.firstOrNull()?.takeIf { it.isNotBlank() }
val lyrics = propertyMap["LYRICS"]?.firstOrNull()?.takeIf { it.isNotBlank() }
?: propertyMap["UNSYNCEDLYRICS"]?.firstOrNull()?.takeIf { it.isNotBlank() }
val trackString = propertyMap["TRACKNUMBER"]?.firstOrNull()?.takeIf { it.isNotBlank() }
Expand Down Expand Up @@ -127,6 +130,7 @@ object AudioMetadataReader {
albumArtist = albumArtist ?: fallback?.albumArtist,
album = album ?: fallback?.album,
genre = genre ?: fallback?.genre,
composer = composer ?: fallback?.composer,
lyrics = lyrics ?: fallback?.lyrics,
durationMs = durationMs ?: fallback?.durationMs,
trackNumber = trackNumber ?: fallback?.trackNumber,
Expand Down Expand Up @@ -166,6 +170,7 @@ object AudioMetadataReader {
val albumArtist = tag?.getFirst(FieldKey.ALBUM_ARTIST)?.takeIf { it.isNotBlank() }
val album = tag?.getFirst(FieldKey.ALBUM)?.takeIf { it.isNotBlank() }
val genre = tag?.getFirst(FieldKey.GENRE)?.takeIf { it.isNotBlank() }
val composer = tag?.getFirst(FieldKey.COMPOSER)?.takeIf { it.isNotBlank() }
val lyrics = tag?.getFirst(FieldKey.LYRICS)?.takeIf { it.isNotBlank() }
val trackNumber = tag?.getFirst(FieldKey.TRACK)?.takeIf { it.isNotBlank() }
?.substringBefore('/')?.toIntOrNull()
Expand Down Expand Up @@ -197,6 +202,7 @@ object AudioMetadataReader {
albumArtist = albumArtist,
album = album,
genre = genre,
composer = composer,
lyrics = lyrics,
durationMs = durationMs,
trackNumber = trackNumber,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,8 @@ class SongMetadataEditor(
const val MAX_TITLE_LENGTH = 500
const val MAX_ARTIST_LENGTH = 500
const val MAX_ALBUM_LENGTH = 500
const val MAX_ALBUM_ARTIST_LENGTH = 500
const val MAX_COMPOSER_LENGTH = 500
const val MAX_GENRE_LENGTH = 100
const val MAX_LYRICS_LENGTH = 50_000
}
Expand All @@ -107,13 +109,17 @@ class SongMetadataEditor(
title: String,
artist: String,
album: String,
albumArtist: String?,
composer: String?,
genre: String,
lyrics: String
): String? {
if (title.isBlank()) return "Title cannot be empty"
if (title.length > MetadataLimits.MAX_TITLE_LENGTH) return "Title too long"
if (artist.length > MetadataLimits.MAX_ARTIST_LENGTH) return "Artist name too long"
if (album.length > MetadataLimits.MAX_ALBUM_LENGTH) return "Album name too long"
if (!albumArtist.isNullOrBlank() && albumArtist.length > MetadataLimits.MAX_ALBUM_ARTIST_LENGTH) return "Album artist name too long"
if (!composer.isNullOrBlank() && composer.length > MetadataLimits.MAX_COMPOSER_LENGTH) return "Composer name too long"
if (genre.length > MetadataLimits.MAX_GENRE_LENGTH) return "Genre too long"
if (lyrics.length > MetadataLimits.MAX_LYRICS_LENGTH) return "Lyrics too long"
return null
Expand Down Expand Up @@ -229,6 +235,8 @@ class SongMetadataEditor(
newTitle: String,
newArtist: String,
newAlbum: String,
newAlbumArtist: String? = null,
newComposer: String? = null,
newGenre: String,
newLyrics: String,
newTrackNumber: Int,
Expand All @@ -237,7 +245,7 @@ class SongMetadataEditor(
newReplayGainAlbumGainDb: String? = null,
coverArtUpdate: CoverArtUpdate? = null,
): SongMetadataEditResult = withContext(Dispatchers.IO) {
val validationError = validateMetadataInput(newTitle, newArtist, newAlbum, newGenre, newLyrics)
val validationError = validateMetadataInput(newTitle, newArtist, newAlbum, newAlbumArtist, newComposer, newGenre, newLyrics)
if (validationError != null) {
Timber.w("Metadata validation failed: $validationError")
return@withContext SongMetadataEditResult(
Expand Down Expand Up @@ -339,6 +347,8 @@ class SongMetadataEditor(
newTitle = newTitle,
newArtist = newArtist,
newAlbum = newAlbum,
newAlbumArtist = newAlbumArtist,
newComposer = newComposer,
newGenre = trimmedGenre,
newLyrics = trimmedLyrics,
newTrackNumber = newTrackNumber,
Expand All @@ -354,6 +364,8 @@ class SongMetadataEditor(
newTitle = newTitle,
newArtist = newArtist,
newAlbum = newAlbum,
newAlbumArtist = newAlbumArtist,
newComposer = newComposer,
newGenre = trimmedGenre,
newLyrics = trimmedLyrics,
newTrackNumber = newTrackNumber,
Expand All @@ -369,6 +381,8 @@ class SongMetadataEditor(
newTitle = newTitle,
newArtist = newArtist,
newAlbum = newAlbum,
newAlbumArtist = newAlbumArtist,
newComposer = newComposer,
newGenre = trimmedGenre,
newLyrics = trimmedLyrics,
newTrackNumber = newTrackNumber,
Expand All @@ -385,6 +399,8 @@ class SongMetadataEditor(
newTitle = newTitle,
newArtist = newArtist,
newAlbum = newAlbum,
newAlbumArtist = newAlbumArtist,
newComposer = newComposer,
newGenre = trimmedGenre,
newLyrics = trimmedLyrics,
newTrackNumber = newTrackNumber,
Expand Down Expand Up @@ -442,6 +458,7 @@ class SongMetadataEditor(
title = newTitle,
artist = newArtist,
album = newAlbum,
albumArtist = newAlbumArtist,
genre = trimmedGenre,
trackNumber = newTrackNumber,
discNumber = newDiscNumber
Expand Down Expand Up @@ -727,6 +744,8 @@ class SongMetadataEditor(
newTitle: String,
newArtist: String,
newAlbum: String,
newAlbumArtist: String?,
newComposer: String?,
newGenre: String,
newLyrics: String,
newTrackNumber: Int,
Expand Down Expand Up @@ -771,6 +790,10 @@ class SongMetadataEditor(
propertyMap["TITLE"] = arrayOf(newTitle)
propertyMap["ARTIST"] = arrayOf(newArtist)
propertyMap["ALBUM"] = arrayOf(newAlbum)
if (!newAlbumArtist.isNullOrBlank()) {
propertyMap["ALBUMARTIST"] = arrayOf(newAlbumArtist)
}
propertyMap.upsertOrRemove("COMPOSER", newComposer)
propertyMap.upsertOrRemove("GENRE", newGenre)
propertyMap.upsertOrRemove("LYRICS", newLyrics)
propertyMap["TRACKNUMBER"] = arrayOf(newTrackNumber.toString())
Expand All @@ -779,7 +802,6 @@ class SongMetadataEditor(
} else {
propertyMap.remove("DISCNUMBER")
}
propertyMap["ALBUMARTIST"] = arrayOf(newArtist)
propertyMap.applyReplayGainUpdate(REPLAYGAIN_TRACK_GAIN_KEY, replayGainTrackUpdate)
propertyMap.applyReplayGainUpdate(REPLAYGAIN_ALBUM_GAIN_KEY, replayGainAlbumUpdate)
Timber.tag(TAG).e("TAGLIB: Updated property map, saving...")
Expand Down Expand Up @@ -848,6 +870,8 @@ class SongMetadataEditor(
newTitle: String,
newArtist: String,
newAlbum: String,
newAlbumArtist: String?,
newComposer: String?,
newGenre: String,
newLyrics: String,
newTrackNumber: Int,
Expand All @@ -869,7 +893,14 @@ class SongMetadataEditor(
tag.setField(FieldKey.TITLE, newTitle)
tag.setField(FieldKey.ARTIST, newArtist)
tag.setField(FieldKey.ALBUM, newAlbum)
tag.setField(FieldKey.ALBUM_ARTIST, newArtist)
if (!newAlbumArtist.isNullOrBlank()) {
tag.setField(FieldKey.ALBUM_ARTIST, newAlbumArtist)
}
if (!newComposer.isNullOrBlank()) {
tag.setField(FieldKey.COMPOSER, newComposer)
} else {
tag.deleteField(FieldKey.COMPOSER)
}

if (newGenre.isNotBlank()) {
tag.setField(FieldKey.GENRE, newGenre)
Expand Down Expand Up @@ -937,6 +968,8 @@ class SongMetadataEditor(
newTitle: String,
newArtist: String,
newAlbum: String,
newAlbumArtist: String?,
newComposer: String?,
newGenre: String,
newLyrics: String,
newTrackNumber: Int,
Expand Down Expand Up @@ -967,7 +1000,8 @@ class SongMetadataEditor(

tags.replaceSingleComment("TITLE", newTitle)
tags.replaceSingleComment("ARTIST", newArtist)
tags.replaceSingleComment("ALBUMARTIST", newArtist)
tags.replaceSingleComment("ALBUMARTIST", newAlbumArtist?.takeIf { it.isNotBlank() })
tags.replaceSingleComment("COMPOSER", newComposer)
tags.replaceSingleComment("ALBUM", newAlbum)
tags.replaceSingleComment("GENRE", newGenre)
tags.replaceSingleComment("LYRICS", newLyrics)
Expand Down Expand Up @@ -1039,6 +1073,7 @@ class SongMetadataEditor(
title: String,
artist: String,
album: String,
albumArtist: String?,
genre: String,
trackNumber: Int,
discNumber: Int?
Expand All @@ -1054,7 +1089,9 @@ class SongMetadataEditor(
val encodedTrack = ((discNumber ?: 0) * 1000) + trackNumber
put(MediaStore.Audio.Media.TRACK, encodedTrack)
put(MediaStore.Audio.Media.DATE_MODIFIED, System.currentTimeMillis() / 1000)
put(MediaStore.Audio.Media.ALBUM_ARTIST, artist)
if (!albumArtist.isNullOrBlank()) {
put(MediaStore.Audio.Media.ALBUM_ARTIST, albumArtist)
}
}

val rowsUpdated = context.contentResolver.update(uri, values, null, null)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -145,12 +145,14 @@ fun DailyMixSection(
onNavigateToGenre(song)
showSongInfoSheet = false
},
onEditSong = { newTitle, newArtist, newAlbum, newGenre, newLyrics, newTrackNumber, newDiscNumber, replayGainTrackGainDb, replayGainAlbumGainDb, coverArtUpdate ->
onEditSong = { newTitle, newArtist, newAlbum, newAlbumArtist, newComposer, newGenre, newLyrics, newTrackNumber, newDiscNumber, replayGainTrackGainDb, replayGainAlbumGainDb, coverArtUpdate ->
playerViewModel.editSongMetadata(
song,
newTitle,
newArtist,
newAlbum,
newAlbumArtist,
newComposer,
newGenre,
newLyrics,
newTrackNumber,
Expand Down
Loading
Loading