実行環境
Node.jsでの実行を想定しているためJavaScriptコードになります。
コマンドラインで同様のコマンドを打てばNode.js以外でも実行可能です。
画面の分割と複数動画の合成
画面を4分割して、左上、右上、左下に動画を合成した場合の例です。
const { execSync } = require('child_process');
function overlay(input1, input2, input3, output)
{
const stdout = execSync(`ffprobe -i ${input1} -show_streams -print_format json`);
let streamInfo = JSON.parse(stdout);
// 幅、高さを取得
let width = streamInfo.streams[0].coded_width;
let height = streamInfo.streams[0].coded_height;
// 4分割後の幅、高さを計算
let cutWidth = width/2;
let cutHeight = height/2;
// コマンド生成
command = `ffmpeg -i ${input1} -i ${input2} -i ${input3} -filter_complex "\
amix=inputs=3:duration=longest;\
[0:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [upperleft];\
[1:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [upperright];\
[2:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [lowerleft];\
[upperleft]pad=2*iw:2*ih[a];\
[a][upperright]overlay=w:0[b];\
[b][lowerleft]overlay=0:h\
" \
${output}`;
// コマンド実行
execSync(command);
}
コマンド内容
関数前半は、input1のストリーム情報から幅、高さを取得し、4分割後の各動画の幅、高さを計算しています。
Audio
amix=inputs=3:duration=longest;はaudioの合成になります。
amix=inputs=3:duration=longest;を省いた場合は、左上の動画音声のみになります。
Video
[0:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [upperleft];部分は、
[0:v]:input1のVideoを表しています。
scale=${cutWidth}x${cutHeight}:スケール変更しています。
[upperleft]:upperleftという名前で定義しています。名前なので任意に変更可能。
[1:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [upperright];、
[2:v] setpts=PTS-STARTPTS, scale=${cutWidth}x${cutHeight} [lowerleft];
はinput2、input3に同様の処理を行っています。
[upperleft]pad=2*iw:2*ih[a];
は[upperleft]映像に余白を追加しています。
iwはinput Widthを、ihはinput heightを意味しており、幅、高さ2倍の余白を追加しています。
またそれを[a]という名前で定義しています。
[a][upperright]overlay=w:0[b];
は[a]に[upperright]を横方向座標w([upperright]の幅)、縦方向座標0の位置に合成しています。
またそれを[b]という名前で定義しています。
[b][lowerleft]overlay=0:h
は[b]に[lowerleft]を横方向座標0、縦方向座標h([lowerleft]の高さ)の位置に合成しています。
注意事項
最後のオプション[b][lowerleft]overlay=0:hには;を付けるとエラー(No such filter: '')になります。
