Ich habe in letzter Zeit versucht über MightyCore den zweiten I2C Port an einen
AtMega324PB zu nutzen (PE6 / PE5) - über Wire1.
Ich habe zwei Temp. Sensoren deren Adresse nicht geändert werden kann (SHT21), daher wollte
ich jeden Sensor einen eigenen I2C Port zuweisen.
Machen kann man das auch mit einen Multiplexer etc. - aber wenn ich noch einen Port frei habe
möchte ich den auch nutzen können.
Das wäre für micht die beste und auch "einfachste" Lösung.
Ein angepasster I2C Scanner zeigt mir auch die Geräte an diesen Port an - vom Grundsatz her ist
die Hardware soweit i.O.
Ich kann aber mit den Arduino Libs nicht auf das Device an den zweiten Port zugreifen - der zweite
I2C Anschluss wird nicht "angesprochen".
Ich denke es liegt daran, dass die Arduino Libs standardmäßig mit der "normalen" Wire.h.
kommunizieren und nur auf den ersten Port an A4 und A5 bei den Nanos zugreifen und eine
Kommunikation über Wire1.h nicht vorgesehen ist.
Daher meine Frage: muss ich die Libs entsprechend anpassen damit Geräte über Wire1.h.
am zweiten Port erkannt / eingesetzt werden können oder hat das schon einmal jemand gemacht. ?
Kann schon sein, dass du recht hast.
Wire1 ist nicht so verbreitet, und nicht jeder Lib Ersteller hatte es auf dem Schirm, dass es eine Welt neben Wire gibt.
Tipp:
Irgendwie erscheint es mir seltsam, über eine Lib zu jammern, Aussagen darüber zu erwarten, ohne sie zu nennen oder gar diese zu verlinken.
Ja, so ein Eiertanz irritiert mich!
Ich frage mich dann:
Will er/sie/es überhaupt eine Lösung?
Ist es überhaupt bereit dafür?
Oder soll ich lieber meines Weges gehen....
Ja, das ist auch einen gute Idee!
Ein Tab mit einer modifizierten Lib
#pragma once
#include <Wire.h>
//---------- Defines -----------------------------------------------------------
#define I2C_ADD 0x40 // I2C device address
const uint16_t POLYNOMIAL = 0x131; // P(x)=x^8+x^5+x^4+1 = 100110001
//==============================================================================
#define TRIGGER_T_MEASUREMENT_HM 0XE3 // command trig. temp meas. hold master
#define TRIGGER_RH_MEASUREMENT_HM 0XE5 // command trig. hum. meas. hold master
#define TRIGGER_T_MEASUREMENT_NHM 0XF3 // command trig. temp meas. no hold master
#define TRIGGER_RH_MEASUREMENT_NHM 0XF5 // command trig. hum. meas. no hold master
#define USER_REGISTER_W 0XE6 // command writing user register
#define USER_REGISTER_R 0XE7 // command reading user register
#define SOFT_RESET 0XFE // command soft reset
//==============================================================================
// HOLD MASTER - SCL line is blocked (controlled by sensor) during measurement
// NO HOLD MASTER - allows other I2C communication tasks while sensor performing
// measurements.
template<TwoWire &wire>
class SHT21
{
public:
float getHumidity(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_RH_MEASUREMENT_NHM);
return CalcRH(result);
}
float getTemperature(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_T_MEASUREMENT_NHM);
return CalcT(result);
}
void reset()
{
wire.beginTransmission(I2C_ADD);
wire.write(SOFT_RESET);
wire.endTransmission();
delay(15); // wait for SHT to reset
}
uint8_t getSerialNumber(uint8_t return_sn)
{
uint8_t serialNumber[8];
// read memory location 1
wire.beginTransmission(I2C_ADD);
wire.write(0xFA);
wire.write(0x0F);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 8);
while (wire.available() < 8) {}
serialNumber[5] = wire.read(); // read SNB_3
wire.read(); // CRC SNB_3 not used
serialNumber[4] = wire.read(); // read SNB_2
wire.read(); // CRC SNB_2 not used
serialNumber[3] = wire.read(); // read SNB_1
wire.read(); // CRC SNB_1 not used
serialNumber[2] = wire.read(); // read SNB_0
wire.read(); // CRC SNB_0 not used
// read memory location 2
wire.beginTransmission(I2C_ADD);
wire.write(0xFC);
wire.write(0xC9);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 6);
while (wire.available() < 6) {}
serialNumber[1] = wire.read(); // read SNC_1
serialNumber[0] = wire.read(); // read SNC_0
wire.read(); // CRC SNC_1/SNC_0 not used
serialNumber[7] = wire.read(); // read SNA_1
serialNumber[6] = wire.read(); // read SNA_0
wire.read(); // CRC SNA_1/SNA_0 not used
return serialNumber[return_sn];
}
private:
uint16_t readSensor_hm(uint8_t command)
{
uint8_t checksum;
uint8_t data[2];
uint16_t result;
uint8_t n = 0;
uint8_t d;
if (command == TRIGGER_RH_MEASUREMENT_HM || command == TRIGGER_RH_MEASUREMENT_NHM) d = 30;
if (command == TRIGGER_T_MEASUREMENT_HM || command == TRIGGER_T_MEASUREMENT_NHM) d = 85;
wire.beginTransmission(I2C_ADD);
wire.write(command);
wire.endTransmission();
delay(d);
wire.requestFrom(I2C_ADD, 3);
while (wire.available() < 3)
{
delay(10);
n++;
if (n > 10) return 0;
}
data[0] = wire.read(); // read data (MSB)
data[1] = wire.read(); // read data (LSB)
checksum = wire.read(); // read checksum
result = (data[0] << 8);
result += data[1];
if (CRC_Checksum (data, 2, checksum))
{
reset();
return 1;
}
else return result;
}
float CalcRH(uint16_t rh)
{
rh &= ~0x0003; // clean last two bits
return (-6.0 + 125.0 / 65536 * (float)rh); // return relative humidity
}
float CalcT(uint16_t t)
{
t &= ~0x0003; // clean last two bits
return (-46.85 + 175.72 / 65536 * (float)t);
}
uint8_t CRC_Checksum(uint8_t data[], uint8_t no_of_bytes, uint8_t checksum)
{
uint8_t crc = 0;
uint8_t byteCtr;
//calculates 8-Bit checksum with given polynomial
for (byteCtr = 0; byteCtr < no_of_bytes; ++byteCtr)
{
crc ^= (data[byteCtr]);
for (uint8_t bit = 8; bit > 0; --bit)
{
if (crc & 0x80) crc = (crc << 1) ^ POLYNOMIAL;
else crc = (crc << 1);
}
}
if (crc != checksum) return 1;
else return 0;
}
};
Ein Beispiel mit Wire und Wire1
//==============================================================================
// E - R A D I O N I C A . C O M, H.Kolomana 6/A, Djakovo 31400, Croatia
//==============================================================================
// Project : SHT21 Arduino Library
// File : SHT21 Demo Arduino Example
// Author : e-radionica.com 2017
// Licence : Open-source !
//==============================================================================
//==============================================================================
// Use with any SHT21 breakout. Check ours:
// https://e-radionica.com/en/sht21-humidity-and-temperature-sensor.html
// Shows temperature and humidity from SHT21 sensor in Serial monitor.
// If any questions,
// just contact techsupport@e-radionica.com
//==============================================================================
#include "SHT21.h" // include SHT21 library
SHT21<Wire> sht;
SHT21<Wire1> sht1;
float temp; // variable to store temperature
float humidity; // variable to store hemidity
void setup() {
Wire.begin(); // begin Wire(I2C)
Wire1.begin(); // begin Wire1(I2C)
Serial.begin(9600); // begin Serial
}
void loop() {
temp = sht.getTemperature(); // get temp from SHT
humidity = sht.getHumidity(); // get temp from SHT
Serial.print("Temp: "); // print readings
Serial.print(temp);
Serial.print("\t Humidity: ");
Serial.println(humidity);
temp = sht1.getTemperature(); // get temp from SHT1
humidity = sht1.getHumidity(); // get temp from SHT1
Serial.print("Temp1: "); // print readings
Serial.print(temp);
Serial.print("\t Humidity1: ");
Serial.println(humidity);
delay(85); // min delay for 14bit temp reading is 85ms
}
Die Idee heißt:
Dependency Injection über Template Parameter.
Constuctor Injection würde auch gehen, wenn man denn einen solchen einführt.
Die Arduino-IDE bzw die Bibliotheken kennen standartmäßig keinen 328PB und darum gibt es keine unterstüzung für die zusätzliche Hardware des PB.
Darum mußt Du entweder einen Bibliothek für den PB finden oder selbst schreiben bzw die Zusatzhardware direkt in Deinem Sketch ansprechen.
Grüße Uwe
Ich werde wahrscheinlich das dann über Soft I2C lösen oder einen Multiplexer nehmen.
Eine Library zu schreiben / umzuschreiben oder das zu "Fuß" zu machen, dass übersteigt dann doch
meine Fertigkeiten.
Trotzdem herzlichen Dank für die Bemühungen !
maik_s:
Eine Library zu schreiben / umzuschreiben oder das zu "Fuß" zu machen, dass übersteigt dann doch
meine Fertigkeiten.
Ich habe keinen AtMega324PB und keinen Sensor SHT21, daher kann ich praktisch nichts probieren. Aber wenn ich MightyCore auf AtMega324PB stelle, kann ich ein Programm mit Wire1 kompilieren. Daher kann ich Dein Problem leider nicht erkennen.
maik_s:
Ich kann aber mit den Arduino Libs nicht auf das Device an den zweiten Port zugreifen - der zweite
I2C Anschluss wird nicht "angesprochen".
Welche Libs meinst Du? Es gibt sehr, sehr viele verschiedene teilweise mit gleichlautenden Namen!
In #1 sehe ich ein Beispiel mit einer Bibliothek für SHT21, die ganz offensichtlich mit Wire1 umgehen kann. Warum nutzt Du nicht diese?
Hab ich probiert - kein Erfolg.
Ich bekomme keine Daten vom Sensor - am "normalen" I2C Port läuft alles.
Mit meinen Latein bin ich am Ende - daher meine anderen Lösungsvorschläge.
Den Sensor kann man auch ohne Lib auslesen - ich muss mal sehen ob ich das schaffe.
Ansonsten bleibt nur einen anderen Sensor zu verwenden wo ich die Adresse ändern kann
oder eben Multiplexing / Soft I2C (ich bin eben kein Profi).
Ich wollte eben gern das nehmen was ich hier schon zu liegen habe.
Edit: @combie: Die Liblösung über Templates ist genial. Das ist eine Combielösung.
Danke, für die Blumen.
Naja.... (auf die schnelle aus dem Ärmel geschüttelt)
Konnte nicht testen, hatte weder den µC noch diese Sensoren.
Schätze aber schon, dass das so funktioniert
Und: Ich fühle mich gebauchpinselt, wenn es gefällt.
Ein paar Dinge würde ich allerdings schon noch anders machen.....
Den Wire Type per Template Parameter übergeben
Die Wire Instanz per Konstruktor
Dann tuts das auch mit SoftI2C, TinyWire und sonstigen, solange sie das Wire Interface implementieren. Auf jedem Kesselchen, welcher irgendwie in den Arduino Zoo gehört. Zudem bleibt sich der Flashverbrauch etwas angenehmer.
Dass dann die Instanziierung irgendwie so aussieht:
SHT21<TwoWire> sht(Wire); // wenn man den Type kennt
SHT21<decltype(Wire1)> sht1(Wire1); // Type zur Kompilezeit ermitteln
Mit C++11 ist an der Stelle kein auto erlaubt, was die Sache vereinfachen würde, wenn dem so wäre.
Die Type Ermittlung ist nötig, weil es z.B. für den UNO kein TinyWire gibt, und so das Wort TinyWire dann nicht im Quellcode auftauchen darf.
#pragma once
#include <Wire.h>
//---------- Defines -----------------------------------------------------------
#define I2C_ADD 0x40 // I2C device address
//const uint16_t POLYNOMIAL = 0x131; // P(x)=x^8+x^5+x^4+1 = 100110001
#define POLYNOMIAL 0x131u
//==============================================================================
#define TRIGGER_T_MEASUREMENT_HM 0XE3 // command trig. temp meas. hold master
#define TRIGGER_RH_MEASUREMENT_HM 0XE5 // command trig. hum. meas. hold master
#define TRIGGER_T_MEASUREMENT_NHM 0XF3 // command trig. temp meas. no hold master
#define TRIGGER_RH_MEASUREMENT_NHM 0XF5 // command trig. hum. meas. no hold master
#define USER_REGISTER_W 0XE6 // command writing user register
#define USER_REGISTER_R 0XE7 // command reading user register
#define SOFT_RESET 0XFE // command soft reset
//==============================================================================
// HOLD MASTER - SCL line is blocked (controlled by sensor) during measurement
// NO HOLD MASTER - allows other I2C communication tasks while sensor performing
// measurements.
template<typename WireType>
class SHT21
{
public:
SHT21(WireType &wire): wire(wire) {}
float getHumidity(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_RH_MEASUREMENT_NHM);
return CalcRH(result);
}
float getTemperature(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_T_MEASUREMENT_NHM);
return CalcT(result);
}
void reset()
{
wire.beginTransmission(I2C_ADD);
wire.write(SOFT_RESET);
wire.endTransmission();
delay(15); // wait for SHT to reset
}
uint8_t getSerialNumber(uint8_t return_sn)
{
uint8_t serialNumber[8];
// read memory location 1
wire.beginTransmission(I2C_ADD);
wire.write(0xFA);
wire.write(0x0F);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 8);
while (wire.available() < 8) {}
serialNumber[5] = wire.read(); // read SNB_3
wire.read(); // CRC SNB_3 not used
serialNumber[4] = wire.read(); // read SNB_2
wire.read(); // CRC SNB_2 not used
serialNumber[3] = wire.read(); // read SNB_1
wire.read(); // CRC SNB_1 not used
serialNumber[2] = wire.read(); // read SNB_0
wire.read(); // CRC SNB_0 not used
// read memory location 2
wire.beginTransmission(I2C_ADD);
wire.write(0xFC);
wire.write(0xC9);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 6);
while (wire.available() < 6) {}
serialNumber[1] = wire.read(); // read SNC_1
serialNumber[0] = wire.read(); // read SNC_0
wire.read(); // CRC SNC_1/SNC_0 not used
serialNumber[7] = wire.read(); // read SNA_1
serialNumber[6] = wire.read(); // read SNA_0
wire.read(); // CRC SNA_1/SNA_0 not used
return serialNumber[return_sn];
}
private:
WireType &wire;
uint16_t readSensor_hm(uint8_t command)
{
uint8_t checksum;
uint8_t data[2];
uint16_t result;
uint8_t n = 0;
uint8_t d;
if (command == TRIGGER_RH_MEASUREMENT_HM || command == TRIGGER_RH_MEASUREMENT_NHM) d = 30;
if (command == TRIGGER_T_MEASUREMENT_HM || command == TRIGGER_T_MEASUREMENT_NHM) d = 85;
wire.beginTransmission(I2C_ADD);
wire.write(command);
wire.endTransmission();
delay(d);
wire.requestFrom(I2C_ADD, 3);
while (wire.available() < 3)
{
delay(10);
n++;
if (n > 10) return 0;
}
data[0] = wire.read(); // read data (MSB)
data[1] = wire.read(); // read data (LSB)
checksum = wire.read(); // read checksum
result = (data[0] << 8);
result += data[1];
if (CRC_Checksum (data, 2, checksum))
{
reset();
return 1;
}
else return result;
}
float CalcRH(uint16_t rh)
{
rh &= ~0x0003; // clean last two bits
return (-6.0 + 125.0 / 65536 * (float)rh); // return relative humidity
}
float CalcT(uint16_t t)
{
t &= ~0x0003; // clean last two bits
return (-46.85 + 175.72 / 65536 * (float)t);
}
uint8_t CRC_Checksum(uint8_t data[], uint8_t no_of_bytes, uint8_t checksum)
{
uint8_t crc = 0;
uint8_t byteCtr;
//calculates 8-Bit checksum with given polynomial
for (byteCtr = 0; byteCtr < no_of_bytes; ++byteCtr)
{
crc ^= (data[byteCtr]);
for (uint8_t bit = 8; bit > 0; --bit)
{
if (crc & 0x80) crc = (crc << 1) ^ POLYNOMIAL;
else crc = (crc << 1);
}
}
if (crc != checksum) return 1;
else return 0;
}
};
Ich will nicht unhöflich sein - aber am WE ist bei mir die Zeit knapp.
Daher auch meine verhaltene Reaktion auf die hier geleistete Hilfe.
Im allgemeinen liegt mir die Hardware mehr als die Software (dass sieht man auch in meinen Beiträgen).
In der Woche nach Feierabend ist mehr Zeit und da werde ich mich mit dem Thema noch weiter beschäfftigen.
Pullups sind vorhanden - der I2C Scanner zeigt ja alle Devices/Adressen an.
Sorry, aber vor Mo. oder Die. werde ich es nicht schaffen weitere Neuigkeiten zu verkünden.
Ich denke, das Thema Wire1 ist auch für andere von Interesse - im Web gibt es zu diesen Thema genügend
Fragen und einige weichen dann auf Soft I2C oder Multiplexer aus.
maik_s:
Ich denke, das Thema Wire1 ist auch für andere von Interesse - im Web gibt es zu diesen Thema genügend
Fragen und einige weichen dann auf Soft I2C oder Multiplexer aus.
Das denke ich auch, weshalb ich viele Bibliotheken, die das unterstützen, erwartet hätte. Eine kurze Suche ergab aber, daß scheinbar alle von einer Quelle abgeschrieben haben. Zumindest konnte ich keine Unterstützung für Wire1 finden. Schon merkwürdig
Morgen ist Wartung, daher dann wohl bis Dienstag ... oder nie
Zumindest konnte ich keine Unterstützung für Wire1 finden. Schon merkwürdig
Das wundert mich eigentlich nicht.
Wire selber, ist ganz ok.
Aber die Integration in die Arduino Welt ist krank, schwer verletzt.
Es leidet unter den Spätfolgen der Geburt und den ersten Revisionen.
Das ist der Fluch der Simplifizierung.
Wirklich hilfreich wäre, wenn die verschiedensten Wire Inkarnationen ein gemeinsames Interface hätten.
Dann hätten es die Lib Ersteller viel leichter.
Ich habe jetzt noch einmal alles in Ruhe gemacht und die Lib oben eingebunden.
Fehlermeldung : SHT21.cpp:171:2: error: explicit instantiation of non-template type 'SHT21'
Außerdem fehlt oben in der Lib nach #include unter #pragma once`noch etwas - der Compiler meckert an dieser Stelle.
Ansosnsten keine Auswertung auf den zweiten Port über wire1 möglich.
Ich denke es liegt nur an der Library - der I2C Scanner läuft und zeigt auch beide Devices an.
Hier der Code vom Scanner (etwas modifizert entgegen dem Orginal für Mightycore mit AtMega324pb):
for(address = 1; address < 127; address++ )
{
// The i2c_scanner uses the return value of
// the Write.endTransmisstion to see if
// a device did acknowledge to the address.
Wire.beginTransmission(address);
error = Wire.endTransmission();
if (error == 0)
{
Serial.print("I2C device found at first Port at address 0x");
if (address<16)
Serial.print("0");
Serial.print(address,HEX);
Serial.println(" !");
nDevices++;
}
else if (error==4)
{
Serial.print("Unknow error at address 0x");
if (address<16)
Serial.print("0");
Serial.println(address,HEX);
}
for(address = 1; address < 127; address++ )
{
// The i2c_scanner uses the return value of
// the Write.endTransmisstion to see if
// a device did acknowledge to the address.
Wire1.beginTransmission(address);
error = Wire1.endTransmission();
if (error == 0)
{
Serial.print("I2C device found at second Port at address 0x");
if (address<16)
Serial.print("0");
Serial.print(address,HEX);
Serial.println(" !");
nDevices++;
}
else if (error==4)
{
Serial.print("Unknow error at address 0x");
if (address<16)
Serial.print("0");
Serial.println(address,HEX);
}
//==============================================================================
// E - R A D I O N I C A . C O M, H.Kolomana 6/A, Djakovo 31400, Croatia
//==============================================================================
// Project : SHT21 Arduino Library
// File : SHT21 Demo Arduino Example
// Author : e-radionica.com 2017
// Licence : Open-source !
//==============================================================================
//==============================================================================
// Use with any SHT21 breakout. Check ours:
// https://e-radionica.com/en/sht21-humidity-and-temperature-sensor.html
// Shows temperature and humidity from SHT21 sensor in Serial monitor.
// If any questions,
// just contact techsupport@e-radionica.com
//==============================================================================
#include "SHT21.h" // include SHT21 library
SHT21<TwoWire> sht(Wire); // wenn man den Type kennt
SHT21<decltype(Wire1)> sht1(Wire1); // Type zur Kompilezeit ermitteln
//SHT21<Wire> sht;
//SHT21<Wire1> sht1;
float temp; // variable to store temperature
float humidity; // variable to store hemidity
void setup() {
Wire.begin(); // begin Wire(I2C)
Wire1.begin(); // begin Wire1(I2C)
Serial.begin(9600); // begin Serial
}
void loop() {
temp = sht.getTemperature(); // get temp from SHT
humidity = sht.getHumidity(); // get temp from SHT
Serial.print("Temp: "); // print readings
Serial.print(temp);
Serial.print("\t Humidity: ");
Serial.println(humidity);
temp = sht1.getTemperature(); // get temp from SHT1
humidity = sht1.getHumidity(); // get temp from SHT1
Serial.print("Temp1: "); // print readings
Serial.print(temp);
Serial.print("\t Humidity1: ");
Serial.println(humidity);
delay(85); // min delay for 14bit temp reading is 85ms
}
Das 2te Tab, die SHT21.h
#pragma once
#include <Wire.h>
//---------- Defines -----------------------------------------------------------
#define I2C_ADD 0x40 // I2C device address
//const uint16_t POLYNOMIAL = 0x131; // P(x)=x^8+x^5+x^4+1 = 100110001
#define POLYNOMIAL 0x131u
//==============================================================================
#define TRIGGER_T_MEASUREMENT_HM 0XE3 // command trig. temp meas. hold master
#define TRIGGER_RH_MEASUREMENT_HM 0XE5 // command trig. hum. meas. hold master
#define TRIGGER_T_MEASUREMENT_NHM 0XF3 // command trig. temp meas. no hold master
#define TRIGGER_RH_MEASUREMENT_NHM 0XF5 // command trig. hum. meas. no hold master
#define USER_REGISTER_W 0XE6 // command writing user register
#define USER_REGISTER_R 0XE7 // command reading user register
#define SOFT_RESET 0XFE // command soft reset
//==============================================================================
// HOLD MASTER - SCL line is blocked (controlled by sensor) during measurement
// NO HOLD MASTER - allows other I2C communication tasks while sensor performing
// measurements.
template<typename WireType>
class SHT21
{
public:
SHT21(WireType &wire):wire(wire){}
float getHumidity(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_RH_MEASUREMENT_NHM);
return CalcRH(result);
}
float getTemperature(void)
{
uint16_t result; // return variable
result = readSensor_hm(TRIGGER_T_MEASUREMENT_NHM);
return CalcT(result);
}
void reset()
{
wire.beginTransmission(I2C_ADD);
wire.write(SOFT_RESET);
wire.endTransmission();
delay(15); // wait for SHT to reset
}
uint8_t getSerialNumber(uint8_t return_sn)
{
uint8_t serialNumber[8];
// read memory location 1
wire.beginTransmission(I2C_ADD);
wire.write(0xFA);
wire.write(0x0F);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 8);
while (wire.available() < 8) {}
serialNumber[5] = wire.read(); // read SNB_3
wire.read(); // CRC SNB_3 not used
serialNumber[4] = wire.read(); // read SNB_2
wire.read(); // CRC SNB_2 not used
serialNumber[3] = wire.read(); // read SNB_1
wire.read(); // CRC SNB_1 not used
serialNumber[2] = wire.read(); // read SNB_0
wire.read(); // CRC SNB_0 not used
// read memory location 2
wire.beginTransmission(I2C_ADD);
wire.write(0xFC);
wire.write(0xC9);
wire.endTransmission();
wire.requestFrom(I2C_ADD, 6);
while (wire.available() < 6) {}
serialNumber[1] = wire.read(); // read SNC_1
serialNumber[0] = wire.read(); // read SNC_0
wire.read(); // CRC SNC_1/SNC_0 not used
serialNumber[7] = wire.read(); // read SNA_1
serialNumber[6] = wire.read(); // read SNA_0
wire.read(); // CRC SNA_1/SNA_0 not used
return serialNumber[return_sn];
}
private:
WireType &wire;
uint16_t readSensor_hm(uint8_t command)
{
uint8_t checksum;
uint8_t data[2];
uint16_t result;
uint8_t n = 0;
uint8_t d;
if (command == TRIGGER_RH_MEASUREMENT_HM || command == TRIGGER_RH_MEASUREMENT_NHM) d = 30;
if (command == TRIGGER_T_MEASUREMENT_HM || command == TRIGGER_T_MEASUREMENT_NHM) d = 85;
wire.beginTransmission(I2C_ADD);
wire.write(command);
wire.endTransmission();
delay(d);
wire.requestFrom(I2C_ADD, 3);
while (wire.available() < 3)
{
delay(10);
n++;
if (n > 10) return 0;
}
data[0] = wire.read(); // read data (MSB)
data[1] = wire.read(); // read data (LSB)
checksum = wire.read(); // read checksum
result = (data[0] << 8);
result += data[1];
if (CRC_Checksum (data, 2, checksum))
{
reset();
return 1;
}
else return result;
}
float CalcRH(uint16_t rh)
{
rh &= ~0x0003; // clean last two bits
return (-6.0 + 125.0 / 65536 * (float)rh); // return relative humidity
}
float CalcT(uint16_t t)
{
t &= ~0x0003; // clean last two bits
return (-46.85 + 175.72 / 65536 * (float)t);
}
uint8_t CRC_Checksum(uint8_t data[], uint8_t no_of_bytes, uint8_t checksum)
{
uint8_t crc = 0;
uint8_t byteCtr;
//calculates 8-Bit checksum with given polynomial
for (byteCtr = 0; byteCtr < no_of_bytes; ++byteCtr)
{
crc ^= (data[byteCtr]);
for (uint8_t bit = 8; bit > 0; --bit)
{
if (crc & 0x80) crc = (crc << 1) ^ POLYNOMIAL;
else crc = (crc << 1);
}
}
if (crc != checksum) return 1;
else return 0;
}
};
Danke - meckert aber noch : 'SHT21' is not a template.
sketch_apr13b:3:1: error: 'SHT21' is not a template
SHT21 sht(Wire); // wenn man den Type kennt
^~~~~
sketch_apr13b:3:24: error: no matching function for call to 'SHT21::SHT21(TwoWire&)'
SHT21 sht(Wire); // wenn man den Type kennt
Da fehlt nichts!
Es benutzt weiter die alte Lib, nicht meine Änderung.
Hast du die Datei in einem Tab untergebracht!
Und auch so eingebunden, wie ich es gezeigt habe?
Falsch:
SHT21 sht(Wire); // wenn man den Type kennt
Richtig:
SHT21<TwoWire> sht(Wire); // wenn man den Type kennt