Skip to content

Commit

Permalink
Implement format sorting (#119)
Browse files Browse the repository at this point in the history
  • Loading branch information
StefanLobbenmeier authored Jan 7, 2025
1 parent 288627f commit 8858626
Show file tree
Hide file tree
Showing 7 changed files with 71 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -172,6 +172,7 @@ class DownloadItem(
"--dump-single-json",
"--no-clean-info-json",
"--flat-playlist",
*ytDlp.initialFormatSelection(),
url,
) { log, logLevel ->
when (logLevel) {
Expand All @@ -180,7 +181,9 @@ class DownloadItem(
metadata.value = videoMetadata
async { writeMetadataToFile(log) }

videoMetadata.requestedDownloadFormats?.forEach(format::selectFormat)
if (ytDlp.shouldSelectFormats()) {
videoMetadata.requestedDownloadFormats?.forEach(format::selectFormat)
}
}
LogLevel.STDERR -> {
logger.info { log }
Expand All @@ -201,6 +204,7 @@ class DownloadItem(
val tmpFilePath = Files.createTempFile("yt-dlp-compose", "yt-dlp-metadata.json")
tmpFilePath.writeText(videoMetadataJson)
val tmpFile = tmpFilePath.toFile()
logger.info { "Wrote metadata to $tmpFile" }
tmpFile.deleteOnExit()
metadataFile.value = tmpFile
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ val VideoMetadata.entryThumbnail
get() = thumbnails?.firstOrNull()?.url ?: thumbnail

val VideoMetadata.requestedDownloadFormats: List<Format>?
get() = requestedDownloads?.firstOrNull()?.requestedFormats
get() = requestedDownloads?.firstOrNull()?.requestedFormats ?: requestedDownloads

@Serializable
data class Format(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,4 +65,26 @@ class YtDlp(private val binaries: Binaries, private val settings: Settings) {
action()
}
}

fun initialFormatSelection(): Array<out String> {
return when {
settings.selectAudio && settings.selectVideo -> {
// Default choice by yt-dlp is to download both audio and video
arrayOf()
}
settings.selectAudio -> {
arrayOf("--format", "bestaudio/bestaudio*")
}
settings.selectVideo -> {
arrayOf("--format", "bestvideo/bestvideo*")
}
else -> {
// Even with --skip-download the metadata will include requested downloads,
// so we have to filter them out manually, see shouldSelectFormats
arrayOf()
}
}
}

fun shouldSelectFormats(): Boolean = settings.selectAudio || settings.selectVideo
}
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,9 @@ fun Settings.toYtDlpConfiguration(): Array<String> =
addArgument("--recode-video", recodeFormat)
addArgument("--audio-format", audioFormat)

addArgument("--prefer-free-formats", preferFreeFormats)
addArgument("--format-sort", formatSort)

addArgument("--embed-subs", embedSubtitles)
addArgument("--embed-metadata", embedMetadata)
addArgument("--embed-thumbnail", embedThumbnail)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,12 @@ data class Settings(
val cookiesFromBrowser: String?,
val cookiesFile: String?,

// Format
val selectVideo: Boolean = true,
val selectAudio: Boolean = true,
val preferFreeFormats: Boolean = false,
val formatSort: String?,

// Output
val mergeOutputFormat: String?,
val remuxFormat: String?,
Expand Down
32 changes: 32 additions & 0 deletions src/main/kotlin/de/lobbenmeier/stefan/settings/ui/SettingsUI.kt
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,13 @@ fun SettingsUI(settings: Settings, save: (Settings) -> Unit, cancel: () -> Unit)
)
}

Section("Formats") {
formatSettings(
settings = mutableSettings,
updateSettings = { mutableSettings = it }
)
}

Section("Output") {
TextInput(
"Merge Output Format (Fast)",
Expand Down Expand Up @@ -263,6 +270,31 @@ fun authenticationSettings(settings: Settings, updateSettings: (Settings) -> Uni
)
}

@Composable
fun formatSettings(settings: Settings, updateSettings: (Settings) -> Unit) {
BooleanInput("Select best Video by default", settings.selectVideo) {
updateSettings(settings.copy(selectVideo = it))
}
BooleanInput("Select best Audio by default", settings.selectAudio) {
updateSettings(settings.copy(selectAudio = it))
}
BooleanInput("Prefer free formats (ogg, opus, webm)", settings.preferFreeFormats) {
updateSettings(settings.copy(preferFreeFormats = it))
}
ChoiceInput(
"Sort formats",
settings.formatSort,
onValueChange = { updateSettings(settings.copy(formatSort = it)) },
options =
listOf(
"res:1080",
"res:720",
"res:480",
"res:360",
)
)
}

@Composable
fun Section(sectionTitle: String, content: @Composable (ColumnScope.() -> Unit)) {
Column {
Expand Down
3 changes: 2 additions & 1 deletion src/main/kotlin/de/lobbenmeier/stefan/ui/Footer.kt
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import de.lobbenmeier.stefan.common.ui.icons.SubtitlesOff
import de.lobbenmeier.stefan.settings.business.Settings
import de.lobbenmeier.stefan.settings.ui.DirectoryPickerButton
import de.lobbenmeier.stefan.settings.ui.authenticationSettings
import de.lobbenmeier.stefan.settings.ui.formatSettings
import de.lobbenmeier.stefan.settings.ui.textFieldWidth

@Composable
Expand Down Expand Up @@ -96,7 +97,7 @@ fun SubtitlesSetting(settings: Settings, updateSettings: (Settings) -> Unit) {

@Composable
fun FormatSelectionSetting(settings: Settings, updateSettings: (Settings) -> Unit) {
return QuickSettingButton("Formats", "Formats") { Text("TODO for next PR") }
return QuickSettingButton("Formats", "Formats") { formatSettings(settings, updateSettings) }
}

@Composable
Expand Down

0 comments on commit 8858626

Please sign in to comment.