2016年4月13日水曜日

BLE MIDIの仕様でハマりそうなところ集

MIDI公式サイトでBLE MIDIの仕様書が公開されていたので、ハマりそうな部分について書いておきます。主にタイムスタンプについてです。
BLE MIDIのデバイスやライブラリを自前で実装してみようかな、という方にとって参考になるかもしれません。

BLE MIDIのタイムスタンプの仕様

BLE MIDIのデータの形式はこんな感じです(仕様書より)。従来のMIDI 1.0なメッセージにタイムスタンプ情報が付いた形です。BLEの1パケットに収まらない場合は分割することもできます。
上図はSysExというデータで、システムエクスクルーシブメッセージといい、機器の設定情報などをバイナリで送受信するためのものです。
  • SysEx開始は 0xF0 (最初の緑色背景のデータ) 
  • SysEx終端は 0xF7 (最後の緑色背景のデータ)
  • SysEx終端が来るまでが、データです。データの内容・長さは自由です。
  • SysEx終端もMIDIメッセージなので、「直前1バイト」に、タイムスタンプ下位7bitと0x80を論理和(OR)したデータが入ります (水色背景のデータ)
  • タイムスタンプは、下位7ビットと、ヘッダ内にある上位の6ビット分と組み合わせて13ビット(0〜8191、ミリ秒)の値になります。この値で通信のレイテンシを吸収します。

ハマりポイント1: タイムスタンプの精度

タイムスタンプは送信側デバイスのクロック精度に依存するので、送信側のタイムスタンプの値が1000増えたからといって、受信側の時計でも正確に1000ミリ秒が経過しているとは限りません。
単体のキーボードや音源など、マイコンで処理しているデバイスでは精度がわりと怪しくなります。あくまで前回のイベントからの間隔として扱うのが良さそうです。8192ミリ秒までの間隔しか測れないので気をつけます。

ハマりポイント2: タイムスタンプの上限値跨ぎ処理

1パケットで複数のMIDIメッセージを受信することがあり、それらのタイムスタンプ下位が0xFFを跨いだ場合(図の例だと、SysEx開始時が0xFFで、SysEx終端が0x00のとき)や、タイムスタンプ全体の値が8191を跨いだ場合も、デバッグしていて微妙にハマります。8秒遅れてイベントが発火したり…。
こちらは、前回のイベントのタイムスタンプとの差がマイナスなら8192を足す、みたいな対処で回避できるでしょう。

ハマりポイント3: SysExデータの末尾に現れるタイムスタンプ情報

SysEx終端の直前にタイムスタンプ下位が入るので、その1バイトだけを除いたデータをSysExデータとする必要があります。先頭の0xF0と末尾の0xF7を含めたデータを返却することを前提としたAPIであれば、ちょっとだけ面倒な実装になりそうです。

ハマりポイント4: たまにSysExデータが欠ける

これが一番デカい罠だと思います。
SysExとタイムスタンプの仕様を見て、素直に「SysEx終端:0xF7が来るまでデータを読んだら、その直前の1バイトをタイムスタンプとして扱う」という解析処理を書いていると、仕様の罠にハマります。
そういう風に実装すると、イベントの発火タイミングが最大で127ミリ秒ズレて、その際にデータが欠損します。これはSysEx送受信の128回に1度の確率で発生します。

何故こんなことになるかというと…
タイムスタンプ下位7bitが0x77だった場合、送信されるバイト値は0xF7になります。0xF7を受信したからといって、この時点ではSysExをイベントキュー等に入れてはいけません。
正しくは「0xF7を受信したら次のデータ1バイトをチェックし、次も0xF7なら次のデータまでがSysEx、それ以外ならこのデータまでがSysEx」という風に実装する必要があります。

BLE MIDIは様々なデバイス間で使われる通信プロトコルのため、送受信の実装が拙いデバイスについても、異常動作しないように対応する必要があります。
具体的にはこの2つです。
  • SysEx受信のときは、0xF7の2回受信を考慮して解析する。
  • SysEx送信のときは、タイムスタンプの値として0xF7を送信しない。
以上、BLE MIDIを実装する際のハマりポイントでした。

2015年6月20日土曜日

フリューを退職しました

2015年7月20日をもちまして、派遣時代から含めて13年間在籍していたフリューを退職いたしました。
今後のことはまだ決まっていません。のんびりやります。

2015年4月17日金曜日

超音波でカレーを熟成してみた

最近、超音波にハマっています。超音波で出来ることをググってみると色々なワクワクする用途が見つかるのです。
例えば…
  • 超音波による成分抽出
    • 数十kHzの音波を当てることで水や油やアルコールや溶剤などに成分を抽出します。
    • 混合液の乳化などにも使われています。
  • 超音波を変調して、指向性のあるスピーカー(パラメトリックスピーカー)
    • 超音波自体に指向性があるので、それを干渉させることで元の音波をビーム状に復元させる仕組みのようです。
  • 数MHzの超音波を水に掛けることで霧化することを利用した、超音波式加湿器
    • 水に含まれる雑菌やミネラル分まで霧化して部屋中にバラ撒くので、あまりよろしくないようです…。
    • この霧化器にも他の利用法がありそうなので後日実験します。
  • 超音波による化学反応の促進
    • 局所的にエネルギーを集中させることで化学反応が促進されるようです。
  • 洗浄
    • 眼鏡屋さんによく置いてあるやつです。細かな泡が割れるときのエネルギーを利用しています。複数の周波数を出し分けることで洗浄効果が増すようです。
だいたいこういった感じに使われているようです。論文とか特許を検索すると興味深いものが見つかります。

今回は「超音波による成分抽出」を利用して調理をしてみました。

2015年1月28日水曜日

Android用のBLE MIDIライブラリのご紹介

去年から、Android端末上でBLE MIDI通信を使えるようにするライブラリを作っていました。(→前回の記事を参照)
AppleがBluetooth Low Energy MIDI Specification(PDF)を公開していたのを先日見つけたので、その仕様に合うよう実装してみました。

このライブラリを使って出来ること:
  • AndroidアプリとBLE MIDIなデバイスとが接続でき、演奏やイベントの記録などをすることができます。
  • iOSやOS X上で動くBLE MIDIなアプリとも接続できます。
  • Android LollipopかつPeripheral機能がサポートされている端末では、端末をBLE MIDIデバイスとして振る舞わせることができます。
注意:
このAppleの仕様は、まだMIDI公式から承認されていません。以前問い合わせをしたところ、「ドラフトの仕様はあるが絶賛議論中だよ。議論を見たかったら会員になってね」とのことでした。公式としてリリースされる仕様ではAppleのものとの食い違いが出てくるかもしれません。頑張って追従します。

ライブラリの機能

このライブラリを使うことで、AndroidはBLE MIDI CentralとPeripheralの機能を使えるようになります。

BLE MIDI Central機能とは

AndroidアプリがBLE MIDIデバイスを探して、接続します。アプリはデバイスとMIDIメッセージを送受信できます。
この機能にはAndroid JellyBean MR2(4.3 / API Level 18)以降が必要です。ペアリング機能を使うにはAndroid KitKat(4.4 / API Level 19)以降が必要です。

BLE MIDI Peripheral機能とは

AndroidアプリがBLE MIDIデバイスとして振舞います。アプリは他の端末上(Android, iOS, OS X)のCentralなアプリから接続して使用されます。


2015年1月21日水曜日

MIDI over Bluetooth LE library for Android

I've been developing the library to enable BLE MIDI feature on the Android devices from last year. The Apple Bluetooth Low Energy MIDI Specification(PDF) had revealed at December 2014. And finally, I implemented all of features on the specification.

Using this library, the app can connect with BLE MIDI devices, and BLE MIDI compatible iOS/Android/OS X apps. On the Android Lollipop, the app can act as BLE MIDI device.

Note:
This Apple's specification has not been approved by MIDI Manufacturers Association(MMA). I've asked about the specification to MMA at the past, but it was under discussion with MMA members.
The MMA's official release version's specification might be different from Apple's one.

The library's features

With this library, the Android can provide BLE MIDI Central / Peripheral features.

BLE MIDI Central feature

The Android app can host BLE MIDI devices. The app can receive MIDI messages from BLE MIDI devices, and send MIDI messages to them.
This feature requires Android KitKat(4.4 / API Level 19) or later.

BLE MIDI Peripheral feature

The Android app can pretend as BLE MIDI device. The application on the another machine(Android / iOS / OS X) can connect with the Android app.

2014年11月10日月曜日

BLE MIDIのAndroid向けライブラリを作っています

iOS 8での新機能、MIDI over Bluetooth LEの最初のデバイス「mi.1」がindiegogoにて発表されていたので、早速投資して3つポチりました。


その後、ブツが届いたのはいいのですがファームウェアが導入されておらず、実際に使えるようになるまでにしばらく掛かりました。
製品版ではファームウェア書き込み済の状態で出荷しないとユーザが混乱しそうです。

まだmi.1が届いていないうちから、Android 4.3にて追加されたBluetooth LEのAPIを使ってMIDIっぽい通信をするライブラリを書いていました。
Appleが仕様を作るとして、極力既存のMIDIと互換を持たせたシンプルな形に実装するだろう、おそらくBluetooth LEにレガシMIDIのデータをそのまま垂れ流す程度のものだろう、などと想像しつつ先行して実装していました。
mi.1のファームウェアを更新した後、受信したデータをログに出したりしつつプロトコルを調整して、受信までは動作確認できました。

というわけで、まだ道半ばですが現状報告な感じで。

2013年6月24日月曜日

ニューファミコンでプレゼンするためのツール集を作ってみた

「ファミコン用の自作ソフトを作って遊ぼう」の記事の続きです。社内の勉強会でプレゼンする機会があったので、ファミコンソフトを作って発表してみました。

参考:社内勉強会の発表資料
(Chrome推奨。枠内をクリックしてから、左右キーでページ送りします)