react-native-ble-manager 12.1.0 → 12.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/android/src/main/java/it/innove/BleManager.java +66 -34
- package/android/src/main/java/it/innove/Peripheral.java +1 -1
- package/dist/cjs/NativeBleManager.d.ts +1 -0
- package/dist/cjs/NativeBleManager.js.map +1 -1
- package/dist/esm/NativeBleManager.d.ts +1 -0
- package/dist/esm/NativeBleManager.js.map +1 -1
- package/ios/BleManager.mm +12 -0
- package/ios/SwiftBleManager.swift +304 -294
- package/package.json +1 -1
- package/src/NativeBleManager.ts +8 -0
|
@@ -5,11 +5,11 @@ import CoreBluetooth
|
|
|
5
5
|
@objc public class SwiftBleManager: NSObject, CBCentralManagerDelegate, CBPeripheralDelegate {
|
|
6
6
|
static var shared:SwiftBleManager?
|
|
7
7
|
static var sharedManager:CBCentralManager?
|
|
8
|
-
|
|
8
|
+
|
|
9
9
|
private weak var bleManager: BleManager?
|
|
10
10
|
private var manager: CBCentralManager?
|
|
11
11
|
private var scanTimer: Timer?
|
|
12
|
-
|
|
12
|
+
|
|
13
13
|
private var peripherals: Dictionary<String, Peripheral>
|
|
14
14
|
private var connectCallbacks: Dictionary<String, [RCTResponseSenderBlock]>
|
|
15
15
|
private var readCallbacks: Dictionary<String, [RCTResponseSenderBlock]>
|
|
@@ -21,18 +21,18 @@ import CoreBluetooth
|
|
|
21
21
|
private var writeQueue: Array<Any>
|
|
22
22
|
private var notificationCallbacks: Dictionary<String, [RCTResponseSenderBlock]>
|
|
23
23
|
private var stopNotificationCallbacks: Dictionary<String, [RCTResponseSenderBlock]>
|
|
24
|
-
|
|
24
|
+
|
|
25
25
|
private var connectedPeripherals: Set<String>
|
|
26
|
-
|
|
26
|
+
|
|
27
27
|
private var retrieveServicesLatches: Dictionary<String, Set<CBService>>
|
|
28
28
|
private var characteristicsLatches: Dictionary<String, Set<CBCharacteristic>>
|
|
29
|
-
|
|
29
|
+
|
|
30
30
|
private let serialQueue = DispatchQueue(label: "BleManager.serialQueue")
|
|
31
|
-
|
|
31
|
+
|
|
32
32
|
private var exactAdvertisingName: [String]
|
|
33
|
-
|
|
33
|
+
|
|
34
34
|
static var verboseLogging = false
|
|
35
|
-
|
|
35
|
+
|
|
36
36
|
@objc public init(bleManager:BleManager) {
|
|
37
37
|
peripherals = [:]
|
|
38
38
|
connectCallbacks = [:]
|
|
@@ -50,18 +50,18 @@ import CoreBluetooth
|
|
|
50
50
|
exactAdvertisingName = []
|
|
51
51
|
connectedPeripherals = []
|
|
52
52
|
self.bleManager = bleManager
|
|
53
|
-
|
|
53
|
+
|
|
54
54
|
super.init()
|
|
55
|
-
|
|
55
|
+
|
|
56
56
|
NSLog("BleManager created");
|
|
57
|
-
|
|
57
|
+
|
|
58
58
|
SwiftBleManager.shared = self
|
|
59
|
-
|
|
60
|
-
|
|
59
|
+
|
|
60
|
+
|
|
61
61
|
NotificationCenter.default.addObserver(self, selector: #selector(bridgeReloading), name: NSNotification.Name(rawValue: "RCTBridgeWillReloadNotification"), object: nil)
|
|
62
62
|
}
|
|
63
63
|
|
|
64
|
-
|
|
64
|
+
|
|
65
65
|
@objc func bridgeReloading() {
|
|
66
66
|
if let manager = manager {
|
|
67
67
|
if let scanTimer = self.scanTimer {
|
|
@@ -69,33 +69,33 @@ import CoreBluetooth
|
|
|
69
69
|
self.scanTimer = nil
|
|
70
70
|
manager.stopScan()
|
|
71
71
|
}
|
|
72
|
-
|
|
72
|
+
|
|
73
73
|
manager.delegate = nil
|
|
74
74
|
}
|
|
75
|
-
|
|
75
|
+
|
|
76
76
|
serialQueue.sync {
|
|
77
77
|
for p in peripherals.values {
|
|
78
78
|
p.instance.delegate = nil
|
|
79
79
|
}
|
|
80
80
|
}
|
|
81
|
-
|
|
81
|
+
|
|
82
82
|
peripherals = [:]
|
|
83
83
|
}
|
|
84
|
-
|
|
85
|
-
|
|
84
|
+
|
|
85
|
+
|
|
86
86
|
// Helper method to find a peripheral by UUID
|
|
87
87
|
func findPeripheral(byUUID uuid: String) -> Peripheral? {
|
|
88
88
|
var foundPeripheral: Peripheral? = nil
|
|
89
|
-
|
|
89
|
+
|
|
90
90
|
serialQueue.sync {
|
|
91
91
|
if let peripheral = peripherals[uuid] {
|
|
92
92
|
foundPeripheral = peripheral;
|
|
93
93
|
}
|
|
94
94
|
}
|
|
95
|
-
|
|
95
|
+
|
|
96
96
|
return foundPeripheral
|
|
97
97
|
}
|
|
98
|
-
|
|
98
|
+
|
|
99
99
|
// Helper method to insert callback in different queues
|
|
100
100
|
func insertCallback(_ callback: @escaping RCTResponseSenderBlock, intoDictionary dictionary: inout Dictionary<String, [RCTResponseSenderBlock]>, withKey key: String) {
|
|
101
101
|
serialQueue.sync {
|
|
@@ -104,35 +104,35 @@ import CoreBluetooth
|
|
|
104
104
|
dictionary[key] = peripheralCallbacks
|
|
105
105
|
}
|
|
106
106
|
}
|
|
107
|
-
|
|
107
|
+
|
|
108
108
|
// Helper method to call the callbacks for a specific peripheral and clear the queue
|
|
109
109
|
func invokeAndClearDictionary(_ dictionary: inout Dictionary<String, [RCTResponseSenderBlock]>, withKey key: String, usingParameters parameters: [Any]) {
|
|
110
110
|
serialQueue.sync {
|
|
111
111
|
invokeAndClearDictionary_THREAD_UNSAFE(&dictionary, withKey: key, usingParameters: parameters)
|
|
112
112
|
}
|
|
113
113
|
}
|
|
114
|
-
|
|
114
|
+
|
|
115
115
|
func invokeAndClearDictionary_THREAD_UNSAFE(_ dictionary: inout Dictionary<String, [RCTResponseSenderBlock]>, withKey key: String, usingParameters parameters: [Any]) {
|
|
116
116
|
if let peripheralCallbacks = dictionary[key] {
|
|
117
117
|
for callback in peripheralCallbacks {
|
|
118
118
|
callback(parameters)
|
|
119
119
|
}
|
|
120
|
-
|
|
120
|
+
|
|
121
121
|
dictionary.removeValue(forKey: key)
|
|
122
122
|
}
|
|
123
123
|
}
|
|
124
|
-
|
|
124
|
+
|
|
125
125
|
@objc func getContext(_ peripheralUUIDString: String, serviceUUIDString: String, characteristicUUIDString: String, prop: CBCharacteristicProperties, callback: @escaping RCTResponseSenderBlock) -> BLECommandContext? {
|
|
126
126
|
let serviceUUID = CBUUID(string: serviceUUIDString)
|
|
127
127
|
let characteristicUUID = CBUUID(string: characteristicUUIDString)
|
|
128
|
-
|
|
128
|
+
|
|
129
129
|
guard let peripheral = peripherals[peripheralUUIDString] else {
|
|
130
130
|
let error = String(format: "Could not find peripheral with UUID %@", peripheralUUIDString)
|
|
131
131
|
NSLog(error)
|
|
132
132
|
callback([error])
|
|
133
133
|
return nil
|
|
134
134
|
}
|
|
135
|
-
|
|
135
|
+
|
|
136
136
|
guard let service = Helper.findService(fromUUID: serviceUUID, peripheral: peripheral.instance) else {
|
|
137
137
|
let error = String(format: "Could not find service with UUID %@ on peripheral with UUID %@",
|
|
138
138
|
serviceUUIDString,
|
|
@@ -141,19 +141,19 @@ import CoreBluetooth
|
|
|
141
141
|
callback([error])
|
|
142
142
|
return nil
|
|
143
143
|
}
|
|
144
|
-
|
|
144
|
+
|
|
145
145
|
var characteristic = Helper.findCharacteristic(fromUUID: characteristicUUID, service: service, prop: prop)
|
|
146
|
-
|
|
146
|
+
|
|
147
147
|
// Special handling for INDICATE. If characteristic with notify is not found, check for indicate.
|
|
148
148
|
if prop == CBCharacteristicProperties.notify && characteristic == nil {
|
|
149
149
|
characteristic = Helper.findCharacteristic(fromUUID: characteristicUUID, service: service, prop: CBCharacteristicProperties.indicate)
|
|
150
150
|
}
|
|
151
|
-
|
|
151
|
+
|
|
152
152
|
// As a last resort, try to find ANY characteristic with this UUID, even if it doesn't have the correct properties
|
|
153
153
|
if characteristic == nil {
|
|
154
154
|
characteristic = Helper.findCharacteristic(fromUUID: characteristicUUID, service: service)
|
|
155
155
|
}
|
|
156
|
-
|
|
156
|
+
|
|
157
157
|
guard let finalCharacteristic = characteristic else {
|
|
158
158
|
let error = String(format: "Could not find characteristic with UUID %@ on service with UUID %@ on peripheral with UUID %@",
|
|
159
159
|
characteristicUUIDString,
|
|
@@ -163,15 +163,15 @@ import CoreBluetooth
|
|
|
163
163
|
callback([error])
|
|
164
164
|
return nil
|
|
165
165
|
}
|
|
166
|
-
|
|
166
|
+
|
|
167
167
|
let context = BLECommandContext()
|
|
168
168
|
context.peripheral = peripheral
|
|
169
169
|
context.service = service
|
|
170
170
|
context.characteristic = finalCharacteristic
|
|
171
171
|
return context
|
|
172
172
|
}
|
|
173
|
-
|
|
174
|
-
|
|
173
|
+
|
|
174
|
+
|
|
175
175
|
@objc public func start(_ options: NSDictionary,
|
|
176
176
|
callback: RCTResponseSenderBlock) {
|
|
177
177
|
if SwiftBleManager.verboseLogging {
|
|
@@ -186,25 +186,25 @@ import CoreBluetooth
|
|
|
186
186
|
return
|
|
187
187
|
}
|
|
188
188
|
var initOptions = [String: Any]()
|
|
189
|
-
|
|
189
|
+
|
|
190
190
|
if let showAlert = options["showAlert"] as? Bool {
|
|
191
191
|
initOptions[CBCentralManagerOptionShowPowerAlertKey] = showAlert
|
|
192
192
|
}
|
|
193
|
-
|
|
193
|
+
|
|
194
194
|
if let verboseLogging = options["verboseLogging"] as? Bool {
|
|
195
195
|
SwiftBleManager.verboseLogging = verboseLogging
|
|
196
196
|
}
|
|
197
|
-
|
|
197
|
+
|
|
198
198
|
var queue: DispatchQueue
|
|
199
199
|
if let queueIdentifierKey = options["queueIdentifierKey"] as? String {
|
|
200
200
|
queue = DispatchQueue(label: queueIdentifierKey, qos: DispatchQoS.background)
|
|
201
201
|
} else {
|
|
202
202
|
queue = DispatchQueue.main
|
|
203
203
|
}
|
|
204
|
-
|
|
204
|
+
|
|
205
205
|
if let restoreIdentifierKey = options["restoreIdentifierKey"] as? String {
|
|
206
206
|
initOptions[CBCentralManagerOptionRestoreIdentifierKey] = restoreIdentifierKey
|
|
207
|
-
|
|
207
|
+
|
|
208
208
|
if let sharedManager = SwiftBleManager.sharedManager {
|
|
209
209
|
manager = sharedManager
|
|
210
210
|
manager?.delegate = self
|
|
@@ -216,10 +216,10 @@ import CoreBluetooth
|
|
|
216
216
|
manager = CBCentralManager(delegate: self, queue: queue, options: initOptions)
|
|
217
217
|
SwiftBleManager.sharedManager = manager
|
|
218
218
|
}
|
|
219
|
-
|
|
219
|
+
|
|
220
220
|
callback([])
|
|
221
221
|
}
|
|
222
|
-
|
|
222
|
+
|
|
223
223
|
@objc public func scan(_ serviceUUIDStrings: [Any],
|
|
224
224
|
timeoutSeconds: NSNumber,
|
|
225
225
|
allowDuplicates: Bool,
|
|
@@ -230,7 +230,7 @@ import CoreBluetooth
|
|
|
230
230
|
} else {
|
|
231
231
|
NSLog("scan")
|
|
232
232
|
}
|
|
233
|
-
|
|
233
|
+
|
|
234
234
|
// Clear the peripherals before scanning again, otherwise cannot connect again after disconnection
|
|
235
235
|
// Only clear peripherals that are not connected - otherwise connections fail silently (without any
|
|
236
236
|
// onDisconnect* callback).
|
|
@@ -241,24 +241,24 @@ import CoreBluetooth
|
|
|
241
241
|
peripherals.removeValue(forKey: uuid)
|
|
242
242
|
}
|
|
243
243
|
}
|
|
244
|
-
|
|
244
|
+
|
|
245
245
|
var serviceUUIDs = [CBUUID]()
|
|
246
246
|
if let serviceUUIDStrings = serviceUUIDStrings as? [String] {
|
|
247
247
|
serviceUUIDs = serviceUUIDStrings.map { CBUUID(string: $0) }
|
|
248
248
|
}
|
|
249
|
-
|
|
249
|
+
|
|
250
250
|
var options: [String: Any]?
|
|
251
251
|
if allowDuplicates {
|
|
252
252
|
options = [CBCentralManagerScanOptionAllowDuplicatesKey: true]
|
|
253
253
|
}
|
|
254
|
-
|
|
254
|
+
|
|
255
255
|
exactAdvertisingName.removeAll()
|
|
256
256
|
if let names = scanningOptions["exactAdvertisingName"] as? [String] {
|
|
257
257
|
exactAdvertisingName.append(contentsOf: names)
|
|
258
258
|
}
|
|
259
|
-
|
|
259
|
+
|
|
260
260
|
manager?.scanForPeripherals(withServices: serviceUUIDs, options: options)
|
|
261
|
-
|
|
261
|
+
|
|
262
262
|
if timeoutSeconds.doubleValue > 0 {
|
|
263
263
|
if let scanTimer = scanTimer {
|
|
264
264
|
scanTimer.invalidate()
|
|
@@ -268,46 +268,46 @@ import CoreBluetooth
|
|
|
268
268
|
self.scanTimer = Timer.scheduledTimer(timeInterval: timeoutSeconds.doubleValue, target: self, selector: #selector(self.stopTimer), userInfo: nil, repeats: false)
|
|
269
269
|
}
|
|
270
270
|
}
|
|
271
|
-
|
|
271
|
+
|
|
272
272
|
callback([])
|
|
273
273
|
}
|
|
274
|
-
|
|
274
|
+
|
|
275
275
|
@objc func stopTimer() {
|
|
276
276
|
NSLog("Stop scan");
|
|
277
277
|
scanTimer = nil;
|
|
278
278
|
manager?.stopScan()
|
|
279
279
|
bleManager?.emit(onStopScan: ["status": 10])
|
|
280
280
|
}
|
|
281
|
-
|
|
282
|
-
|
|
281
|
+
|
|
282
|
+
|
|
283
283
|
@objc public func stopScan(_ callback: @escaping RCTResponseSenderBlock) {
|
|
284
284
|
if let scanTimer = self.scanTimer {
|
|
285
285
|
scanTimer.invalidate()
|
|
286
286
|
self.scanTimer = nil
|
|
287
287
|
}
|
|
288
|
-
|
|
288
|
+
|
|
289
289
|
manager?.stopScan()
|
|
290
|
-
|
|
290
|
+
|
|
291
291
|
bleManager?.emit(onStopScan: ["status": 0])
|
|
292
|
-
|
|
292
|
+
|
|
293
293
|
callback([])
|
|
294
294
|
}
|
|
295
|
-
|
|
296
|
-
|
|
295
|
+
|
|
296
|
+
|
|
297
297
|
@objc public func connect(_ peripheralUUID: String,
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
298
|
+
options: NSDictionary,
|
|
299
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
300
|
+
|
|
301
301
|
if let peripheral = peripherals[peripheralUUID] {
|
|
302
302
|
// Found the peripheral, connect to it
|
|
303
303
|
NSLog("Connecting to peripheral with UUID: \(peripheralUUID)")
|
|
304
|
-
|
|
304
|
+
|
|
305
305
|
insertCallback(callback, intoDictionary: &connectCallbacks, withKey: peripheral.instance.uuidAsString())
|
|
306
306
|
manager?.connect(peripheral.instance)
|
|
307
307
|
} else {
|
|
308
308
|
// Try to retrieve the peripheral
|
|
309
309
|
NSLog("Retrieving peripheral with UUID: \(peripheralUUID)")
|
|
310
|
-
|
|
310
|
+
|
|
311
311
|
if let uuid = UUID(uuidString: peripheralUUID) {
|
|
312
312
|
let peripheralArray = manager?.retrievePeripherals(withIdentifiers: [uuid])
|
|
313
313
|
if let retrievedPeripheral = peripheralArray?.first {
|
|
@@ -315,7 +315,7 @@ import CoreBluetooth
|
|
|
315
315
|
peripherals[retrievedPeripheral.uuidAsString()] = Peripheral(peripheral:retrievedPeripheral)
|
|
316
316
|
}
|
|
317
317
|
NSLog("Successfully retrieved and connecting to peripheral with UUID: \(peripheralUUID)")
|
|
318
|
-
|
|
318
|
+
|
|
319
319
|
// Connect to the retrieved peripheral
|
|
320
320
|
insertCallback(callback, intoDictionary: &connectCallbacks, withKey: retrievedPeripheral.uuidAsString())
|
|
321
321
|
manager?.connect(retrievedPeripheral, options: nil)
|
|
@@ -330,13 +330,13 @@ import CoreBluetooth
|
|
|
330
330
|
}
|
|
331
331
|
}
|
|
332
332
|
}
|
|
333
|
-
|
|
333
|
+
|
|
334
334
|
@objc public func disconnect(_ peripheralUUID: String,
|
|
335
|
-
|
|
336
|
-
|
|
335
|
+
force: Bool,
|
|
336
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
337
337
|
if let peripheral = peripherals[peripheralUUID] {
|
|
338
338
|
NSLog("Disconnecting from peripheral with UUID: \(peripheralUUID)")
|
|
339
|
-
|
|
339
|
+
|
|
340
340
|
if let services = peripheral.instance.services {
|
|
341
341
|
for service in services {
|
|
342
342
|
if let characteristics = service.characteristics {
|
|
@@ -349,46 +349,46 @@ import CoreBluetooth
|
|
|
349
349
|
}
|
|
350
350
|
}
|
|
351
351
|
}
|
|
352
|
-
|
|
352
|
+
|
|
353
353
|
manager?.cancelPeripheralConnection(peripheral.instance)
|
|
354
354
|
callback([])
|
|
355
|
-
|
|
355
|
+
|
|
356
356
|
} else {
|
|
357
357
|
let error = "Could not find peripheral \(peripheralUUID)."
|
|
358
358
|
NSLog(error)
|
|
359
359
|
callback([error])
|
|
360
360
|
}
|
|
361
361
|
}
|
|
362
|
-
|
|
362
|
+
|
|
363
363
|
@objc public func retrieveServices(_ peripheralUUID: String,
|
|
364
|
-
|
|
365
|
-
|
|
364
|
+
services: [String],
|
|
365
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
366
366
|
NSLog("retrieveServices \(services)")
|
|
367
|
-
|
|
367
|
+
|
|
368
368
|
if let peripheral = peripherals[peripheralUUID], peripheral.instance.state == .connected {
|
|
369
369
|
insertCallback(callback, intoDictionary: &retrieveServicesCallbacks, withKey: peripheral.instance.uuidAsString())
|
|
370
|
-
|
|
370
|
+
|
|
371
371
|
var uuids: [CBUUID] = []
|
|
372
372
|
for string in services {
|
|
373
373
|
let uuid = CBUUID(string: string)
|
|
374
374
|
uuids.append(uuid)
|
|
375
375
|
}
|
|
376
|
-
|
|
376
|
+
|
|
377
377
|
if !uuids.isEmpty {
|
|
378
378
|
peripheral.instance.discoverServices(uuids)
|
|
379
379
|
} else {
|
|
380
380
|
peripheral.instance.discoverServices(nil)
|
|
381
381
|
}
|
|
382
|
-
|
|
382
|
+
|
|
383
383
|
} else {
|
|
384
384
|
callback(["Peripheral not found or not connected"])
|
|
385
385
|
}
|
|
386
386
|
}
|
|
387
|
-
|
|
387
|
+
|
|
388
388
|
@objc public func readRSSI(_ peripheralUUID: String,
|
|
389
|
-
|
|
389
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
390
390
|
NSLog("readRSSI")
|
|
391
|
-
|
|
391
|
+
|
|
392
392
|
if let peripheral = peripherals[peripheralUUID], peripheral.instance.state == .connected {
|
|
393
393
|
insertCallback(callback, intoDictionary: &readRSSICallbacks, withKey: peripheral.instance.uuidAsString())
|
|
394
394
|
peripheral.instance.readRSSI()
|
|
@@ -396,93 +396,93 @@ import CoreBluetooth
|
|
|
396
396
|
callback(["Peripheral not found or not connected"])
|
|
397
397
|
}
|
|
398
398
|
}
|
|
399
|
-
|
|
399
|
+
|
|
400
400
|
@objc public func readDescriptor(_ peripheralUUID: String,
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
401
|
+
serviceUUID: String,
|
|
402
|
+
characteristicUUID: String,
|
|
403
|
+
descriptorUUID: String,
|
|
404
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
405
405
|
NSLog("readDescriptor")
|
|
406
|
-
|
|
406
|
+
|
|
407
407
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.read, callback: callback) else {
|
|
408
408
|
return
|
|
409
409
|
}
|
|
410
|
-
|
|
410
|
+
|
|
411
411
|
let peripheral = context.peripheral
|
|
412
412
|
let characteristic = context.characteristic
|
|
413
|
-
|
|
413
|
+
|
|
414
414
|
guard let descriptor = Helper.findDescriptor(fromUUID: CBUUID(string: descriptorUUID), characteristic: characteristic!) else {
|
|
415
415
|
let error = "Could not find descriptor with UUID \(descriptorUUID) on characteristic with UUID \(String(describing: characteristic?.uuid.uuidString)) on peripheral with UUID \(peripheralUUID)"
|
|
416
416
|
NSLog(error)
|
|
417
417
|
callback([error])
|
|
418
418
|
return
|
|
419
419
|
}
|
|
420
|
-
|
|
420
|
+
|
|
421
421
|
if let peripheral = peripheral?.instance {
|
|
422
422
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: characteristic!, andDescriptor: descriptor)
|
|
423
423
|
insertCallback(callback, intoDictionary: &readDescriptorCallbacks, withKey: key)
|
|
424
|
-
|
|
424
|
+
|
|
425
425
|
}
|
|
426
|
-
|
|
426
|
+
|
|
427
427
|
peripheral?.instance.readValue(for: descriptor)
|
|
428
428
|
}
|
|
429
|
-
|
|
429
|
+
|
|
430
430
|
@objc public func writeDescriptor(_ peripheralUUID: String,
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
431
|
+
serviceUUID: String,
|
|
432
|
+
characteristicUUID: String,
|
|
433
|
+
descriptorUUID: String,
|
|
434
|
+
message: [UInt8],
|
|
435
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
436
436
|
NSLog("writeDescriptor")
|
|
437
|
-
|
|
437
|
+
|
|
438
438
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.read, callback: callback) else {
|
|
439
439
|
return
|
|
440
440
|
}
|
|
441
|
-
|
|
441
|
+
|
|
442
442
|
let peripheral = context.peripheral
|
|
443
443
|
let characteristic = context.characteristic
|
|
444
|
-
|
|
444
|
+
|
|
445
445
|
guard let descriptor = Helper.findDescriptor(fromUUID: CBUUID(string: descriptorUUID), characteristic: characteristic!) else {
|
|
446
446
|
let error = "Could not find descriptor with UUID \(descriptorUUID) on characteristic with UUID \(String(describing: characteristic?.uuid.uuidString)) on peripheral with UUID \(peripheralUUID)"
|
|
447
447
|
NSLog(error)
|
|
448
448
|
callback([error])
|
|
449
449
|
return
|
|
450
450
|
}
|
|
451
|
-
|
|
451
|
+
|
|
452
452
|
if let peripheral = peripheral?.instance {
|
|
453
453
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: characteristic!, andDescriptor: descriptor)
|
|
454
454
|
insertCallback(callback, intoDictionary: &writeDescriptorCallbacks, withKey: key)
|
|
455
|
-
|
|
455
|
+
|
|
456
456
|
}
|
|
457
|
-
|
|
457
|
+
|
|
458
458
|
let dataMessage = Data(message)
|
|
459
459
|
peripheral?.instance.writeValue(dataMessage, for: descriptor)
|
|
460
460
|
}
|
|
461
|
-
|
|
461
|
+
|
|
462
462
|
@objc public func getDiscoveredPeripherals(_ callback: @escaping RCTResponseSenderBlock) {
|
|
463
463
|
NSLog("Get discovered peripherals")
|
|
464
464
|
var discoveredPeripherals: [[String: Any]] = []
|
|
465
|
-
|
|
465
|
+
|
|
466
466
|
serialQueue.sync {
|
|
467
467
|
for (_, peripheral) in peripherals {
|
|
468
468
|
discoveredPeripherals.append(peripheral.advertisingInfo())
|
|
469
469
|
}
|
|
470
470
|
}
|
|
471
|
-
|
|
471
|
+
|
|
472
472
|
callback([NSNull(), discoveredPeripherals])
|
|
473
473
|
}
|
|
474
|
-
|
|
474
|
+
|
|
475
475
|
@objc public func getConnectedPeripherals(_ serviceUUIDStrings: [String],
|
|
476
|
-
|
|
476
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
477
477
|
NSLog("Get connected peripherals")
|
|
478
478
|
var serviceUUIDs: [CBUUID] = []
|
|
479
|
-
|
|
479
|
+
|
|
480
480
|
for uuidString in serviceUUIDStrings {
|
|
481
481
|
serviceUUIDs.append(CBUUID(string: uuidString))
|
|
482
482
|
}
|
|
483
|
-
|
|
483
|
+
|
|
484
484
|
var connectedPeripherals: [Peripheral] = []
|
|
485
|
-
|
|
485
|
+
|
|
486
486
|
if serviceUUIDs.isEmpty {
|
|
487
487
|
serialQueue.sync {
|
|
488
488
|
connectedPeripherals = peripherals.filter({ $0.value.instance.state == .connected }).map({ p in
|
|
@@ -491,7 +491,7 @@ import CoreBluetooth
|
|
|
491
491
|
}
|
|
492
492
|
} else {
|
|
493
493
|
let connectedCBPeripherals: [CBPeripheral] = manager?.retrieveConnectedPeripherals(withServices: serviceUUIDs) ?? []
|
|
494
|
-
|
|
494
|
+
|
|
495
495
|
serialQueue.sync {
|
|
496
496
|
for ph in connectedCBPeripherals {
|
|
497
497
|
if let peripheral = peripherals[ph.uuidAsString()] {
|
|
@@ -502,26 +502,26 @@ import CoreBluetooth
|
|
|
502
502
|
}
|
|
503
503
|
}
|
|
504
504
|
}
|
|
505
|
-
|
|
505
|
+
|
|
506
506
|
var foundedPeripherals: [[String: Any]] = []
|
|
507
|
-
|
|
507
|
+
|
|
508
508
|
for peripheral in connectedPeripherals {
|
|
509
509
|
foundedPeripherals.append(peripheral.advertisingInfo())
|
|
510
510
|
}
|
|
511
|
-
|
|
511
|
+
|
|
512
512
|
callback([NSNull(), foundedPeripherals])
|
|
513
513
|
}
|
|
514
|
-
|
|
514
|
+
|
|
515
515
|
@objc public func isPeripheralConnected(_ peripheralUUID: String,
|
|
516
|
-
|
|
517
|
-
|
|
516
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
517
|
+
|
|
518
518
|
if let peripheral = peripherals[peripheralUUID] {
|
|
519
519
|
callback([NSNull(), peripheral.instance.state == .connected])
|
|
520
520
|
} else {
|
|
521
521
|
callback(["Peripheral not found"])
|
|
522
522
|
}
|
|
523
523
|
}
|
|
524
|
-
|
|
524
|
+
|
|
525
525
|
@objc public func isScanning(_ callback: @escaping RCTResponseSenderBlock) {
|
|
526
526
|
if let manager = manager {
|
|
527
527
|
callback([NSNull(), manager.isScanning])
|
|
@@ -529,38 +529,38 @@ import CoreBluetooth
|
|
|
529
529
|
callback(["CBCentralManager not found"])
|
|
530
530
|
}
|
|
531
531
|
}
|
|
532
|
-
|
|
532
|
+
|
|
533
533
|
@objc public func checkState(_ callback: @escaping RCTResponseSenderBlock) {
|
|
534
534
|
if let manager = manager {
|
|
535
535
|
centralManagerDidUpdateState(manager)
|
|
536
|
-
|
|
536
|
+
|
|
537
537
|
let stateName = Helper.centralManagerStateToString(manager.state)
|
|
538
538
|
callback([stateName])
|
|
539
539
|
}
|
|
540
540
|
}
|
|
541
|
-
|
|
541
|
+
|
|
542
542
|
@objc public func write(_ peripheralUUID: String,
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
543
|
+
serviceUUID: String,
|
|
544
|
+
characteristicUUID: String,
|
|
545
|
+
message: [UInt8],
|
|
546
|
+
maxByteSize: Int,
|
|
547
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
548
548
|
NSLog("write")
|
|
549
|
-
|
|
549
|
+
|
|
550
550
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.write, callback: callback) else {
|
|
551
551
|
return
|
|
552
552
|
}
|
|
553
|
-
|
|
553
|
+
|
|
554
554
|
let dataMessage = Data(message)
|
|
555
|
-
|
|
555
|
+
|
|
556
556
|
if let peripheral = context.peripheral, let characteristic = context.characteristic {
|
|
557
557
|
let key = Helper.key(forPeripheral:peripheral.instance, andCharacteristic: characteristic)
|
|
558
558
|
insertCallback(callback, intoDictionary: &writeCallbacks, withKey: key)
|
|
559
|
-
|
|
559
|
+
|
|
560
560
|
if SwiftBleManager.verboseLogging {
|
|
561
561
|
NSLog("Message to write(\(dataMessage.count)): \(dataMessage.hexadecimalString())")
|
|
562
562
|
}
|
|
563
|
-
|
|
563
|
+
|
|
564
564
|
if dataMessage.count > maxByteSize {
|
|
565
565
|
var count = 0
|
|
566
566
|
var offset = 0
|
|
@@ -570,16 +570,16 @@ import CoreBluetooth
|
|
|
570
570
|
count += maxByteSize
|
|
571
571
|
offset += maxByteSize
|
|
572
572
|
}
|
|
573
|
-
|
|
573
|
+
|
|
574
574
|
if count < dataMessage.count {
|
|
575
575
|
let splitMessage = dataMessage.subdata(in: offset..<dataMessage.count)
|
|
576
576
|
writeQueue.append(splitMessage)
|
|
577
577
|
}
|
|
578
|
-
|
|
578
|
+
|
|
579
579
|
if SwiftBleManager.verboseLogging {
|
|
580
580
|
NSLog("Queued splitted message: \(writeQueue.count)")
|
|
581
581
|
}
|
|
582
|
-
|
|
582
|
+
|
|
583
583
|
if case let firstMessage as Data = writeQueue.removeFirst() {
|
|
584
584
|
peripheral.instance.writeValue(firstMessage, for: characteristic, type: .withResponse)
|
|
585
585
|
}
|
|
@@ -588,103 +588,113 @@ import CoreBluetooth
|
|
|
588
588
|
}
|
|
589
589
|
}
|
|
590
590
|
}
|
|
591
|
-
|
|
591
|
+
|
|
592
592
|
@objc public func writeWithoutResponse(_ peripheralUUID: String,
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
593
|
+
serviceUUID: String,
|
|
594
|
+
characteristicUUID: String,
|
|
595
|
+
message: [UInt8],
|
|
596
|
+
maxByteSize: Int,
|
|
597
|
+
queueSleepTime: Int,
|
|
598
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
599
599
|
NSLog("writeWithoutResponse")
|
|
600
|
-
|
|
600
|
+
|
|
601
601
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.writeWithoutResponse, callback: callback) else {
|
|
602
602
|
return
|
|
603
603
|
}
|
|
604
|
-
|
|
604
|
+
|
|
605
605
|
let dataMessage = Data(message)
|
|
606
|
-
|
|
606
|
+
|
|
607
607
|
if SwiftBleManager.verboseLogging {
|
|
608
608
|
NSLog("Message to write(\(dataMessage.count)): \(dataMessage.hexadecimalString())")
|
|
609
609
|
}
|
|
610
|
-
|
|
610
|
+
|
|
611
611
|
if dataMessage.count > maxByteSize {
|
|
612
612
|
var offset = 0
|
|
613
613
|
let peripheral = context.peripheral
|
|
614
614
|
guard let characteristic = context.characteristic else { return }
|
|
615
|
-
|
|
615
|
+
|
|
616
616
|
repeat {
|
|
617
617
|
let thisChunkSize = min(maxByteSize, dataMessage.count - offset)
|
|
618
618
|
let chunk = dataMessage.subdata(in: offset..<offset + thisChunkSize)
|
|
619
|
-
|
|
619
|
+
|
|
620
620
|
offset += thisChunkSize
|
|
621
621
|
peripheral?.instance.writeValue(chunk, for: characteristic, type: .withoutResponse)
|
|
622
|
-
|
|
622
|
+
|
|
623
623
|
let sleepTimeSeconds = TimeInterval(queueSleepTime) / 1000
|
|
624
624
|
Thread.sleep(forTimeInterval: sleepTimeSeconds)
|
|
625
625
|
} while offset < dataMessage.count
|
|
626
|
-
|
|
626
|
+
|
|
627
627
|
callback([])
|
|
628
628
|
} else {
|
|
629
629
|
let peripheral = context.peripheral
|
|
630
630
|
guard let characteristic = context.characteristic else { return }
|
|
631
|
-
|
|
631
|
+
|
|
632
632
|
peripheral?.instance.writeValue(dataMessage, for: characteristic, type: .withoutResponse)
|
|
633
633
|
callback([])
|
|
634
634
|
}
|
|
635
635
|
}
|
|
636
|
-
|
|
636
|
+
|
|
637
637
|
@objc public func read(_ peripheralUUID: String,
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
638
|
+
serviceUUID: String,
|
|
639
|
+
characteristicUUID: String,
|
|
640
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
641
641
|
NSLog("read")
|
|
642
|
-
|
|
642
|
+
|
|
643
643
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.read, callback: callback) else {
|
|
644
644
|
return
|
|
645
645
|
}
|
|
646
|
-
|
|
646
|
+
|
|
647
647
|
let peripheral = context.peripheral
|
|
648
648
|
let characteristic = context.characteristic
|
|
649
|
-
|
|
649
|
+
|
|
650
650
|
let key = Helper.key(forPeripheral:peripheral!.instance as CBPeripheral, andCharacteristic: characteristic!)
|
|
651
651
|
insertCallback(callback, intoDictionary: &readCallbacks, withKey: key)
|
|
652
|
-
|
|
652
|
+
|
|
653
653
|
peripheral?.instance.readValue(for: characteristic!) // callback sends value
|
|
654
654
|
}
|
|
655
|
-
|
|
655
|
+
|
|
656
|
+
|
|
657
|
+
|
|
658
|
+
@objc public func startNotificationWithBuffer(_ peripheralUUID: String,
|
|
659
|
+
serviceUUID: String,
|
|
660
|
+
characteristicUUID: String,
|
|
661
|
+
bufferLength: NSNumber,
|
|
662
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
663
|
+
callback(["Not supported"])
|
|
664
|
+
}
|
|
665
|
+
|
|
656
666
|
@objc public func startNotification(_ peripheralUUID: String,
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
667
|
+
serviceUUID: String,
|
|
668
|
+
characteristicUUID: String,
|
|
669
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
660
670
|
NSLog("startNotification")
|
|
661
|
-
|
|
671
|
+
|
|
662
672
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.notify, callback: callback) else {
|
|
663
673
|
return
|
|
664
674
|
}
|
|
665
|
-
|
|
675
|
+
|
|
666
676
|
guard let peripheral = context.peripheral else { return }
|
|
667
677
|
guard let characteristic = context.characteristic else { return }
|
|
668
|
-
|
|
678
|
+
|
|
669
679
|
let key = Helper.key(forPeripheral: (peripheral.instance as CBPeripheral?)!, andCharacteristic: characteristic)
|
|
670
680
|
insertCallback(callback, intoDictionary: ¬ificationCallbacks, withKey: key)
|
|
671
|
-
|
|
681
|
+
|
|
672
682
|
peripheral.instance.setNotifyValue(true, for: characteristic)
|
|
673
683
|
}
|
|
674
|
-
|
|
684
|
+
|
|
675
685
|
@objc public func stopNotification(_ peripheralUUID: String,
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
686
|
+
serviceUUID: String,
|
|
687
|
+
characteristicUUID: String,
|
|
688
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
679
689
|
NSLog("stopNotification")
|
|
680
|
-
|
|
690
|
+
|
|
681
691
|
guard let context = getContext(peripheralUUID, serviceUUIDString: serviceUUID, characteristicUUIDString: characteristicUUID, prop: CBCharacteristicProperties.notify, callback: callback) else {
|
|
682
692
|
return
|
|
683
693
|
}
|
|
684
|
-
|
|
694
|
+
|
|
685
695
|
let peripheral = context.peripheral
|
|
686
696
|
guard let characteristic = context.characteristic else { return }
|
|
687
|
-
|
|
697
|
+
|
|
688
698
|
if characteristic.isNotifying {
|
|
689
699
|
let key = Helper.key(forPeripheral: (peripheral?.instance as CBPeripheral?)!, andCharacteristic: characteristic)
|
|
690
700
|
insertCallback(callback, intoDictionary: &stopNotificationCallbacks, withKey: key)
|
|
@@ -695,16 +705,16 @@ import CoreBluetooth
|
|
|
695
705
|
callback([])
|
|
696
706
|
}
|
|
697
707
|
}
|
|
698
|
-
|
|
708
|
+
|
|
699
709
|
@objc public func getMaximumWriteValueLengthForWithoutResponse(_ peripheralUUID: String,
|
|
700
|
-
|
|
710
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
701
711
|
NSLog("getMaximumWriteValueLengthForWithoutResponse")
|
|
702
|
-
|
|
712
|
+
|
|
703
713
|
guard let peripheral = peripherals[peripheralUUID] else {
|
|
704
714
|
callback(["Peripheral not found or not connected"])
|
|
705
715
|
return
|
|
706
716
|
}
|
|
707
|
-
|
|
717
|
+
|
|
708
718
|
if peripheral.instance.state == .connected {
|
|
709
719
|
let max = NSNumber(value: peripheral.instance.maximumWriteValueLength(for: .withoutResponse))
|
|
710
720
|
callback([NSNull(), max])
|
|
@@ -712,16 +722,16 @@ import CoreBluetooth
|
|
|
712
722
|
callback(["Peripheral not found or not connected"])
|
|
713
723
|
}
|
|
714
724
|
}
|
|
715
|
-
|
|
725
|
+
|
|
716
726
|
@objc public func getMaximumWriteValueLengthForWithResponse(_ peripheralUUID: String,
|
|
717
|
-
|
|
727
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
718
728
|
NSLog("getMaximumWriteValueLengthForWithResponse")
|
|
719
|
-
|
|
729
|
+
|
|
720
730
|
guard let peripheral = peripherals[peripheralUUID] else {
|
|
721
731
|
callback(["Peripheral not found or not connected"])
|
|
722
732
|
return
|
|
723
733
|
}
|
|
724
|
-
|
|
734
|
+
|
|
725
735
|
if peripheral.instance.state == .connected {
|
|
726
736
|
let max = NSNumber(value: peripheral.instance.maximumWriteValueLength(for: .withResponse))
|
|
727
737
|
callback([NSNull(), max])
|
|
@@ -729,7 +739,7 @@ import CoreBluetooth
|
|
|
729
739
|
callback(["Peripheral not found or not connected"])
|
|
730
740
|
}
|
|
731
741
|
}
|
|
732
|
-
|
|
742
|
+
|
|
733
743
|
public func centralManager(_ central: CBCentralManager, willRestoreState dict: [String : Any]) {
|
|
734
744
|
if let restoredPeripherals = dict[CBCentralManagerRestoredStatePeripheralsKey] as? [CBPeripheral], restoredPeripherals.count > 0 {
|
|
735
745
|
serialQueue.sync {
|
|
@@ -744,13 +754,13 @@ import CoreBluetooth
|
|
|
744
754
|
}
|
|
745
755
|
}
|
|
746
756
|
}
|
|
747
|
-
|
|
748
|
-
|
|
757
|
+
|
|
758
|
+
|
|
749
759
|
public func centralManager(_ central: CBCentralManager,
|
|
750
|
-
|
|
760
|
+
didConnect peripheral: CBPeripheral) {
|
|
751
761
|
NSLog("Peripheral Connected: \(peripheral.uuidAsString() )")
|
|
752
762
|
peripheral.delegate = self
|
|
753
|
-
|
|
763
|
+
|
|
754
764
|
/*
|
|
755
765
|
The state of the peripheral isn't necessarily updated until a small
|
|
756
766
|
delay after didConnectPeripheral is called and in the meantime
|
|
@@ -760,69 +770,69 @@ import CoreBluetooth
|
|
|
760
770
|
Timer.scheduledTimer(withTimeInterval: 0.002, repeats: false) { timer in
|
|
761
771
|
// didFailToConnectPeripheral should have been called already if not connected by now
|
|
762
772
|
self.invokeAndClearDictionary(&self.connectCallbacks, withKey: peripheral.uuidAsString(), usingParameters: [NSNull()])
|
|
763
|
-
|
|
773
|
+
|
|
764
774
|
self.connectedPeripherals.insert(peripheral.uuidAsString())
|
|
765
775
|
self.bleManager?.emit(onConnectPeripheral: ["peripheral": peripheral.uuidAsString()])
|
|
766
776
|
}
|
|
767
777
|
}
|
|
768
778
|
}
|
|
769
|
-
|
|
779
|
+
|
|
770
780
|
public func centralManager(_ central: CBCentralManager,
|
|
771
|
-
|
|
772
|
-
|
|
781
|
+
didFailToConnect peripheral: CBPeripheral,
|
|
782
|
+
error: Error?) {
|
|
773
783
|
let errorStr = "Peripheral connection failure: \(peripheral.uuidAsString() ) (\(error?.localizedDescription ?? "")"
|
|
774
784
|
NSLog(errorStr)
|
|
775
|
-
|
|
785
|
+
|
|
776
786
|
invokeAndClearDictionary(&connectCallbacks, withKey: peripheral.uuidAsString(), usingParameters: [errorStr])
|
|
777
787
|
}
|
|
778
|
-
|
|
788
|
+
|
|
779
789
|
public func centralManager(_ central: CBCentralManager,
|
|
780
|
-
|
|
781
|
-
|
|
790
|
+
didDisconnectPeripheral peripheral:
|
|
791
|
+
CBPeripheral, error: Error?) {
|
|
782
792
|
let peripheralUUIDString:String = peripheral.uuidAsString()
|
|
783
793
|
NSLog("Peripheral Disconnected: \(peripheralUUIDString)")
|
|
784
|
-
|
|
794
|
+
|
|
785
795
|
if let error = error {
|
|
786
796
|
NSLog("Error: \(error)")
|
|
787
797
|
}
|
|
788
|
-
|
|
798
|
+
|
|
789
799
|
let errorStr = "Peripheral did disconnect: \(peripheralUUIDString)"
|
|
790
|
-
|
|
800
|
+
|
|
791
801
|
invokeAndClearDictionary(&connectCallbacks, withKey: peripheralUUIDString, usingParameters: [errorStr])
|
|
792
802
|
invokeAndClearDictionary(&readRSSICallbacks, withKey: peripheralUUIDString, usingParameters: [errorStr])
|
|
793
803
|
invokeAndClearDictionary(&retrieveServicesCallbacks, withKey: peripheralUUIDString, usingParameters: [errorStr])
|
|
794
|
-
|
|
795
|
-
|
|
804
|
+
|
|
805
|
+
|
|
796
806
|
for key in readCallbacks.keys {
|
|
797
807
|
if let keyString = key as String?, keyString.hasPrefix(peripheralUUIDString) {
|
|
798
808
|
invokeAndClearDictionary(&readCallbacks, withKey: key, usingParameters: [errorStr])
|
|
799
809
|
}
|
|
800
810
|
}
|
|
801
|
-
|
|
811
|
+
|
|
802
812
|
for key in writeCallbacks.keys {
|
|
803
813
|
if let keyString = key as String?, keyString.hasPrefix(peripheralUUIDString) {
|
|
804
814
|
invokeAndClearDictionary(&writeCallbacks, withKey: key, usingParameters: [errorStr])
|
|
805
815
|
}
|
|
806
816
|
}
|
|
807
|
-
|
|
817
|
+
|
|
808
818
|
for key in notificationCallbacks.keys {
|
|
809
819
|
if let keyString = key as String?, keyString.hasPrefix(peripheralUUIDString) {
|
|
810
820
|
invokeAndClearDictionary(¬ificationCallbacks, withKey: key, usingParameters: [errorStr])
|
|
811
821
|
}
|
|
812
822
|
}
|
|
813
|
-
|
|
823
|
+
|
|
814
824
|
for key in readDescriptorCallbacks.keys {
|
|
815
825
|
if let keyString = key as String?, keyString.hasPrefix(peripheralUUIDString) {
|
|
816
826
|
invokeAndClearDictionary(&readDescriptorCallbacks, withKey: key, usingParameters: [errorStr])
|
|
817
827
|
}
|
|
818
828
|
}
|
|
819
|
-
|
|
829
|
+
|
|
820
830
|
for key in stopNotificationCallbacks.keys {
|
|
821
831
|
if let keyString = key as String?, keyString.hasPrefix(peripheralUUIDString) {
|
|
822
832
|
invokeAndClearDictionary(&stopNotificationCallbacks, withKey: key, usingParameters: [errorStr])
|
|
823
833
|
}
|
|
824
834
|
}
|
|
825
|
-
|
|
835
|
+
|
|
826
836
|
connectedPeripherals.remove(peripheralUUIDString)
|
|
827
837
|
if let e:Error = error {
|
|
828
838
|
self.bleManager?.emit(onDisconnectPeripheral: ["peripheral": peripheralUUIDString, "domain": e._domain, "code": e._code, "description": e.localizedDescription])
|
|
@@ -830,8 +840,8 @@ import CoreBluetooth
|
|
|
830
840
|
self.bleManager?.emit(onDisconnectPeripheral: ["peripheral": peripheralUUIDString])
|
|
831
841
|
}
|
|
832
842
|
}
|
|
833
|
-
|
|
834
|
-
|
|
843
|
+
|
|
844
|
+
|
|
835
845
|
public func centralManagerDidUpdateState(_ central: CBCentralManager) {
|
|
836
846
|
let stateName = Helper.centralManagerStateToString(central.state)
|
|
837
847
|
self.bleManager?.emit(onDidUpdateState: ["state": stateName])
|
|
@@ -845,14 +855,14 @@ import CoreBluetooth
|
|
|
845
855
|
}
|
|
846
856
|
}
|
|
847
857
|
}
|
|
848
|
-
|
|
858
|
+
|
|
849
859
|
func handleDiscoveredPeripheral(_ peripheral: CBPeripheral,
|
|
850
860
|
advertisementData: [String : Any],
|
|
851
861
|
rssi : NSNumber) {
|
|
852
862
|
if SwiftBleManager.verboseLogging {
|
|
853
863
|
NSLog("Discover peripheral: \(peripheral.name ?? "NO NAME")");
|
|
854
864
|
}
|
|
855
|
-
|
|
865
|
+
|
|
856
866
|
var cp: Peripheral? = nil
|
|
857
867
|
serialQueue.sync {
|
|
858
868
|
if let p = peripherals[peripheral.uuidAsString()] {
|
|
@@ -864,14 +874,14 @@ import CoreBluetooth
|
|
|
864
874
|
peripherals[peripheral.uuidAsString()] = cp
|
|
865
875
|
}
|
|
866
876
|
}
|
|
867
|
-
|
|
877
|
+
|
|
868
878
|
self.bleManager?.emit(onDiscoverPeripheral: cp?.advertisingInfo())
|
|
869
879
|
}
|
|
870
|
-
|
|
880
|
+
|
|
871
881
|
public func centralManager(_ central: CBCentralManager,
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
882
|
+
didDiscover peripheral: CBPeripheral,
|
|
883
|
+
advertisementData: [String : Any],
|
|
884
|
+
rssi RSSI: NSNumber) {
|
|
875
885
|
if exactAdvertisingName.count > 0 {
|
|
876
886
|
if let peripheralName = peripheral.name {
|
|
877
887
|
if exactAdvertisingName.contains(peripheralName) {
|
|
@@ -887,12 +897,12 @@ import CoreBluetooth
|
|
|
887
897
|
} else {
|
|
888
898
|
handleDiscoveredPeripheral(peripheral, advertisementData: advertisementData, rssi: RSSI)
|
|
889
899
|
}
|
|
890
|
-
|
|
891
|
-
|
|
900
|
+
|
|
901
|
+
|
|
892
902
|
}
|
|
893
|
-
|
|
903
|
+
|
|
894
904
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
895
|
-
|
|
905
|
+
didDiscoverServices error: Error?) {
|
|
896
906
|
if let error = error {
|
|
897
907
|
NSLog("Error: \(error)")
|
|
898
908
|
return
|
|
@@ -900,11 +910,11 @@ import CoreBluetooth
|
|
|
900
910
|
if SwiftBleManager.verboseLogging {
|
|
901
911
|
NSLog("Services Discover")
|
|
902
912
|
}
|
|
903
|
-
|
|
913
|
+
|
|
904
914
|
var servicesForPeripheral = Set<CBService>()
|
|
905
915
|
servicesForPeripheral.formUnion(peripheral.services ?? [])
|
|
906
916
|
retrieveServicesLatches[peripheral.uuidAsString()] = servicesForPeripheral
|
|
907
|
-
|
|
917
|
+
|
|
908
918
|
if let services = peripheral.services {
|
|
909
919
|
for service in services {
|
|
910
920
|
if SwiftBleManager.verboseLogging {
|
|
@@ -915,20 +925,20 @@ import CoreBluetooth
|
|
|
915
925
|
}
|
|
916
926
|
}
|
|
917
927
|
}
|
|
918
|
-
|
|
928
|
+
|
|
919
929
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
920
|
-
|
|
921
|
-
|
|
930
|
+
didDiscoverIncludedServicesFor service: CBService,
|
|
931
|
+
error: Error?) {
|
|
922
932
|
if let error = error {
|
|
923
933
|
NSLog("Error: \(error)")
|
|
924
934
|
return
|
|
925
935
|
}
|
|
926
936
|
peripheral.discoverCharacteristics(nil, for: service) // discover characteristics for included service
|
|
927
937
|
}
|
|
928
|
-
|
|
938
|
+
|
|
929
939
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
930
|
-
|
|
931
|
-
|
|
940
|
+
didDiscoverCharacteristicsFor service: CBService,
|
|
941
|
+
error: Error?) {
|
|
932
942
|
if let error = error {
|
|
933
943
|
NSLog("Error: \(error)")
|
|
934
944
|
return
|
|
@@ -936,42 +946,42 @@ import CoreBluetooth
|
|
|
936
946
|
if SwiftBleManager.verboseLogging {
|
|
937
947
|
NSLog("Characteristics For Service Discover")
|
|
938
948
|
}
|
|
939
|
-
|
|
949
|
+
|
|
940
950
|
var characteristicsForService = Set<CBCharacteristic>()
|
|
941
951
|
characteristicsForService.formUnion(service.characteristics ?? [])
|
|
942
952
|
characteristicsLatches[service.uuid.uuidString] = characteristicsForService
|
|
943
|
-
|
|
953
|
+
|
|
944
954
|
if let characteristics = service.characteristics {
|
|
945
955
|
for characteristic in characteristics {
|
|
946
956
|
peripheral.discoverDescriptors(for: characteristic)
|
|
947
957
|
}
|
|
948
958
|
}
|
|
949
959
|
}
|
|
950
|
-
|
|
960
|
+
|
|
951
961
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
952
|
-
|
|
953
|
-
|
|
962
|
+
didDiscoverDescriptorsFor characteristic: CBCharacteristic,
|
|
963
|
+
error: Error?) {
|
|
954
964
|
if let error = error {
|
|
955
965
|
NSLog("Error: \(error)")
|
|
956
966
|
return
|
|
957
967
|
}
|
|
958
968
|
let peripheralUUIDString:String = peripheral.uuidAsString()
|
|
959
969
|
let serviceUUIDString:String = (characteristic.service?.uuid.uuidString)!
|
|
960
|
-
|
|
970
|
+
|
|
961
971
|
if SwiftBleManager.verboseLogging {
|
|
962
972
|
NSLog("Descriptor For Characteristic Discover \(serviceUUIDString) \(characteristic.uuid.uuidString)")
|
|
963
973
|
}
|
|
964
|
-
|
|
974
|
+
|
|
965
975
|
if var servicesLatch = retrieveServicesLatches[peripheralUUIDString], var characteristicsLatch = characteristicsLatches[serviceUUIDString] {
|
|
966
|
-
|
|
976
|
+
|
|
967
977
|
characteristicsLatch.remove(characteristic)
|
|
968
978
|
characteristicsLatches[serviceUUIDString] = characteristicsLatch
|
|
969
|
-
|
|
979
|
+
|
|
970
980
|
if characteristicsLatch.isEmpty {
|
|
971
981
|
// All characteristics for this service have been checked
|
|
972
982
|
servicesLatch.remove(characteristic.service!)
|
|
973
983
|
retrieveServicesLatches[peripheralUUIDString] = servicesLatch
|
|
974
|
-
|
|
984
|
+
|
|
975
985
|
if servicesLatch.isEmpty {
|
|
976
986
|
// All characteristics and services have been checked
|
|
977
987
|
if let peripheral = peripherals[peripheral.uuidAsString()] {
|
|
@@ -981,41 +991,41 @@ import CoreBluetooth
|
|
|
981
991
|
retrieveServicesLatches.removeValue(forKey: peripheralUUIDString)
|
|
982
992
|
}
|
|
983
993
|
}
|
|
984
|
-
|
|
994
|
+
|
|
985
995
|
}
|
|
986
996
|
}
|
|
987
|
-
|
|
997
|
+
|
|
988
998
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
989
|
-
|
|
990
|
-
|
|
999
|
+
didReadRSSI RSSI: NSNumber,
|
|
1000
|
+
error: Error?) {
|
|
991
1001
|
if SwiftBleManager.verboseLogging {
|
|
992
1002
|
print("didReadRSSI \(RSSI)")
|
|
993
1003
|
}
|
|
994
|
-
|
|
1004
|
+
|
|
995
1005
|
if let error = error {
|
|
996
1006
|
invokeAndClearDictionary(&readRSSICallbacks, withKey: peripheral.uuidAsString(), usingParameters: [error.localizedDescription, RSSI])
|
|
997
1007
|
} else {
|
|
998
1008
|
invokeAndClearDictionary(&readRSSICallbacks, withKey: peripheral.uuidAsString(), usingParameters: [NSNull(), RSSI])
|
|
999
1009
|
}
|
|
1000
1010
|
}
|
|
1001
|
-
|
|
1011
|
+
|
|
1002
1012
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
1003
|
-
|
|
1004
|
-
|
|
1013
|
+
didUpdateValueFor descriptor: CBDescriptor,
|
|
1014
|
+
error: Error?) {
|
|
1005
1015
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: descriptor.characteristic!, andDescriptor: descriptor)
|
|
1006
|
-
|
|
1016
|
+
|
|
1007
1017
|
if let error = error {
|
|
1008
1018
|
NSLog("Error reading descriptor value for \(descriptor.uuid) on characteristic \(descriptor.characteristic!.uuid) :\(error)")
|
|
1009
1019
|
invokeAndClearDictionary(&readDescriptorCallbacks, withKey: key, usingParameters: [error.localizedDescription, NSNull()])
|
|
1010
1020
|
return
|
|
1011
1021
|
}
|
|
1012
|
-
|
|
1022
|
+
|
|
1013
1023
|
if let descriptorValue = descriptor.value as? Data {
|
|
1014
1024
|
NSLog("Read value [descriptor: \(descriptor.uuid), characteristic: \(descriptor.characteristic!.uuid)]: (\(descriptorValue.count)) \(descriptorValue.hexadecimalString())")
|
|
1015
1025
|
} else {
|
|
1016
1026
|
NSLog("Read value [descriptor: \(descriptor.uuid), characteristic: \(descriptor.characteristic!.uuid)]: \(String(describing: descriptor.value))")
|
|
1017
1027
|
}
|
|
1018
|
-
|
|
1028
|
+
|
|
1019
1029
|
if readDescriptorCallbacks[key] != nil {
|
|
1020
1030
|
// The most future proof way of doing this that I could find, other option would be running strcmp on CBUUID strings
|
|
1021
1031
|
// https://developer.apple.com/documentation/corebluetooth/cbuuid/characteristic_descriptors
|
|
@@ -1046,22 +1056,22 @@ import CoreBluetooth
|
|
|
1046
1056
|
}
|
|
1047
1057
|
}
|
|
1048
1058
|
}
|
|
1049
|
-
|
|
1059
|
+
|
|
1050
1060
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
1051
|
-
|
|
1052
|
-
|
|
1061
|
+
didUpdateValueFor characteristic: CBCharacteristic,
|
|
1062
|
+
error: Error?) {
|
|
1053
1063
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: characteristic)
|
|
1054
|
-
|
|
1064
|
+
|
|
1055
1065
|
if let error = error {
|
|
1056
1066
|
NSLog("Error \(characteristic.uuid) :\(error)")
|
|
1057
1067
|
invokeAndClearDictionary(&readCallbacks, withKey: key, usingParameters: [error.localizedDescription, NSNull()])
|
|
1058
1068
|
return
|
|
1059
1069
|
}
|
|
1060
|
-
|
|
1070
|
+
|
|
1061
1071
|
if SwiftBleManager.verboseLogging, let value = characteristic.value {
|
|
1062
1072
|
NSLog("Read value [\(characteristic.uuid)]: \( value.hexadecimalString())")
|
|
1063
1073
|
}
|
|
1064
|
-
|
|
1074
|
+
|
|
1065
1075
|
serialQueue.sync {
|
|
1066
1076
|
if readCallbacks[key] != nil {
|
|
1067
1077
|
invokeAndClearDictionary_THREAD_UNSAFE(&readCallbacks, withKey: key, usingParameters: [NSNull(), characteristic.value!.toArray()])
|
|
@@ -1075,13 +1085,13 @@ import CoreBluetooth
|
|
|
1075
1085
|
}
|
|
1076
1086
|
}
|
|
1077
1087
|
}
|
|
1078
|
-
|
|
1088
|
+
|
|
1079
1089
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
1080
|
-
|
|
1081
|
-
|
|
1090
|
+
didUpdateNotificationStateFor characteristic: CBCharacteristic,
|
|
1091
|
+
error: Error?) {
|
|
1082
1092
|
if let error = error {
|
|
1083
1093
|
NSLog("Error in didUpdateNotificationStateForCharacteristic: \(error)")
|
|
1084
|
-
|
|
1094
|
+
|
|
1085
1095
|
self.bleManager?.emitOnDidUpdateNotificationState(for: [
|
|
1086
1096
|
"peripheral": peripheral.uuidAsString(),
|
|
1087
1097
|
"characteristic": characteristic.uuid.uuidString.lowercased(),
|
|
@@ -1094,11 +1104,11 @@ import CoreBluetooth
|
|
|
1094
1104
|
"peripheral": peripheral.uuidAsString(),
|
|
1095
1105
|
"characteristic": characteristic.uuid.uuidString.lowercased(),
|
|
1096
1106
|
"isNotifying": characteristic.isNotifying
|
|
1097
|
-
])
|
|
1107
|
+
])
|
|
1098
1108
|
}
|
|
1099
|
-
|
|
1109
|
+
|
|
1100
1110
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: characteristic)
|
|
1101
|
-
|
|
1111
|
+
|
|
1102
1112
|
if let error = error {
|
|
1103
1113
|
if notificationCallbacks[key] != nil {
|
|
1104
1114
|
invokeAndClearDictionary(¬ificationCallbacks, withKey: key, usingParameters: [error])
|
|
@@ -1125,12 +1135,12 @@ import CoreBluetooth
|
|
|
1125
1135
|
}
|
|
1126
1136
|
}
|
|
1127
1137
|
}
|
|
1128
|
-
|
|
1138
|
+
|
|
1129
1139
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
1130
|
-
|
|
1131
|
-
|
|
1140
|
+
didWriteValueFor descriptor: CBDescriptor,
|
|
1141
|
+
error: Error?) {
|
|
1132
1142
|
NSLog("didWrite descriptor")
|
|
1133
|
-
|
|
1143
|
+
|
|
1134
1144
|
let key = Helper.key(forPeripheral: peripheral, andCharacteristic: descriptor.characteristic!, andDescriptor: descriptor)
|
|
1135
1145
|
let callbacks = writeDescriptorCallbacks[key]
|
|
1136
1146
|
if callbacks != nil {
|
|
@@ -1142,15 +1152,15 @@ import CoreBluetooth
|
|
|
1142
1152
|
}
|
|
1143
1153
|
}
|
|
1144
1154
|
}
|
|
1145
|
-
|
|
1155
|
+
|
|
1146
1156
|
public func peripheral(_ peripheral: CBPeripheral,
|
|
1147
|
-
|
|
1148
|
-
|
|
1157
|
+
didWriteValueFor characteristic: CBCharacteristic,
|
|
1158
|
+
error: Error?) {
|
|
1149
1159
|
NSLog("didWrite")
|
|
1150
|
-
|
|
1160
|
+
|
|
1151
1161
|
let key = Helper.key(forPeripheral:peripheral, andCharacteristic: characteristic)
|
|
1152
1162
|
let peripheralWriteCallbacks = writeCallbacks[key]
|
|
1153
|
-
|
|
1163
|
+
|
|
1154
1164
|
if peripheralWriteCallbacks != nil {
|
|
1155
1165
|
if let error = error {
|
|
1156
1166
|
NSLog("\(error)")
|
|
@@ -1166,74 +1176,74 @@ import CoreBluetooth
|
|
|
1166
1176
|
}
|
|
1167
1177
|
}
|
|
1168
1178
|
}
|
|
1169
|
-
|
|
1170
|
-
|
|
1179
|
+
|
|
1180
|
+
|
|
1171
1181
|
static func getCentralManager() -> CBCentralManager? {
|
|
1172
1182
|
return sharedManager
|
|
1173
1183
|
}
|
|
1174
|
-
|
|
1184
|
+
|
|
1175
1185
|
static func getInstance() -> SwiftBleManager? {
|
|
1176
1186
|
return shared
|
|
1177
1187
|
}
|
|
1178
|
-
|
|
1188
|
+
|
|
1179
1189
|
@objc public func enableBluetooth(_ callback: @escaping RCTResponseSenderBlock) {
|
|
1180
1190
|
callback(["Not supported"])
|
|
1181
1191
|
}
|
|
1182
|
-
|
|
1192
|
+
|
|
1183
1193
|
@objc public func getBondedPeripherals(_ callback: @escaping RCTResponseSenderBlock) {
|
|
1184
1194
|
callback(["Not supported"])
|
|
1185
1195
|
}
|
|
1186
|
-
|
|
1196
|
+
|
|
1187
1197
|
@objc public func createBond(_ peripheralUUID: String,
|
|
1188
|
-
|
|
1189
|
-
|
|
1198
|
+
devicePin: String,
|
|
1199
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1190
1200
|
callback(["Not supported"])
|
|
1191
1201
|
}
|
|
1192
|
-
|
|
1202
|
+
|
|
1193
1203
|
@objc public func removeBond(_ peripheralUUID: String,
|
|
1194
|
-
|
|
1204
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1195
1205
|
callback(["Not supported"])
|
|
1196
1206
|
}
|
|
1197
|
-
|
|
1207
|
+
|
|
1198
1208
|
@objc public func removePeripheral(_ peripheralUUID: String,
|
|
1199
|
-
|
|
1209
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1200
1210
|
callback(["Not supported"])
|
|
1201
1211
|
}
|
|
1202
|
-
|
|
1212
|
+
|
|
1203
1213
|
@objc public func requestMTU(_ peripheralUUID: String,
|
|
1204
|
-
|
|
1205
|
-
|
|
1214
|
+
mtu: Int,
|
|
1215
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1206
1216
|
callback(["Not supported"])
|
|
1207
1217
|
}
|
|
1208
|
-
|
|
1218
|
+
|
|
1209
1219
|
@objc public func requestConnectionPriority(_ peripheralUUID: String,
|
|
1210
|
-
|
|
1211
|
-
|
|
1220
|
+
connectionPriority: Int,
|
|
1221
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1212
1222
|
callback(["Not supported"])
|
|
1213
1223
|
}
|
|
1214
|
-
|
|
1224
|
+
|
|
1215
1225
|
@objc public func refreshCache(_ peripheralUUID: String,
|
|
1216
|
-
|
|
1226
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1217
1227
|
callback(["Not supported"])
|
|
1218
1228
|
}
|
|
1219
|
-
|
|
1229
|
+
|
|
1220
1230
|
@objc public func setName(_ name: String) {
|
|
1221
1231
|
// Not supported
|
|
1222
1232
|
}
|
|
1223
|
-
|
|
1233
|
+
|
|
1224
1234
|
@objc public func getAssociatedPeripherals(_ callback: @escaping RCTResponseSenderBlock) {
|
|
1225
1235
|
callback(["Not supported"])
|
|
1226
1236
|
}
|
|
1227
|
-
|
|
1237
|
+
|
|
1228
1238
|
@objc public func removeAssociatedPeripheral(_ peripheralUUID: String,
|
|
1229
|
-
|
|
1239
|
+
callback: @escaping RCTResponseSenderBlock) {
|
|
1230
1240
|
callback(["Not supported"])
|
|
1231
1241
|
}
|
|
1232
|
-
|
|
1242
|
+
|
|
1233
1243
|
@objc public func supportsCompanion(_ callback: @escaping RCTResponseSenderBlock) {
|
|
1234
1244
|
callback([NSNull(), false])
|
|
1235
1245
|
}
|
|
1236
|
-
|
|
1246
|
+
|
|
1237
1247
|
@objc public func companionScan(_ serviceUUIDs: [Any],
|
|
1238
1248
|
option: NSDictionary,
|
|
1239
1249
|
callback:RCTResponseSenderBlock) {
|