#include <WiFi.h>
#include <ThingsBoard.h>
#include <Arduino_MQTT_Client.h>
#define WIFI_AP "Wokwi-GUEST"
#define WIFI_PASS ""
#define TB_SERVER "192.168.0.105"
#define TOKEN "foaivLKatjrnQJePCCcv"
constexpr uint16_t MAX_MESSAGE_SIZE = 256U;
WiFiClient espClient;
Arduino_MQTT_Client mqttClient(espClient);
ThingsBoard tb(mqttClient, MAX_MESSAGE_SIZE);
void connectToWiFi() {
Serial.println("Connecting to WiFi...");
int attempts = 0;
while (WiFi.status() != WL_CONNECTED && attempts < 20) {
WiFi.begin(WIFI_AP, WIFI_PASS, 6);
delay(500);
Serial.print(".");
attempts++;
}
if (WiFi.status() != WL_CONNECTED) {
Serial.println("\nFailed to connect to WiFi.");
} else {
Serial.println("\nConnected to WiFi");
}
}
void connectToThingsBoard() {
if (!tb.connected()) {
Serial.println("Connecting to ThingsBoard server");
if (!tb.connect(TB_SERVER, TOKEN)) {
Serial.println("Failed to connect to ThingsBoard");
} else {
Serial.println("Connected to ThingsBoard");
}
}
}
void sendDataToThingsBoard(int pH, int ozone, int CO2) {
String jsonData = "{\"pH\":" + String(pH) + ", \"Ozone\":" + String(ozone) + ", \"CO2\":" + String(CO2) + "}";
tb.sendTelemetryJson(jsonData.c_str());
Serial.println("Data sent");
}
// ####################pH pakaging and pins #################
#define SensorPin 33 // the pH meter Analog pin
unsigned long int avgValue; //Store the average value of the sensor feedback
float b;
int buf[10],temp;
// ############### MQ-131 pakages and pins #######################
#include <MQ131.h>
// ################## MQ-9 pakages and pins ####################################
#include <MQUnifiedsensor.h>
#define Board ("ESP-32")
#define Pin (35)
#define Type ("MQ-9")
#define Voltage_Resolution (3.3)
#define ADC_Bit_Resolution (12)
#define RatioMQ9CleanAir (9.6)
MQUnifiedsensor MQ9(Board, Voltage_Resolution, ADC_Bit_Resolution, Pin, Type);
// ############ pH sensor setup to be called in setup function##########
void pHsensorSetup(){
Serial.println("pH sensor is ready"); //pH sensor start
}
// #################### MQ-131 setup function ########################
void MQ_131_Ozone_Setup(){
// Init the sensor
// - Heater control on pin 2
// - Sensor analog read on pin A0
// - Model LOW_CONCENTRATION
// - Load resistance RL of 1MOhms (1000000 Ohms)
MQ131.begin(2,34, HIGH_CONCENTRATION, 1000000);
Serial.println("Calibration parameters");
Serial.print("R0 = ");
Serial.print(MQ131.getR0());
Serial.println(" Ohms");
Serial.print("Time to heat = ");
Serial.print(MQ131.getTimeToRead());
Serial.println(" s");
}
//#################### MQ-9 setup function #################################
void MQ_9_CO2_Setup(){
MQ9.setRegressionMethod(1);
MQ9.init();
//If the RL value is different from 10K please assign your RL value with the following method:MQ9.setRL(10);
Serial.print("MQ-9 Calibrating please wait.");
float calcR0 = 0;
for(int i = 1; i<=10; i ++){
MQ9.update();
calcR0 += MQ9.calibrate(RatioMQ9CleanAir);
Serial.print(".");
}
MQ9.setR0(calcR0/10);
Serial.println("MQ-131 Calibration is done!.");
if(isinf(calcR0)) {Serial.println("Warning: Conection issue, R0 is infinite (Open circuit detected) please check your wiring and supply"); while(1);}
if(calcR0 == 0){Serial.println("Warning: Conection issue found, R0 is zero (Analog pin shorts to ground) please check your wiring and supply"); while(1);}
}
// ####################### pH sensor read function ####################"
float pHread(){
for(int i=0;i<10;i++){
//Get 10 sample value from the sensor for smooth the value
buf[i]=analogRead(SensorPin);
delay(10);
}
for(int i=0;i<9;i++){
//sort the analog from small to large
for(int j=i+1;j<10;j++){
if(buf[i]>buf[j]){
temp=buf[i];
buf[i]=buf[j];
buf[j]=temp;
}
}
}
avgValue=0;
for(int i=2;i<8;i++) //take the average value of 6 center sample
avgValue+=buf[i];
float phValue=(float)avgValue*5.0/1024/6; //convert the analog into millivolt
phValue=3.5*phValue; //convert the millivolt into pH value
Serial.print("pH:");
Serial.print(phValue,2);
Serial.println(" ");
return phValue;
}
// ########################## MQ-131 Ozone reading function ##############################
float MQ_131_Ozone_Read(){
Serial.println("Sampling...");
MQ131.sample();
Serial.print("Concentration O3 : ");
Serial.print(MQ131.getO3(PPM));
Serial.println(" ppm");
delay(3000);
float OZ = 0.0;
OZ = MQ131.getO3(PPM);
return OZ;
}
// ########################## MQ-9 co2 read function #######################
float MQ_9_CO2_Read(){
MQ9.update();
MQ9.setA(599.65); MQ9.setB(-2.244);
float CO = MQ9.readSensor();
Serial.print("CO2 Concentration "); Serial.print(CO); Serial.print(" PPM");
delay(500); //Sampling frequency
return CO;
}
// ##################### setup() function ###############
void setup(){
Serial.begin(115200);
connectToWiFi();
connectToThingsBoard();
pHsensorSetup();
MQ_131_Ozone_Setup();
MQ_9_CO2_Setup();
}
// ##################### loop() function ###############
void loop() {
connectToWiFi();
float pH = pHread();
Serial.println();
float CO2 = MQ_9_CO2_Read();
Serial.println();
float Ozone = MQ_131_Ozone_Read();
Serial.println();
if (!tb.connected()) {
connectToThingsBoard();
}
sendDataToThingsBoard(pH, Ozone, CO2);
delay(3000);
tb.loop();
}