BlueNinjaでBLEを使ってみました。
そもそも仕様すら知らない状態からのスタートなので、仕様を覚えながらいじって行こうかなと。
<使用環境>
BlueNinja_DSP:RELEASE_150929
Android 5.0
サンプルを動かしてみる
まずはBLEのサンプルプログラムを動かしてみました。
これ
サーバプログラム
https://github.com/cerevo/BlueNinja_BLE_EXAMPLE
クライアントプログラム
https://github.com/cerevo/BlueNinja_BLE_EXAMPLE_App4Android
両方のプログラムを実行し、BlueNinjaのペアリングボタンを押した後、スマホの「CONNECT BLUENINJA」ボタンを押します。
接続できたら、スマホの「ENABLE NOTIFICATION」ボタンを押します。
すると、BlueNinjaから送信される加速度センサ値や大気圧などがスマホに表示されました。
BLEってペアリングしなくても通信できるんですね!
送信データを追加してみる
通信できることは確認できたので、今度はサンプルプログラムに送信データを追加してみました。
とりあえず今回は適当なカウンタを作って、その値を送信してみることにします。
まずはBlueNinja側のプログラムを変更していきます。
BLEはGATT(Generic Attribute Profile)でデータを送受信します。
GATTでデータを送受信するには、
・サービスを定義
・そのサービスで扱うCharacteristicを追加(複数可)
Characteristicはデータを格納するためのもの
・CharacteristicにDescriptorを追加(複数可、なくてもいい)
Characteristicに情報を追加するためのもの
を用意する必要がありそうです。
※ちがうかも…
<参考>
https://developer.bluetooth.org/gatt/Pages/default.aspx
http://yegang.hatenablog.com/entry/2014/08/09/195246
http://qiita.com/__moai/items/111e2b637f3404a2de49
1.CCCD(Client Characteristic Configuration Descriptor)の定義を追加
CCCDとは、最もよく使われる重要なdescriptorらしく、characteristicのNotificationとIndicatorの有効/無効を切り替えるために使用されます。
Notificationが有効だと、データ変化があった時にクライアントに通知されます。
Indicatorが有効だと、データ変化があった時にクライアントに通知、かつ、通知できたことをサーバ側にコールバックします。
※Notificationは、単純にデータを送信する時に使用し、Indicatorは1発もの(コマンド)などを送信する際に使用するのだと思います。
ble_tracker.cに下記を追加。
/* Counter */ const BLELib_Descriptor tz01_tracker_counter_desc = { BLE_GATT_UNIQUE_ID_TZ01_COUNTER_DESC, 0x2902, 0, BLELIB_UUID_16, BLELIB_PERMISSION_READ | BLELIB_PERMISSION_WRITE, tz01_counter_desc, sizeof(tz01_counter_desc) }; const BLELib_Descriptor *const tz01_tracker_counter_descriptors[] = { &tz01_tracker_counter_desc };
0x2902は、CCCDのUUIDです。BluetoothSIGで定義されており、2byte長です。
CCCDはクライアントから有効/無効が書き換えられる様に、READとWRITEの許可を与えています。
2.Characteristic定義を追加
次にCharacteristicを追加します。
ble_tracker.cに下記を追加。
const BLELib_Characteristics tz01_tracker_counter = { BLE_GATT_UNIQUE_ID_TZ01_COUNTER, 0x91825f82ff67e8f8, 0xd43a02130e5f4a80, BLELIB_UUID_128, BLELIB_PROPERTY_NOTIFY, BLELIB_PERMISSION_READ, tz01_counter, sizeof(tz01_counter), tz01_tracker_counter_descriptors, 1 };
characteristicのUUIDは、こちらで生成したIDなので16Byte長(BLELIB_UUID_128)になります。
上記の例だと、
D43A0213-0E5F-4A80-9182-25F82FF67E8F8
となっています。
Propertesは“Notify”として、クライアントにデータ変化を通知します。
通知するだけなので、PermissionsはREADのみ。
3.Serviceに追加
作成したcharacteristicをServiceに追加します。
今回は既にあるtz01_trackerサービスに追加。
ble_tracker.cを編集。
/* Characteristics list */ const BLELib_Characteristics *const tz01_tracker_characteristics[] = { &tz01_tracker_gyro, &tz01_tracker_acel, &tz01_tracker_magm, &tz01_tracker_axangl, &tz01_tracker_temp, &tz01_tracker_airp, &tz01_tracker_counter, }; /* TZ1 Tracker service */ const BLELib_Service tz01_tracker_service = { BLE_GATT_UNIQUE_ID_TZ01_SERVICE, 0x91825f82ff67e8f8, 0xd43a02000e5f4a80, BLELIB_UUID_128, true, NULL, 0, tz01_tracker_characteristics, 7 };
4.データ送信処理を追加
あとは、データ送信を追加だけです。
(正確には、今回の変更に伴う変数やIDの定義やフラグの追加など必要ですが割愛w)
ble_tracker.cに追加。
if (tz01_tracker_notif_counter_enable) { counter++; len = sprintf(msg, "{cnt:%d}", counter); ret = BLELib_notifyValue(BLE_GATT_UNIQUE_ID_TZ01_COUNTER, msg, len); if (ret != 0) { sprintf(msg, "%d BLELib_notifyValue(): %d\r\n", __LINE__, ret); TZ01_console_puts(msg); } }
jsonフォーマットに変換して、BLELibに渡すだけです。
5.データ受信処理の追加
次にAndroid側に受信処理を追加します。
こちらは、サンプルの他データの受信処理とほとんど同じなので割愛。
以上です。
実行してみた
BlueNinjaから受信したカウンタ値を、スマホ画面の右上に表示してみました。
ちゃんとデータ受信できているようです。
CharacteristicのPropetyをIndicateに変更してみる
次にIndicateを試してみました。
1.Characteristicの定義を変更
“NOTIFY”→”INDICATE”
const BLELib_Characteristics tz01_tracker_counter = { BLE_GATT_UNIQUE_ID_TZ01_COUNTER, 0x91825f82ff67e8f8, 0xd43a02130e5f4a80, BLELIB_UUID_128, BLELIB_PROPERTY_INDICATE, BLELIB_PERMISSION_READ, tz01_counter, sizeof(tz01_counter), tz01_tracker_counter_descriptors, 1 };
2.データ送信処理を変更
ret = BLELib_indicateValue(BLE_GATT_UNIQUE_ID_TZ01_COUNTER,
3.コールバック処理を追加
void indicationConfirmCb(const uint8_t unique_id) { uint8_t msg[32]; sprintf(msg, "indicated:%d\r\n", unique_id); TZ01_console_puts(msg); }
4.Android側でCCCDのindicationフラグを立てる様に変更
private void enableBleNotification() { for (int i = 0; i < UUIDS_CHARACTERISTIC.length; i++) { boolean reg = mGatt.setCharacteristicNotification(mCharacteristics[i], true); BluetoothGattDescriptor desc = mCharacteristics[i].getDescriptor(UUID.fromString(UUID_CLIENT_CHARACTERISTIC_CONFIG)); //desc.setValue(BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE); desc.setValue(BluetoothGattDescriptor.ENABLE_INDICATION_VALUE); mGatt.writeDescriptor(desc);
実行してみた
データ変化通知後にコールバックが呼ばれることが確認できました。
今回試したのは以上です。
あとがき
とりあえずデータの送信方法は解りました。
BlueNinjaは東芝作BLEライブラリを使用するのですが、こいつのドキュメントが見つからない…。
まぁ、そんなにでかくないのでソース嫁ってことなのかな。
※追記
…と思ったらドキュメントありました。
DFP解凍したフォルダに入ってますね。
次は、Android側からBlueNinjaを操作するところまでやってみたいと思います。
ではでは〜。