【ffmpeg】 比較動画の作り方

この方法は動画内にテキストが含まれない、左右か上下に単純配置した比較動画を作るものです。動画のエンコード設定をそれなりに理解していて、コマンドラインの扱いにも慣れている人には手軽に比較動画を作ることができます。

新しい方法はこちらを参照。
ffmpeg で差分動画を作る

動画のエンコードには ffmpeg の libx264 を用い、音声をオリジナルのままにコピーしたり、2つの動画の音声を左右に分けることができます。動画内に比較した動画のIDやタイトルを入れる場合には AviUtl の拡張編集プラグインを使用してください。
使用する ffmpeg は Zeranoe FFmpeg - Builds より、OS に合わせて32-bit Builds (Static) か、64-bit Builds (Static) の (Latest) を保存する。

圧縮ファイルが 7z なので使用している解凍ソフトで解凍できない場合は、7-Zip を使う。解凍するとbinフォルダの中に ffmpeg と ffplay があるのでその2つを使う。

また2つの動画を並べるのに動画の横幅を知る必要があるので 真空波動研Lite を使う。

注意点


  • 横に並べる動画の場合は4:3の動画の比較に、縦に並べる場合は16:9の動画を使う
  • 違うアスペクト比の場合は横に並べたほうが見栄えがいいかもしれない
  • 異なる横幅の動画を横に並べる場合には大きい方の入力ファイルのフィルタのところに、小さい方の動画の横幅の値をscaleフィルタで指定する
    例:右の動画の音声を使い、同じアスペクト比の動画
    左の動画が640x480、右の動画が512x384の解像度の動画の場合
    ffmpeg -i left.mp4 -vf "[in] pad=2*iw:ih,scale=512:-1 [left];movie=right.mp4[right];[left][right] overlay=main_w/2:0,scale=2*iw/3:2*ih/3[out]"
  • 異なる横幅の動画を縦に並べる場合にはpadの値を別途変える
    Windowsのffmpegで生放送する方法 : pad を参照
  • overlay や scale、pad の値次第でエラーになる(色々な解像度を未検証)
  • 左右に配置する動画は left.mp4 が左の位置にある動画、right.mp4 が右の位置にある動画
  • 上下に配置する動画は up.mp4 が上の位置にある動画、down.mp4 が下に位置にある動画
  • 左右に音声を振る音声は left.mp4 が左の位置にある音声、right.mp4 が右の位置にある音声
  • 下のコマンドの ffmpeg を ffplay に変えるとプレビューして再生確認ができる
  • ffplay で再生するときは入力ファイル設定とフィルタ設定だけでエンコード設定と出力設定をしない


左右に配置する動画


  • 右の動画の音声を使い、同じアスペクト比の動画
    ffmpeg -i left.mp4 -vf "[in] pad=2*iw:ih [left];movie=right.mp4[right];[left][right] overlay=main_w/2:0,scale=2*iw/3:2*ih/3[out]"
  • 左の動画の音声を使い、同じアスペクト比の動画
    ffmpeg -i right.mp4 -vf "[in] pad=2*iw:ih:iw:0 [right];movie=left.mp4[left];[right][left] overlay,scale=2*iw/3:2*ih/3[out]"
  • 左の動画が4:3、右の動画が16:9で音声は左の動画
    ffmpeg -i left.mp4 -vf "[in] pad=2*iw:ih [left];movie=right.mp4[right];[left][right] overlay=W/2:(H-h)/2,scale=2*iw/3:2*ih/3[out]"
  • 左の動画が4:3、右の動画が16:9で音声は右の動画
    ffmpeg -i right.mp4 -vf "[in] pad=2*iw:384:iw:(384-ih)/2[right];movie=left.mp4[left];[right][left]overlay,scale=2*iw/3:2*ih/3[out]"
  • 左の動画が16:9、右の動画が4:3で音声は左の動画
    ffmpeg -i left.mp4 -vf "[in] pad=2*iw:384:0:(384-ih)/2 [left];movie=right.mp4[right];[left][right] overlay=W/2:(H-h)/2,scale=2*iw/3:2*ih/3[out]"
  • 左の動画が16:9、右の動画が4:3で音声は右の動画
    ffmpeg -i right.mp4 -vf "[in] pad=2*iw:ih:iw:0[right];movie=left.mp4[left];[right][left]overlay=0:(H-h)/2,scale=2*iw/3:2*ih/3[out]"


上下に配置する動画


  • 上の動画の音声を使い、同じアスペクト比の動画
    ffmpeg -i up.mp4 -vf "[in] pad=iw:2*ih [up];movie=down.mp4[down];[up][down] overlay=0:H/2,scale=-1:486[out]"
  • 下の動画の音声を使い、同じアスペクト比の動画
    ffmpeg -i down.mp4 -vf "[in] pad=iw:2*ih:0:ih [down];movie=up.mp4[up];[down][up] overlay=0:0,scale=-1:486[out]"
  • 上の動画が4:3、下の動画(横幅288px)が16:9で音声は上の動画
    ffmpeg -i up.mp4 -vf "[in] pad=iw:ih+288 [up];movie=down.mp4[down];[up][down] overlay=0:384,scale=-1:486[out]"
  • 上の動画(横幅384px)が4:3、下の動画が16:9で音声は下の動画
    ffmpeg -i down.mp4 -vf "[in] pad=iw:ih+384:00:384 [down];movie=up.mp4[up];[down][up] overlay,scale=-1:486[out]"
  • 下の動画が4:3、上の動画(横幅384px)が16:9で音声は上の動画
    ffmpeg -i up.mp4 -vf "[in] pad=iw:ih+384 [up];movie=down.mp4[down];[up][down] overlay=0:288,scale=-1:486[out]"
  • 下の動画が4:3、上の動画(横幅288px)が16:9で音声は下の動画
    ffmpeg -i down.mp4 -vf "[in] pad=iw:ih+288:00:288 [down];movie=up.mp4[up];[down][up] overlay,scale=-1:486[out]"

    ここまでの ffmpeg を ffplay に変えると再生確認ができる。


ffmpeg に慣れている人向け stack を使う方が処理が早い


左右に配置する動画
ffmpeg -i left.mp4 -i right.mp4 -filter_complex hstack

時間指定して並べる場合
ffmpeg -ss 10 -i left.mp4 -t 10 -ss 20 -i right.mp4 -t 10 -filter_complex hstack

フレーム指定で並べる場合(音声も時間通りにカットする場合は atrim も併用する)
ffmpeg -i left.mp4 -i right.mp4 -filter_complex [0:0]trim=start_frame=100:end_frame=300,setpts=PTS-STARTPTS[l];[1:0]trim=start_frame=100:end_frame=300,setpts=PTS-STARTPTS[r];[l][r]hstack -an

3つの映像を使い、1つは黒枠を追加する場合
pad で余白をつけるのと nullsrc を連結する場合では pad を使った方が早い
ffmpeg -i tleft.mp4 -i tright.mp4 -i bleft.mp4 -filter_complex [0:0][1:0]hstack[top];[2:0]pad=2*iw:ih:0:0[bot];[top][bot]vstack

Windows の ffmpeg で生放送する方法 : スタック(映像を並べる)
trim フィルタの使い方

動画のエンコード設定


上のコマンドではエンコード設定をしていないので、更に上のコマンドの後ろにエンコード設定を足す。

ニコニコの投稿でよく用いられる2passエンコードではなく crf(品質指定) の1passでエンコードする。
crf は元映像からどれだけの品質で出力するかの設定だが、出力される動画のビットレートは元映像によるので容量制限を超えてしまう可能性が出てくる。その制限を超えないためにビットレートを調整するのが maxrate と bufsize である。容量が気になる場合はまず最初に crf と軽い preset を設定して一度テスト出力し、大体のビットレートが分かったらエンコード設定を見直して最終出力とする。

preset の x264 で見た場合のエンコード設定

  • ultrafast:
    --no-8x8dct --aq-mode 0 --b-adapt 0
    --bframes 0 --no-cabac --no-deblock
    --no-mbtree --me dia --no-mixed-refs
    --partitions none --rc-lookahead 0 --ref 1
    --scenecut 0 --subme 0 --trellis 0
    --no-weightb --weightp 0
  • superfast:
    --no-mbtree --me dia --no-mixed-refs
    --partitions i8x8,i4x4 --rc-lookahead 0
    --ref 1 --subme 1 --trellis 0 --weightp 1
  • veryfast:
    --no-mixed-refs --rc-lookahead 10
    --ref 1 --subme 2 --trellis 0 --weightp 1
  • faster:
    --no-mixed-refs --rc-lookahead 20
    --ref 2 --subme 4 --weightp 1
  • fast:
    --rc-lookahead 30 --ref 2 --subme 6
    --weightp 1
  • medium:
    Default settings apply.
  • slow:
    --b-adapt 2 --direct auto --me umh
    --rc-lookahead 50 --ref 5 --subme 8
  • slower:
    --b-adapt 2 --direct auto --me umh
    --partitions all --rc-lookahead 60
    --ref 8 --subme 9 --trellis 2



エンコードの基本設定
-sws_flags accurate_rnd+lanczos -x264-params colormatrix=smpte170m -vcodec libx264 -preset slow -crf 23 -g 240 -qmax 51 -qmin 10 -keyint_min 0 -bufsize 1800k -maxrate 800k -acodec copy hoge.mp4

-g が keyint, -keyint_min 0 で fps の値指定
-maxrate が平均ビットレート,-bufsize が最大ビットレート
ただし crf で高品質(値を小さくする)すればするほど平均ビットレートが maxrate の値に近づきビットレートの変動幅が小さくなる。

右の動画の音声を使い、同じアスペクト比の動画を例に出力する場合は
ffmpeg -i left.mp4 -vf "[in] pad=2*iw:ih [left];movie=right.mp4[right];[left][right] overlay=main_w/2:0,scale=2*iw/3:2*ih/3[out]" -sws_flags accurate_rnd+lanczos -x264-params colormatrix=smpte170m -vcodec libx264 -preset slow -crf 23 -g 240 -qmax 51 -qmin 10 -keyint_min 0 -bufsize 1800k -maxrate 800k -acodec copy hoge.mp4

libx264 の設定は x264 と指定オプションが少し異なるので Windowsのffmpegで生放送する方法 : libx264 の設定 を参照

音声を左右別々の動画にする


音声は上のコマンドだと一つの動画の音声だが、これを2つの動画の音声を合わせて、片方の動画の音声を左だけに、もう片方の動画の音声を右だけにすることもできる。しかし映像と音声(必ず再エンコードされる)を同時出力する場合には上で書いたコマンドがごっそり変わってしまう(filter_complex を使う)。

標準の ffmpeg の音声エンコーダーは品質が良くないので音声は2つの音声を合成し hoge.wav で出力して別途 Nero や qaac(Apple QuickTime の AACエンコーダー) でエンコードして mux する方法を取る。

各ステレオの音声 left.mp4 が左 right.mp4 を右に配置して音声合成
ffmpeg -f lavfi -i "amovie="left",pan=stereo|c0=c0+c1[a1]; amovie="right",pan=stereo|c1=c0+c1[a2];[a1][a2] amix" hoge.wav

こちらの方法でも音声を左右別々の動画の音声にすることができる
注: -filter_complex を使うと ffplay で再生できない

各ステレオの音声 left.mp4 を左、right.mp4 を右に配置して音声合成
ffmpeg -i left.mp4 -i right.mp4 -filter_complex "[0:0]pan=stereo|c0=c0+c1[a];[1:0]pan=stereo|c1=c0+c1[b];[a][b]amix" hoge.wav

音声のサンプリング周波数が異なる場合は aresample=44100 などを付けて大きい方を小さい方に合わせる
ffmpeg -i left.mp4 -i right.mp4 -filter_complex "[0:0]aresample=44100,pan=stereo|c0=c0+c1[a];[1:0]aresample=44100,pan=stereo|c1=c0+c1[b];[a][b]amix" hoge.wav

入力するファイルが音声ではなく、動画(映像と音声)の場合は [0:0],[1:0] を [0:1],[1:1] に変える。
ffmpeg -i left.mp4 -i right.mp4 -filter_complex "[0:1]pan=stereo|c0=c0+c1[a];[1:1]pan=stereo|c1=c0+c1[b];[a][b]amix" -vn hoge.wav

[0:0] などの map の指定方法は 【ffmpeg】 マルチトラックの動画の作り方 を参照。

参考記事


追記 2015/09/02
aconvert が使えなくなっていた部分を削除した。

音声をエンコードする


音声エンコーダーは Nero よりも qaac のほうが高音質らしいのでできればそちらを使う。

  • qaac を使うには QuickTime で 7.7.1 以降のバージョンか、iTunes で 10.5 以降のバージョンのどちらかをインストールする必要がある。
    Apple - iTunes - Download iTunes Now
    現時点で最新版の qaac_1.39.zip をダウンロードする。
    cabinet - qaac

    qaac はコマンドラインから起動するツールなので以下のようにコマンドを記述する


    qaac -a 96k -o out.m4a input.wav
    qaac -V 100 -q 1 --threading -o out.m4a input.wav
    qaac -v 30 --he --threading -o out.m4a input.wav
    qaac -V 100 -q 1 --threading --concat -o out.m4a input1.wav input2.wav


    コマンドの詳しい設定は -h より抜粋

    -a, --abr AAC ABR mode / bitrate
    -V, --tvbr AAC True VBR mode / quality [0-127]
    -v, --cvbr AAC Constrained VBR mode / bitrate
    -c, --cbr AAC CBR mode / bitrate
    For -a, -v, -c, "0" as bitrate means "highest".
    Highest bitrate available is automatically chosen.
    For LC, default is -V90
    For HE, default is -v0
    --he HE AAC mode (TVBR is not available)
    -q, --quality AAC encoding Quality [0-2]
    --threading Enable multi-threading
    -o Output filename
    --concat Encode whole inputs into single file.
    Requires output filename (with -o)


    -q の設定で 0 は高速高ビットレート、2 が規定値、1 はその中間
  • Nero を使う場合は手軽に使える「えこでこツール」を利用する

    Nero - Download the Nero AAC Codec
    えこでこツール Wiki - SourceForge.JP

そして出力した音声と、上で出力した動画を yamb(mp4box のフロントエンド) で mux してニコニコにアップできる mp4 にする。

MP4box を各サイトからダウンロードする

各フィルタは以下の記事を参照
関連記事

コメント

非公開コメント

プロフィール

ロベルト

お問い合わせはこちらまで
robelt2525[at]gmail.com

中の人 @nico_lab

広告リンク
Amazon
楽天市場

ブログ更新用 @blo_nico_lab

詳しいプロフィールはこちら

当ブログは、Amazonアソシエイトに参加しています。