incyclist-devices 1.4.64 → 1.4.67
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/lib/ble/ble-device.d.ts +1 -0
- package/lib/ble/ble-device.js +8 -5
- package/lib/ble/ble-interface.d.ts +1 -0
- package/lib/ble/ble-interface.js +34 -15
- package/lib/ble/ble-peripheral.d.ts +1 -0
- package/lib/ble/ble-peripheral.js +10 -3
- package/lib/ble/fm.d.ts +1 -0
- package/lib/ble/fm.js +30 -3
- package/lib/ble/pwr.d.ts +1 -0
- package/lib/ble/pwr.js +11 -2
- package/lib/ble/wahoo-kickr.d.ts +1 -0
- package/lib/ble/wahoo-kickr.js +25 -2
- package/package.json +1 -1
package/lib/ble/ble-device.d.ts
CHANGED
|
@@ -30,6 +30,7 @@ export declare abstract class BleDevice extends BleDeviceClass {
|
|
|
30
30
|
logEvent(event: any): void;
|
|
31
31
|
setLogger(logger: EventLogger): void;
|
|
32
32
|
setInterface(ble: BleInterfaceClass): void;
|
|
33
|
+
isMatching(characteristics: string[]): boolean;
|
|
33
34
|
cleanupListeners(): void;
|
|
34
35
|
onDisconnect(): void;
|
|
35
36
|
waitForConnectFinished(timeout: any): Promise<unknown>;
|
package/lib/ble/ble-device.js
CHANGED
|
@@ -47,7 +47,9 @@ class BleDevice extends ble_1.BleDeviceClass {
|
|
|
47
47
|
if (this.logger) {
|
|
48
48
|
this.logger.logEvent(event);
|
|
49
49
|
}
|
|
50
|
-
|
|
50
|
+
if (process.env.BLE_DEBUG) {
|
|
51
|
+
console.log('~~~BLE:', event);
|
|
52
|
+
}
|
|
51
53
|
}
|
|
52
54
|
setLogger(logger) {
|
|
53
55
|
this.logger = logger;
|
|
@@ -55,6 +57,9 @@ class BleDevice extends ble_1.BleDeviceClass {
|
|
|
55
57
|
setInterface(ble) {
|
|
56
58
|
this.ble = ble;
|
|
57
59
|
}
|
|
60
|
+
isMatching(characteristics) {
|
|
61
|
+
return true;
|
|
62
|
+
}
|
|
58
63
|
cleanupListeners() {
|
|
59
64
|
if (this.characteristics === undefined) {
|
|
60
65
|
this.characteristics = [];
|
|
@@ -244,7 +249,6 @@ class BleDevice extends ble_1.BleDeviceClass {
|
|
|
244
249
|
if (writeIdx !== -1) {
|
|
245
250
|
const writeItem = this.writeQueue[writeIdx];
|
|
246
251
|
this.writeQueue.splice(writeIdx, 1);
|
|
247
|
-
console.log('~~~ write queue', this.writeQueue);
|
|
248
252
|
if (writeItem.resolve)
|
|
249
253
|
writeItem.resolve(data);
|
|
250
254
|
}
|
|
@@ -255,9 +259,9 @@ class BleDevice extends ble_1.BleDeviceClass {
|
|
|
255
259
|
try {
|
|
256
260
|
const connector = this.ble.getConnector(this.peripheral);
|
|
257
261
|
const isAlreadySubscribed = connector.isSubscribed(characteristicUuid);
|
|
258
|
-
console.log('~~~ write ', characteristicUuid, data.toString('hex'), isAlreadySubscribed, this.subscribedCharacteristics);
|
|
259
262
|
if (!withoutResponse && !isAlreadySubscribed) {
|
|
260
263
|
const connector = this.ble.getConnector(this.peripheral);
|
|
264
|
+
connector.removeAllListeners(characteristicUuid);
|
|
261
265
|
connector.on(characteristicUuid, (uuid, data) => {
|
|
262
266
|
this.onData(uuid, data);
|
|
263
267
|
});
|
|
@@ -282,12 +286,11 @@ class BleDevice extends ble_1.BleDeviceClass {
|
|
|
282
286
|
let messageDeleted = false;
|
|
283
287
|
this.writeQueue.push({ uuid: characteristicUuid.toLocaleLowerCase(), data, resolve, reject });
|
|
284
288
|
const to = setTimeout(() => {
|
|
285
|
-
console.log('~~~ write timeout');
|
|
286
289
|
if (this.writeQueue.length > writeId && !messageDeleted)
|
|
287
290
|
this.writeQueue.splice(writeId, 1);
|
|
288
291
|
this.logEvent({ message: 'writing response', err: 'timeout' });
|
|
289
292
|
reject(new Error('timeout'));
|
|
290
|
-
},
|
|
293
|
+
}, 5000);
|
|
291
294
|
this.logEvent({ message: 'writing' });
|
|
292
295
|
characteristic.write(data, withoutResponse, (err) => {
|
|
293
296
|
clearTimeout(to);
|
|
@@ -77,6 +77,7 @@ export default class BleInterface extends BleInterfaceClass {
|
|
|
77
77
|
getDeviceClasses(peripheral: any, props?: {
|
|
78
78
|
deviceTypes?: (typeof BleDeviceClass)[];
|
|
79
79
|
profile?: string;
|
|
80
|
+
services?: string[];
|
|
80
81
|
}): (typeof BleDeviceClass)[];
|
|
81
82
|
createDevice(DeviceClass: (typeof BleDeviceClass), peripheral: BlePeripheral, characteristics?: BleCharacteristic[]): any;
|
|
82
83
|
connectDevice(requested: BleDeviceClass | BleDeviceDescription, timeout?: number): Promise<BleDeviceClass>;
|
package/lib/ble/ble-interface.js
CHANGED
|
@@ -336,13 +336,13 @@ class BleInterface extends ble_1.BleInterfaceClass {
|
|
|
336
336
|
}
|
|
337
337
|
getDeviceClasses(peripheral, props = {}) {
|
|
338
338
|
let DeviceClasses;
|
|
339
|
-
const { deviceTypes, profile } = props;
|
|
339
|
+
const { deviceTypes, profile, services = peripheral.advertisement.serviceUuids } = props;
|
|
340
340
|
if ((!deviceTypes || deviceTypes.length === 0)) {
|
|
341
341
|
const classes = BleInterface.deviceClasses.map(c => c.Class);
|
|
342
|
-
DeviceClasses = this.getDevicesFromServices(classes,
|
|
342
|
+
DeviceClasses = this.getDevicesFromServices(classes, services);
|
|
343
343
|
}
|
|
344
344
|
else {
|
|
345
|
-
DeviceClasses = this.getDevicesFromServices(deviceTypes,
|
|
345
|
+
DeviceClasses = this.getDevicesFromServices(deviceTypes, services);
|
|
346
346
|
}
|
|
347
347
|
if (profile && DeviceClasses && DeviceClasses.length > 0) {
|
|
348
348
|
DeviceClasses = DeviceClasses.filter(C => {
|
|
@@ -355,15 +355,26 @@ class BleInterface extends ble_1.BleInterfaceClass {
|
|
|
355
355
|
return DeviceClasses;
|
|
356
356
|
}
|
|
357
357
|
createDevice(DeviceClass, peripheral, characteristics) {
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
358
|
+
try {
|
|
359
|
+
const C = DeviceClass;
|
|
360
|
+
const device = new C({ peripheral });
|
|
361
|
+
const cids = characteristics ? characteristics.map(c => (0, ble_1.uuid)(c.uuid)) : [];
|
|
362
|
+
this.logEvent({ message: 'trying to create device', peripheral: peripheral.address, characteristics: cids, profile: device.getProfile() });
|
|
363
|
+
const existingDevice = this.devices.find(i => i.device.id === device.id && i.device.getProfile() === device.getProfile());
|
|
364
|
+
if (existingDevice)
|
|
365
|
+
return existingDevice;
|
|
366
|
+
device.setInterface(this);
|
|
367
|
+
if (characteristics && device.isMatching(cids)) {
|
|
368
|
+
device.characteristics = characteristics;
|
|
369
|
+
return device;
|
|
370
|
+
}
|
|
371
|
+
else {
|
|
372
|
+
this.logEvent({ message: 'failed to create device', peripheral: peripheral.address, profile: device.getProfile() });
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
catch (err) {
|
|
376
|
+
this.logEvent({ message: 'error', fn: '', error: err.message || err, stack: err.stack });
|
|
377
|
+
}
|
|
367
378
|
}
|
|
368
379
|
connectDevice(requested, timeout = DEFAULT_SCAN_TIMEOUT + CONNECT_TIMEOUT) {
|
|
369
380
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -540,8 +551,8 @@ class BleInterface extends ble_1.BleInterfaceClass {
|
|
|
540
551
|
if (fromCache)
|
|
541
552
|
this.logEvent({ message: 'adding from Cache', peripheral: peripheral.address });
|
|
542
553
|
else {
|
|
543
|
-
const { id, name, address } = peripheral;
|
|
544
|
-
this.logEvent({ message: 'BLE scan: found device', peripheral: { id, name, address } });
|
|
554
|
+
const { id, name, address, advertisement = {} } = peripheral;
|
|
555
|
+
this.logEvent({ message: 'BLE scan: found device', peripheral: { id, name, address, services: advertisement.serviceUuids } });
|
|
545
556
|
}
|
|
546
557
|
if (!peripheral || !peripheral.advertisement || !peripheral.advertisement.serviceUuids || peripheral.advertisement.serviceUuids.length === 0)
|
|
547
558
|
return;
|
|
@@ -552,7 +563,13 @@ class BleInterface extends ble_1.BleInterfaceClass {
|
|
|
552
563
|
return;
|
|
553
564
|
peripheralsProcessed.push(peripheral.address);
|
|
554
565
|
const characteristics = yield this.getCharacteristics(peripheral);
|
|
555
|
-
const
|
|
566
|
+
const connector = this.getConnector(peripheral);
|
|
567
|
+
const connectedServices = connector.getServices();
|
|
568
|
+
const services = connectedServices ? connectedServices.map(cs => cs.uuid) : undefined;
|
|
569
|
+
const connectedPeripheral = connector.getPeripheral();
|
|
570
|
+
const { id, name, address, advertisement = {} } = connectedPeripheral;
|
|
571
|
+
const DeviceClasses = this.getDeviceClasses(connectedPeripheral, { profile, services });
|
|
572
|
+
this.logEvent({ message: 'BLE scan: device connected', peripheral: { id, name, address, services: advertisement.serviceUuids }, services, classes: DeviceClasses.map(c => c.prototype.constructor.name) });
|
|
556
573
|
let cntFound = 0;
|
|
557
574
|
DeviceClasses.forEach((DeviceClass) => __awaiter(this, void 0, void 0, function* () {
|
|
558
575
|
if (!DeviceClass)
|
|
@@ -560,6 +577,8 @@ class BleInterface extends ble_1.BleInterfaceClass {
|
|
|
560
577
|
if (scanForDevice && cntFound > 0)
|
|
561
578
|
return;
|
|
562
579
|
const d = this.createDevice(DeviceClass, peripheral, characteristics);
|
|
580
|
+
if (!d)
|
|
581
|
+
return;
|
|
563
582
|
yield d.connect();
|
|
564
583
|
if (scanForDevice) {
|
|
565
584
|
if ((id && id !== '' && d.id === id) ||
|
|
@@ -31,7 +31,9 @@ class BlePeripheralConnector {
|
|
|
31
31
|
if (this.logger) {
|
|
32
32
|
this.logger.logEvent(event);
|
|
33
33
|
}
|
|
34
|
-
|
|
34
|
+
if (process.env.BLE_DEBUG) {
|
|
35
|
+
console.log('~~~BLE:', event);
|
|
36
|
+
}
|
|
35
37
|
}
|
|
36
38
|
connect() {
|
|
37
39
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -110,7 +112,6 @@ class BlePeripheralConnector {
|
|
|
110
112
|
try {
|
|
111
113
|
yield this.subscribe(c.uuid);
|
|
112
114
|
subscribed.push(c.uuid);
|
|
113
|
-
this.state.subscribed.push(c.uuid);
|
|
114
115
|
}
|
|
115
116
|
catch (err) {
|
|
116
117
|
this.logEvent({ message: 'cannot subscribe', peripheral: this.peripheral.address, characteristic: c.uuid, error: err.message || err });
|
|
@@ -137,6 +138,7 @@ class BlePeripheralConnector {
|
|
|
137
138
|
reject(new Error('Characteristic not found'));
|
|
138
139
|
return;
|
|
139
140
|
}
|
|
141
|
+
characteristic.removeAllListeners('data');
|
|
140
142
|
characteristic.on('data', (data, _isNotification) => {
|
|
141
143
|
this.onData(characteristicUuid, data);
|
|
142
144
|
});
|
|
@@ -149,8 +151,10 @@ class BlePeripheralConnector {
|
|
|
149
151
|
this.logEvent({ message: 'subscribe result', characteristic: characteristicUuid, error: err });
|
|
150
152
|
if (err)
|
|
151
153
|
reject(err);
|
|
152
|
-
else
|
|
154
|
+
else {
|
|
155
|
+
this.state.subscribed.push(characteristicUuid);
|
|
153
156
|
resolve(true);
|
|
157
|
+
}
|
|
154
158
|
});
|
|
155
159
|
}
|
|
156
160
|
catch (err) {
|
|
@@ -181,5 +185,8 @@ class BlePeripheralConnector {
|
|
|
181
185
|
getServices() {
|
|
182
186
|
return this.services;
|
|
183
187
|
}
|
|
188
|
+
getPeripheral() {
|
|
189
|
+
return this.peripheral;
|
|
190
|
+
}
|
|
184
191
|
}
|
|
185
192
|
exports.default = BlePeripheralConnector;
|
package/lib/ble/fm.d.ts
CHANGED
|
@@ -52,6 +52,7 @@ export default class BleFitnessMachineDevice extends BleDevice {
|
|
|
52
52
|
windSpeed: number;
|
|
53
53
|
wheelSize: number;
|
|
54
54
|
constructor(props?: any);
|
|
55
|
+
isMatching(characteristics: string[]): boolean;
|
|
55
56
|
init(): Promise<boolean>;
|
|
56
57
|
onDisconnect(): void;
|
|
57
58
|
getProfile(): string;
|
package/lib/ble/fm.js
CHANGED
|
@@ -21,6 +21,8 @@ const power_meter_1 = __importDefault(require("../modes/power-meter"));
|
|
|
21
21
|
const ble_st_mode_1 = __importDefault(require("./ble-st-mode"));
|
|
22
22
|
const ble_erg_mode_1 = __importDefault(require("./ble-erg-mode"));
|
|
23
23
|
const FTMS_CP = '2ad9';
|
|
24
|
+
const FTMS_STATUS = '2ada';
|
|
25
|
+
const INDOOR_BIKE_DATA = '2ad2';
|
|
24
26
|
const cwABike = {
|
|
25
27
|
race: 0.35,
|
|
26
28
|
triathlon: 0.29,
|
|
@@ -94,12 +96,37 @@ class BleFitnessMachineDevice extends ble_device_1.BleDevice {
|
|
|
94
96
|
this.wheelSize = 2100;
|
|
95
97
|
this.data = {};
|
|
96
98
|
}
|
|
99
|
+
isMatching(characteristics) {
|
|
100
|
+
if (!characteristics)
|
|
101
|
+
return false;
|
|
102
|
+
const hasStatus = characteristics.find(c => c === FTMS_STATUS) !== undefined;
|
|
103
|
+
const hasCP = characteristics.find(c => c === FTMS_CP) !== undefined;
|
|
104
|
+
const hasIndoorBike = characteristics.find(c => c === INDOOR_BIKE_DATA) !== undefined;
|
|
105
|
+
return hasStatus && hasCP && hasIndoorBike;
|
|
106
|
+
}
|
|
97
107
|
init() {
|
|
98
108
|
const _super = Object.create(null, {
|
|
99
109
|
init: { get: () => super.init }
|
|
100
110
|
});
|
|
101
111
|
return __awaiter(this, void 0, void 0, function* () {
|
|
102
112
|
try {
|
|
113
|
+
const connector = this.ble.getConnector(this.peripheral);
|
|
114
|
+
const isAlreadySubscribed = connector.isSubscribed(FTMS_CP);
|
|
115
|
+
if (!isAlreadySubscribed) {
|
|
116
|
+
connector.removeAllListeners(FTMS_CP);
|
|
117
|
+
let prev = undefined;
|
|
118
|
+
let prevTS = undefined;
|
|
119
|
+
connector.on(FTMS_CP, (uuid, data) => {
|
|
120
|
+
const message = data.toString('hex');
|
|
121
|
+
if (prevTS && prev && message === prev && Date.now() - prevTS < 500) {
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
prevTS = Date.now();
|
|
125
|
+
prev = message;
|
|
126
|
+
this.onData(uuid, data);
|
|
127
|
+
});
|
|
128
|
+
yield connector.subscribe(FTMS_CP);
|
|
129
|
+
}
|
|
103
130
|
this.logEvent({ message: 'get device info' });
|
|
104
131
|
yield _super.init.call(this);
|
|
105
132
|
yield this.getFitnessMachineFeatures();
|
|
@@ -278,13 +305,13 @@ class BleFitnessMachineDevice extends ble_device_1.BleDevice {
|
|
|
278
305
|
const uuid = characteristic.toLocaleLowerCase();
|
|
279
306
|
let res = undefined;
|
|
280
307
|
switch (uuid) {
|
|
281
|
-
case
|
|
308
|
+
case INDOOR_BIKE_DATA:
|
|
282
309
|
res = this.parseIndoorBikeData(data);
|
|
283
310
|
break;
|
|
284
311
|
case '2a37':
|
|
285
312
|
res = this.parseHrm(data);
|
|
286
313
|
break;
|
|
287
|
-
case
|
|
314
|
+
case FTMS_STATUS:
|
|
288
315
|
res = this.parseFitnessMachineStatus(data);
|
|
289
316
|
break;
|
|
290
317
|
case '2a63':
|
|
@@ -452,7 +479,7 @@ class BleFitnessMachineDevice extends ble_device_1.BleDevice {
|
|
|
452
479
|
}
|
|
453
480
|
exports.default = BleFitnessMachineDevice;
|
|
454
481
|
BleFitnessMachineDevice.services = ['1826'];
|
|
455
|
-
BleFitnessMachineDevice.characteristics = ['2acc',
|
|
482
|
+
BleFitnessMachineDevice.characteristics = ['2acc', INDOOR_BIKE_DATA, '2ad6', '2ad8', FTMS_CP, FTMS_STATUS];
|
|
456
483
|
ble_interface_1.default.register('BleFitnessMachineDevice', 'fm', BleFitnessMachineDevice, BleFitnessMachineDevice.services);
|
|
457
484
|
class FmAdapter extends Device_1.default {
|
|
458
485
|
constructor(device, protocol) {
|
package/lib/ble/pwr.d.ts
CHANGED
|
@@ -33,6 +33,7 @@ export default class BleCyclingPowerDevice extends BleDevice {
|
|
|
33
33
|
currentCrankData: CrankData;
|
|
34
34
|
prevCrankData: CrankData;
|
|
35
35
|
constructor(props?: any);
|
|
36
|
+
isMatching(characteristics: string[]): boolean;
|
|
36
37
|
init(): Promise<boolean>;
|
|
37
38
|
getProfile(): string;
|
|
38
39
|
getServiceUUids(): string[];
|
package/lib/ble/pwr.js
CHANGED
|
@@ -37,6 +37,8 @@ const ble_interface_1 = __importDefault(require("./ble-interface"));
|
|
|
37
37
|
const Device_1 = __importStar(require("../Device"));
|
|
38
38
|
const gd_eventlog_1 = require("gd-eventlog");
|
|
39
39
|
const power_meter_1 = __importDefault(require("../modes/power-meter"));
|
|
40
|
+
const CP_MEASUREMENT = '2a63';
|
|
41
|
+
const CP_FEATURE = '2a65';
|
|
40
42
|
class BleCyclingPowerDevice extends ble_device_1.BleDevice {
|
|
41
43
|
constructor(props) {
|
|
42
44
|
super(props);
|
|
@@ -49,6 +51,13 @@ class BleCyclingPowerDevice extends ble_device_1.BleDevice {
|
|
|
49
51
|
this.currentCrankData = undefined;
|
|
50
52
|
this.prevCrankData = undefined;
|
|
51
53
|
}
|
|
54
|
+
isMatching(characteristics) {
|
|
55
|
+
if (!characteristics)
|
|
56
|
+
return false;
|
|
57
|
+
const hasCPMeasurement = characteristics.find(c => c === CP_MEASUREMENT) !== undefined;
|
|
58
|
+
const hasCPFeature = characteristics.find(c => c === CP_FEATURE) !== undefined;
|
|
59
|
+
return hasCPMeasurement && hasCPFeature;
|
|
60
|
+
}
|
|
52
61
|
init() {
|
|
53
62
|
const _super = Object.create(null, {
|
|
54
63
|
init: { get: () => super.init }
|
|
@@ -131,7 +140,7 @@ class BleCyclingPowerDevice extends ble_device_1.BleDevice {
|
|
|
131
140
|
}
|
|
132
141
|
onData(characteristic, data) {
|
|
133
142
|
super.onData(characteristic, data);
|
|
134
|
-
if (characteristic.toLocaleLowerCase() ===
|
|
143
|
+
if (characteristic.toLocaleLowerCase() === CP_MEASUREMENT) {
|
|
135
144
|
const res = this.parsePower(data);
|
|
136
145
|
this.emit('data', res);
|
|
137
146
|
}
|
|
@@ -149,7 +158,7 @@ class BleCyclingPowerDevice extends ble_device_1.BleDevice {
|
|
|
149
158
|
}
|
|
150
159
|
exports.default = BleCyclingPowerDevice;
|
|
151
160
|
BleCyclingPowerDevice.services = ['1818'];
|
|
152
|
-
BleCyclingPowerDevice.characteristics = [
|
|
161
|
+
BleCyclingPowerDevice.characteristics = [CP_MEASUREMENT, CP_FEATURE, '2a5d', '2a3c'];
|
|
153
162
|
ble_interface_1.default.register('BleCyclingPowerDevice', 'cp', BleCyclingPowerDevice, BleCyclingPowerDevice.services);
|
|
154
163
|
class PwrAdapter extends Device_1.default {
|
|
155
164
|
constructor(device, protocol) {
|
package/lib/ble/wahoo-kickr.d.ts
CHANGED
|
@@ -35,6 +35,7 @@ export default class WahooAdvancedFitnessMachineDevice extends BleFitnessMachine
|
|
|
35
35
|
timeOffset: number;
|
|
36
36
|
tsPrevWrite: any;
|
|
37
37
|
constructor(props?: any);
|
|
38
|
+
isMatching(characteristics: string[]): boolean;
|
|
38
39
|
init(): Promise<boolean>;
|
|
39
40
|
getProfile(): string;
|
|
40
41
|
getServiceUUids(): string[];
|
package/lib/ble/wahoo-kickr.js
CHANGED
|
@@ -36,7 +36,7 @@ const ble_interface_1 = __importDefault(require("./ble-interface"));
|
|
|
36
36
|
const Device_1 = require("../Device");
|
|
37
37
|
const gd_eventlog_1 = require("gd-eventlog");
|
|
38
38
|
const fm_1 = __importStar(require("./fm"));
|
|
39
|
-
const WAHOO_ADVANCED_FTMS = '
|
|
39
|
+
const WAHOO_ADVANCED_FTMS = 'a026e00b';
|
|
40
40
|
const WAHOO_ADVANCED_TRAINER_CP = 'a026e037';
|
|
41
41
|
const cwABike = {
|
|
42
42
|
race: 0.35,
|
|
@@ -54,12 +54,35 @@ class WahooAdvancedFitnessMachineDevice extends fm_1.default {
|
|
|
54
54
|
this.tsPrevWrite = undefined;
|
|
55
55
|
this.data = {};
|
|
56
56
|
}
|
|
57
|
+
isMatching(characteristics) {
|
|
58
|
+
if (!characteristics)
|
|
59
|
+
return false;
|
|
60
|
+
const hasWahooCP = characteristics.find(c => c === WAHOO_ADVANCED_TRAINER_CP) !== undefined;
|
|
61
|
+
return hasWahooCP;
|
|
62
|
+
}
|
|
57
63
|
init() {
|
|
58
64
|
const _super = Object.create(null, {
|
|
59
65
|
init: { get: () => super.init }
|
|
60
66
|
});
|
|
61
67
|
return __awaiter(this, void 0, void 0, function* () {
|
|
62
68
|
try {
|
|
69
|
+
const connector = this.ble.getConnector(this.peripheral);
|
|
70
|
+
const isAlreadySubscribed = connector.isSubscribed(WAHOO_ADVANCED_TRAINER_CP);
|
|
71
|
+
if (!isAlreadySubscribed) {
|
|
72
|
+
connector.removeAllListeners(WAHOO_ADVANCED_TRAINER_CP);
|
|
73
|
+
let prev = undefined;
|
|
74
|
+
let prevTS = undefined;
|
|
75
|
+
connector.on(WAHOO_ADVANCED_TRAINER_CP, (uuid, data) => {
|
|
76
|
+
const message = data.toString('hex');
|
|
77
|
+
if (prevTS && prev && message === prev && Date.now() - prevTS < 500) {
|
|
78
|
+
return;
|
|
79
|
+
}
|
|
80
|
+
prevTS = Date.now();
|
|
81
|
+
prev = message;
|
|
82
|
+
this.onData(uuid, data);
|
|
83
|
+
});
|
|
84
|
+
yield connector.subscribe(WAHOO_ADVANCED_TRAINER_CP);
|
|
85
|
+
}
|
|
63
86
|
this.logEvent({ message: 'get device info' });
|
|
64
87
|
yield _super.init.call(this);
|
|
65
88
|
this.logEvent({ message: 'device info', deviceInfo: this.deviceInfo, features: this.features });
|
|
@@ -298,7 +321,7 @@ class WahooAdvancedFitnessMachineDevice extends fm_1.default {
|
|
|
298
321
|
}
|
|
299
322
|
exports.default = WahooAdvancedFitnessMachineDevice;
|
|
300
323
|
WahooAdvancedFitnessMachineDevice.services = ['a026ee0b'];
|
|
301
|
-
WahooAdvancedFitnessMachineDevice.characteristics = ['2acc', '2ad2', '2ad6', '2ad8', '2ad9', '2ada',
|
|
324
|
+
WahooAdvancedFitnessMachineDevice.characteristics = ['2acc', '2ad2', '2ad6', '2ad8', '2ad9', '2ada', WAHOO_ADVANCED_TRAINER_CP];
|
|
302
325
|
ble_interface_1.default.register('WahooAdvancedFitnessMachineDevice', 'wahoo-fm', WahooAdvancedFitnessMachineDevice, WahooAdvancedFitnessMachineDevice.services);
|
|
303
326
|
class WahooAdvancedFmAdapter extends fm_1.FmAdapter {
|
|
304
327
|
constructor(device, protocol) {
|