影音轉檔壓縮紀錄

最近透過Convertio輸出多個不同格式的影音,在不同格式下選用的品質差異很大,多次嘗試後以人工比對細節發現傳統H.264的質量與webM(VP9)在等畫質情況下檔案大小差距不到15個百分點,而AV1則可以讓檔案大小差距增加到50%以上,對於縮減影音體積來說幫助更為顯著。

AV1與H.265格式建議普通畫質參數:

AOM-av1                >CRF/QP       24(普通畫質-體積最小)
SVT-av1                  >CRF/QP        28(普通畫質)
rav1e-av1              >QP                 60(普通畫質)
Medium-H.265    >CRF/QP        20(普通畫質)
Slow-H.265           >CRF/QP        24(普通畫質-體積次之,效率較高)

convertio.co輸出多個格式建議最低畫質:

(以畫面不破不殘影為基準,實際輸出可能會因為影格動態差異而有所變化)

    av1                        >CQ               39(低畫質)
webM                       >CQ               30(低畫質高一級)
 H.264                      >CRF             23(一般畫質)

 H.264                      >CRF             28(極低畫質,窄頻網路適用)

 H.264                      >CQ               39(極低畫質,窄頻網路適用)

參考資料 https://www.reddit.com/ (文件 備)

2024/12/29 更新

最近有無損剪輯影片的需求,常見的無損切割片段的工具有VidTrimLosslessCut分別針對手機跟電腦端,其中LosslessCut額外提供無損合併影片的功能,經測試相同編碼格式的無損切片確實可以順利合併,但合併後的影片在接合處容易因為畫格不足導致聲音沒跟時間戳同步的情況,這塊可以透過ffmpeg修復,修復指令如下:

ffmpeg -i input.mp4 -c:v copy -c:a aac -async 1 output_fixed.mp4

其中-async 1將以影片本身的時間戳作為基準對聲音進行校正,操作後實現影像跟聲音同步。


2025/01/21更新

在Debian快速編碼成720p畫質並限制CPU 40%使用率

apt install cpulimit

cpulimit -l 40 -- ffmpeg -i h264.mp4 -c:a copy -c:v libx264 -preset fast -crf 24 -vf "scale='if(gt(a,1280/720),min(iw,1280),if(lt(iw,1280),iw,-2))':'if(gt(a,1280/720),if(lt(ih,720),ih,-2),min(ih,720))':force_original_aspect_ratio=decrease,scale=trunc(iw/2)*2:trunc(ih/2)*2" -movflags faststart output_720p.mp4

cpulimit -l 60 -- ffmpeg -i h264.mp4 -c:a aac -b:a 96k -ac 2 -c:v libx264 -preset fast -crf 24 -vf "scale='if(gt(a,854/480),min(iw,854),if(lt(iw,854),iw,-2))':'if(gt(a,854/480),if(lt(ih,480),ih,-2),min(ih,480))':force_original_aspect_ratio=decrease,scale=trunc(iw/2)*2:trunc(ih/2)*2" -movflags faststart output_480p.mp4

主要目的是希望在控制CPU負載的情況下快速輸出。

建立批次轉檔腳本

vim batch_ffmpeg.sh

寫入以下內容

#!/bin/bash
# 設定 A 目錄與 B 目錄
INPUT_DIR="/path/to/A" # 替換成 A 目錄的實際路徑
OUTPUT_DIR="/path/to/B" # 替換成 B 目錄的實際路徑

# 確保輸出目錄存在
mkdir -p "$OUTPUT_DIR"

# 開始處理每一個視頻檔案
for input_file in "$INPUT_DIR"/*; do
  if [ -f "$input_file" ]; then
    filename=$(basename "$input_file")
    output_file="$OUTPUT_DIR/$filename"
    
    echo "處理中: $input_file -> $output_file"

    # 捕獲 cpulimit 和 ffmpeg 的輸出
    cpulimit_output=$(cpulimit -l 60 -- ffmpeg -i "$input_file" -map 0:v:0 \
      -map 0:a? -c:a aac -b:a 96k -ac 2 \
      -c:v libx264 -preset fast -crf 24 \
      -vf "scale=-2:480:force_original_aspect_ratio=decrease,crop=min(iw\,854):480:(iw-min(iw\,854))/2:0,pad=854:480:(ow-iw)/2:(oh-ih)/2:color=black,setsar=1:1" \
      -movflags faststart \
      -map 0:s? -c:s copy \
      "$output_file" 2>&1)

    # 分析 cpulimit 的輸出
    if echo "$cpulimit_output" | grep -q "Process .* detected"; then
      # 檢查是否生成輸出文件
      if [ -f "$output_file" ] && [ -s "$output_file" ]; then
        echo "成功處理: $input_file"
      else
        echo "處理失敗: $input_file - 輸出文件未生成或為空"
      fi
    else
      echo "處理失敗: $input_file - cpulimit 未檢測到進程"
    fi
  fi
done

echo "所有視頻處理完成!"

保存後增加執行權限

chmod +x batch_ffmpeg.sh

執行腳本

./batch_ffmpeg.sh

其他濾鏡寫法

-vf "scale='if(gt(a,854/480),min(iw,854),if(lt(iw,854),iw,-2))':'if(gt(a,854/480),if(lt(ih,480),ih,-2),min(ih,480))':force_original_aspect_ratio=decrease,scale=trunc(iw/2)*2:trunc(ih/2)*2"

進程為目的覆蓋,所以OUTPUT_DIR如果有相同檔名會直接替換。

留言

這個網誌中的熱門文章

Redmi紅米 Note4x (Qualcomm SD625)啟用VoLTE功能

紅米手機MIUI設置SD卡為延伸儲存空間