Move Firmata into Arduino node so we don't rely on their version of serialport

This commit is contained in:
Dave Conway-Jones 2023-11-17 15:07:38 +00:00
parent 4c3e7bff91
commit 81501dfbdf
No known key found for this signature in database
GPG Key ID: 1DDB0E91A28C2643
8 changed files with 2854 additions and 7 deletions

View File

@ -2,7 +2,7 @@
module.exports = function(RED) { module.exports = function(RED) {
"use strict"; "use strict";
var Board = require('firmata'); var Board = require('./lib/firmata');
var SP = require('serialport'); var SP = require('serialport');
// The Board Definition - this opens (and closes) the connection // The Board Definition - this opens (and closes) the connection
@ -165,7 +165,7 @@ module.exports = function(RED) {
node.board.digitalWrite(node.pin, node.board.LOW); node.board.digitalWrite(node.pin, node.board.LOW);
} }
} }
if (node.state === "PWM") { if (node.state === "PWM") {
msg.payload = parseInt((msg.payload * 1) + 0.5); msg.payload = parseInt((msg.payload * 1) + 0.5);
if ((msg.payload >= 0) && (msg.payload <= 255)) { if ((msg.payload >= 0) && (msg.payload <= 255)) {
node.board.analogWrite(node.pin, msg.payload); node.board.analogWrite(node.pin, msg.payload);

View File

@ -1,4 +1,4 @@
Copyright 2016 JS Foundation and other contributors, https://js.foundation/ Copyright 2016-2023 JS Foundation and other contributors, https://js.foundation/
Copyright 2013-2016 IBM Corp. Copyright 2013-2016 IBM Corp.
Licensed under the Apache License, Version 2.0 (the "License"); Licensed under the Apache License, Version 2.0 (the "License");
@ -12,3 +12,33 @@ distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and See the License for the specific language governing permissions and
limitations under the License. limitations under the License.
Firmata lib License - The MIT License
Copyright (c) 2011-2015 Julian Gautier julian.gautier@alumni.neumont.edu
Copyright (c) 2015-2020 The Firmata.js Authors (see AUTHORS.md)
Authors
Rick Waldron Julian Gautier Glen Arrowsmith Jeff Hoefs Olivier Louvignes
Francis Gulotta Luis Montes Lars Toft Jacobsen Érico Jean-Philippe Côté
Ernesto Laval Dustan Kasten Lars Gregori Andrey Bezugliy Donovan Buck
Pravdomil jywarren Andrew Stewart Richard Rodd Dwayn Matthies Sarah GP
achingbrain David Resseguie Nick Stewart the1337guy
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the 'Software'),
to deal in the Software without restriction, including without limitation
the rights to use, copy, modify, merge, publish, distribute, sublicense,
and/or sell copies of the Software, and to permit persons to whom the Software
is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

View File

@ -0,0 +1,67 @@
"use strict";
const Emitter = require("events");
class TransportStub extends Emitter {
constructor(path /*, options, openCallback*/) {
super();
this.isOpen = true;
this.baudRate = 0;
this.path = path;
}
write(buffer) {
// Tests are written to work with arrays not buffers
// this shouldn't impact the data, just the container
// This also should be changed in future test rewrites
/* istanbul ignore else */
if (Buffer.isBuffer(buffer)) {
buffer = Array.from(buffer);
}
this.lastWrite = buffer;
this.emit("write", buffer);
}
static list() {
/* istanbul ignore next */
return Promise.resolve([]);
}
}
// This trash is necessary for stubbing with sinon.
TransportStub.SerialPort = TransportStub;
let com;
let error;
let SerialPort;
try {
/* istanbul ignore else */
if (process.env.IS_TEST_MODE) {
com = TransportStub;
} else {
SerialPort = require("serialport").SerialPort;
com = SerialPort;
}
} catch (err) {
/* istanbul ignore next */
error = err;
}
/* istanbul ignore if */
if (com == null) {
if (process.env.IS_TEST_MODE) {
com = TransportStub;
} else {
console.log("It looks like serialport didn't install properly.");
console.log(
"More information can be found here https://serialport.io/docs/guide-installation"
);
console.log(`The result of requiring the package is: ${SerialPort}`);
console.log(error);
throw "Missing serialport dependency";
}
}
module.exports = com;

View File

@ -0,0 +1,49 @@
"use strict";
/**
* "Inspired" by Encoder7Bit.h/Encoder7Bit.cpp in the
* Firmata source code.
*/
module.exports = {
to7BitArray(data) {
let shift = 0;
let previous = 0;
const output = [];
for (let byte of data) {
if (shift === 0) {
output.push(byte & 0x7f);
shift++;
previous = byte >> 7;
} else {
output.push(((byte << shift) & 0x7f) | previous);
if (shift === 6) {
output.push(byte >> 1);
shift = 0;
} else {
shift++;
previous = byte >> (8 - shift);
}
}
}
/* istanbul ignore else */
if (shift > 0) {
output.push(previous);
}
return output;
},
from7BitArray(encoded) {
const expectedBytes = encoded.length * 7 >> 3;
const decoded = [];
for (let i = 0; i < expectedBytes; i++) {
const j = i << 3;
const pos = (j / 7) >>> 0;
const shift = j % 7;
decoded[i] = (encoded[pos] >> shift) | ((encoded[pos + 1] << (7 - shift)) & 0xFF);
}
return decoded;
}
};

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,3 @@
"use strict";
module.exports = require("./firmata-io.js")(require("./com"));

View File

@ -0,0 +1,47 @@
"use strict";
const Encoder7Bit = require("./encoder7bit");
const OneWireUtils = {
crc8(data) {
let crc = 0;
for (let inbyte of data) {
for (let n = 8; n; n--) {
const mix = (crc ^ inbyte) & 0x01;
crc >>= 1;
if (mix) {
crc ^= 0x8C;
}
inbyte >>= 1;
}
}
return crc;
},
readDevices(data) {
const deviceBytes = Encoder7Bit.from7BitArray(data);
const devices = [];
for (let i = 0; i < deviceBytes.length; i += 8) {
const device = deviceBytes.slice(i, i + 8);
if (device.length !== 8) {
continue;
}
const check = OneWireUtils.crc8(device.slice(0, 7));
if (check !== device[7]) {
console.error("ROM invalid!");
}
devices.push(device);
}
return devices;
}
};
module.exports = OneWireUtils;

View File

@ -1,9 +1,9 @@
{ {
"name": "node-red-node-arduino", "name": "node-red-node-arduino",
"version": "0.3.1", "version": "1.0.0",
"description": "A Node-RED node to talk to an Arduino running firmata", "description": "A Node-RED node to talk to an Arduino running firmata",
"dependencies": { "dependencies": {
"firmata": "^2.3.0" "serialport": "^12.0.0"
}, },
"repository": { "repository": {
"type": "git", "type": "git",
@ -17,16 +17,17 @@
"firmata" "firmata"
], ],
"node-red": { "node-red": {
"version": ">=3.0.0",
"nodes": { "nodes": {
"arduino": "35-arduino.js" "arduino": "35-arduino.js"
} }
}, },
"engines": { "engines": {
"node": ">=8" "node": ">=16.0.0"
}, },
"author": { "author": {
"name": "Dave Conway-Jones", "name": "Dave Conway-Jones",
"email": "ceejay@vnet.ibm.com", "email": "dceejay@gmail.com",
"url": "http://nodered.org" "url": "http://nodered.org"
} }
} }