Skip to content

Instantly share code, notes, and snippets.

@bradwilson
Last active March 9, 2020 18:33
Show Gist options
  • Star 5 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bradwilson/d340fdf082f26b6f80cd91e0d19c2ac3 to your computer and use it in GitHub Desktop.
Save bradwilson/d340fdf082f26b6f80cd91e0d19c2ac3 to your computer and use it in GitHub Desktop.
Converts FLAC/MP3 input, resamples down to ReplayGain levels, and converts to MP3. Requires on the path: flac, metaflac, ffmpeg, mogrify
param(
[string][Parameter(Mandatory=$true)]$InputFile,
[string][Parameter(Mandatory=$true)]$OutputFile,
[int]$SampleRate = 44100,
[string]$BitRate = "160k"
)
$ErrorActionPreference = "Stop"
$InputFile = [System.IO.Path]::Combine((Get-Location), $InputFile)
$OutputFile = [System.IO.Path]::Combine((Get-Location), $OutputFile)
$OutputFilePath = [System.IO.Path]::GetDirectoryName($OutputFile)
if ((Test-Path -LiteralPath $OutputFilePath) -eq $false) {
New-Item -type directory -path $OutputFilePath | out-null
}
$TempFile = [System.IO.Path]::GetTempFileName()
$ErrorActionPreference = "Continue"
try {
ffmpeg -i "$InputFile" -y -ar $SampleRate -ac 2 -b:a $BitRate -map_metadata 0 -id3v2_version 3 "$OutputFile" 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "ffmpeg failure"
exit -1
}
}
finally {
Remove-Item -LiteralPath $TempFile -ErrorAction Ignore
}
$Error.Clear()
param(
[string]$srcFolder = "D:\Music\2.0",
[string]$destFolder = "D:\Music\2.0_MP3"
)
$srcFolder = Resolve-Path $srcFolder.Trim("\")
$destFolder = Resolve-Path $destFolder.Trim("\")
$lastFolder = $null
$TempFile = [System.IO.Path]::GetTempFileName()
$ErrorActionPreference = "Continue"
try {
Get-ChildItem -Recurse -Include @("*.mp3", "*.flac") $srcFolder | %{
$src = $_.FullName
$folder = Split-Path $src
if ($folder -ne $lastFolder) {
Write-Progress -Activity $folder
$lastFolder = $folder
}
$dest = $_.FullName.Replace($srcFolder, $destFolder)
$dest = ((Join-Path ([System.IO.Path]::GetDirectoryName($dest)) ([System.IO.Path]::GetFileNameWithoutExtension($dest))) + ".mp3")
$srcWrite = ([System.IO.FileInfo]$src).LastWriteTime
$destWrite = ([System.IO.FileInfo]$dest).LastWriteTime
if ($destWrite -lt $srcWrite) {
$destPath = [System.IO.Path]::GetDirectoryName($dest)
if ((Test-Path -LiteralPath $destPath) -eq $false) {
New-Item -type directory -path $destPath | out-null
}
Write-Host -ForegroundColor Blue -NoNewline "Converting: "
Write-Host $src.Replace($srcFolder, "").Trim("\")
if ($_.Name.EndsWith(".mp3")) {
# Convert to FLAC
& ffmpeg -y -i "$src" "$($dest).flac" 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "ffmpeg failure"
exit -1
}
} else {
# Copy the FLAC file
Copy-Item -LiteralPath $src -Destination "$($dest).flac"
}
# Remove unwanted tags
& metaflac --remove-tag=unsyncedlyrics --remove-tag=lyrics --remove-tag=account_id --remove-tag=copyright "$($dest).flac" 2>&1 >$TempFile
# Extract tags
& metaflac --export-tags-to="$($dest).tags" "$($dest).flac" 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "metaflac failure"
exit -1
}
# Extract cover art
& ffmpeg -y -i "$src" "$($dest).jpg" 2>&1 >$TempFile
# Resample to a stable volume level
& flac -f -d "$($dest).flac" -o "$($dest).wav" --apply-replaygain-which-is-not-lossless=5a --delete-input-file 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "flac failure"
exit -1
}
# Encode into FLAC so we can import the tags & image
& flac -f "$($dest).wav" -o "$($dest).flac" --delete-input-file 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "flac failure"
exit -1
}
# Import tags
& metaflac --import-tags-from="$($dest).tags" --remove-replay-gain "$($dest).flac" 2>&1 >$TempFile
if ($global:LASTEXITCODE -ne 0) {
Get-Content $TempFile
Write-Error "metaflac failure"
exit -1
}
Remove-Item -LiteralPath "$($dest).tags" -ErrorAction Stop
# Resize and import cover art
if (Test-Path -LiteralPath "$($dest).jpg") {
& mogrify -resize "800x800>" -quality 90 "$($dest).jpg"
& metaflac --import-picture-from="$($dest).jpg" "$($dest).flac" 2>&1 >$TempFile
Remove-Item -LiteralPath "$($dest).jpg" -ErrorAction Stop
}
# Final step, convert the resampled, properly tagged FLAC into MP3
ConvertTo-MP3 "$($dest).flac" $dest -BitRate "320k"
Remove-Item -LiteralPath "$($dest).flac" -ErrorAction Stop
}
}
}
finally {
Remove-Item $TempFile -Force
}
$Error.Clear()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment