ESP32 & Arduino Uno data processing from serial communication

Hey, I am working on smart home app. The problem is, that my code in ESP32 doesn't process the data from Arduino Uno. I get output in serial monitor, but I don't know how to use it right.

My code:

//TRANSMITTER ESP32

#include <Arduino.h>
#include <WiFi.h>
#include <Firebase_ESP_Client.h>
#include "addons/TokenHelper.h"
#include "addons/RTDBHelper.h"
#include <BME280I2C.h>
#include <Wire.h>

#define RX 2
#define TX 1

#define WIFI_SSID "wifi ssid"
#define WIFI_PASSWORD "wifi password"

#define API_KEY "api key"

#define DATABASE_URL "database url"

int readBufOffset = 0;
char readBuf[10];

unsigned long sendDataPrevMillis = 0;
unsigned long sendGraphDataPrevMillis = 0;

bool signupOK = false;


int tempf = 0;
int humif = 0;

int val = 0;

BME280I2C bme;
FirebaseData fbdo;
FirebaseAuth auth;
FirebaseConfig config;

void setup() {
  // put your setup code here, to run once:
  Serial.begin(115200);
  Serial2.begin(9600, SERIAL_8N1, RX, TX);
  Wire.begin();
  bme.begin();
  WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
  Serial.print("Connecting to Wi-Fi");
  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    delay(300);
  }
  Serial.println();
  Serial.print("Connected with IP: ");
  Serial.println(WiFi.localIP());
  Serial.println();

  config.api_key = API_KEY;
  config.database_url = DATABASE_URL;

  if (Firebase.signUp(&config, &auth, "", "")) {
    Serial.println("ok");
    signupOK = true;
  }
  else {
    Serial.printf("%s\n", config.signer.signupError.message.c_str());
  }

  config.token_status_callback = tokenStatusCallback;

  Firebase.begin(&config, &auth);
  Firebase.reconnectWiFi(true);
}
void loop() {
  if (Firebase.ready() && signupOK && (millis() - sendDataPrevMillis > 15000 || sendDataPrevMillis == 0)) {
    sendDataPrevMillis = millis();
    sendGraphDataPrevMillis = millis();

    for (int i = 0; i < 2; i++) {                  // THERE'S THE PROBLEM AREA STARTING
      char c = Serial2.read();                  // Code explanation - For loop is here, because I measure two
      if (c != '\n') {                                    // values. Then char c is for storing single numbers. When "\n" 
        readBuf[readBufOffset++] = c;  // shows in Uno output, value from buffer is stored as tempf 
      }                                                      // and converted to int. Than same thing happens for humidity.
      else {
        val += 1;
        switch (val) {
          case 1: {
              tempf = atoi(readBuf);
              readBuf[readBufOffset] = 0;
              readBufOffset = 0;
              break;
            }
          case 2: {
              humif = atoi(readBuf);
              val = 0;
              readBuf[readBufOffset] = 0;
              readBufOffset = 0;
              break;
            }
        }
      }
    }

    float temp(NAN), hum(NAN), pres(NAN);
    BME280::TempUnit tempUnit(BME280::TempUnit_Celsius);
    BME280::PresUnit presUnit(BME280::PresUnit_Pa);
    bme.read(pres, temp, hum, tempUnit, presUnit);
    pres = pres / 100;

    Firebase.RTDB.setFloat(&fbdo, "bme/teplota", temp);
    Firebase.RTDB.setFloat(&fbdo, "bme/tlak", pres);
    Firebase.RTDB.setInt(&fbdo, "dht/teplota", tempf);
    Firebase.RTDB.setInt(&fbdo, "dht/vlhkost", humif);


    if (millis() - sendGraphDataPrevMillis > 3600000000 || sendGraphDataPrevMillis == 0) {
      Firebase.RTDB.pushFloat(&fbdo, "graf/teplotag", temp);
      Firebase.RTDB.pushFloat(&fbdo, "graf/tlakg", pres);
      Firebase.RTDB.pushInt(&fbdo, "graf/teplotaf", tempf);
      Firebase.RTDB.pushInt(&fbdo, "graf/vlhkostf", humif);
      sendGraphDataPrevMillis == 0;
    }
  }
}

need to check if there's in fact any bytes available.

if (Serial.available()>2){
//your code here..
}

Thank you, but unfortunately it didn't help.

I recommend that you review this tutorial on Serial communication and use the techniques given.
https://forum.arduino.cc/t/serial-input-basics-updated/382007

If that is the ESP32's GPIO pins what ESP32 do you have that you can use GPIO pin 1 and 2 for serial communications?

Typically Serial2 on a ESP32 uses GPIO_NUM_16 and GPIO_NUM_17.

Post a pin out diagram for the ESP32 developer module you are using.

Thanks for your answer. I changed the code according to the guide, but still no values in Firebase rtdb. Some advice?

    if (Serial2.available()) {
      for (int i = 0; i < 2; i++) {
        char c = Serial2.read();
        if (c != '\n') {
          readBuf[ndx] = c;
          ndx++;
          if (ndx >= numChars) {
            ndx = numChars - 1;
          }
        }
        else {
          val += 1;
          switch (val) {
            case 1: {
                tempf = atoi(readBuf);
                readBuf[ndx] = '\0';
                ndx = 0;
                break;
              }
            case 2: {
                humif = atoi(readBuf);
                val = 0;
                readBuf[ndx] = '\0';
                ndx = 0;
                break;
              }
          }
        }
      }
    }

Is this code for an ESP32?

Why don't you post the whole code?

#include <HardwareSerial.h>


HardwareSerial GPSSerial ( 1 );
HardwareSerial LIDARSerial ( 2 );

voided setup()
{
  LIDARSerial.begin ( SerialDataBits, SERIAL_8N1, 26, 25 );
  GPSSerial.begin ( GPS_DataBits, SERIAL_8N1, 2, 15 ); // begin GPS hardware serial

}

Here

#include <Arduino.h>
#include <WiFi.h>
#include <Firebase_ESP_Client.h>
#include "addons/TokenHelper.h"
#include "addons/RTDBHelper.h"
#include <BME280I2C.h>
#include <Wire.h>

#define RX 2
#define TX 1

#define WIFI_SSID ""
#define WIFI_PASSWORD ""

#define API_KEY ""

#define DATABASE_URL ""

const byte numChars = 4;
char readBuf[numChars];
static byte ndx = 0;

unsigned long sendDataPrevMillis = 0;
unsigned long sendGraphDataPrevMillis = 0;

bool signupOK = false;


int tempf = 0;
int humif = 0;

int val = 0;

BME280I2C bme;
FirebaseData fbdo;
FirebaseAuth auth;
FirebaseConfig config;

void setup() {
  // put your setup code here, to run once:
  Serial.begin(115200);
  Serial1.begin(9600, SERIAL_8N1, RX, TX);
  Wire.begin();
  bme.begin();
  WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
  Serial.print("Connecting to Wi-Fi");
  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    delay(300);
  }
  Serial.println();
  Serial.print("Connected with IP: ");
  Serial.println(WiFi.localIP());
  Serial.println();

  config.api_key = API_KEY;
  config.database_url = DATABASE_URL;

  if (Firebase.signUp(&config, &auth, "", "")) {
    Serial.println("ok");
    signupOK = true;
  }
  else {
    Serial.printf("%s\n", config.signer.signupError.message.c_str());
  }

  config.token_status_callback = tokenStatusCallback;

  Firebase.begin(&config, &auth);
  Firebase.reconnectWiFi(true);
}
void loop() {
  if (Firebase.ready() && signupOK && (millis() - sendDataPrevMillis > 15000 || sendDataPrevMillis == 0)) {
    sendDataPrevMillis = millis();
    sendGraphDataPrevMillis = millis();

    if (Serial1.available()) {
      for (int i = 0; i < 2; i++) {
        char c = Serial1.read();
        if (c != '\n') {
          readBuf[ndx] = c;
          ndx++;
          if (ndx >= numChars) {
            ndx = numChars - 1;
          }
        }
        else {
          val += 1;
          switch (val) {
            case 1: {
                tempf = atoi(readBuf);
                readBuf[ndx] = '\0';
                ndx = 0;
                break;
              }
            case 2: {
                humif = atoi(readBuf);
                val = 0;
                readBuf[ndx] = '\0';
                ndx = 0;
                break;
              }
          }
        }
      }
    }

    float temp(NAN), hum(NAN), pres(NAN);
    BME280::TempUnit tempUnit(BME280::TempUnit_Celsius);
    BME280::PresUnit presUnit(BME280::PresUnit_Pa);
    bme.read(pres, temp, hum, tempUnit, presUnit);
    pres = pres / 100;

    Firebase.RTDB.setFloat(&fbdo, "bme/teplota", temp);
    Firebase.RTDB.setFloat(&fbdo, "bme/tlak", pres);
    Firebase.RTDB.setInt(&fbdo, "dht/teplota", tempf);
    Firebase.RTDB.setInt(&fbdo, "dht/vlhkost", humif);


    if (millis() - sendGraphDataPrevMillis > 3600000000 || sendGraphDataPrevMillis == 0) {
      Firebase.RTDB.pushFloat(&fbdo, "graf/teplotag", temp);
      Firebase.RTDB.pushFloat(&fbdo, "graf/tlakg", pres);
      Firebase.RTDB.pushInt(&fbdo, "graf/teplotaf", tempf);
      Firebase.RTDB.pushInt(&fbdo, "graf/vlhkostf", humif);
      sendGraphDataPrevMillis == 0;
    }
  }
}

Your code posted in #8 still shows that GPIO_NUM_2 and GPIO_NUM_1 are still being used for serial on a ESP32?

I changed Serial2 to Serial1 and still got same output as before.

Yes, I'd expect changing the words from Serial1 to Serial2 or Serial3 or Serial4 or Serial5 or Serial6... will not fix the issue.

Well, I've got wroom esp32 where's just rx0 and tx0 marked and as I wrote at beginning, I receive values, I just don't know how to make int from them.

Sorry I was unable to help.

Nevermind, thanks for your time.

Can you please clarify what is being sent from the Arduino? Is readBuf[] big enough to hold both temp and humidity values?

Do you have a level shifter to keep the Arduino Tx from being 5v at the ESP32 Rx?

I agree with @Idahowalker that your choice of pins for the Serial1 input from the Arduino is not correct.

wroom esp32 where's just rx0 and tx0 marked
Those pins are connected to the usb converter and you would be better off with different pins if you want to load code and use the monitor.

You can not go wrong with

#define RXD2 16
#define TXD2 17

void setup() { 
  Serial2.begin(9600, SERIAL_8N1, RXD2, TXD2);

I receive values, I just don't know how to make int from them.

atoi is a c-string function and requires null terminated values.

What happens if you reverse your null termination and atoi instructions?

if (Serial2.available()) {
      for (int i = 0; i < 2; i++) {
        char c = Serial2.read();
        if (c != '\n') {
          readBuf[ndx] = c;
          ndx++;
          if (ndx >= numChars) {
            ndx = numChars - 1;
          }
        }
        else {
          val += 1;
          switch (val) {
            case 1: {
               // tempf = atoi(readBuf);
                readBuf[ndx] = '\0';
                tempf = atoi(readBuf);
                ndx = 0;
                break;
              }
            case 2: {
               // humif = atoi(readBuf);
                val = 0;
                readBuf[ndx] = '\0';
                humif = atoi(readBuf);
                ndx = 0;
                break;
              }
          }
        }
      }
    }

Can you please clarify what is being sent from the Arduino?

#include <SimpleDHT.h>

int pinDHT11 = 8;
SimpleDHT11 dht11(pinDHT11);

byte tempg = 0;
byte humig = 0;

void setup() {
  Serial.begin(9600);

}

void loop() {
  int err = SimpleDHTErrSuccess;
  if ((err = dht11.read(&tempg, &humig, NULL)) != SimpleDHTErrSuccess) {
    Serial.print("Read DHT11 failed, err="); Serial.println(err); delay(1000);
    return;
  }
  Serial.println(tempg);
  Serial.println(humig);
  delay(10000);
}

s readBuf[] big enough to hold both temp and humidity values?

I set it to 4 bytes, what should be great for one int - for the second one I clear the array

Do you have a level shifter to keep the Arduino Tx from being 5v at the ESP32 Rx?

I don't. I read about it earlier , but there's output without it too.

I agree with @Idahowalker that your choice of pins for the Serial1 input from the Arduino is not correct.

changed

atoi is a c-string function and requires null terminated values.

I didin't use null terminated character in arduino code

looks like bytes..

try changing the buffer to ints or bytes..
and don't read it as a char.. so c could be int too..
look for c!=0 in place of \n

After doing this I got error: invalid conversion from 'int*' to 'int' [-fpermissive]

After changing rx(to 16) and tx(to 17) I don't see any outputs from arduino in serial monitor. I also found out, that in if (Serial1.available() > 0) { Serial1.available() is never greater than 0 (I put Serial.print in next line).

strange..
this compiles and works..

const byte numChars = 4;
int readBuf[numChars];
static byte ndx = 0;
bool haveAll = false;





void setup() {
  // put your setup code here, to run once:
Serial.begin(115200);
Serial.println("Ready");

}

void loop() {
  // put your main code here, to run repeatedly:

  if (Serial.available()>0)
  {
    int data = Serial.read();
    if (data>0 && data != 10)
    {
      readBuf[ndx]=data;
      ndx++;
      if (ndx>numChars)
      {
        haveAll = true;
        ndx = 0;//reset for nexr
          for (int i = 0; i < numChars; i++) Serial.println(readBuf[i]);
      } else haveAll = false;
    }


  }

}