読者です 読者をやめる 読者になる 読者になる

リズムのじかん

javascript、typescriptなど中心に書きます。

YouTube動画からコード譜を自動生成する

はじめに

最終的にこんなものが出来上がります。

f:id:chords:20160801003325p:plain

http://chordkitchen.net/sheet/B1-Bh-RNNS

処理フロー

f:id:chords:20160719000834p:plain

処理①:動画のダウンロード→音声ファイル抽出→正規化

動画のダウンロードと音声ファイル抽出

まずyoutube-dlを使用して、YouTubeから動画をダウンロードし、音声ファイルを抽出します。

github.com

以下を実行すると、EnxTRrBzkcQ.m4aが生成されます。

youtube-dl --extract-audio --audio-format m4a -o /tmp/EnxTRrBzkcQ.%(ext)s https://www.youtube.com/watch?v=EnxTRrBzkcQ --verbose

今回は音声ファイルのみ必要なので、--extract-audioオプションを使用して音声のみ抽出します。

音声の抽出には、youtube-dlから内部的にffmpegが呼ばれます。

音声ファイル正規化

この作業は必須ではないのですが、システムの簡易化と高速化のために、音声ファイルを正規化します。

やることは、

  • サンプリング周波数を44.1kHzに揃える(後続処理の条件を揃えることでシステムを簡易化)
  • wavに変換する(wavだと後続のツールの処理が速い)

この処理にはffmpegを使用しました。

ffmpeg -y -i EnxTRrBzkcQ.m4a -ar 44100 -acodec pcm_s16le EnxTRrBzkcQ.wav

処理②:コード解析

次にSonic Annotatorを使用して、音声ファイルのコードを解析します。

www.vamp-plugins.org

Sonic Annotatorの使い方

Sonic Annotatorは、ロンドン大学クイーン・メアリー (Queen Mary University of London)によって開発された、音声ファイルから特徴抽出・注釈付けを行うツールです。

インストールするには、Downloads - Sonic Annotator - Sound Software .ac.ukからバイナリをダウンロードするか、ソースからビルドしてください。

Sonic Annotatorインストールしただけでは、できることは限られており、コード解析などを行うにはVamp Pluginsを利用します。

今回は以下の2つのプラグインをインストールします。(インストール方法はhttp://www.vamp-plugins.org/download.html#installを参照)

sonic-annotator -lを実行すると、現在使用できるプラグインが一覧表示されます。

$ sonic-annotator -l
vamp:beatroot-vamp:beatroot:beats
vamp:nnls-chroma:chordino:simplechord
vamp:nnls-chroma:chordino:harmonicchange
vamp:nnls-chroma:chordino:loglikelihood
vamp:nnls-chroma:chordino:chordnotes

Sonic Annotatorでコード解析

今回はYouTubeから抽出した音声ファイルに対し、コード解析と拍抽出を実行し、最終的にコードをYouTubeの再生時間にマッピングします。

実行するコマンドは以下です。

# 拍抽出
sonic-annotator -t beatroot.txt /tmp/EnxTRrBzkcQ.wav -w csv --csv-omit-filename --csv-force

# コード解析
sonic-annotator -t simplechord.txt /tmp/EnxTRrBzkcQ.wav -w csv --csv-omit-filename --csv-force

beatroot.txtの中身は以下のようになります。

@prefix xsd:      <http://www.w3.org/2001/XMLSchema#> .
@prefix vamp:     <http://purl.org/ontology/vamp/> .
@prefix :         <#> .

:transform_plugin a vamp:Plugin ;
    vamp:identifier "beatroot" .

:transform_library a vamp:PluginLibrary ;
    vamp:identifier "beatroot-vamp" ;
    vamp:available_plugin :transform_plugin .

:transform a vamp:Transform ;
    vamp:plugin :transform_plugin ;
    vamp:step_size "441"^^xsd:int ; 
    vamp:block_size "2048"^^xsd:int ; 
    vamp:plugin_version """1""" ; 
    vamp:parameter_binding [
        vamp:parameter [ vamp:identifier "expiryTime" ] ;
        vamp:value "10"^^xsd:float ;
    ] ;
    vamp:parameter_binding [
        vamp:parameter [ vamp:identifier "maxChange" ] ;
        vamp:value "0.2"^^xsd:float ;
    ] ;
    vamp:parameter_binding [
        vamp:parameter [ vamp:identifier "postMarginFactor" ] ;
        vamp:value "0.3"^^xsd:float ;
    ] ;
    vamp:parameter_binding [
        vamp:parameter [ vamp:identifier "preMarginFactor" ] ;
        vamp:value "0.15"^^xsd:float ;
    ] ;
    vamp:output [ vamp:identifier "beats" ] .

これはsonic-annotator -s vamp:beatroot-vamp:beatroot:beats > beatroot.txtを実行するとスケルトンファイルができるので、それを必要に応じて変更したものになります。

Sonic Annotatorの実行結果

実行結果は標準出力されます。

拍抽出 => 拍の位置のtimeが返される

sonic-annotator -t beatroot.txt /tmp/EnxTRrBzkcQ.wav -w csv --csv-omit-filename --csv-force
0.130000000
0.840000000
1.166666667
1.493333333
1.820000000
2.146666667
2.473333333
2.800000000
3.126666667
3.453333333
3.780000000
...(以下省略)

コード解析 => timeとコードが返される

sonic-annotator -t simplechord.txt /tmp/EnxTRrBzkcQ.wav -w csv --csv-omit-filename --csv-force
0.000000000,"N"
6.826666666,"Em"
12.817414965,"G"
17.322086167,"G6"
21.873197278,"Cmaj7"
22.894875283,"G"
28.003265306,"G6"
30.928979591,"Bmaj7"
31.857777777,"C"
33.808253968,"Ebm"
34.411972789,"Emaj7"
36.037369614,"G6"
...(以下省略)

処理③:譜面化

Sonic Annotatorの出力結果から、拍の位置(time)とコードの位置(time)が取得できるので、svgとかで頑張って譜面化します。

さいごに

約1年前に書いた記事の続編でした。

u0u0.net

わかりやすい曲はそれなりの精度でコード譜が自動生成できますが、難しい曲はまだ手修正が必要です。

拍の位置と何拍目かの精度が上がれば、もっと品質の良い譜面ができそうな気がします。LSTMとか使って上手くできないかな。。。

いい方法があれば教えて下さい(・∀・)