3

I'm trying to use FFmpeg to extract one frame per second from every file in a directory.

I use this command for individual files, but I can't figure out how to input a directory instead:

ffmpeg -i "C:\input\clip1.mp4" -vf fps=1 -qscale:v 2 "C:\output\clip1\clip1A"%d.jpg

Ideally, I want the frames saved to their own folder like below, but I think I can work that part out myself. It's fine if they're all output to the same folder with the same prefix and sequential numbering.

C:\output\clip1\clip1-001.jpg, clip1-002.jpg

C:\output\clip2\clip2-001.jpg, clip2-002.jpg

I've been trying for many hours now and I'm still completely lost. Any help at all would be extremely appreciated.

1

2 Answers 2

2

Done it! This code will output frames to folders of the same name as the video they came from. The frames will be prefixed by the video name and suffixed by sequential numbers starting at 001. So for my files it spits out "/clip1/clip1-001.jpg" etc.

Just in case you're like me and don't have a clue what you're doing, paste the below code in to notepad, save as "extractframesorwhatever.bat", and run from from the directory where your clips are.

for %%F in (*.mp4) do (
If not Exist "%%~nF" MkDir "%%~nF"
ffmpeg -i %%F -r 1 -qscale:v 2 %%~nF\%%~nF-%%3d.jpg
)

If you want to output the folders somewhere else, change:

If not Exist "%%~nF" MkDir "%%~nF"

To something like this:

If not Exist "C:\wherever\%%~nF" MkDir "C:\wherever\%%~nF"

If you do that you'll also need to change the output from (in my example):

%%~nF\%%~nF-%%3d.jpg

to

C:\wherever\%%~nF\%%~nF-%%3d.jpg

Or if you want all frames in one folder. Replace the first %%~nF from the output with your preferred directory. Using my example, it would go from C:\wherever\%%~nF\%%~nF-%%3d.jpg to C:\wherever\frames\%%~nF-%%3d.jpg. You will also either want to edit the second line to point to the new location and stop it from creating a bunch of unnecessary directories, or take out the second line entirely. If you remove the second line, you'll have to create that "frames" folder yourself first.

EDIT - You might need to remove all spaces from file names before they can be processed. "Bulk rename utility" can save you a lot of time.

1
  • No need to remove spaces from file names. instead you need to wrap %%F in double quotes. I'm going to edit your answer to reflect that.
    – yathish
    Commented Dec 11, 2019 at 16:57
1

I like this method for extracting frames, it is very handy. But when I use the code you provide:

for %%F in (*.mp4) do (
If not Exist "%%~nF" MkDir "%%~nF"
ffmpeg -i %%F -r 1 -qscale:v 2 %%~nF\%%~nF-%%3d.jpg
)

I get two output folders:

One of the file name (which is where I want my images to go) and a test folder (which is where my images do go).

I know this is how the code is supposed to work, but perhaps changes over the past four years has changed something with how this code works now. But really, all in all, it's not TOO inconvenient.

I will also add, for those who want to make GIFs of higher quality, you can just change .jpg to .png.

Also, you can make this work with any video format (or more, at least, as I haven't tested this much) by changing the (.mp4) into (.mkv), which I know works.

I assume all other video formats would work also, such as (.avi), (.mpeg), (.ts), (.flv), etc. - though this is not tested.

But as I am the same as the OP in that I don't understand this code, only copy/paste what I find online and play around with it some, it is handy to just have the .bat files ready to go.

I would just like to know how to fix the "test" folder being created and have the screenshots instead go into the folder it already creates of the file name.

To show how I've altered the code to work with other video formats, I'll include a couple of examples:

The first example, which I know works, is for .mkv files instead of .mp4, making the screenshots into .png.

for %%F in (*.mkv) do (
If not Exist "%%~nF" MkDir "%%~nF"
ffmpeg -i %%F -r 1 -qscale:v 2 %%~nF\%%~nF-%%3d.png
)

The last example SHOULD work for .ts files making the screenshots into .png.

for %%F in (*.ts) do (
If not Exist "%%~nF" MkDir "%%~nF"
ffmpeg -i %%F -r 1 -qscale:v 2 %%~nF\%%~nF-%%3d.png
)
1
  • That's strange. The code still works as intended for me. Maybe you could trying running it as admin, or from a different directory.
    – River
    Commented Aug 14, 2022 at 16:01

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .