Bluetoothでレゴをリモートプログラミングしよう

1.5K Views

September 12, 22

スライド概要

iOSDC 2022 day1 LTの発表資料です
https://fortee.jp/iosdc-japan-2022/proposal/f554bc51-9c63-4487-a556-0085269511c4

profile-image

SwiftとLEGOとBluetooth LEが好きなプログラマ

シェア

埋め込む »CMSなどでJSが使えない場合

各ページのテキスト
1.

Bluetoothでレゴを リモートプログラミングしよう 大庭 慎一郎 @ooba / @bricklife

2.

自己紹介 大庭 慎一郎(おおば しんいちろう) ID: @ooba / @bricklife SwiftとLEGOが好きなプログラマ メルカリiOS版 立ち上げメンバー

3.

今日話すこと Bluetoothに対応しているレゴのセットがいっぱいあるよ Bluetooth通信でモーターやセンサーを制御できるよ そのための通信プロトコルがいくつかあるよ Bluetooth LE向けの「LEGO Wireless Protocol」を紹介するよ

4.

レゴでBluetooth? レゴでモーター? レゴでセンサー?

5.

Bluetooth対応パーツ ポートあり WeDo 2.0 2006 2013 2016 2017 2018 SPIKEプライム 2019 SPIKEベーシック 2021 2020 2019

6.

ポート LPF2

7.

LPF2規格のパーツ

8.

カラーセンサーが赤を検知した モーターを50%のスピードで回せ

10.

Bluetooth対応パーツ ポートなし 2020 2018 2021 2018 2022

11.

レゴ公式のプログラミング環境 Powered UP SPIKE MINDSTORMS

13.

LEGO Wireless Protocol

14.

LEGO Wireless Protocol https://lego.github.io/lego-ble-wireless-protocol-docs/ レゴ社がGitHubで公開しているBluetooth LEの通信仕様 最近のBluetooth LE対応パーツはすべてこのプロトコルを採用

15.

LEGO Wireless Protocol対応 ポートあり 2017 2018 SPIKEベーシック 2021 2019

16.

LEGO Wireless Protocol対応 ポートなし 2020 2018 2021 2018 2022

17.

Bluetooth LEの2つの役割 ペリフェラル ペリフェラル セントラル ペリフェラル ペリフェラル

18.

Bluetooth LEの2つの役割

19.

LEGO Wireless Protocolの設計 サービス UUID: 00001623-1212-EFDE-1623-785FEABCD123 Write キャラクタリスティック UUID: 00001624-1212-EFDE-1623-785FEABCD123 Notify

20.

セントラル側のプログラミング手順 1. ペリフェラルをスキャンする 2. ペリフェラルに接続する 3. サービスを取得する 4. キャラクタリスティックを取得する 5. キャラクタリスティックに対して操作をする

21.

iOS / macOSのBluetooth LEプログラミング Core Bluetoothフレームワークを使う ほぼすべてがデリゲートベースの非同期処理 説明しづらいので今日はAsyncBluetoothを使う

22.

AsyncBluetooth https://github.com/manolofdez/AsyncBluetooth Core BluetoothをSwift Concurrencyに対応させるライブラリ セントラル側の一連の流れを直列に書ける

23.

セントラル側のプログラミング手順 1. ペリフェラルをスキャンする 2. ペリフェラルに接続する 3. サービスを取得する 4. キャラクタリスティックを取得する 5. キャラクタリスティックに対して操作をする

24.
[beta]
モーターを回すまでの最小コード
let serviceUuid = CBUUID(string: "00001623-1212-EFDE-1623-785FEABCD123")
let characteristicUuid = CBUUID(string: "00001624-1212-EFDE-1623-785FEABCD123")
let centralManager = CentralManager()
try await centralManager.waitUntilReady()
1

let scanDataStream = try await centralManager.scanForPeripherals(withServices: [serviceUuid])

2

for await scanData in scanDataStream {
let peripheral = scanData.peripheral
try await centralManager.connect(peripheral, options: nil)

3

try await peripheral.discoverServices([serviceUuid])
guard let service = peripheral.discoveredServices?.first else { continue }

4

try await peripheral.discoverCharacteristics([characteristicUuid], for: service)
guard let characteristic = service.discoveredCharacteristics?.first else { continue }

5

try await peripheral.writeValue(Data([0x08,
[0x08, 0x00, 0x81, 0x00, 0x11, 0x51, 0x00, 0x32]),
0x32]
for: characteristic, type: .withResponse)
}

25.

モーターのパワーを設定するメッセージ https://lego.github.io/lego-ble-wireless-protocol-docs/index.html#output-sub-command-startpower-power ヘッダーパート メッセージパート [0x08, 0x00, 0x81, 0x00, 0x11, 0x51, 0x00, 0x32] メッセージ長: 8 ポート: A (0x00) メッセージタイプ: Port Output Command (0x81) パワー: 50%

26.

メッセージタイプ一覧 https://lego.github.io/lego-ble-wireless-protocol-docs/index.html#message-types Name Value Notes Name Value Notes Hub Properties 0x01 Set or retrieve standard Hub Property information Port Information Request 0x21 Request Port information Hub Actions 0x02 Perform actions on connected hub Port Mode Information Request 0x22 Request Port Mode information Hub Alerts 0x03 Subscribe or retrieve Hub alerts Port Input Format Setup (Single) 0x41 Setup input format for single mode Port Input Format Setup (CombinedMode) 0x42 Setup input format for multiple modes (CombinedMode) Port Information 0x43 N/A Port Mode Information 0x44 N/A Port Value (Single) 0x45 Value update related to single Port Mode Port Value (CombinedMode) 0x46 Value update related to multiple Port Modes in combination (CombinedMode) Port Input Format (Single) 0x47 N/A Port Input Format (CombinedMode) 0x48 N/A Virtual Port Setup 0x61 Used to control synchronization between synchronizable ports. Port Output Command 0x81 Used to execute Port Output commands Port Output Command Feedback 0x82 Provides feedback on completed Port Output commands Hub Attached I/O Generic Error Messages H/W NetWork Commands F/W Update - Go Into Boot Mode F/W Update Lock memory F/W Update Lock Status Request F/W Lock Status 0x04 0x05 0x08 0x10 0x11 0x12 0x13 Transmitted upon Hub detection of attached I/O Generic Error Messages from the Hub Commands used for H/W Networks Set the Hub in a special Boot Loader mode Locks the memory Request the Memory Locking State Answer to the F/W Lock Status Request

27.

実装の参考になるプロジェクト https://github.com/nathankellenicki/node-poweredup - 対応が早くて充実 (Node.js) https://github.com/bricklife/BoostRemote/ - LEGO Wireless Protocol公開前に作り始めたリモコンアプリ (Swift / iOS) https://github.com/LLK/scratch-vm/tree/develop/src/extensions - Scratchの公式拡張機能としてMINDSTORMS EV3、WeDo 2.0、BOOSTに対応している (Node.js) https://github.com/bricklife/scratch-lego-bluetooth-extensions - 上記以外のBluetooth対応レゴをScratchで制御するための拡張機能セット (Node.js)

28.

ありがとうございました