SciTech-AV-Video-DVP(Digital Video Processing)-CV/CG-ffmpeg-剪下/格式轉換 & 影片拆幀圖 & 圖片合成影片 & 拼接 & time duration 格式 & 時間 起始點 時長 及 幀數設定

abaelhe發表於2024-10-15

FFmpeg Image/Video/Audio Processing


按幀截圖, 圖片合成影片, 影片格式轉換, 影片拼接:

video_file = 'Cartier.flv'
cmd_probe = "ffprobe  -hide_banner  -v quiet -print_format json -show_format -show_streams    -i  %s"
cmd_frame = "ffmpeg  -i %s  -y   -s 1280x960  -ss %s -frames 1  %s"
vinfo =[ i.strip() for i in os.popen3(cmd_probe % video_file)[2].read().splitlines() ]

合成影片流


用 圖片序列+音訊 合成

MP3:/home/ffmpeg_data/001.mp3、/home/ffmpeg_data/002.mp3
ffmpeg -r 0.5   -i 001.jpg  001.mp3    -vcodec mpeg4    001.mp4
ffmpeg -r 0.5   -i 001.jpg  001.mp3    -vcodec mpeg4    001.mp4
# 或將需要合併的影片檔案寫入 inputs.txt( 一行一個), 接著執行:
ffmpeg -y -f concat -safe 0 -i  inputs.txt -c copy output.mp4

ffprobe提取影片資訊


  1. 取得JSON格式影片/音訊資訊( 幀一級高精度的Stream 欄位, 格式欄位)
ffprobe  -hide_banner  -v quiet -print_format json -show_format -show_streams  -i  VIDEO_FILE/AUDIO_FILE
   -count_frames 選項會在結果里加入每個 Stream 總幀數字段資訊: "nb_read_frames" ,
      但因需要處理每一幀,會影響呼叫執行的效能;  
   -show_frames 選項會在結果里加入frames幀資訊(所有Stream的所有幀),
      但因需要處理每一幀,會影響呼叫執行的效能;  
  1. 提取TEXT格式影片/音訊資訊
Abael:flvs abael$ ffprobe  -hide_banner   -i  Cartier.flv
Input #0, flv, from 'Cartier.flv':
  Metadata:
    major_brand     : mp42
    minor_version   : 0
    compatible_brands: isommp42
    encoder         : Lavf58.12.100
  Duration: 00:00:31.45, start: 0.057000, bitrate: 888 kb/s
    Stream #0:0: Video: h264 (High), yuv420p(progressive), 1280x720 [SAR 1:1 DAR 16:9], 25 fps, 25 tbr, 1k tbn, 50 tbc
    Stream #0:1: Audio: aac (LC), 44100 Hz, stereo, fltp, 128 kb/s

TEXT格式資訊可以取得Duration(時長), start(開始時間), fps(frame per second, 影片 Stream 的幀率).

  • 擷取影片的1幀圖片: 例如在0.0 時間擷取一幀圖片:
    ffmpeg -i /www/data/nginx/rtmp/flvs/CartierAD.flv -y -s 1280x960 -ss 0.0 -frames 1 ./bg.jpg
  • 拆分出影片的全部幀圖片:
    ffmpeg -i video.avi frames_%05d.jpg
    匯出結果 用 frame_ 為字首,以5位數字為編號(不夠前邊用0補全),
    至於frames_%Nd.jpg保留幾位數字長度, 可以先用 ffprobe 得到影片/音訊 的總幀數來確定;

裁剪/合併/拼接 影片


  1. FFMPEG 裁剪影片:
    ffmpeg -ss START -t DURATION -i INPUT -vcodec copy -acodec copy OUTPUT
    -vcode copy和-acodec copy 表示使用的影片和音訊的編碼格式,copy表示原樣複製影片源的。

  2. FFMPEG 合併影片檔案:
    ffmpeg -i concat:"PART1.mpg|PART2.mpg" -vcodec copy -acodec copy OUTPUT.mpg
    PART1:要合併的第一個影片檔名,
    PART2:要合併的第二個影片檔名,
    OUTPUT:合併後的影片檔名

  3. FFMPEG 轉換影片格式
    ffmpeg -i INPUT -f OUTPUT_FOMRMAT OUTPUT
    例如:ffmpeg -i /tmp/a.avi -f mpeg ./result.mpg

  4. 圖片 和 音訊檔案 合成影片:

    • 照片(要提前準備好的):
      /home/ffmpeg_data/001.jpg、/home/ffmpeg_data/002.jpg
    • MP3(要提前準備好的):
      /home/ffmpeg_data/001.mp3、/home/ffmpeg_data/002.mp3
    • 用FFmpeg轉換:
      ffmpeg -r 0.5 -i 001.jpg 001.mp3 -vcodec mpeg4 001.mp4
      也可以將需要合併的影片檔案 放寫在 inputs.txt( 一行一個), 接著執行:
      ffmpeg -y -f concat -safe 0 -i inputs.txt -c copy output.mp4
  5. 圖片 合成 影片:
    ffmpeg [-start_number START_NUMBER] -i img/frames_%05d.jpg -vcodec OUTPUT_VIDEO_CODEC test.avi
    例如
    ffmpeg -i img/frames_%05d.jpg -vcodec mpeg4 test.avi

    • -vodec影片編碼格式,所有ffmpeg支援的格式都可以,具體可以ffmpeg -codecs檢視。
    • -i輸入檔名,上例意為讀取img資料夾檔名frame_ 為字首 而且 後接五位數字jpg 圖片序列
    • 報錯解決: Could find no file with path ‘img/frames_%05d.jpg’ and index in the range 0-4
      這是因為ffmpeg預設圖片編號從0開始的。即如果找不到 frames_00000.jpg報錯
      指定讀取圖片檔名的起始編號為:
      ffmpeg -start_number 345 -i img/frames_%05d.jpg -vcodec mpeg4 test.avi
    • 注意:
      • 讀取圖片檔案序列時會順序讀取,若出現編號中斷,影片會就此結束
      • 預設圖片檔名從0開始編號讀取。如不存在frames_00000.jpg檔案則報錯.
      • 還可以透過:
        • -r 設定fps(frames per second, 幀率), 即每秒提取或整合幾幀圖片
        • -y 若輸出檔名衝突,直接覆蓋。
          參考 "Clarification for ffmpeg input option with image files as input"



FFmpeg CommandLine Arguments and Parameters

Video options:


-vframes number     **set the number of video frames to output**
-r rate             **set frame rate (Hz value, fraction or abbreviation)**
-fpsmax rate        **set max frame rate (Hz value, fraction or abbreviation)**
-s size             **set frame size (WxH or abbreviation)**
-aspect aspect      **set aspect ratio** (4:3, 16:9 or 1.3333, 1.7777)
-display_rotation angle  **set pure counter-clockwise rotation in degrees for stream(s)**
-display_hflip      **set display horizontal flip for stream(s)** (overrides any display rotation if it is not set)
-display_vflip      **set display vertical flip for stream(s)** (overrides any display rotation if it is not set)
-vn                 **disable video**
-vcodec codec       **force video codec** ('copy' to copy stream)
-timecode hh:mm:ss[:;.]ff  **set initial TimeCode value**.
-pass n             **select the pass number** (1 to 3)
-vf filter_graph    **set video filters**
-b bitrate          **video bitrate (please use -b:v)**
-dn                 **disable data**

Subtitle options:

-s size             set frame size (WxH or abbreviation)
-sn                 disable subtitle
-scodec codec       force subtitle codec ('copy' to copy stream)
-stag fourcc/tag    force subtitle tag/fourcc
-fix_sub_duration   fix subtitles duration
-canvas_size size   set canvas size (WxH or abbreviation)
-spre preset        set the subtitle options to the indicated preset

FFmpeg Time Duration

FFmpeg時間段( time duration )格式,兩種:

  • [-][:]:[....]
    HH 小時, MM 分鐘(最大兩位數), SS 秒(最多兩位數),
    m 小數秒(高精度, 十進位制);
  • [-]<S>+[.<m>...]
    S 秒數, m 作小數秒(高精度, 十進位制);;

上兩種duration, 都可選前加-指示negative duration.
例如:

-13.567:      **negative** 13.567 seconds
12:03:45:    12hours 03minutes 45 seconds
23.189:       23.189 seconds
00:01:00:    60 seconds
60:               60 seconds

FFmpeg Global options

affect whole program instead of just one file:

  • -loglevel loglevel set logging level
  • -v loglevel **set logging level**
  • -report generate a report
  • -max_alloc bytes **set maximum size of a single allocated block**
  • -y **overwrite output files**
  • -n never overwrite output files
  • -ignore_unknown Ignore unknown stream types
  • -filter_threads **number of non-complex filter threads**
  • -filter_complex_threads **number of threads for -filter_complex**
  • -stats print progress report during encoding
  • -max_error_rate maximum error rate ratio of decoding errors (0.0: no errors, 1.0: 100% errors) above which ffmpeg returns an error instead of success.
  • -frames[:stream_specifier] framecount (output,per-stream)
    指定產出幀數: 設定產出影片的幀數 framecount .
  • -f fmt (input/output)
    指定檔案格式:
    • 匯入:會自動檢測匯入格式;
    • 產出:副檔名自動推導產出格式 ( 因此這個 -f fmt 選項只在必要時使用. )
    • FFmpeg 支援的所有 fmt 格式可以檢視執行: ffmpeg -formats
  • -ss position (input/output)
    指定時間起點:
    • -i 引數的前面是作為匯入設定, 從匯入檔案快進到指定position.
      注️意:
      • 多數檔案不真正支援seek, ffmpeg 會快進到 position 之前最接近的seek point.
      • 轉碼(transcoding)時並啟用選項 -accurate_seek(預設), 則解碼並丟棄 前置seek point 和 position 之間的幀.
      • 流複製(stream copy) 時並啟用選項 -noaccurate_seek (預設), 則保留seek point 和 position 之間的幀.
    • -i 引數的後面是作為產出選項(放在 output url 之前);
      解碼讀入檔案並丟棄匯入, 直到產出流的 timestamp 到達這個指定的 position.
  • -sseof position (input/output)
    類似 "-ss" 選項,但時間點相對於 eof(end of file). 0 表示 EOF, 負數表示檔案的stream上.
  • -to position (input/output)
    指定時間終點.
    • 在 寫產出檔案 / 讀匯入檔案 到達指定時間終點 position後停止. ( ffmpeg Time duration 格式)
    • -to -t 兩個選項只能兩選一,且 -t優先順序更高.
  • -t duration (input/output)
    指定時長.
    • 在 "-i" 的前面,作為匯入設定, 指定只從匯入檔案讀取的資料時間長度.
    • 在 "-i" 的後面(output url前),作為產出設定, 指定只寫指定時長的資料,就停止.
    • -to -t 兩個選項只能兩選一,且 -t優先順序更高
  • -fs limit_size (output)
    Set the file size limit, expressed in bytes.
    No further chunk of bytes is written after the limit is exceeded.
    The size of the output file is slightly more than the requested file size.
  • -itsoffset offset (input)
    指定匯入時間偏移. offsetffmpeg time duration 格式
    offset 被新增到匯入檔案的timestamps(時間戳).
    指定positive offset 表示 streams 被 delayed 到指定 offset 的時間.
  • -timestamp date (output)
    指定錄製時間戳
    在 container(資料容器, 輸出stream到儲存的格式容器)上 設定錄製 timestamp.

FFmpeg Per-file main options:

-f fmt              **force format**
-c codec            **codec name**
-codec codec        codec name
-pre preset         preset name
-map_metadata outfile[,metadata]:infile[,metadata]  **set metadata information of outfile from infile**
-t duration         **record or transcode "duration" seconds of audio/video**
-to time_stop       **record or transcode stop time**
-fs limit_size      **set the limit file size in bytes**
-ss time_off        **set the start time offset**
-sseof time_off     **set the start time offset relative to EOF**
-seek_timestamp     enable/disable seeking by timestamp with -ss
-timestamp time     set the recording timestamp ('now' to set the current time)
-metadata string=string  **add metadata**
-program title=string:st=number...  add program with specified streams
-target type        specify target file type ("vcd", "svcd", "dvd", "dv" or "dv50" with optional prefixes "pal-", "ntsc-" or "film-")
-apad               audio pad
-frames number      **set the number of frames to output**
-filter filter_graph  **set stream filtergraph**
-filter_script filename  **read stream filtergraph description from a file**
-reinit_filter      **reinit filtergraph on input parameter changes**
-discard            discard
-disposition        disposition

FFmpeg 常用到PCM格式


 DE s16be           PCM signed 16-bit big-endian
 DE s16le            PCM signed 16-bit little-endian
 DE s24be           PCM signed 24-bit big-endian
 DE s24le            PCM signed 24-bit little-endian
 DE s32be           PCM signed 32-bit big-endian
 DE s32le            PCM signed 32-bit little-endian
 DE s8                 PCM signed 8-bit
 DE f32be           PCM 32-bit floating-point big-endian
 DE f32le            PCM 32-bit floating-point little-endian
 DE f64be           PCM 64-bit floating-point big-endian
 DE f64le            PCM 64-bit floating-point little-endian
 DE mulaw         PCM mu-law
 DE u16be           PCM unsigned 16-bit big-endian
 DE u16le           PCM unsigned 16-bit little-endian
 DE u24be           PCM unsigned 24-bit big-endian
 DE u24le           PCM unsigned 24-bit little-endian
 DE u32be           PCM unsigned 32-bit big-endian
 DE u32le           PCM unsigned 32-bit little-endian
 DE u8                PCM unsigned 8-bit

ffmpeg 的解碼編碼格式

相關文章