Here is a bit of code to extract individual frames from a video:
The code expects that ffmpeg is installed and in your PATH.
the inputs to the function:
filename = video file name
saved_directory is a path to save the files.
frame_list is a list of dictionaries where each dictionary contains ‘frame_number’ and ‘filename’.
frame_number is the index of the frame to extract.
filename is the name of the image after its been extracted
example of frame list:
first_item = {‘frame_number’:10, ‘filename’:‘frame_10.jpg’}
second_item = {‘frame_number’:20, 'filename:‘frame_20.jpg’}
frame_list = [first_item, second_item]
import os, sys, glob, shutil
import subprocess
import binascii
def extract_frame_list(filename, frame_list, saved_directory="saved"):
frame_list = sorted(frame_list, key=lambda x: x['frame_number'])
if not os.path.exists(saved_directory):
os.makedirs(saved_directory)
frames_used = []
frames_used.append(frame_list[0]['frame_number'])
portion = "select=\'eq(n\,{})".format(frame_list[0]['frame_number'])
for instance in frame_list[1:]:
while instance['frame_number'] in frames_used:
instance['frame_number'] += 1
frame_index = int(instance['frame_number'])
portion += '+eq(n\,{})'.format(frame_index)
frames_used.append(frame_index)
portion += "\'"
print("portion = ", portion)
random_string = binascii.b2a_hex(os.urandom(5)).decode()
command_list = ["ffmpeg", "-i", filename, "-qscale:v", "1", "-vf", portion, "-vsync", "0", "{}/{}_frames%d.jpg".format(saved_directory, random_string)]
print(command_list)
subprocess.call(command_list)
for i in range(1, len(frame_list)+1):
os.rename("{}/{}_frames{}.jpg".format(saved_directory, random_string,i), os.path.join(saved_directory, frame_list[i-1]['filename']))
return len(frame_list)