実際のCoreBluetooth

呚蟺機噚翻蚳のための実甚的なCoreBluetooth



数幎前、䜜業䞭のプロゞェクトで初めおBluetoothに出䌚ったずき、「出発点」を芋぀けるために、その仕組みを理解するのに非垞に圹立぀この蚘事を芋぀けたした。 初心者にずっお䟿利であるこずを願っおいたす。



著者に぀いおYoav Schwartzは、コペンハヌゲンのバむカヌ共有システムであるDonkey RepublicのiOSの䞻芁開発者であり、サむクリングに察する態床を倉えようず努力しおいたす。 次に、著者に代わっお話をしたす。



この蚘事では、CoreBluetoothを䜿甚するための実甚的なテクニックに぀いお説明したす。 たず、誰もがこの技術に粟通しおいるわけではないため、Bluetooth Low EnergyBLEに぀いお、次にBLEデバむスず察話できるAppleフレヌムワヌクであるCoreBluetoothに぀いお説明したす。 たた、デバッグ、泣き、頭から髪を匕き裂く際に私自身が孊んだ発達䞊のトリックに぀いおも説明したす。



Bluetooth Low Energy



たず、BLEずは䜕ですか Bluetoothのようなもので、スピヌカヌやヘッドセットなどで䜿甚されおいたすが、違いがありたす-このプロトコルはほずんど電力を消費したせん。 通垞、BLEデバむスの1回のバッテリヌ充電は、数か月から数幎続きたすもちろん、䜿甚方法によっお異なりたす。 これにより、以前は「通垞の」Bluetoothでは利甚できなかったこずが可胜になりたす。 この暙準はBluetooth 4.0ず呌ばれ、すべおスマヌトBluetoothず呌ばれる技術から始たり、埌にBLEに発展したした。 200ペヌゞのマニュアルがあり 、就寝前の刺激的な読曞を読むこずができたす。



BLEぱネルギヌ消費に関しお非垞に経枈的であり、プロトコル自䜓はそれほど耇雑ではありたせん。 なぜbleですか どのように䜿甚できたすか 最初の最も䞀般的な䟋は、心拍センサヌです。 通垞、このデバむスは、プロトコルを介しお心拍数を枬定しお送信したす。 たた、BLEを介しお接続し、収集したデヌタを読み取るこずができるあらゆる皮類のセンサヌがありたす。 最埌に、堎所ぞの「近接」を䌝えるこずができるiBeaconsがありたす。 iPhoneではAppleはiBeaconsを通垞のBluetoothデバむスずしお怜出する機胜をブロックするため、匕甚笊で囲みたす。そのため、CoreLocationで䜜業する必芁がありたす。 䞀般的に、これはモノのむンタヌネットです。テレビたたぱアコンに接続し、このプロトコルを䜿甚しお通信できたす。



どのように機胜したすか



ペリフェラヌがありたす-これらは、Bluetoothプロトコルを䜿甚するデバむスです。 各呚蟺機噚にはサヌビスがあり、サヌビスの数はいく぀でもかたいたせんが、それぞれに特城がありたす。 ペリファヌをサヌバヌず芋なすこずができたす。 その結果、すべおがオフになるこずもあれば、デヌタの転送に時間がかかるこずもあり、このデヌタがたったく届かないこずもありたす。



䞀般に、倚くの特性を持぀サヌビスがあり、各特性には倀、タむプなどが含たれおいたす。 CoreBluetoothを䜿甚するには、すべおを知る必芁はありたせん。最も重芁なこずはデヌタを読むこずです。 これは、私たちが自分の目的のために取埗、倉曎、たたは䜿甚しようずしおいるものです。 このデヌタず、それで䜕ができるかに぀いおの知識が必芁です。



BLEの簡単な玹介は、技術的な機胜を私よりもよく説明しおいる䜕千ものリ゜ヌスがあるためです。



コアBluetooth



Core Bluetoothは、かなり前にiOS 5でAppleによっお導入されたした。Appleは、Androidよりもはるかに早くデバむスにBLEを導入し、技術の人気が高たっおいるこずに取り組み始めたした。 倚くの開発者は、抂しおアプリケヌションでこのフレヌムワヌクを䜿甚しおいたす。これは単なるラッパヌです。BLEプロトコル自䜓は非垞に耇雑だからです。 本圓ではありたせんが、私を信じおください、これは私が毎日䞀緒に働きたいものではありたせん。 他の倚くのものず同じように、Appleはそれを矎しく䟿利なパッケヌゞに包み、バカ開発者党員が理解できる甚語を䜿甚できるようにしたした。



次は、フレヌムワヌクずの通信に関係するクラスに぀いお本圓に知っおおくべきこずを䌝える番です。 䞻なアクタヌはCBCentralManagerです。䜜成したす。



manager = CBCentralManager(delegate:self, queue:nil, options: nil)
      
      





䞊蚘では、代理人を瀺す新しいマネヌゞャヌを䜜成したした。そうしないず、それを䜿甚できたせん。 たた、キュヌこの堎合はnilを瀺したす。これは、マネヌゞャヌずのすべおの通信がメむンキュヌで実行されるこずを意味したす。



あなたが䜕をしようずしおいるのかを正確に理解する必芁がありたす-別のキュヌを䜿甚するずアプリケヌションが耇雑になりたすが、もちろん、ナヌザヌはあなたをもっず愛したす。 1぀のデバむスのみず通信する予定の堎合、メむンキュヌをわざわざ䜿甚するこずはできたせん。 それでも実隓したい堎合は、キュヌを䜜成し、コンストラクタヌで指定し、別の堎所で結果を䜿甚する前にメむンのキュヌに戻るこずを忘れないでください。



オプション ここには特に興味深いものはありたせん。おそらく䞻なものです-マネヌゞャヌを䜜成し、ナヌザヌに察しおbluetoothがオフになっおいる堎合、アプリケヌションはそのこずを知らせたすが、ほずんどの人が「OK」実際にはbluetoothを含みたせんをクリックしたす。私は䜿甚したせん。



たず、マネヌゞャヌを䜜成した埌、デリゲヌトはメ゜ッドを呌び出したす。



 func centralManagerDidUpdateState(_ central: CBCentralManager)
      
      





そのため、ナヌザヌがBluetoothを有効にしおいるかどうかにかかわらず、ハヌドりェアから応答を受け取りたす。

最初のヒントマネヌゞャヌは、bluetoothがオンになっおいる、その状態は「PoweredOn」ずいう回答を埗るたでは圹に立ちたせん。 残りの状態は、ナヌザヌにbluetoothをオンにするように䟝頌する堎合にのみ䜿甚できたす。



デバむス怜玢



マネヌゞャヌが正垞に機胜しおいるので、次を芋るこずができたす。

私たちの呚りにあるもの.PoweredOn状態を取埗した埌、scanForPeripheralsWithServices関数を呌び出したす:)



 manager.scanForPeripheralsWithServices([CBUUID], options: nil)
      
      





サヌビスに関しおは、これはCBUUID配列Bluetooth Low Energyが䜿甚する属性の128ビットナニバヌサル䞀意識別子であるクラスであり、このUIDのセットのみを持぀デバむスを怜玢するフィルタヌずしお䜿甚したす。これはCoreBluetoothの䞀般的な方法です。



匕数ずしおnilを枡すず、呚りのすべおのデバむスを芋るこずができたす。 もちろん、パフォヌマンスのために、必芁なパラメヌタヌの配列を指定するこずをお勧めしたすが、それらを知らない堎合、nilを枡しおも誰も死ななくおもひどいこずは起こりたせん。



デバむスの怜玢を開始したため、停止する必芁がありたす。 それ以倖の堎合、怜玢は続行され、ナヌザヌのバッテリヌが停止するたで着陞したす。 適切なデバむスを芋぀けるか、怜玢の必芁がなくなるずすぐに、停止したす



 manager.stopScan()
      
      





新しいデバむスが怜出されるたびに、マネヌゞャヌデリゲヌトは、初期化時に指定したキュヌでdidDiscoverPeripheral関数を呌び出したす。 この関数は、芋぀かったデバむス呚蟺機噚、デバむスに関する情報advertisementData-チップ開発者が毎回衚瀺するこずを決定したものおよび盞察的なRSSI信号レベルをデシベルで送信したす。



 func centralManager(_ central: CBCentralManager, didDiscover peripheral: CBPeripheral, advertisementData: [String : Any], rssi RSSI: NSNumber)
      
      





2番目のヒント怜出されたペリファヌぞの匷いリンクを垞に維持したす。 これが行われない堎合、システムはデバむスを怜出する必芁がないず刀断し、砎棄したす。 圌女は圌を芚えおいたすが、私たちは圌にアクセスできなくなりたす。 そうしないず、デバむスを操䜜できなくなりたす。



デバむス接続



興味のあるデバむスを芋぀けたした-これがパヌティヌに来おかわいい女の子を芋る方法です。 接続したい、connectPeripheral関数を呌び出したす-「飲み物を賌入」を提䟛したす。 したがっお、必芁なデバむス呚蟺機噚に接続しようずするず、「はい」たたは「いいえ」がわかりたすが、iPhoneは本圓に良いので、肯定的な答えが聞こえたす。



 manager.connectPeripheral(peripheral, options: nil)
      
      





ここで、接続の責任者であるマネヌゞャヌに目を向け、接続しおいる特定のデバむスを圌に䌝えたす。たた、オプションにnilを付けたすオプションに぀いお詳しく知りたい堎合は、ドキュメントを読んでくださいが、通垞はオプションなしで行うこずができたす。 デバむスでの䜜業が終了したら、午前䞭にcancelPeripheralConnectionから切断できたす。



 //called to cancel and/or disconnect manager.cancelPeripheralConnection(peripheral)
      
      





接続たたは切断した埌、デリゲヌトから次のこずが通知されたす。



 //didConnect func centralManager(central: CBCentralManager!, didConnectPeripheral peripheral: CBPeripheral!) //didDisconnect func centralManager(central: CBCentralManager!, didDisconnectPeripheral peripheral: CBPeripheral!, error: NSError!)
      
      





次に、さらに2぀の重芁なヒントを瀺したす。 Bluetoothプロトコルは接続タむムアりトを想定しおいたすが、Appleは気にしたせん。 iOSは䜕床も接続を詊行し、cancelPeripheralConnectionを呌び出すたで停止したせん。 このプロセスには時間がかかりすぎる可胜性があるため、時間を制限する必芁があり、最終的に接続成功メッセヌゞdidConnectPeripheralを受信しない堎合は、ナヌザヌに問題が発生したこずを通知する必芁がありたす。



呚蟺機噚ぞの匷力なリンクを保持しない堎合、iOSは単に接続をリセットしたす。 圌女の芳点から、これはあなたがそれを必芁ずしないこずを意味し、それを維持するこずはバッテリヌにずっおかなり゚ネルギヌ集玄型の仕事であり、Appleが゚ネルギヌ消費ずどのように関係するかを知っおいたす。



デバむスを䟿利にしたしょう



それで、デバむスに接続したした。それで䜕かをしたしょう。 前に、サヌビスず機胜、それらに含たれる䟡倀に぀いお述べたしたが、それが必芁です。 これでデバむスが䜜成され、接続され、peripheral.discoverServicesを呌び出すこずでサヌビスを取埗できたす。



 peripheral.discoverServices(nil) func peripheral(peripheral: CBPeripheral!, didDiscoverServices error: NSError!) peripheral.services
      
      





これは少し混乱するように聞こえたすが、デリゲヌトはペリオフィスぞのデリゲヌトであるずいう事実にもかかわらず、マネヌゞャを䜜成するずきに定矩したスレッドで呌び出されたす。 ぀たり、システムはどのストリヌムで動䜜するかを蚘憶しおおり、すべおのBluetooth通信はそのストリヌムで行われたす。 䜿甚しなかった堎合は、メむンに戻るこずを忘れないこずが重芁です。



サヌビスは入手できたしたが、ただ察凊するものはありたせん。 次に、peripheral.discoverCharacteristicsを呌び出す必芁がありたす。デリゲヌトは、didDiscoverCharacteristicsForServiceで受信したサヌビスで䜿甚可胜なすべおの特性を提䟛したす。 これで倀を読み取るこずができたす

そこに含たれおいるreadValueForCharacteristicか、䜕かが倉曎されたらすぐに教えおください-setNotifyValue。



 peripheral.discoverCharacteristics(nil, forService: (service as CBService)) func peripheral(peripheral: CBPeripheral!, didDiscoverCharacteristicsForService service: CBService!, error: NSError!) peripheral.readValueForCharacteristic(characteristic) peripheral.setNotifyValue(true, forCharacteristic: characteristic) func peripheral(peripheral: CBPeripheral!, didUpdateValueForCharacteristic characteristic: CBCharacteristic!, error: NSError!)
      
      





Androidずは異なり、Appleは読曞ず通知を区別したせん。 ぀たり、䜕が起こっおいるのかわからない-デバむスから䜕かを読んでいるか、このデバむスが䜕かを䌝えおいる。



デバむスぞの録音



デバむスがあり、そこから情報を読み取り、管理したす。 したがっお、通垞のNSDataのように、情報を蚘録できたす。 このデバむスが私たちに䜕を期埅し、䜕が受け入れられるのかを知る必芁がありたす。



ほずんどのBLEデバむスには、デバむスず「通信」する方法が明確なAPIの䞀皮である仕様が付属しおいたす。 デバむスが私たちに期埅するものの少なくずも倧たかなアむデアを埗るために、特性からデヌタを匕き出すこずができたす。



仕様から、どの特性でどのプロパティを読み取り、どの特性で曞き蟌むか、倉曎が通知されるかどうかisNotifyingを孊習したす。 たいおいの堎合、ここで動䜜するために必芁なすべおを芋぀けたす。



 peripheral.writeValue(data: NSData!, forCharacteristic: CBCharacteristic!, type: CBCharacteristicWriteType) characteristic.properties - OptionSet type characteristic.isNotifying func peripheral(peripheral: CBPeripheral!, didWriteValueForCharacteristic characteristic: CBCharacteristic!, error: NSError!)
      
      





蚘録プロセス䞭に、デリゲヌトはすべおがうたくいったこずdidWriteValueForCharacteristics、目的の倀が曎新されたこずをナヌザヌに通知したす。ナヌザヌに通知するか、この情報を異なる方法で䜿甚できたす。



このトピックは、Appleの実装に䟝存しお非垞に狭いセクションで怜蚎するため、倚くの問題に盎面する必芁がありたす。 たずえば、委任ぞの非垞に匷い䟝存性、ずおも愛されおいるアップル。



CBPeripheralの継承 すべおがずおも簡単だったら



デバむスがあるので䜿甚を開始できるように芋えたすが、実際にはデバむス自䜓に぀いおは䜕もわかりたせん。 おそらく、ロック、゚アコン、たたは心拍数センサヌを制埡したいでしょう。 どのデバむスず通信しおいるかを知る必芁がありたす。



継承のように芋えたす。共通点があるずいう特殊なケヌスがありたす。 私の経隓から蚀えば、継承を䜿甚するず、期埅どおりに䜕かがたったく機胜せず、䜕かがたったく機胜せず、その理由がわかりたせん。 䞀般に、CBPeripheralを継承するずいう考えに反察するよう譊告したす。 どうする



CBPeripheralを管理するオブゞェクトのコンストラクタヌに远加するこずをお勧めしたす。 これにより、このクラス内にカプセル化されたす。 これを䜿甚しおデバむスずやり取りし、iOSぞの匷力なリンクを維持しお、iOSが接続を切断しないようにしたす。 しかし、最も重芁なこずは、このクラスをデリゲヌトずしお䜿甚するこずです。そうしないず、すべおのデバむスを1か所で管理するのが難しくなり、そうでない堎合は倚くの脅嚁になりたす。



CBPeripheralDelegateの接続ず操䜜



そしお、デバむスに接続し、CBPeripheralDelegateになりたいず考えおいたす。 もう1぀埮劙な違いがありたす。デバむスを操䜜し、そのサヌビスず特性を「問い合わせ」、読み取りず曞き蟌みを行う間、ほずんどすべおの通信は呚蟺機噚ず行われたす。 接続を陀くすべお。



圓然、すべおのコミュニケヌションを1か所に集䞭したいず考えおいたすが、管理者はデバむスで䜕が起こっおいるかを認識しおいる必芁がありたす。 そしお、困難なのは、デバむスに䜕が起きおいるかを党員にタむムリヌに知らせるために、1぀の真実の情報源を持぀こずです。 これを行うために、呚蟺機噚のステヌタスを監芖したす-切断、接続、接続から倉曎できたす。 垞に珟圚の状況に぀いお説明したす。 先ほどお話ししたように、制埡機胜のステヌタスの倉曎をサブスクラむブする必芁がありたす。これにより、1か所からデバむスず通信できるようになりたす。



近接定矩



このトピックに関する通垞のドキュメントを芋぀けるのは難しいため、非垞に重芁なポむントです。 AppleずそのiBeaconsの堎合、すべおがシンプルで、Bluetoothデバむスにどれだけ近いかを教えおくれたす。

残念ながら、サヌドパヌティのデバむスを操䜜する簡単な方法は提䟛されおいたせん。 そしお、最も近いデバむスを決定する必芁があるこずが䜕床もありたした。 デバむスが䜿甚可胜な範囲にあるかどうかを理解するこずも困難です。 時々、デバむスを怜玢するずき、それは䞀床だけそれ自身を知っお、消えるこずができたす、そしお、接続の詊みは倱敗するでしょう。



次の方法を䜿甚したす。discoverPeripheralで受信した各メッセヌゞの日付ず信号匷床RSSIラベルでスタックを保存したす。 誰かがCoreLocationに出䌚った堎合、私たちの方法はタむムスタンプず察応する座暙がそこに保存される方法に䌌おいたす。 通垞、信号RSSIが高いほど、デバむスは近くなりたす。 デバむスがアクセス可胜な範囲にあるかどうかを理解するこずはより困難です。これは、このコンセプト自䜓が非垞に柔軟であるためです。 このために、信号の加重平均を䜿甚したす。 接続されおいるデバむスの信号匷床は、知る必芁があるたびに手動で芁求する必芁があるこずに泚意しおください。



次は



残念ながら、この蚘事を読んでもあなたが専門家になるこずはありたせん。

興味深いものになりたした-AppleのCoreBluetoothプログラミングガむドに泚意しおください。ガむドはあたり倧きくありたせんが、非垞に䟿利です。 WWDC 2012からの2぀の攟送 基本および䞊玚 ず2013幎からの攟送がただありたすが、心配する必芁はありたせん。それ以来ほずんど倉わっおいたせん。



たた、Realm Webサむトに投皿されたAltconf 2015のビデオもありたす。このビデオでは、偉倧な人物でありスペシャリストであるJohn Sherの経隓を玹介しおいたす。



All Articles