@blackmagic-controller/core
Version:
An npm module for interfacing with the Blackmagic usb/bluetooth controllers
129 lines • 5.04 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.BlackmagicControllerBase = void 0;
const eventemitter3_1 = require("eventemitter3");
class BlackmagicControllerBase extends eventemitter3_1.EventEmitter {
get CONTROLS() {
return this.deviceProperties.CONTROLS;
}
get MODEL() {
return this.deviceProperties.MODEL;
}
get PRODUCT_NAME() {
return this.deviceProperties.PRODUCT_NAME;
}
device;
deviceProperties;
#options;
#propertiesService;
#inputService;
#ledService;
#authTimeout = null;
constructor(device, options, services) {
super();
this.device = device;
this.deviceProperties = services.deviceProperties;
this.#options = options;
this.#propertiesService = services.properties;
this.#inputService = services.inputService;
this.#ledService = services.led;
// propogate events
services.events?.listen((key, ...args) => this.emit(key, ...args));
this.device.on('input', (data) => this.#inputService.handleInput(data));
this.device.on('error', (err) => {
// This means the device has failed, and can be treated as 'closed'
if (this.#authTimeout)
clearTimeout(this.#authTimeout);
this.emit('error', err);
});
this.#scheduleNextAuthenticate(this.#options.nextAuthMaxDelay || 600, 1);
}
#scheduleNextAuthenticate(maxDelay, attempt) {
const authenticateFn = this.#options.authenticate;
if (!authenticateFn)
return;
if (this.#authTimeout)
clearTimeout(this.#authTimeout);
const targetWait = maxDelay * 0.5 * 1000; // Do it halfway through the timeout
this.#authTimeout = setTimeout(() => {
authenticateFn(this.device)
.then((nextDelay) => {
this.#scheduleNextAuthenticate(nextDelay, 1);
})
.catch((err) => {
if (attempt < 3) {
this.#scheduleNextAuthenticate(15, attempt + 1); // Retry soon, in case it was a temporary failure
}
else {
this.emit('error', new Error('Failed to authenticate', { cause: err }));
}
});
}, targetWait);
}
checkValidKeyId(keyId, feedbackType) {
const buttonControl = this.deviceProperties.CONTROLS.find((control) => control.type === 'button' && control.id === keyId);
if (!buttonControl) {
throw new TypeError(`Expected a valid keyId`);
}
if (feedbackType && buttonControl.feedbackType !== feedbackType) {
throw new TypeError(`Expected a keyIndex with expected feedbackType`);
}
return buttonControl;
}
checkValidTbarIndex(id) {
const tbarControl = this.deviceProperties.CONTROLS.find((control) => control.type === 'tbar' && control.id === id);
if (!tbarControl) {
throw new TypeError(`Expected a valid tbar index`);
}
return tbarControl;
}
async close() {
if (this.#authTimeout)
clearTimeout(this.#authTimeout);
return this.device.close();
}
async getHidDeviceInfo() {
return this.device.getDeviceInfo();
}
async getBatteryLevel() {
return this.#propertiesService.getBatteryLevel();
}
async getFirmwareVersion() {
return this.#propertiesService.getFirmwareVersion();
}
async getSerialNumber() {
return this.#propertiesService.getSerialNumber();
}
async setButtonColor(keyId, red, green, blue) {
const control = this.checkValidKeyId(keyId, 'rgb');
await this.#ledService.setControlColors([{ type: 'button', control, red, green, blue }]);
}
async setButtonColors(values) {
const translated = values.map((value) => {
// TODO - avoid iterating over all controls inside `checkValidKeyId`
return {
...value,
type: 'button',
control: this.checkValidKeyId(value.keyId, 'rgb'),
};
});
await this.#ledService.setControlColors(translated);
}
async setTbarLeds(leds) {
const control = this.checkValidTbarIndex(0);
if (control.ledSegments <= 0)
throw new Error(`TBar does not have leds`);
if (leds.length !== control.ledSegments)
throw new Error(`Expected ${control.ledSegments} led values`);
await this.#ledService.setControlColors([{ type: 'tbar', control, leds }]);
}
async clearKey(keyId) {
const control = this.checkValidKeyId(keyId, 'rgb');
await this.#ledService.setControlColors([{ type: 'button', control, red: false, green: false, blue: false }]);
}
async clearPanel() {
await this.#ledService.clearPanel();
}
}
exports.BlackmagicControllerBase = BlackmagicControllerBase;
//# sourceMappingURL=base.js.map