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

ごちゃログぴこっ

はなまるデジタル創作紀行(DTM、TAS、いろいろな技術)

各種MIDI2MMLプログラムを比較してみた

このたび、ごちゃと loveemu さんで PetiteMM という変換ツールを発表しました。開発に着手する前「既に優れたツールがあれば開発する必要はないのでは?」と思ったのですが、いくつか探して試した限りでは納得行くものが見つかりませんでした。

そんなわけで、この記事ではサンプルファイル mmldec.mid を各種MIDIコンバータにかけて難癖をつけながら、PetiteMM のステマを行っていきたいと思います。

PetiteMM (2013-09-02)

t128r1
/* 最も変換しやすそうな旋律(ベタ打ち) */
o5c8d8e8f8g4a8f8
e8r8d8r8c4.r8
/* Gate ×0.85 */
c16.r32d16.r32e16.r32f16.r32g8..r32a16.r32f16.r32
e16.r8r32d16.r8r32c3r6
/* Gate -4 */
c16.r32d16.r32e16.r32f16.r32g8..r32a16.r32f16.r32
e16.r8r32d16.r8r32c4.r8
/* 途中で長い休符を挟む */
g8.f16e16r16g16r1
r1
r1
r16
f16r16e16r16d8.r16
/* ベロシティ変更 */
g8.f16e16r16g16r16f16r16e16r16d8.r16
d1
/* 三連符、クオンタイズ変更、休符も入れる */
c6d6e6f16r48g16r48a16r48f16r12r48f16r48
/* 長い音符 */
e16e16e16e16d16r16d16r16c1&c1&c4
r4
/* 拍子変更(試しに小節の区切りをまたぐ) */
c8d8e8f8g8a4
f8e16.r32e16.r32d16.r32d16.r32
c2r4
/* 4分音符±1tick */
c4r4c4r4
/* 付点4分音符±1tick */
e4.r8e4.r8
/* 複付点4分音符±1tick */
g4..r16g4..r16
/* クオンタイズを伴う「中途半端なトラック終了」 */
c16d16e16f16g8a16f16e24r12d24r12c48&c64

変換結果を再生できるようにニコニコ大百科にも置きました。タイを ^ から & に置換してコメントを記入しましたが、それ以外はデフォルト設定で変換した通りの出力です。

クオンタイズのための r32 が少々邪魔に感じられますが、精度を16分音符単位に落とせば取り除くことも可能です。

  • MMLの内容のシンプルさを追求しつつ、クオンタイズを極力損なわないよう休符を挿入します。
    • シンプルさを犠牲にしてタイミングを正確に出力できるオプションも備えています。
  • 仕組み上、連符や短い音符によってトラック間でずれが広がっていくようなことは絶対に起こりません。
  • 細かすぎる音符や付点の数を制御する仕組みがあり、ターゲットの制約に合わせた変換が可能です。
  • SMFフォーマット1で単一チャンネルの演奏を複数トラックに分けている場合、個別トラックで出力します。
  • 拍子情報にもとづいて、小節ごとに改行します。(ただしタイでつながっている音符は改行しない*1
  • tick単位による出力 c%24 などは一切出現しません。
  • 和音のあるトラックは単音のみが変換されます。

改善できそうな点もありますが、なかなか良さそうではないでしょうか! (*>ヮ<*)

開発着手時は「きっと既存のツールだって同等以上の性能があるだろう」と思って探したのですが……。

TinyMM

PetiteMM が誕生するきっかけになったツールです。

{ Ch 01 ===================================== }
r1
c8d8e8f8g4a8f8
e8r8d8r8c4^8r8
c16^32r32d16^32r32e16^32r32f16^32r32g8^16^32r32a16^32r32f16^32r32
e16^32r8^32d16^32r8^32c4^16r8^16
c16^32r32d16^32r32e16^32r32f16^32r32g8^16^32r32a16^32r32f16^32r32
e16^32r8^32d16^32r8^32c4^16^32r8^32
g8^16f16e16r16g16r1^1^1^16
f16r16e16r16d8^16r16
g8^16f16e16r16g16r16f16r16e16r16d8^16r16
d1
c8^32d8^16e8^32f16r32g32r32a16r32f16r16^32f16r32
e16e16e16e16d16r16d16r16c1^1^4
r4
c8d8e8f8g8a4f8
e16^32r32e16^32r32d16^32r32d16^32r32c2
r4c4r4c4
r4e4^8r8e4^8
r8g4^8^16r16g4^8^16
r16c16d16e16f16g8a16f16e32r16^32d32r16^32
c32;
  • MMLの内容はシンプルですが、精度や表現にやや難があります。
    • 付点出力なし、休符をタイでつなぐ、連符対応なし(よくトラック間でタイミングずれが起きます)
  • 小節ごとに改行するようですが、曲の途中の拍子変更には対応できていないようです。
  • 和音のあるトラックは単音のみが変換されます。

ノートの長さを「32分音符n個分」に換算して変換していそうです。

テキスト音楽「サクラ」 ver.2.375

MMLMIDIを作成する有名なツールです。

r1 v100q100o5l8c d e f l4g l8a f l4e d q75l2c q83l8c 
d e f l4g l8a f l4e d q63l2c q83l8c d e f q91l4g 
q83l8a f l4e d q70l2c q100l8.g l16f l8e l1^1^1^8g 
r1^1^1^16 l8f e q75l4d v-50l8.g q100l16f l8e 
g f e q75l4d v+50q100l1d l8^24c d e q62l12f g 
a l8^24f l12f q100l16e e e e l8d d q90l1^1^2c q100l8c 
d e f g l4a l8f q75e e d d q66l2.c q48l2c 
q51c q73e q76e q86g q88g q100l16c d e f l8g l16a 
f q29l8e d c%7

上記の変換結果は抜粋です。ターゲットがMIDIファイルなので、メタデータやコントロールチェンジに関しても出力されます。

基本的には音符と音符の距離を測り、距離に対する発音の長さからクオンタイズを出力しています。この方式では、数小節にわたる長い休符が入ったときのデュレーションの精度はあまり良くなさそうです。

  • MMLの内容はシンプルですが、精度や表現にやや難があります(上述)。
    • 連符を等分して出力できるようですが、長さ表現が冗長です。(l8^24 → l6)
    • 半端な長さについてはtick単位の指定が適用される? (MML末尾のc%7)
  • コントロールチェンジ等のノート以外の情報もある程度出力します。
  • 一定の間隔で改行するようです(小節単位ではない?)
  • 和音も変換されます(精度は確認していない)

和音が出力できるのはすごいですね。

SMF2MML 1.03

同じくサクラ向けのツールです。出力するイベントの種類や改行タイミングなど細かく指定できます。今回はノートのみ出力する設定で変換しました。下記は主要な出力の抜粋です。

q100 h-1
r1
v100o5c8d8e8f8g4a8f8
e8r8d8r8c4.r8
c%20r48d%20r48e%20r48f%20r48g%40r24a%20r48f%20r48

e%20r12..d%20r12..c%61r%35
c%20r48d%20r48e%20r48f%20r48g%44r48a%20r48f%20r48
e%20r12..d%20r12..c%68r12..
g8.f16e16r16g16r%108

^1
^1
^2f16r16e16r16d8.r16
v50g8.f16e16r16g16r16f16r16e16r16d8.r16

v100d1
c6d6e6f%10r32g%10r32a%10r32f%10r%22f%10r32
e16e16e16e16d16r16d16r16c2
^1

^2.r4
c8d8e8f8g8a4f8
e16.r32e16.r32d16.r32d16.r32c2
r4c%47r%49c4

^192r%47e%71r%25e4
^%25r%23g%83r%13g4
^%37r%11c16d16e16f16g8a16f16e48..r%17d48..r%17
c48..

c6d6e6 の連符が理想的に変換されています。ノートの長さを分解能に照らし合わせて変換しているようで、演奏情報を正確に反映していそうです。

情報のロスがない反面、tick表記が目立ちます。クオンタイズの概念がないため、ベタベタに打ち込んだノート以外は半端な長さの音符と認識されるためです。最初から変換用に作成したデータであれば良質な結果が期待できますが、そうでないデータはtick表記だらけにならざるを得ません。

  • MMLの演奏精度は良いですが、クオンタイズを伴うデータではtick表記だらけになります。
    • 変換用に調整されたデータであれば、結構良い結果が期待できるのではないでしょうか?
  • コントロールチェンジ等のノート以外の情報もある程度出力します。
  • 小節ごとに改行するようですが、曲の途中の拍子変更には対応できていないようです。 小節ごとに改行を行います。が、メタイベントをマスクすると拍子変更への対応は効かなくなる様子?
  • 和音も変換されます(精度は確認していないが、サクラ本体の出力より読みやすく思えた)

mid2mml for ppmck Ver1.0β

ppmckはファミコン音楽作成環境です。こちらはそのppmck向けの変換ツール。

// mid2mml for ppmck Ver1.0β by ZEX
//  mid2mml mmldec /c:GHIJKLABCPQRSTUVWXYZabMNO
#TITLE		mmldec
#COMPOSER	
#MAKER		
#PROGRAMER	mid2mml for ppmck Ver1.0β & gocha
#AUTO-BANKSWITCH 0
#PITCH-CORRECTION
#EX-VRC7
@OP0	={$11,$11,$8F,$4A,$C1,$F2,$33,$21}			// Ch.G			PrgNo.1	Acoustic Piano
@MP0	={29,2,1,0}									// Ch.G			PrgNo.1	Acoustic Piano
@v0 	={4}					// Ch.G Vol.4	PrgNo.0	Acoustic Piano
@v1 	={9}					// Ch.G Vol.9	PrgNo.0	Acoustic Piano

G	t128
G l8	o4	@v1 	@@0OP0MP0

G cdefg4af
G erdrc4.r
G c16.^128r64.d16.^128r64.e16.^128r64.f16.^128r64.g.^64^128r32^128a16.^128r64.f16.^128r64.
G e16.^128r^64^128d16.^128r^64^128c4^16^128r^32^64^128
G c16.^128r64.d16.^128r64.e16.^128r64.f16.^128r64.g..^128r64.a16.^128r64.f16.^128r64.
G e16.^128r^64^128d16.^128r^64^128c4^16^32^128r^64^128
G g.f16e16r16g16r2^16
G r1
G r1
G r2f16r16e16r16d.r16
G @v0g.f16e16r16g16r16f16r16e16r16d.r16
G @v1d1
G c^32^128d^32^64e^32^128f32..r32g32.r32a32..r32f32..r16..f32..r32
G e16e16e16e16d16r16d16r16c2&
G c1&
G c2.r4
G cdefga&
G afe16.r32e16.r32d16.r32d16.r32
G c2r4
G c....r4^128c4^128r....
G e4^16^32^64^128r^128e4.^128r16...
G g4.^32^64^128r16^128g4..^128r32..
G c16d16e16f16ga16f16e32^128r16^64^128d32^128r16^64^128c32^128

128分音符単位に整列するタイプのようなので、連符が変換できません。クオンタイズ込みの箇所はやはり表現が複雑になりがちです。

  • MMLの内容はシンプルですが、連符には対応しておらず、クオンタイズのある音符はやや複雑に表現されます。
  • ppmck向けの音色情報を出力します。(特化したツールならではの良さ!)
  • 拍子情報にもとづいて、小節ごとに改行します。
  • 頭の休符を取り除けちゃうみたいです。わぁい親切~♪
  • 和音は複数トラックに分割されて変換されます。

意外と多くのツールが和音に対応しているのが驚きです。

Midi2MabiML ver1.0

マビノギ向けのツールらしいです。変換結果の改行はすべて手作業で挿入しました。

O5L8
R1
CDEFG4AF
ER8DR8C4.R8
CDEFG4AF
ER8DR8C4.R8
CDEFG4AF
ER8DR8C4.R8
G.F16E16R16G16R1
R1
R1
R16F16R16E16R16D.R16
G.F16E16R16G16R16F16R16E16R16D.R16
D1
C.R8R64E.R16G16R64A16R64F16R16R32F16R64
E16E16E16E16D16R16D16R16C1&C1&C4R4
CDEFGA4
FE16.R32E16.R32D16.R32D16.R32C2R4
C4R4C4.R8
E4.R8R2
R2R2
C16D16E16F16GA16F16E32.R16D32.R16C32.

MMLを見ると64分休符があるのに、クオンタイズのせいで休符まみれになることもなく、それでいて適度に休符が挿入されています。

ただ、連符用の例外処理があるにもかかわらず連符が変換できないうえ、終盤の四分音符が休符にされてしまいました。

T7ES: MIDIMML converter

Windows 7 (64bit) で動作を試みたところ、凶悪なフリーズが発生して再起動を余儀なくされました。

mid2mml for ppmck に似た感じだと思いますが、変換動作の良し悪しはわかりません。

mid2flmmlsmf2mml.py

どちらも Python スクリプトで動作未確認ですが、上述の他のコンバータが抱える問題を少なからず抱えていそうです。

あずねっと MIDI->P/ECE用MMLコンバータ MID2MML

入手不可だったのですが、人づてに入手できました。再配布可とのことなので置いておきます。

A T128V120@0Ll8
A r1
A o4cdefg4af
A erdrc4&cr
A cdefg4af
A erdrc4&c16&c32rr32
A cdefg4af
A erdrc4&cr
A g&g16f16e16r16g16r2r16
A r1
A r1
A r2f16r16e16r16d&d16r16
A g&g16f16e16r16g16r16f16r16e16r16d&d16r16
A d1
A c&c32&c32d&d32e&e32f16r32g32&g32r32a32r32f16rf32r32
A e16e16e16e16d16r16d16r16c2&
A c1&c2&c4r4
A cdefga&
A afe16&e32r32e16&e32r32d16&d32r32d16&d32r32
A c2r4
A c4r4c4&c32r4
A e4&e16&e32re2
A g2g2
A c16d16e16f16ga16f16e32&e32r16d32&d32r16c32&c32

32分音符に整列するタイプらしく3連符は出力できません。付点がないのも特徴的です。結構綺麗なのですが、終盤の c4 と e4 の箇所で32分音符の間延びが起きているのが気になります。タイミングのずれがかさんでいく可能性が考えられるのではないでしょうか。

  • MMLの内容はシンプルですが、連符には対応していません。
  • 拍子情報にもとづいて、小節ごとに改行します。(単一ノートで表現できる箇所も、小節の境目であれば複数に分けるようです)
  • 細かなタイミングずれが発生しているように見えます。

総評

多くのツールが、下記のいずれかの問題を抱えています。

  • 連符を正しく簡潔に出力できない。
  • クオンタイズのある音符が求める以上に複雑に表現されてしまう(tick表記を伴う場合も)。
  • その他、クオンタイズの再現精度が低かったり、不可解なノートの消失が起きたりする。

PetiteMM はこれらの問題を解消し、シンプルかつ質の高いMMLを生成することを目標に作られました。目的によってベストなツールは異なるかもしれませんが、ぜひ新しい選択肢として覚えて頂ければと思います。

より良い変換ツールの紹介や、PetiteMM のご意見・ご感想などがありましたら、ぜひコメント欄か @gochaism 宛にお願いします。ハッシュタグ #PetiteMM の付いたひとりごとなども歓迎です。

PetiteMM の技術的アプローチなど、正式なリリース情報は関心を寄せてくださる皆様がいっぱい褒めて紹介してくれて、あわよくば10万ドルPON☆とくれたりしたら公開したいと思います!*2 (*>ヮ<)/

→書きました。MIDI(SMF)→MML変換ツール「PetiteMM」の紹介・アルゴリズム

*1:タイで改行しないのは特別に意図があってそうしたわけでもないです。半ば開発上の経緯的な問題です。

*2:褒められたら公開というのは冗談ですが、ポジティブなフィードバックをもらえると嬉しくてモチベーションが上がります。