import { Device } from "./device.js"; import { IDeviceInterface } from "../interfaces.js"; import * as Consts from "../consts.js"; /** * @class TechnicMediumHubTiltSensor * @extends Device */ export class TechnicMediumHubTiltSensor extends Device { protected _impactThreshold: number = 10; // guess of default value protected _impactHoldoff: number = 10; // guess of default value constructor (hub: IDeviceInterface, portId: number) { super(hub, portId, ModeMap, Consts.DeviceType.TECHNIC_MEDIUM_HUB_TILT_SENSOR); } public receive (message: Buffer) { const mode = this._mode; switch (mode) { case Mode.TILT: /** * Emits when a tilt sensor is activated. * * @event TechnicMediumHubTiltSensor#tilt * @type {object} * @param {number} x * @param {number} y * @param {number} z */ let z = -message.readInt16LE(4); const y = message.readInt16LE(6); const x = message.readInt16LE(8); // workaround for calibration problem or bug in technicMediumHub firmware 1.1.00.0000 if(y === 90 || y === -90) { z = Math.sign(y)*(z + 180); if(z > 180) z -= 360; if(z < -180) z += 360; } this.notify("tilt", { x, y, z }); break; case Mode.IMPACT_COUNT: if (message.length !== 8) { // if mode of device has not changed to this._mode yet break; } const count = message.readUInt32LE(4); /** * Emits when proper acceleration is above threshold (e.g. on impact when being thrown to the ground). * @event TechnicMediumHubTiltSensor#impactCount * @type {object} * @param {number} number of impact events. */ this.notify("impactCount", { count }); break; } } /** * Set the impact count value. * @param {number} count impact count between 0 and 2^32 * @returns {Promise} Resolved upon completion of the command. */ public setImpactCount (count: number) { const payload = Buffer.alloc(4); payload.writeUInt32LE(count % 2**32); // no need to subscribe, can be set in different mode return this.writeDirect(0x01, payload); } /** * Set the impact threshold. * @param {number} threshold value between 1 and 127 * @returns {Promise} Resolved upon completion of the command. */ public setImpactThreshold (threshold: number) { this._impactThreshold = threshold; return this.writeDirect(0x02, Buffer.from([this._impactThreshold, this._impactHoldoff])); } /** * Set the impact holdoff time. * @param {number} holdoff value between 1 and 127 * @returns {Promise} Resolved upon completion of the command. */ public setImpactHoldoff (holdoff: number) { this._impactHoldoff = holdoff; return this.writeDirect(0x02, Buffer.from([this._impactThreshold, this._impactHoldoff])); } } export enum Mode { TILT = 0x00, IMPACT_COUNT = 0x01 } export const ModeMap: {[event: string]: number} = { "tilt": Mode.TILT, "impactCount": Mode.IMPACT_COUNT };