Arduinoから16ビットのデータをMIDIで転送し、Web MIDIで受信して表示するプログラムです。なかなか使う機会は無いかもしれません。16ビットデータ(下図のように、INT16と名前をつけておきます)の転送には、MIDIとしてはめったに使わないキープレッシャーのステータス(0xA0)を利用します。
転送フォーマットを下図を基に説明します。INT16をMMIDIで転送する方法です。MIDIは8ビット、3バイトのデータです。全部で24ビットのデータを転送することができます。INT16を3バイトに分けて送ります。ステータスの上位4ビットはステータスとして決まった値を送らないとなりません。またデータ1、データ2の最上位ビットはゼロでなければなりません。この条件を基に、16ビットを24ビットに下図のように割り振ります。
ステータスの上位4ビットは0xAを使います。それに続く2バイト(赤で示したxx)は、チャンネル番号とします。すなわち、この場合は4つのチャンネル(異なる種類)のデータを送ることができます。
Arduino側のプログラムを示します。
#include <usbmidi.h> // USB MIDIのライブラリをインクルードします。
// 16ビットのデータをチャンネル番号にキープレッシャーとして送信します。
void SendData16(unsigned int data, unsigned char channel)
{
unsigned char dataH;
unsigned char dataM;
unsigned char dataL;
dataL=(unsigned char)(data&0x7F);
dataM=(unsigned char)((data>>7)&0x7F);
dataH=(unsigned char)((data>>14)&0x03);
USBMIDI.write(0xA0+(channel<<2)+dataH);
USBMIDI.write(dataM);
USBMIDI.write(dataL);
USBMIDI.flush();
}
void setup() {
}
int _x;
// テストデータを4チャンネルに別々に送信します。
void loop() {
SendData16(_x,0);
SendData16(_x<<4,1);
SendData16(_x<<6+_x,2);
SendData16(_x<<8+_x,3);
_x++;
delay(1000);
}
Web MIDIの受信プログラムは以下の通りです。配列dataにチャンネルごとにデータが入ります。
var data=[0,0,0,0];
status=event.data[0]&0xF0;
if(status==0xA0){
channel=(event.data[0]&0x0C)>>2
data0=event.data[0]&0x03;
data1=event.data[1];
data2=event.data[2];
data[channel]=data2+(data1<<7)+(data0<<14);
}
このページにArduinoをつないで、上記スケッチを動作させると、以下のように表示されます。ここではArduino Leonardoを使っています。MIDI inport: のプルダウンメニューで、Arduino Leonardoを選択します。MIDI outport:は何でもかまいません。
↓↓↓ 以下がアプリケーションのビューになります。
| MIDI outport: | MIDI inport: |