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: |