Ubuntuでtsからmp4へ変換する設定 (2016年版)

2018年7月8日Linux・Ubuntu Tips, DTVLinux, DTV, Ubuntu, ffmpeg

driver-ffmpeg-teaser

tsをmp4にするのに、昔は莫大なことを行っていたのだが、今は非常にシンプルにしている。といっても、真面目な(つまり綺麗な)エンコードを行おうとすると、やはり20fpsが限界。とはいえ設定としては固まりつつあるので、ここでご紹介しよう。

やりたいこと

やりたいことはこんな感じだ。ちなみに、私は映画や海外ドラマを録画して、良かったものの保存用にこのエンコード方法を採用している。

  • aac音源はac3音源に変更する
  • 画質は極力落とさない
  • インタレースは綺麗に解除する
  • いらないCMはカット

うん。少ない。

そこでこんな感じになった。ただし、3770Kで行っているのでそんなにfpsが出てくれない(サイズを720pにリサイズすりゃいいんだろうが)。6700Kがちょっと欲しいこの頃。

なお、普段はバッチを組んでcronで回しているのだが、恥ずかしいので要素だけピックアップ。ちなみに、重要じゃない動画は自動的に下記でエンコードをしていて、自動的に重要だって見つけたものはフラグをつけて、そのフラグに従ってこっちの設定を使うようにしています。

UbuntuでQSVを利用したエンコードでtsをmp4に爆速変換
最近のIntel CPUに付属しているGPUでは、GPGPUを用いたエンコードが利用可能である。平たく言ってしまえばQSV、Quick Sync Video。Windowsでは

TsSplitterでいらない部分をカット

TsSplitterはwineでも動作するので、次のような形で余分な部分をそぎ落としている。

TsSplitter.exe -EIT -ECM -SD -1SEG -SEP2 -SEPA -OUT "/splitted/${BASENAME}" "${BASENAME}.m2ts"

{$BASENAME}.m2tsがもとのファイル。これをsplittedディレクトリに展開して、そこでTsSplitterを動作。

このあと、一番大きいファイルがTsSplitterで処理した後の本編であろうという推測のもと、そのファイル名を下記のような形で読み取っている。

SPLIT=ls -S "/splitted/${BASENAME}" | head -n 1

これで、/splitted/${SPLIT}はTsSplitter処理後のファイル。

CMカット

CMカットには、ComskipBatch.rbを使っている。作者さんのサイトで詳しい解説がしてあるので、そちらを参照していただきたい。

どうやら、映像を全部解析したのちに局ロゴ(ウォーターマーク)を解析、ウォーターマークのない部分を削除しているようだ。地デジで行われる映画なんかにもってこいである。

こいつは普通に、こんな感じで使っている。うまくいけばsucceedディレクトリに入る。

ruby ComskipBatch.rb --margin 3 --file "/splitted/${BASENAME}/${SPLIT}" --move_to "/succeed/" --failed_to "/failed/"

ffmpegでエンコード

その後ファイル有無や重複確認などいろいろはさんで、お待ちかねのエンコード。ffmpegを使用している(以前はHandBrakeだったけど乗り換えた)。最近のffmpegは音ズレもなしにaacをac3に変換してくれるし、インタレース解除も非常に綺麗になったし、良い感じに進化していますね。

プリセットは先人達の知恵を借りて、次のようなものを使っています。

codec=libx264
coder=1
level=4.0
crf=18
qmin=10
i_qfactor=0.71
bufsize=30M
maxrate=30M
g=250
keyint_min=25
sc_threshold=40
me_method=umh
me_range=16
subq=7
refs=6
bf=16
b_strategy=1
partitions=+i8x8+i4x4+p4x4+p8x8+b8x8
flags=+loop
deblock=0:0
cmp=chroma

そして肝心のffmpeg。新進気鋭のインタレース解除フィルター「bwdif」を使っています。

ffmpeg -y -vsync 1 -i "${BASENAME}.m2ts" -f mp4 -vcodec libx264 -fpre "h264.ffpreset" -filter:v bwdif -acodec ac3 -b:a 192k -threads 8 "${BASENAME}.mp4"

ちなみにこの設定で1080iの動画を処理すると……

frame=162718 <strong>fps=22</strong> q=26.0 size= 1968199kB time=00:45:14.74 bitrate=5939.2kbits/s dup=12387 drop=0 speed=0.359x

クソおせえ。cronでエンコードをしているのだが、映画なんかが大量に録画された日にはたまらん。うーむ……。