Web MIDI APIでシンセサイザーの入力を受け取ってみた

  • 1
    いいね
  • 0
    コメント

はじめに

この記事は SLP_KBITその2 Advent Calendar 2016 の24日目の記事です。

最近Web MIDI APIなるものを知りました。
これを使うとMIDIに対応しているデバイスをPCに接続するだけで、JavascriptでMIDIの入出力が行えるそうです。なにそれすごい。
そんなわけで早速シンセサイザーを使ってMIDIの入力を受け取ってみます。

MIDIについて

MIDIは電子楽器の演奏データを通信するための規格です。
演奏情報の音を、音の高さ(ノート)、音の強さ(ベロシティ)、音の長さ(デュレーション)表現するそうです。
詳しいことはWebAudio Web MIDI API Advent Calendar 201618日目の記事が参考になりました。

MIDIプロトコル

MIDIのプロトコルで扱うデータとして、音のON/OFF、使用するチャンネル、音の強弱、音程の変化があります
WikipediaでMIDIを調べたところ他にもいろいろなデータを送信しているようですが、これらのデータがあれば最低限演奏に必要なものは揃っています。

MIDIデバイスを繋げる(物理)

今回はJUNO-Giというシンセサイザーを使用します。
このシンセサイザーをUSBケーブルでPCに接続します。
写真 2016-12-25 0 52 34.jpg

使用できるMIDIデバイスを表示する

htmlはこんな感じです。

index.html
<html>
  <head>
    <meta charset="UTF-8" />
    <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
    <script type="text/javascript" src="sample.js"></script>
    <title>Web MIDI API</title>
  </head>
  <body>
    <label>入力デバイス</label>
    <ul id="input">
    </ul>

    <label>出力デバイス</label>
    <ul id="output">
    </ul>

    <label id="data">00 00 00</label>
  </body>
</html>

MIDIの有効化

ブラウザでMIDIを有効にするには、requestMIDIAccess()を使用します。
また、引数にMIDIの有効が成功したときと失敗したときのコールバックを指定します。

navigator.requestMIDIAccess().then(successCallback,faildCallback);

MIDIデバイスの表示

成功時のコールバックで、入力のMIDIデバイスと出力のMIDIデバイスを配列で記録します。
また、記録時にリストで表示も行います。

sample.js
navigator.requestMIDIAccess().then(successCallback,faildCallback);

var midi = null;
var inputs = [];
var outputs = [];

// MIDI接続成功時
function successCallback(m){
  midi = m;
  // 入力MIDIデバイスの記録
  var it = midi.inputs.values();
  for(var o = it.next(); !o.done; o = it.next()){
    inputs.push(o.value);
    $("#input").append("<li>"+ o.value.name +"</li>");
  }

  // 出力MIDIデバイスの記録
  var ot = midi.outputs.values();
  for(var o = ot.next(); !o.done; o = ot.next()){
    outputs.push(o.value);
    $("#output").append("<li>"+ o.value.name +"</li>");
  }
}

// MIDI接続失敗時
function faildCallback(msg){
  console.log("[Error]:"+msg);
}

うまくいけば、ページ読み込み時に現在接続されているMIDIデバイスが表示されいるはずです。
今回はJUNO-Giというシンセサイザーを使用しているため、その名前が表示されます。

キャプチャ.JPG

MIDI入力の値を表示する

配列に記録している入力のMIDIデバイスに、入力が来たときの処理を登録します。

// 入力MIDIデバイスから入力が来たときの処理の登録
for(var cnt=0;cnt < inputs.length;cnt++){
  inputs[cnt].onmidimessage = onMIDIEvent;
}

今回は送られてきた信号をブラウザ上で表示させます。

//入力MIDIデバイスから入力が来たときの処理
function onMIDIEvent(e){
  var str = "";
  for(var i=0, out=[]; i<e.data.length; i++) {
    str = str + e.data[i].toString(16).substr(-2) + " ";
  }
  str = str;
  $("#data").text(str);
}

全体のコードは以下のようになります。

navigator.requestMIDIAccess().then(successCallback,faildCallback);

var midi = null;
var inputs = [];
var outputs = [];

// MIDI接続成功時
function successCallback(m){
  console.log("asd");
  midi = m;
  // 入力MIDIデバイスの記録
  var it = midi.inputs.values();
  for(var o = it.next(); !o.done; o = it.next()){
    inputs.push(o.value);
    $("#input").append("<li>"+ o.value.name +"</li>");
  }

  // 出力MIDIデバイスの記録
  var ot = midi.outputs.values();
  for(var o = ot.next(); !o.done; o = ot.next()){
    outputs.push(o.value);
    $("#output").append("<li>"+ o.value.name +"</li>");
  }

  // 入力MIDIデバイスから入力が来たときの処理の登録
  for(var cnt=0;cnt < inputs.length;cnt++){
    inputs[cnt].onmidimessage = onMIDIEvent;
  }
}

// MIDI接続失敗時
function faildCallback(msg){
  console.log("[Error]:"+msg);
}

//入力MIDIデバイスから入力が来たときの処理
function onMIDIEvent(e){
  var str = "";
  for(var i=0, out=[]; i<e.data.length; i++) {
    str = str + e.data[i].toString(16).substr(-2) + " ";
  }
  str = str;
  $("#data").text(str);
}

実行する

それでは実行してみます。
鍵盤を叩くたびに値が変わっているのがわかります。
写真 2016-12-25 1 25 57.gif

おわりに

今回はMIDIの入力を受け取るところまで行いました。
この調子で今度は音の出力や可視化を行っていこうと思います。

参考

Web MIDI API

MIDIデバイスの準備不要 !Web MIDI APIを使いこなそう!
JavaScriptだけでMIDIで遊べる!最高に乱暴なWeb MIDI API利用方法

MIDIの知識

Web MIDI APIを扱うためのMIDI基礎知識
MIDIが良く分かる。バンドマンのためのDTMの基礎知識

この投稿は SLP_KBITその2 Advent Calendar 201624日目の記事です。