@hangtime/grip-connect 0.5.1 → 0.5.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.
Files changed (35) hide show
  1. package/README.md +8 -17
  2. package/dist/{is-device.d.ts → helpers/is-device.d.ts} +1 -1
  3. package/dist/{is-device.js → helpers/is-device.js} +1 -1
  4. package/dist/index.d.ts +1 -1
  5. package/dist/index.js +2 -2
  6. package/dist/interfaces/device.interface.d.ts +45 -3
  7. package/dist/models/device/entralpi.model.js +9 -10
  8. package/dist/models/device/forceboard.model.js +3 -4
  9. package/dist/models/device/kilterboard.model.js +1 -2
  10. package/dist/models/device/motherboard.model.js +13 -16
  11. package/dist/models/device/progressor.model.js +12 -13
  12. package/dist/models/device.model.d.ts +45 -0
  13. package/dist/models/device.model.js +116 -0
  14. package/package.json +1 -1
  15. package/src/{is-device.ts → helpers/is-device.ts} +2 -2
  16. package/src/index.ts +2 -2
  17. package/src/interfaces/device.interface.ts +55 -3
  18. package/src/models/device/entralpi.model.ts +9 -10
  19. package/src/models/device/forceboard.model.ts +3 -4
  20. package/src/models/device/kilterboard.model.ts +1 -2
  21. package/src/models/device/motherboard.model.ts +13 -16
  22. package/src/models/device/progressor.model.ts +12 -13
  23. package/src/models/device.model.ts +128 -0
  24. package/dist/characteristic.d.ts +0 -9
  25. package/dist/characteristic.js +0 -21
  26. package/dist/read.d.ts +0 -10
  27. package/dist/read.js +0 -43
  28. package/dist/write.d.ts +0 -34
  29. package/dist/write.js +0 -58
  30. package/src/characteristic.ts +0 -29
  31. package/src/read.ts +0 -45
  32. package/src/write.ts +0 -74
  33. /package/dist/{struct/index.d.ts → helpers/struct.d.ts} +0 -0
  34. /package/dist/{struct/index.js → helpers/struct.js} +0 -0
  35. /package/src/{struct/index.ts → helpers/struct.ts} +0 -0
package/README.md CHANGED
@@ -110,16 +110,16 @@ motherboardButton.addEventListener("click", () => {
110
110
 
111
111
  ## Device support
112
112
 
113
- - ✅ Griptonite - Motherboard
114
- - ✅ Tindeq - Progressor
115
- - ✅ Weiheng - WH-C06
113
+ - ✅ [Griptonite - Motherboard](https://stevie-ray.github.io/hangtime-grip-connect/devices/motherboard.html)
114
+ - ✅ [Tindeq - Progressor](https://stevie-ray.github.io/hangtime-grip-connect/devices/progressor.html)
115
+ - ✅ [Weiheng - WH-C06](https://stevie-ray.github.io/hangtime-grip-connect/devices/wh-c06.html)
116
116
  - By default [watchAdvertisements](https://chromestatus.com/feature/5180688812736512) isn't supported . For Chrome,
117
117
  enable it at `chrome://flags/#enable-experimental-web-platform-features`.
118
- - ✅ Kilter Board
119
- - ✅ Entralpi / Lefu Scale
120
- - ⏳ PitchSix Force Board
121
- - ➡️ Climbro
122
- - ➡️ Smartboard Climbing - mySmartBoard
118
+ - ✅ [Kilter Board](https://stevie-ray.github.io/hangtime-grip-connect/devices/kilterboard.html)
119
+ - ✅ [Entralpi](https://stevie-ray.github.io/hangtime-grip-connect/devices/entralpi.html) / Lefu Scale
120
+ - ⏳ [PitchSix Force Board](https://stevie-ray.github.io/hangtime-grip-connect/devices/forceboard.html)
121
+ - ➡️ [Climbro](https://stevie-ray.github.io/hangtime-grip-connect/devices/climbro.html)
122
+ - ➡️ [Smartboard Climbing - mySmartBoard](https://stevie-ray.github.io/hangtime-grip-connect/devices/mysmartboard.html)
123
123
 
124
124
  ## Features
125
125
 
@@ -132,15 +132,6 @@ reactive `isActive` check and a `download` feature.
132
132
  `chrome://bluetooth-internals/#devices` and press `Start Scan` to look for your device, click on `Inspect` and share all
133
133
  available services with us.
134
134
 
135
- | | [Motherboard](https://stevie-ray.github.io/hangtime-grip-connect/devices/motherboard.html) | [Progressor](https://stevie-ray.github.io/hangtime-grip-connect/devices/progressor.html) | [WH-C06](https://stevie-ray.github.io/hangtime-grip-connect/devices/wh-c06.html) | [Entralpi](https://stevie-ray.github.io/hangtime-grip-connect/devices/entralpi.html) | [Kilter Board](https://stevie-ray.github.io/hangtime-grip-connect/devices/kilterboard.html) | [Force Board](https://stevie-ray.github.io/hangtime-grip-connect/devices/forceboard.html) | [Climbro](https://stevie-ray.github.io/hangtime-grip-connect/devices/climbro.html) | [mySmartBoard](https://stevie-ray.github.io/hangtime-grip-connect/devices/mysmartboard.html) |
136
- | --------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------ | ---------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------- |
137
- | [Download](https://stevie-ray.github.io/hangtime-grip-connect/api/download.html) | ✅ | ✅ | | | | | | |
138
- | [isActive](https://stevie-ray.github.io/hangtime-grip-connect/api/is-active.html) | ✅ | ✅ | ✅ | ✅ | | | | |
139
- | [isDevice](https://stevie-ray.github.io/hangtime-grip-connect/api/is-device.html) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | | |
140
- | [Read](https://stevie-ray.github.io/hangtime-grip-connect/api/read.html) | ✅ | | | ✅ | | ✅ | | |
141
- | [Tare](https://stevie-ray.github.io/hangtime-grip-connect/api/tare.html) | ✅ | ✅ | ✅ | ✅ | | | | |
142
- | [Write](https://stevie-ray.github.io/hangtime-grip-connect/api/write.html) | ✅ | ✅ | | | ✅ | | | |
143
-
144
135
  ## Development
145
136
 
146
137
  ```bash
@@ -1,4 +1,4 @@
1
- import type { Device } from "./models/device.model";
1
+ import type { Device } from "./../models/device.model";
2
2
  /**
3
3
  * Checks if the given device is an Entralpi device.
4
4
  * @param {Device} [board] - The device to check.
@@ -1,4 +1,4 @@
1
- import { AuroraUUID } from "./models/device/kilterboard.model";
1
+ import { AuroraUUID } from "./../models/device/kilterboard.model";
2
2
  /**
3
3
  * Checks if the given device is an Entralpi device.
4
4
  * @param {Device} [board] - The device to check.
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  export { Climbro, Entralpi, ForceBoard, KilterBoard, Motherboard, mySmartBoard, WHC06, Progressor, } from "./models/index";
2
- export { isEntralpi, isKilterboard, isMotherboard, isWHC06, isProgressor } from "./is-device";
2
+ export { isEntralpi, isKilterboard, isMotherboard, isWHC06, isProgressor } from "./helpers/is-device";
3
3
  export { download } from "./download";
4
4
  export { active, isActive } from "./is-active";
5
5
  export { tare } from "./tare";
package/dist/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  export { Climbro, Entralpi, ForceBoard, KilterBoard, Motherboard, mySmartBoard, WHC06, Progressor, } from "./models/index";
2
2
  // helpers
3
- export { isEntralpi, isKilterboard, isMotherboard, isWHC06, isProgressor } from "./is-device";
4
- // functions
3
+ export { isEntralpi, isKilterboard, isMotherboard, isWHC06, isProgressor } from "./helpers/is-device";
4
+ // TODO: Make functions device specific
5
5
  export { download } from "./download";
6
6
  export { active, isActive } from "./is-active";
7
7
  export { tare } from "./tare";
@@ -1,6 +1,5 @@
1
1
  import type { IBase } from "./base.interface";
2
2
  import type { massObject } from "../types/notify";
3
- type NotifyCallback = (data: massObject) => void;
4
3
  /**
5
4
  * Represents a characteristic of a Bluetooth service.
6
5
  */
@@ -54,6 +53,13 @@ export interface IDevice extends IBase {
54
53
  * @returns {string[]} Array of service UUIDs.
55
54
  */
56
55
  getAllServiceUUIDs(): string[];
56
+ /**
57
+ * Retrieves the characteristic from the device's service.
58
+ * @param {string} serviceId - The UUID of the service.
59
+ * @param {string} characteristicId - The UUID of the characteristic.
60
+ * @returns {BluetoothRemoteGATTCharacteristic | undefined} The characteristic, if found.
61
+ */
62
+ getCharacteristic(serviceId: string, characteristicId: string): BluetoothRemoteGATTCharacteristic | undefined;
57
63
  /**
58
64
  * Handles notifications received from a characteristic.
59
65
  * @param {Event} event - The notification event.
@@ -69,13 +75,13 @@ export interface IDevice extends IBase {
69
75
  * @param {NotifyCallback} callback - The callback function to be set.
70
76
  * @returns {void}
71
77
  */
72
- notify(callback: NotifyCallback): void;
78
+ notify(callback: (data: massObject) => void): void;
73
79
  /**
74
80
  * Defines the type for the callback function.
75
81
  * @callback NotifyCallback
76
82
  * @param {massObject} data - The data passed to the callback.
77
83
  */
78
- notifyCallback: NotifyCallback;
84
+ notifyCallback: (data: massObject) => void;
79
85
  /**
80
86
  * Handles the 'connected' event.
81
87
  * @param {Function} onSuccess - Callback function to execute on successful connection.
@@ -86,5 +92,41 @@ export interface IDevice extends IBase {
86
92
  * @param {Event} event - The 'disconnected' event.
87
93
  */
88
94
  onDisconnected(event: Event): void;
95
+ /**
96
+ * Reads the value of the specified characteristic from the device.
97
+ * @param {string} serviceId - The service ID where the characteristic belongs.
98
+ * @param {string} characteristicId - The characteristic ID to read from.
99
+ * @param {number} [duration=0] - The duration to wait before resolving the promise, in milliseconds.
100
+ * @returns {Promise<string>} A promise that resolves when the read operation is completed.
101
+ */
102
+ read(serviceId: string, characteristicId: string, duration?: number): Promise<string>;
103
+ /**
104
+ * Writes a message to the specified characteristic of a Bluetooth device and optionally provides a callback to handle responses.
105
+ * @param {string} serviceId - The service UUID of the Bluetooth device containing the target characteristic.
106
+ * @param {string} characteristicId - The characteristic UUID where the message will be written.
107
+ * @param {string | Uint8Array | undefined} message - The message to be written to the characteristic. It can be a string or a Uint8Array.
108
+ * @param {number} [duration=0] - Optional. The time in milliseconds to wait before resolving the promise. Defaults to 0 for immediate resolution.
109
+ * @param {WriteCallback} [callback=writeCallback] - Optional. A custom callback to handle the response after the write operation is successful.
110
+ *
111
+ * @returns {Promise<void>} A promise that resolves once the write operation is complete.
112
+ *
113
+ * @throws {Error} Throws an error if the characteristic is undefined.
114
+ *
115
+ * @example
116
+ * // Example usage of the write function with a custom callback
117
+ * await Progressor.write("progressor", "tx", ProgressorCommands.GET_BATT_VLTG, 250, (data) => {
118
+ * console.log(`Battery voltage: ${data}`);
119
+ * });
120
+ */
121
+ write(serviceId: string, characteristicId: string, message: string | Uint8Array | undefined, duration?: number, callback?: (data: string) => void): Promise<void>;
122
+ /**
123
+ * A default write callback that logs the response
124
+ */
125
+ writeCallback: (data: string) => void;
126
+ /**
127
+ * The last message written to the device.
128
+ * @type {string | Uint8Array | null}
129
+ */
130
+ writeLast: string | Uint8Array | null;
89
131
  }
90
132
  export {};
@@ -1,7 +1,6 @@
1
1
  import { Device } from "../device.model";
2
2
  import { applyTare } from "../../tare";
3
3
  import { checkActivity } from "../../is-active";
4
- import { read } from "../../read";
5
4
  // Constants
6
5
  let MASS_MAX = "0";
7
6
  let MASS_AVERAGE = "0";
@@ -135,7 +134,7 @@ export class Entralpi extends Device {
135
134
  */
136
135
  battery = async () => {
137
136
  if (this.isConnected()) {
138
- return await read(this, "battery", "level", 250);
137
+ return await this.read("battery", "level", 250);
139
138
  }
140
139
  // If device is not found, return undefined
141
140
  return undefined;
@@ -148,7 +147,7 @@ export class Entralpi extends Device {
148
147
  // Check if the device is connected
149
148
  if (this.isConnected()) {
150
149
  // Read certification from the device
151
- return await read(this, "device", "certification", 250);
150
+ return await this.read("device", "certification", 250);
152
151
  }
153
152
  // If device is not found, return undefined
154
153
  return undefined;
@@ -161,7 +160,7 @@ export class Entralpi extends Device {
161
160
  // Check if the device is connected
162
161
  if (this.isConnected()) {
163
162
  // Read firmware version from the Motherboard
164
- return await read(this, "device", "firmware", 250);
163
+ return await this.read("device", "firmware", 250);
165
164
  }
166
165
  // If device is not found, return undefined
167
166
  return undefined;
@@ -211,7 +210,7 @@ export class Entralpi extends Device {
211
210
  // Check if the device is connected
212
211
  if (this.isConnected()) {
213
212
  // Read hardware version from the device
214
- return await read(this, "device", "hardware", 250);
213
+ return await this.read("device", "hardware", 250);
215
214
  }
216
215
  // If device is not found, return undefined
217
216
  return undefined;
@@ -224,7 +223,7 @@ export class Entralpi extends Device {
224
223
  // Check if the device is connected
225
224
  if (this.isConnected()) {
226
225
  // Read manufacturer information from the device
227
- return await read(this, "device", "manufacturer", 250);
226
+ return await this.read("device", "manufacturer", 250);
228
227
  }
229
228
  // If device is not found, return undefined
230
229
  return undefined;
@@ -237,7 +236,7 @@ export class Entralpi extends Device {
237
236
  // Check if the device is connected
238
237
  if (this.isConnected()) {
239
238
  // Read model number from the Entralpi
240
- return await read(this, "device", "model", 250);
239
+ return await this.read("device", "model", 250);
241
240
  }
242
241
  // If device is not found, return undefined
243
242
  return undefined;
@@ -251,7 +250,7 @@ export class Entralpi extends Device {
251
250
  // Check if the device is connected
252
251
  if (this.isConnected()) {
253
252
  // Read software version from the Entralpi
254
- return await read(this, "device", "pnp", 250);
253
+ return await this.read("device", "pnp", 250);
255
254
  }
256
255
  // If device is not found, return undefined
257
256
  return undefined;
@@ -264,7 +263,7 @@ export class Entralpi extends Device {
264
263
  // Check if the device is connected
265
264
  if (this.isConnected()) {
266
265
  // Read software version from the Entralpi
267
- return await read(this, "device", "software", 250);
266
+ return await this.read("device", "software", 250);
268
267
  }
269
268
  // If device is not found, return undefined
270
269
  return undefined;
@@ -277,7 +276,7 @@ export class Entralpi extends Device {
277
276
  // Check if the device is connected
278
277
  if (this.isConnected()) {
279
278
  // Read system id from the device
280
- return await read(this, "device", "system", 250);
279
+ return await this.read("device", "system", 250);
281
280
  }
282
281
  // If device is not found, return undefined
283
282
  return undefined;
@@ -1,5 +1,4 @@
1
1
  import { Device } from "../device.model";
2
- import { read } from "../../read";
3
2
  /**
4
3
  * Represents a PitchSix Force Board device
5
4
  */
@@ -168,7 +167,7 @@ export class ForceBoard extends Device {
168
167
  */
169
168
  battery = async () => {
170
169
  if (this.isConnected()) {
171
- return await read(this, "battery", "level", 250);
170
+ return await this.read("battery", "level", 250);
172
171
  }
173
172
  // If device is not found, return undefined
174
173
  return undefined;
@@ -180,7 +179,7 @@ export class ForceBoard extends Device {
180
179
  humidity = async () => {
181
180
  // Check if the device is connected
182
181
  if (this.isConnected()) {
183
- return await read(this, "humidity", "level", 250);
182
+ return await this.read("humidity", "level", 250);
184
183
  }
185
184
  // If device is not found, return undefined
186
185
  return undefined;
@@ -193,7 +192,7 @@ export class ForceBoard extends Device {
193
192
  // Check if the device is connected
194
193
  if (this.isConnected()) {
195
194
  // Read manufacturer information from the device
196
- return await read(this, "device", "manufacturer", 250);
195
+ return await this.read("device", "manufacturer", 250);
197
196
  }
198
197
  // If device is not found, return undefined
199
198
  return undefined;
@@ -1,6 +1,5 @@
1
1
  import { Device } from "../device.model";
2
2
  import { KilterBoardPacket, KilterBoardPlacementRoles } from "../../commands/kilterboard";
3
- import { write } from "../../write";
4
3
  /**
5
4
  * Aurora Climbing Advertising service
6
5
  */
@@ -190,7 +189,7 @@ export class KilterBoard extends Device {
190
189
  */
191
190
  async writeMessageSeries(messages) {
192
191
  for (const message of messages) {
193
- await write(this, "uart", "tx", message);
192
+ await this.write("uart", "tx", message);
194
193
  }
195
194
  }
196
195
  /**
@@ -1,11 +1,8 @@
1
1
  import { Device } from "../device.model";
2
- import { write, writeCallback } from "../../write";
3
2
  import { applyTare } from "../../tare";
4
3
  import { MotherboardCommands } from "../../commands";
5
4
  import { checkActivity } from "../../is-active";
6
- import { lastWrite } from "../../write";
7
5
  import { DownloadPackets, emptyDownloadPackets } from "../../download";
8
- import { read } from "../../read";
9
6
  // Constants
10
7
  const PACKET_LENGTH = 32;
11
8
  const NUM_SAMPLES = 3;
@@ -143,7 +140,7 @@ export class Motherboard extends Device {
143
140
  */
144
141
  battery = async () => {
145
142
  if (this.isConnected()) {
146
- return await read(this, "battery", "level", 250);
143
+ return await this.read("battery", "level", 250);
147
144
  }
148
145
  // If device is not found, return undefined
149
146
  return undefined;
@@ -156,7 +153,7 @@ export class Motherboard extends Device {
156
153
  // Check if the device is connected
157
154
  if (this.isConnected()) {
158
155
  // Write the command to get calibration data to the device
159
- await write(this, "uart", "tx", MotherboardCommands.GET_CALIBRATION, 2500, (data) => {
156
+ await this.write("uart", "tx", MotherboardCommands.GET_CALIBRATION, 2500, (data) => {
160
157
  console.log(data);
161
158
  });
162
159
  }
@@ -169,7 +166,7 @@ export class Motherboard extends Device {
169
166
  // Check if the device is connected
170
167
  if (this.isConnected()) {
171
168
  // Read firmware version from the Motherboard
172
- return await read(this, "device", "firmware", 250);
169
+ return await this.read("device", "firmware", 250);
173
170
  }
174
171
  // If device is not found, return undefined
175
172
  return undefined;
@@ -262,7 +259,7 @@ export class Motherboard extends Device {
262
259
  massRight: Math.max(-1000, packet.masses[2]).toFixed(1),
263
260
  });
264
261
  }
265
- else if (lastWrite === MotherboardCommands.GET_CALIBRATION) {
262
+ else if (this.writeLast === MotherboardCommands.GET_CALIBRATION) {
266
263
  // check data integrity
267
264
  if ((receivedData.match(/,/g) || []).length === 3) {
268
265
  const parts = receivedData.split(",");
@@ -272,7 +269,7 @@ export class Motherboard extends Device {
272
269
  }
273
270
  else {
274
271
  // unhandled data
275
- writeCallback(receivedData);
272
+ this.writeCallback(receivedData);
276
273
  }
277
274
  }
278
275
  }
@@ -286,7 +283,7 @@ export class Motherboard extends Device {
286
283
  // Check if the device is connected
287
284
  if (this.isConnected()) {
288
285
  // Read hardware version from the device
289
- return await read(this, "device", "hardware", 250);
286
+ return await this.read("device", "hardware", 250);
290
287
  }
291
288
  // If device is not found, return undefined
292
289
  return undefined;
@@ -307,8 +304,8 @@ export class Motherboard extends Device {
307
304
  // Default to "off" color if config is not set or not found in colorMapping
308
305
  const color = typeof config === "string" && colorMapping[config] ? config : "off";
309
306
  const [redValue, greenValue] = colorMapping[color];
310
- await write(this, "led", "red", new Uint8Array(redValue));
311
- await write(this, "led", "green", new Uint8Array(greenValue), 1250);
307
+ await this.write("led", "red", new Uint8Array(redValue));
308
+ await this.write("led", "green", new Uint8Array(greenValue), 1250);
312
309
  }
313
310
  return undefined;
314
311
  };
@@ -320,7 +317,7 @@ export class Motherboard extends Device {
320
317
  // Check if the device is connected
321
318
  if (this.isConnected()) {
322
319
  // Read manufacturer information from the device
323
- return await read(this, "device", "manufacturer", 250);
320
+ return await this.read("device", "manufacturer", 250);
324
321
  }
325
322
  // If device is not found, return undefined
326
323
  return undefined;
@@ -334,7 +331,7 @@ export class Motherboard extends Device {
334
331
  if (this.isConnected()) {
335
332
  // Write serial number command to the Motherboard and read output
336
333
  let response = undefined;
337
- await write(this, "uart", "tx", MotherboardCommands.GET_SERIAL, 250, (data) => {
334
+ await this.write("uart", "tx", MotherboardCommands.GET_SERIAL, 250, (data) => {
338
335
  response = data;
339
336
  });
340
337
  return response;
@@ -349,7 +346,7 @@ export class Motherboard extends Device {
349
346
  stop = async () => {
350
347
  if (this.isConnected()) {
351
348
  // Stop stream of device
352
- await write(this, "uart", "tx", MotherboardCommands.STOP_WEIGHT_MEAS, 0);
349
+ await this.write("uart", "tx", MotherboardCommands.STOP_WEIGHT_MEAS, 0);
353
350
  }
354
351
  };
355
352
  /**
@@ -367,7 +364,7 @@ export class Motherboard extends Device {
367
364
  await this.calibration();
368
365
  }
369
366
  // Start streaming data
370
- await write(this, "uart", "tx", MotherboardCommands.START_WEIGHT_MEAS, duration);
367
+ await this.write("uart", "tx", MotherboardCommands.START_WEIGHT_MEAS, duration);
371
368
  // Stop streaming if duration is set
372
369
  if (duration !== 0) {
373
370
  await this.stop();
@@ -388,7 +385,7 @@ export class Motherboard extends Device {
388
385
  if (this.isConnected()) {
389
386
  // Write text information command to the Motherboard and read output
390
387
  let response = undefined;
391
- await write(this, "uart", "tx", MotherboardCommands.GET_TEXT, 250, (data) => {
388
+ await this.write("uart", "tx", MotherboardCommands.GET_TEXT, 250, (data) => {
392
389
  response = data;
393
390
  });
394
391
  return response;
@@ -1,10 +1,9 @@
1
1
  import { Device } from "../device.model";
2
- import { applyTare } from "../../tare";
3
- import { checkActivity } from "../../is-active";
4
2
  import { ProgressorCommands, ProgressorResponses } from "../../commands/progressor";
5
- import struct from "../../struct";
3
+ import struct from "../../helpers/struct";
4
+ import { checkActivity } from "../../is-active";
6
5
  import { DownloadPackets, emptyDownloadPackets } from "../../download";
7
- import { lastWrite, write, writeCallback } from "../../write";
6
+ import { applyTare } from "../../tare";
8
7
  // Constants
9
8
  let MASS_MAX = "0";
10
9
  let MASS_AVERAGE = "0";
@@ -57,7 +56,7 @@ export class Progressor extends Device {
57
56
  battery = async () => {
58
57
  if (this.isConnected()) {
59
58
  let response = undefined;
60
- await write(this, "progressor", "tx", ProgressorCommands.GET_BATT_VLTG, 250, (data) => {
59
+ await this.write("progressor", "tx", ProgressorCommands.GET_BATT_VLTG, 250, (data) => {
61
60
  response = data;
62
61
  });
63
62
  return response;
@@ -74,7 +73,7 @@ export class Progressor extends Device {
74
73
  if (this.isConnected()) {
75
74
  // Read firmware version from the device
76
75
  let response = undefined;
77
- await write(this, "progressor", "tx", ProgressorCommands.GET_FW_VERSION, 250, (data) => {
76
+ await this.write("progressor", "tx", ProgressorCommands.GET_FW_VERSION, 250, (data) => {
78
77
  response = data;
79
78
  });
80
79
  return response;
@@ -132,19 +131,19 @@ export class Progressor extends Device {
132
131
  }
133
132
  }
134
133
  else if (kind === ProgressorResponses.COMMAND_RESPONSE) {
135
- if (!lastWrite)
134
+ if (!this.writeLast)
136
135
  return;
137
136
  let value = "";
138
- if (lastWrite === ProgressorCommands.GET_BATT_VLTG) {
137
+ if (this.writeLast === ProgressorCommands.GET_BATT_VLTG) {
139
138
  value = new DataView(data.buffer, 2).getUint32(0, true).toString();
140
139
  }
141
- else if (lastWrite === ProgressorCommands.GET_FW_VERSION) {
140
+ else if (this.writeLast === ProgressorCommands.GET_FW_VERSION) {
142
141
  value = new TextDecoder().decode(data.buffer.slice(2));
143
142
  }
144
- else if (lastWrite === ProgressorCommands.GET_ERR_INFO) {
143
+ else if (this.writeLast === ProgressorCommands.GET_ERR_INFO) {
145
144
  value = new TextDecoder().decode(data.buffer.slice(2));
146
145
  }
147
- writeCallback(value);
146
+ this.writeCallback(value);
148
147
  }
149
148
  else if (kind === ProgressorResponses.LOW_BATTERY_WARNING) {
150
149
  console.warn("⚠️ Low power detected. Please consider connecting to a power source.");
@@ -162,7 +161,7 @@ export class Progressor extends Device {
162
161
  stop = async () => {
163
162
  if (this.isConnected()) {
164
163
  // Stop stream of device
165
- await write(this, "progressor", "tx", ProgressorCommands.STOP_WEIGHT_MEAS, 0);
164
+ await this.write("progressor", "tx", ProgressorCommands.STOP_WEIGHT_MEAS, 0);
166
165
  }
167
166
  };
168
167
  /**
@@ -175,7 +174,7 @@ export class Progressor extends Device {
175
174
  // Reset download packets
176
175
  emptyDownloadPackets();
177
176
  // Start streaming data
178
- await write(this, "progressor", "tx", ProgressorCommands.START_WEIGHT_MEAS, duration);
177
+ await this.write("progressor", "tx", ProgressorCommands.START_WEIGHT_MEAS, duration);
179
178
  // Stop streaming if duration is set
180
179
  if (duration !== 0) {
181
180
  await this.stop();
@@ -3,6 +3,8 @@ import type { IDevice, Service } from "../interfaces/device.interface";
3
3
  import type { massObject } from "./../types/notify";
4
4
  /** Define the type for the callback function */
5
5
  type NotifyCallback = (data: massObject) => void;
6
+ /** Define the type for the callback function */
7
+ type WriteCallback = (data: string) => void;
6
8
  export declare class Device extends BaseModel implements IDevice {
7
9
  filters: BluetoothLEScanFilter[];
8
10
  services: Service[];
@@ -25,6 +27,13 @@ export declare class Device extends BaseModel implements IDevice {
25
27
  * @returns {string[]} Array of service UUIDs.
26
28
  */
27
29
  getAllServiceUUIDs: () => string[];
30
+ /**
31
+ * Retrieves the characteristic from the device's service.
32
+ * @param {string} serviceId - The UUID of the service.
33
+ * @param {string} characteristicId - The UUID of the characteristic.
34
+ * @returns {BluetoothRemoteGATTCharacteristic | undefined} The characteristic, if found.
35
+ */
36
+ getCharacteristic: (serviceId: string, characteristicId: string) => BluetoothRemoteGATTCharacteristic | undefined;
28
37
  /**
29
38
  * Handles notifications received from a characteristic.
30
39
  * @param {Event} event - The notification event.
@@ -57,5 +66,41 @@ export declare class Device extends BaseModel implements IDevice {
57
66
  * @param {Event} event - The 'disconnected' event.
58
67
  */
59
68
  onDisconnected: (event: Event) => void;
69
+ /**
70
+ * Reads the value of the specified characteristic from the device.
71
+ * @param {string} serviceId - The service ID where the characteristic belongs.
72
+ * @param {string} characteristicId - The characteristic ID to read from.
73
+ * @param {number} [duration=0] - The duration to wait before resolving the promise, in milliseconds.
74
+ * @returns {Promise<string>} A promise that resolves when the read operation is completed.
75
+ */
76
+ read: (serviceId: string, characteristicId: string, duration?: number) => Promise<string>;
77
+ /**
78
+ * Writes a message to the specified characteristic of a Bluetooth device and optionally provides a callback to handle responses.
79
+ * @param {string} serviceId - The service UUID of the Bluetooth device containing the target characteristic.
80
+ * @param {string} characteristicId - The characteristic UUID where the message will be written.
81
+ * @param {string | Uint8Array | undefined} message - The message to be written to the characteristic. It can be a string or a Uint8Array.
82
+ * @param {number} [duration=0] - Optional. The time in milliseconds to wait before resolving the promise. Defaults to 0 for immediate resolution.
83
+ * @param {WriteCallback} [callback=writeCallback] - Optional. A custom callback to handle the response after the write operation is successful.
84
+ *
85
+ * @returns {Promise<void>} A promise that resolves once the write operation is complete.
86
+ *
87
+ * @throws {Error} Throws an error if the characteristic is undefined.
88
+ *
89
+ * @example
90
+ * // Example usage of the write function with a custom callback
91
+ * await Progressor.write("progressor", "tx", ProgressorCommands.GET_BATT_VLTG, 250, (data) => {
92
+ * console.log(`Battery voltage: ${data}`);
93
+ * });
94
+ */
95
+ write: (serviceId: string, characteristicId: string, message: string | Uint8Array | undefined, duration?: number, callback?: WriteCallback) => Promise<void>;
96
+ /**
97
+ * A default write callback that logs the response
98
+ */
99
+ writeCallback: WriteCallback;
100
+ /**
101
+ * The last message written to the device.
102
+ * @type {string | Uint8Array | null}
103
+ */
104
+ writeLast: string | Uint8Array | null;
60
105
  }
61
106
  export {};