Получить список I-кадров в видео в FFMPEG / Python

865
Tina J

Я пытаюсь выбрать, скажем, 10 кадров из данного видео, возможно, с самым большим разнообразием и сценами. Я хотел бы поэкспериментировать с различными сценариями выбора, но хорошо то, что понятие по I-frameсвоей сути означает изменение сцены! Поэтому я хотел бы получить I-кадры. Но, может быть, есть много I-кадров, так что, вероятно, мне придется их попробовать.

Как я могу получить список всех frame_number I-кадров в видео в FFMpeg или Python? Я хотел бы использовать список, чтобы выбрать только 10 из них и сохранить их в формате PNG / JPEG.

0

3 ответа на вопрос

1
iangetz

Это выведет все i-кадры в виде изображений PNG.

ffmpeg -i 2.flv -vf "select=eq(pict_type\,I)" -vsync vfr frame-%02d.png 

Отнесите к этому комментарию аналогичный вопрос superuser.com. Как извлечь все ключевые кадры из видеоклипа?

Надеюсь, это поможет. Приветствия.

Ян

Спасибо, но я знаю это. Что я спросил, так это массив индексов I-кадров в коде! Tina J 5 лет назад 0
1
LordNeckbeard

Это похоже на проблему X / Y, поэтому я предложу несколько разных команд:

Список отметок времени

Если вы хотите вывести список временных меток для каждого ключевого кадра:

ffprobe -v error -skip_frame nokey -show_entries frame=pkt_pts_time -select_streams v -of csv=p=0 input 0.000000 2.502000 3.795000 6.131000 10.344000 12.554000 

Обратите внимание -skip_frame nokey.

выберите фильтр

Другой метод - использовать фильтр выбора с sceneвозможностью вывода миниатюр:

ffmpeg -i input -vf "select=gt'(scene,0.4)',scale=160:-1" -vsync vfr %04d.png 
0
Tina J

Получив понимание отсюда, я смог сделать это с ffprobe:

def iframes(): if not os.path.exists(iframe_path): os.mkdir(iframe_path) command = 'ffprobe -v error -show_entries frame=pict_type -of default=noprint_wrappers=1'.split() out = subprocess.check_output(command + [filename]).decode() f_types = out.replace('pict_type=','').split() frame_types = zip(range(len(f_types)), f_types) i_frames = [x[0] for x in frame_types if x[1]=='I'] if i_frames: cap = cv2.VideoCapture(filename) for frame_no in i_frames: cap.set(cv2.CAP_PROP_POS_FRAMES, frame_no) ret, frame = cap.read() outname = iframe_path+'i_frame_'+str(frame_no)+'.jpg' cv2.imwrite(outname, frame) cap.release() print("I-Frame selection Done!!")   if __name__ == '__main__': iframes() 

Похожие вопросы