ちょっと癖があるね。
前回まで
RPiのBLEをnobleから叩いてました。
今回は、micro:bitのBLE機能を有効にして、RPiからmicro:bitをスキャンしてみようと思います。
ちなみに、micro:bitは電池ケースにくっつけて給電できるようにしています。
とりあえずスキャン
フツーにScanすれば良いんですが。
var noble = require('noble') noble.on('discover', function(peripheral){ console.log(peripheral) }) noble.startScanning()
startScanning()
のオプションでGATTのサービスのUUIDを指定することができ、これによってスキャン結果をそのサービスがあるペリフェラルにフィルタできるようで。試しにmicro:bitのサービスを指定してスキャンをしてみました。
たとえば、加速度サービスのUUIDはe95d0753-251d-470a-a062-fa1922dfa9a8
なので、
noble.startScanning(['e95d0753251d470aa062fa1922dfa9a8'], false)
みたいに叩けばよいはず。これで叩いてみると・・・なぜかmicro:bitが見つかりません・・・。
接続しないとサービスがわからない?
そんなのもんなのかなぁ思い、改めてオプション無しでstartScanning()
して、見つかったmicro:bitのプロパティを見てみると・・・。
Peripheral { _noble: Noble { (中略) }, id: 'xxxxxxxxxxxx', uuid: 'xxxxxxxxxxxx', address: 'xx:xx:xx:xx:xx:xx', addressType: 'random', connectable: true, advertisement: { localName: 'BBC micro:bit [xxxxx]', txPowerLevel: undefined, manufacturerData: undefined, serviceData: [], serviceUuids: [], solicitationServiceUuids: [], serviceSolicitationUuids: [] }, rssi: -33, services: null, state: 'disconnected' }
serviceUuids
が空っぽですねぇ。これが空なのでUUIDでフィルタができなかったのでしょうか・・・。とはいえ、localName
にはちゃんとmicro:bitと入っているので、とりあえずワークアラウンドとしてlocalName
でフィルタするしかないんですかね・・・。たとえばこんな感じ。
var noble = require('noble') noble.on('discover', function (peripheral) { var localName = peripheral.advertisement.localName if (localName && localName.startsWith('BBC micro:bit')) { console.log('micro:bit found!') } }) noble.startScanning()
うーん、ちょっとダサいけど、動いてそうだしこれで行くか・・・。