Add SCD30 to config.h.example, README
This commit is contained in:
parent
b3ae34e730
commit
ac3cc44117
3 changed files with 53 additions and 25 deletions
69
README.md
69
README.md
|
@ -16,39 +16,66 @@ Before programming a node, copy src/config.h.example to src/config.h and set the
|
||||||
|
|
||||||
Programming is done using a [MicroUPDI Programmer](https://github.com/MCUdude/microUPDI), settings in platformio.ini are set to use it. For other pogrammer options see the PlatformIO Documentation
|
Programming is done using a [MicroUPDI Programmer](https://github.com/MCUdude/microUPDI), settings in platformio.ini are set to use it. For other pogrammer options see the PlatformIO Documentation
|
||||||
|
|
||||||
## Multisensor Mode
|
## Payload Decoder
|
||||||
|
|
||||||
The Firmware can be configured for multiple sensors at once (see comments in config.h.example). In this case the default payload decoder from the website will not be able to correctly determine the used sensors. You **must** define a specific decoder in this case. In the TTN v3 Stack a decoder can be set per device. Use the following as an example, and uncomment the parts for each enabled sensor, then make sure the placeholder for the byte index (**ii**)
|
You need to specify a Payload Decoder fitting for your configured Sensors for a Node. The Following code Shows an example for a Payload Decoder usable with TTN Stack v3. Uncomment the Parts for your used sensors. There is a Start and End comment for each possible sensor/value, uncomment the Lines between them (The ones starting with //) to activate the Decoding for a particular Sensor. Be aware that there might be an overlap in the sensor namings for sensors with the same Values (e.g. SCD30 and BME280/SHT21 all report Temperature and Humidity. If you use them in parallel you might want to change the names of the decoded fields).
|
||||||
is filled in ascending order, starting with the first enabled sensor from left to right, beginning with 1
|
|
||||||
|
function bytesToInt16(bytes, start) {
|
||||||
|
var out = ((bytes[start]) | (bytes[start+1] << 8 ));
|
||||||
|
var sign = bytes[start+1] & (1 << 7);
|
||||||
|
if (sign)
|
||||||
|
out = 0xFFFF0000 | out;
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
function bytesToUInt16(bytes, start) {
|
||||||
|
return ((bytes[start]) | (bytes[start+1] << 8 ));
|
||||||
|
}
|
||||||
|
|
||||||
|
function bytesToInt32(bytes, start) {
|
||||||
|
return ((bytes[start]) | (bytes[start+1] << 8) | (bytes[start+2] << 16) | (bytes[start+3] << 24));
|
||||||
|
}
|
||||||
|
|
||||||
function decodeUplink(input) {
|
function decodeUplink(input) {
|
||||||
var decoded = {};
|
var decoded = {};
|
||||||
// Battery Voltage, always enabled
|
/* Battery Voltage, always enabled */
|
||||||
decoded.v = (input.bytes[0] * 20) / 1000.0;
|
decoded.v = (input.bytes[0] * 20) / 1000.0;
|
||||||
|
|
||||||
// CO2-Sensor (SG112A, MH-Z19C, Sensair S8)
|
var i = 1;
|
||||||
|
/* Start CO2-Sensor (SG112A, MH-Z19C, Sensair S8, Sensirion SCD30) PPM */
|
||||||
// decoded.ppm = ((input.bytes[ii]) | (input.bytes[ii] << 8 ));
|
// decoded.ppm = ((input.bytes[ii]) | (input.bytes[ii] << 8 ));
|
||||||
|
// i += 2;
|
||||||
|
/* End CO2 Sensor PPM */
|
||||||
|
|
||||||
// Temperature and Humidity (BME280 / SHT21)
|
/* Start Temperature + Humidity SCD30 */
|
||||||
// decoded.t = ((input.bytes[ii]) | (input.bytes[ii] << 8 ) | (input.bytes[ii] << 16 ) | (input.bytes[ii] << 24)) / 100.0;
|
// decoded.t = bytesToInt16(input.bytes, i)/100;
|
||||||
// decoded.h = ((input.bytes[ii]) | (input.bytes[ii] << 8 ) | (input.bytes[ii] << 16 ) | (input.bytes[ii] << 24)) / 100.0;
|
// decoded.h = bytesUToInt16(input.bytes, i+2)/100;
|
||||||
|
// i += 4;
|
||||||
|
/* End Temperature + Humidity SCD30 */
|
||||||
|
|
||||||
|
/* Start Temperature and Humidity (SHT21) */
|
||||||
|
// decoded.t = bytesToInt32(input.bytes, i)/100;
|
||||||
|
// decoded.h = bytesToInt32(input.bytes, i+4)/100;
|
||||||
|
// i += 8;
|
||||||
|
/* End Temperature + Humidity BME/SHT */
|
||||||
|
|
||||||
|
/* Start Temperature, Humidity, Atmospheric Pressure (BME280) */
|
||||||
|
// decoded.t = bytesToInt32(input.bytes, i)/100;
|
||||||
|
// decoded.h = bytesToInt32(input.bytes, i+4)/100;
|
||||||
|
// decoded.p = bytesToInt32(input.bytes, i+8)/100;
|
||||||
|
// i += 12;
|
||||||
|
/* End Atmospheric Pressure
|
||||||
|
|
||||||
// Atmospheric Pressure (BME280)
|
/* Start DS18B20 Temperatures
|
||||||
// decoded.p = ((input.bytes[ii]) | (input.bytes[ii] << 8 ) | (input.bytes[ii] << 16 ) | (input.bytes[ii] << 24)) / 100.0;
|
Will append all recognized Sensors as t1, t2, t3... */
|
||||||
|
// var n = 1;
|
||||||
// DS18B20 - Will append all recognized Sensors as t1, t2, t3...
|
// for (var j = i; j < input.bytes.length-1; j+=2) {
|
||||||
// var i;
|
// decoded["t" + n] = bytesToInt16(input.bytes, j);
|
||||||
// var j = 1;
|
|
||||||
// for (i = ii; i < input.bytes.length-1; i=i+2) {
|
|
||||||
// decoded["t" + j] = ((input.bytes[i]) | (input.bytes[i+1] << 8 ));
|
|
||||||
// var sign = input.bytes[i+1] & (1 << 7);
|
|
||||||
// if (sign)
|
|
||||||
// decoded["t" + j] = 0xFFFF0000 | decoded["t" + j];
|
|
||||||
// decoded["t" + j] = decoded["t" + j] / 100.0;
|
|
||||||
// j++;
|
// j++;
|
||||||
// }
|
// }
|
||||||
|
/* End DS18B20 Temperatures */
|
||||||
|
|
||||||
// Leave this part as is
|
/* Leave this part as is */
|
||||||
return {
|
return {
|
||||||
data: decoded,
|
data: decoded,
|
||||||
warnings: [],
|
warnings: [],
|
||||||
|
|
|
@ -34,7 +34,7 @@ SCD30::SCD30() {};
|
||||||
|
|
||||||
// Constructor with Measuring Interval and Autocalibration Status
|
// Constructor with Measuring Interval and Autocalibration Status
|
||||||
SCD30::SCD30(uint8_t interval, bool selfcalib) {
|
SCD30::SCD30(uint8_t interval, bool selfcalib) {
|
||||||
this->interval = interval;
|
this->interval = interval;
|
||||||
this->selfcalib = selfcalib;
|
this->selfcalib = selfcalib;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -68,11 +68,11 @@ uint8_t SCD30::getSensorData(char *payload, uint8_t startbyte) {
|
||||||
if (ready[1] == 1){
|
if (ready[1] == 1){
|
||||||
// Get All Measurements (18 Bytes)
|
// Get All Measurements (18 Bytes)
|
||||||
getBytes(SCD30_GET_MEASURE, data, 18);
|
getBytes(SCD30_GET_MEASURE, data, 18);
|
||||||
|
|
||||||
// CO2 PPM
|
// CO2 PPM
|
||||||
int16_t value = (int16_t)(byteToFloat(data[0], data[1], data[3], data[4]));
|
int16_t value = (int16_t)(byteToFloat(data[0], data[1], data[3], data[4]));
|
||||||
int16ToPayload(value, payload, startbyte);
|
int16ToPayload(value, payload, startbyte);
|
||||||
|
|
||||||
// Temperature
|
// Temperature
|
||||||
value = (int16_t)(byteToFloat(data[6], data[7], data[9], data[10])*100);
|
value = (int16_t)(byteToFloat(data[6], data[7], data[9], data[10])*100);
|
||||||
int16ToPayload(value, payload, startbyte+2);
|
int16ToPayload(value, payload, startbyte+2);
|
||||||
|
@ -127,7 +127,7 @@ void SCD30::getBytes(uint16_t reg, uint8_t bytes[], uint8_t len) {
|
||||||
if (Wire.available()) {
|
if (Wire.available()) {
|
||||||
for (uint8_t i = 0; i<len; i++)
|
for (uint8_t i = 0; i<len; i++)
|
||||||
bytes[i] = Wire.read();
|
bytes[i] = Wire.read();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calculate CRC8
|
// Calculate CRC8
|
||||||
|
|
|
@ -54,6 +54,7 @@
|
||||||
// #define HAS_MHZ19C
|
// #define HAS_MHZ19C
|
||||||
// #define HAS_SG112A
|
// #define HAS_SG112A
|
||||||
// #define HAS_SENSAIRS8
|
// #define HAS_SENSAIRS8
|
||||||
|
// #define HAS_SCD30
|
||||||
// #define HAS_BME280
|
// #define HAS_BME280
|
||||||
// #define HAS_SHT21
|
// #define HAS_SHT21
|
||||||
// #define HAS_DS18B20
|
// #define HAS_DS18B20
|
||||||
|
|
Loading…
Reference in a new issue