SHT31 reading via i2c

Hi Please help a noob.

I am trying to read data off two sht31 temp and humidity sensors. one is set to 0x44 and the other is set to 0x45
i can read one with the following code but I cant seem to read the second one. I cant find any way online of doing it or any examples
I get an error if i define twice by doing
#define Addr 0x44
#define Addr2 0x45

any way to do this?

thank you for your help

Ian

// Distributed with a free-will license.
// Use it any way you want, profit or free, provided it fits in the licenses of its associated works.
// SHT31
// This code is designed to work with the SHT31_I2CS I2C Mini Module available from ControlEverything.com.
// https://www.controleverything.com/content/Humidity?sku=SHT31_I2CS#tabs-0-product_tabset-2

#include <Wire.h>

// SHT31 I2C address is 0x44(68)
#define Addr 0x44

void setup()
{
  // Initialise I2C communication as MASTER
  Wire.begin();
  // Initialise serial communication, set baud rate = 9600
  Serial.begin(9600);
  delay(300);
}

void loop()
{
  unsigned int data[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data[0] = Wire.read();
    data[1] = Wire.read();
    data[2] = Wire.read();
    data[3] = Wire.read();
    data[4] = Wire.read();
    data[5] = Wire.read();
  }
  // Convert the data
  int temp = (data[0] * 256) + data[1];
  float cTemp = -45.0 + (175.0 * temp / 65535.0);
  float fTemp = (cTemp * 1.8) + 32.0;
  float humidity = (100.0 * ((data[3] * 256.0) + data[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temperature in Celsius :");
  Serial.print(cTemp);
  Serial.println(" C");
  Serial.print("Temperature in Fahrenheit :");
  Serial.print(fTemp);
  Serial.println(" F");
  Serial.print("Relative Humidity :");
  Serial.print(humidity);
  Serial.println(" %RH");
  delay(500);
}

I get an error if i define twice by doing

What does the error say?

Please print the value endtransmission returns as this statement gives info about the I2C communication.

int x = Wire.endTransmission();
Serial.println(x);

ok I have no idea what im doing now! the error has gone but i cant see how to get it to display the second sensors info

// Distributed with a free-will license.
// Use it any way you want, profit or free, provided it fits in the licenses of its associated works.
// SHT31
// This code is designed to work with the SHT31_I2CS I2C Mini Module available from ControlEverything.com.
// https://www.controleverything.com/content/Humidity?sku=SHT31_I2CS#tabs-0-product_tabset-2

#include <Wire.h>

// SHT31 I2C address is 0x44(68)
#define Addr 0x44
#define Addr2 0x45


void setup()
{
  // Initialise I2C communication as MASTER
  Wire.begin();
  // Initialise serial communication, set baud rate = 9600
  Serial.begin(9600);
  delay(300);
}

void loop()
{
  unsigned int data[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data[0] = Wire.read();
    data[1] = Wire.read();
    data[2] = Wire.read();
    data[3] = Wire.read();
    data[4] = Wire.read();
    data[5] = Wire.read();
  }


  
{
  unsigned int data[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr2, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data[0] = Wire.read();
    data[1] = Wire.read();
    data[2] = Wire.read();
    data[3] = Wire.read();
    data[4] = Wire.read();
    data[5] = Wire.read();
 
   }}




  
  // Convert the data
  int temp = (data[0] * 256) + data[1];
  float cTemp = -45.0 + (175.0 * temp / 65535.0);
  float fTemp = (cTemp * 1.8) + 32.0;
  float humidity = (100.0 * ((data[3] * 256.0) + data[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temp   :");
  Serial.print(cTemp);
  Serial.println(" C");
  Serial.print("Humidity :");
  Serial.print(humidity);
  Serial.println(" %");
  delay(500);
}

ok I have no idea what im doing now! the error has gone but i cant see how to get it to display the second sensors info

You are putting the 6 bytes of requested data from the two different sensors in the same array data[6] and the values from the second reading are overwriting the first.

You are only converting the data from the second reading given how you are executing the convert the data code only once per loop.

You also have some extra brackets.

Think this through a bit more, and see what you can come up with. You are close.

Im still totally lost. Ive thought it through
ruined my original data. nothing i try works.

6 hours later and im further back than i was before, all the online documentation has confused me about addressing

You know how to correctly fill one array and print out the data from that array. Declare a second array data2[6] and fill it using the same wire commands as before but using addr2.

Convert and print the data from the two different arrays holding the data.

There are more memory efficient ways to do this, but try the simple "duplicate everthing" to get going.

Please post your latest code.

I tried, I thought i succeeded but turns out I just sucked.

i am still only getting data from one sensor repeated, I don't think I am overwriting now. any ideas?

// Distributed with a free-will license.
// Use it any way you want, profit or free, provided it fits in the licenses of its associated works.
// SHT31
// This code is designed to work with the SHT31_I2CS I2C Mini Module available from ControlEverything.com.
// https://www.controleverything.com/content/Humidity?sku=SHT31_I2CS#tabs-0-product_tabset-2

#include <Wire.h>

// SHT31 I2C address is 0x44(68)
#define Addr 0x44
#define Addr2 0x45


void setup()
{
  // Initialise I2C communication as MASTER
  Wire.begin();
  // Initialise serial communication, set baud rate = 9600
  Serial.begin(9600);
  delay(300);
}

void loop()
{
  unsigned int data[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data[0] = Wire.read();
    data[1] = Wire.read();
    data[2] = Wire.read();
    data[3] = Wire.read();
    data[4] = Wire.read();
    data[5] = Wire.read();
  }

//second write and read
  
{
  unsigned int data2[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr2, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data2[0] = Wire.read();
    data2[1] = Wire.read();
    data2[2] = Wire.read();
    data2[3] = Wire.read();
    data2[4] = Wire.read();
    data2[5] = Wire.read();
 
   }




  
  // Convert the data
  int temp = (data[0] * 256) + data[1];
  float cTemp = -45.0 + (175.0 * temp / 65535.0);
  float fTemp = (cTemp * 1.8) + 32.0;
  float humidity = (100.0 * ((data[3] * 256.0) + data[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temp   :");
  Serial.print(cTemp);
  Serial.println(" C");
  Serial.print("Humidity :");
  Serial.print(humidity);
  Serial.println(" %");
  
   int temp2 = (data2[0] * 256) + data2[1];
  float cTemp2 = -45.0 + (175.0 * temp / 65535.0);
  float fTemp2 = (cTemp * 1.8) + 32.0;
  float humidity2 = (100.0 * ((data2[3] * 256.0) + data2[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temp2   :");
  Serial.print(cTemp2);
  Serial.println(" C");
  Serial.print("Humidity2 :");
  Serial.print(humidity2);
  Serial.println(" %");
  delay(500);
}}

Duhh I fixed it. (facepalm)

I used the orginal string temp to convert the data, not temp2. I noticed when checking my code in the post.

hurrah, now to start doing stuff with it.

thank you :slight_smile:

// Distributed with a free-will license.
// Use it any way you want, profit or free, provided it fits in the licenses of its associated works.
// SHT31
// This code is designed to work with the SHT31_I2CS I2C Mini Module available from ControlEverything.com.
// https://www.controleverything.com/content/Humidity?sku=SHT31_I2CS#tabs-0-product_tabset-2

#include <Wire.h>

// SHT31 I2C address is 0x44(68)
#define Addr 0x44
#define Addr2 0x45


void setup()
{
  // Initialise I2C communication as MASTER
  Wire.begin();
  // Initialise serial communication, set baud rate = 9600
  Serial.begin(9600);
  delay(300);
}

void loop()
{
  unsigned int data[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data[0] = Wire.read();
    data[1] = Wire.read();
    data[2] = Wire.read();
    data[3] = Wire.read();
    data[4] = Wire.read();
    data[5] = Wire.read();
  }

//second write and read
  
{
  unsigned int data2[6];

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Send 16-bit command byte
  Wire.write(0x2C);
  Wire.write(0x06);
  // Stop I2C transmission
  Wire.endTransmission();
  delay(300);

  // Start I2C Transmission
  Wire.beginTransmission(Addr2);
  // Stop I2C Transmission
  Wire.endTransmission();

  // Request 6 bytes of data
  Wire.requestFrom(Addr2, 6);

  // Read 6 bytes of data
  // temp msb, temp lsb, temp crc, hum msb, hum lsb, hum crc
  if (Wire.available() == 6)
  {
    data2[0] = Wire.read();
    data2[1] = Wire.read();
    data2[2] = Wire.read();
    data2[3] = Wire.read();
    data2[4] = Wire.read();
    data2[5] = Wire.read();
 
   }




  
  // Convert the data
  int temp = (data[0] * 256) + data[1];
  float cTemp = -45.0 + (175.0 * temp / 65535.0);
  float fTemp = (cTemp * 1.8) + 32.0;
  float humidity = (100.0 * ((data[3] * 256.0) + data[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temp   :");
  Serial.print(cTemp);
  Serial.println(" C");
  Serial.print("Humidity :");
  Serial.print(humidity);
  Serial.println(" %");
  
   int temp2 = (data2[0] * 256) + data2[1];
  float cTemp2 = -45.0 + (175.0 * temp2 / 65535.0);
  float fTemp2 = (cTemp2 * 1.8) + 32.0;
  float humidity2 = (100.0 * ((data2[3] * 256.0) + data2[4])) / 65535.0;

  // Output data to serial monitor
  Serial.print("Temp2   :");
  Serial.print(cTemp2);
  Serial.println(" C");
  Serial.print("Humidity2 :");
  Serial.print(humidity2);
  Serial.println(" %");
  delay(500);
}}
  // Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

Yo, Addr, wake up. Oh, wait, never mind.

What is this stuff for?

 if (Wire.available() == 6)
  {

And, if the slave didn't return 6 bytes, pretend that it did. Why?

Did you run the I2C scanner sketch? Are those addresses correct?

yeah the code probably sucks. but it works thats all i want it to do.

where were you with your advice when i needed it?

as for the slave question. i have no idea. ask me a question on flying aircraft or diving and i will answer it no problem.

i love the idea that i got the code to work. and then asked to post it then someone who hasnt helped comes along and laughs at it yeah real funny

PaulS:

  // Start I2C Transmission

Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();



Yo, Addr, wake up. Oh, wait, never mind.

What is this stuff for?



if (Wire.available() == 6)
  {



And, if the slave didn't return 6 bytes, pretend that it did. Why?

Did you run the I2C scanner sketch? Are those addresses correct?

i love the idea that i got the code to work

Yes, good job. In my earlier advice I was focused on the main barriers operation as you wanted. Now you can work to refine the code.

As Paul says, this next piece of code is not doing anything useful, but it is pretty harmless. Still it would be better to remove it. I didn't really notice it and was basing my reply on the fact that you received one set of data correctly.

// Start I2C Transmission
  Wire.beginTransmission(Addr);
  // Stop I2C Transmission
  Wire.endTransmission();

The second thing that Paul points out is this, and it opens up a major topic for consideration

if (Wire.available() == 6)
  {

It turns out that Wire.available() returns the number of bytes requested. So checking for 6 doesn't ensure that they were sent. See this discussion in Nick Gammon's tutorial on the i2c bus. The entire article is worth your time.

You need to decide how important the data is, and how robust the communication needs to be. You can be expanding your code to use start and stop markers, crc checking, and data rejection of wild numbers.

You won't be the first Arduino user to blindly accept whatever the assemblage of Wire.read() values produces, but you should think about the issue. If there were issues of safety or equipment damage dependent, or paying customer satisfaction dependent upon the values you read, you would need to address the error situation.