Reputation: 65
I'm currently working on a bash shell script on OS X to get a custom tailored Pashua GUI/automatization package, using ffmpeg in the back, to transcode videos, label them, zip them, upload them, organize them and so on. Everything is working like a charm so far.
My problem now is that I can't make ffmpeg take files or paths that have spaces in them IF I use variables in variables. But that (I think) is a must in order to get ffmpeg to transcode multiple files at once depending on the formats and checkboxes the user ticks on.
I made a little example snippet so you can see my dilemma.
No spaces in path or filename / works great:
#!/bin/bash
infile='/Users/nicolas/Desktop/MASTER_[DE]_Test_140626.mov'
gen_outfile () {
outfile="${1/MASTER/TRANSCODE}"
ffmpeg_cl="-s $2 -c:v libx264 -preset slow -crf 18 -pix_fmt yuv420p -c:a aac -b:a 240k -strict -2 $outfile"
}
gen_outfile "$infile" 1920x1080
./ffmpeg_stat -i "$infile" $ffmpeg_cl
The output is as expected and the file is called "TRANSCODE_[DE]_Test_140626.mov"
Filename variable with spaces - directly fed to ffmpeg:
This works as well but isn't really usable for me because I need to have the option of variable numbers of output files and arguments generated dynamically.
#!/bin/bash
infile_full='/Users/nicolas/Google Drive/encode-o-mat/MASTER_[DE] Test 140626.mov'
gen_outfile () {
outfile="${1/MASTER/TRANSCODE}"
ffmpeg_cl="-s $2 -c:v libx264 -preset slow -crf 18 -pix_fmt yuv420p -c:a aac -b:a 240k -strict -2"
}
gen_outfile "$infile_full" 1920x1080
./ffmpeg_stat -i "$infile_full" $ffmpeg_cl "$outfile"
The output is as expected and the file is called "TRANSCODE_[DE] Test 140626.mov". But this way is just not an option.
This here does not work! Filename is split up and incomplete:
#!/bin/bash
infile_full='/Users/nicolas/Google Drive/encode-o-mat/MASTER_[DE] Test 140626.mov'
gen_outfile () {
outfile="${1/MASTER/TRANSCODE}"
ffmpeg_cl="-s $2 -c:v libx264 -preset slow -crf 18 -pix_fmt yuv420p -c:a aac -b:a 240k -strict -2 $outfile"
}
gen_outfile "$infile_full" 1920x1080
./ffmpeg_stat -i "$infile_full" $ffmpeg_cl
Ffmpeg gives this error: "Unable to find a suitable output format for '/Users/nicolas/Google'". Of course.
This doesn't work as well! Quoting and such:
./ffmpeg_stat -i "$infile_full" "$ffmpeg_cl"
If I put the $ffmpeg_cl variable in various quotes ffmpeg doesn't understand the arguments anymore! This is one example output:
"Unrecognized option 's 1920x1080 -c:v libx264 -preset slow -crf 18 -pix_fmt yuv420p -c:a aac -b:a 240k -strict -2 /Users/nicolas/Google Drive/encode-o-mat/TRANSCODE_[DE] Test 140626.mov'. Error splitting the argument list: Option not found Conversion failed!"
It's really important that the script can handle path- and filenames with spaces because I can't change the environment in which that tool is supposed to run. All ideas and solutions are more than welcome!
Upvotes: 2
Views: 1861
Reputation: 75458
Use arrays instead:
#!/bin/bash
infile_full='/Users/nicolas/Google Drive/encode-o-mat/MASTER_[DE] Test 140626.mov'
gen_outfile () {
outfile="${1/MASTER/TRANSCODE}"
ffmpeg_cl=(-s "$2" -c:v libx264 -preset slow -crf 18 -pix_fmt yuv420p -c:a aac -b:a 240k -strict -2 "$outfile")
}
gen_outfile "$infile_full" 1920x1080
./ffmpeg_stat -i "$infile_full" "${ffmpeg_cl[@]}"
Make sure you quote arguments with variable expansions around ""
properly. Also quote any argument containing *
, ?
, !
, [
and ]
.
Upvotes: 3