I am trying to send a command Serial3.print(“T,44/r”); to the PH circuit (Atlas scientific EZO), but nothing gets sent. After 2 days of debugging I found out it’s because I added Blynk to my project. So it looks like one of the Blynk libraries/functions is conflicting with the hardware serial print. Anyone had this issue before? and is there a way to fix it?
Here is my sketch. Sorry, I didn’t clean it up yet. Hope it’s readable. Everything is working fine except the Serial3.print(“T,44/r”); it doesn’t get sent to the pH circuit. While when i put it in a simple sketch, it does work.
#include<stdlib.h>
#include <ESP8266_Lib.h> //for Blynk
#include <BlynkSimpleShieldEsp8266.h>//for Blynk
#include <SimpleTimer.h>//for Blynk
#include <OneWire.h> //for temp sensor
#include <DallasTemperature.h> //for temp sensor
SimpleTimer timer; //simple timer for Blynk
#define ONE_WIRE_BUS 8 //pin 8 is for temp sensor
#define BLYNK_PRINT Serial
OneWire oneWire(ONE_WIRE_BUS); //for temp sensor
DallasTemperature sensors(&oneWire); //for temp sensor
//STARTwater flow sensor-------------------------------------------
// which pin to use for reading the sensor? can use any pin!
#define FLOWSENSORPIN 7
#define TONE_PIN 6 // buzzer output is pin 6
// count how many pulses!
volatile uint16_t pulses = 0;
// track the state of the pulse pin
volatile uint8_t lastflowpinstate;
// you can try to keep time of how long it is between pulses
volatile uint32_t lastflowratetimer = 0;
// and use that to calculate a flow rate
volatile float flowrate;
// Interrupt is called once a millisecond, looks for any pulses from the sensor!
SIGNAL(TIMER0_COMPA_vect) {
uint8_t x = digitalRead(FLOWSENSORPIN);
if (x == lastflowpinstate) {
lastflowratetimer++;
return; // nothing changed!
}
if (x == HIGH) {
//low to high transition!
pulses++;
}
lastflowpinstate = x;
flowrate = 1000.0;
flowrate /= lastflowratetimer; // in hertz
lastflowratetimer = 0;
}
void useInterrupt(boolean v) {
if (v) {
// Timer0 is already used for millis() - we'll just interrupt somewhere
// in the middle and call the "Compare A" function above
OCR0A = 0xAF;
TIMSK0 |= _BV(OCIE0A);
} else {
// do not call the interrupt function COMPA anymore
TIMSK0 &= ~_BV(OCIE0A);
}
}
//END water flow sensor--------------------------------------------------------------
float tempC;
int sumpfloatswitch = 0; //for wc
int selectedwateramount = 0; //for wc
int wcinp = 0; //for testing water change action
int waterChangeAmount = 0;
float liters = 0;
String enteredstring;
String wcamount;
String wccommandString;
char auth[] = "MyBlynkAuthCode";//Blynk auth code
#define EspSerial Serial1//for Blynk
// Your ESP8266 baud rate:
#define ESP8266_BAUD 9600
ESP8266 wifi(&EspSerial);//for Blynk
WidgetLCD lcd(V1); //define Blynk LCD
WidgetTerminal terminal(V5);
char ph_data[20];
byte ph_string_received = 0;
byte ph_received_from_sensor = 0;
String inputstring = ""; //a string to hold incoming data from the PC
String sensorstring = ""; //a string to hold the data from the Atlas Scientific product
boolean input_string_complete = false; //have we received all the data from the PC
boolean sensor_string_complete = false; //have we received all the data from the Atlas Scientific product
float pH; //used to hold a floating point number that is the pH
//++++++++++++++++++++++++++++++++++++++++++++++++++START SETUP++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
void setup()
{
Serial.begin(9600);
delay(10);
// Set ESP8266 baud rate
Serial1.begin(9600);
delay(10);
Serial3.begin(9600); //PH serial
inputstring.reserve(10); //PH - set aside some bytes for receiving data from the PC
sensorstring.reserve(30); //PH - set aside some bytes for receiving data from Atlas Scientific product
Blynk.begin(auth, wifi, "MYSSID", "MYPW");// for Blynk
sensors.begin();//Start Temperature sensor
pinMode(FLOWSENSORPIN, INPUT);
pinMode(3, INPUT); //sump high float switch
pinMode(9, OUTPUT); //res pump
pinMode(10, OUTPUT); // sump pump
digitalWrite(9, LOW);
digitalWrite(10, LOW);
digitalWrite(FLOWSENSORPIN, HIGH);
lastflowpinstate = digitalRead(FLOWSENSORPIN);
useInterrupt(true);
timer.setInterval(2000L, sendTempToGraphBlynk);
timer.setInterval(2500L, sendPHToGraphBlynk);
}
//++++++++++++++++++++++++++++++++++++++++++++++++++END SETUP++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
void serialEvent3() { //if the hardware serial port_3 receives a PH reading
sensorstring = Serial3.readStringUntil(13); //read the string until we see a <CR>
sensor_string_complete = true; //set the flag used to tell if we have received a completed string from the PH sensor
}
//++++++++++++++++++++++++++++++++++++++++++++++++++START VOID LOOP++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
void loop() {
Blynk.run(); // run Blynk process
timer.run(); // Initiates SimpleTimer
if (input_string_complete == true) {
Serial3.print(inputstring);
Serial3.print('\r');
inputstring = ""; input_string_complete = false;
}
}
//++++++++++++++++++++++++++++++++++++++++++++++++++END VOID LOOP++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
//@@@@@@@functions@@@@@@@@@@@functions@@@@@@@@@@@functions@@@@@@@@@@@functions@@@@@@@@functions@@@@@@@@@
//-------------START send temp Blynk------------//
void sendTempToGraphBlynk()
{
GetTemperature();
Serial.println(tempC);
char buffer[10]; //buffer for the temperature
String temperature = dtostrf(tempC, 4, 2, buffer); //convert the temperature to a string
Blynk.virtualWrite(2, tempC);
}
//-------------END send temp Blynk graph------------//
//-------------START send pH on Blynk graph------------//
void sendPHToGraphBlynk()
{
GetPH();
Serial.println(pH);
char pH_buffer[10]; //buffer for the ph
String pHstring = dtostrf(pH, 3, 2, pH_buffer); //convert the pH to a string
Blynk.virtualWrite(3, 8.2);
}
//-------------END send pH on Blynk graph------------//
//-------------Start Get Temperature Function------------//
void GetTemperature()
{
sensors.requestTemperatures(); // Send the command to get temperatures
tempC = sensors.getTempCByIndex(0);
}
//-------------End Get Temperature Function------------//
//----------START---------Receive command from Blynk terminal and excute accordingly----------------------------------
BLYNK_WRITE(V5)
{
enteredstring = param.asStr();
wcamount = enteredstring.substring(13);
wccommandString = enteredstring.substring(0, 12);
waterChangeAmount = wcamount.toInt();
terminal.println(wcamount);
terminal.println(wccommandString);
if (String("water change") == wccommandString) {
wcinp = 1;
changeWater(waterChangeAmount);
}
else if (String("hi") == param.asStr())
{
terminal.print("Hi Haidar enter a command please");
}
else if (String("hi") == param.asStr())
{
terminal.print("Hi, enter a command please");
}
else if (String("help") == param.asStr())
{
terminal.println("You can enter the following commands:");
terminal.println("- water change #");
}
else if (String("ph temp") == param.asStr())
{
Serial3.print("T,44/r");
while (sensor_string_complete == true) { //if a string from the Atlas Scientific product has been received in its entirety
//Serial.println(sensorstring); //send that string to the PC's serial monitor
terminal.println(sensorstring);
sensorstring = ""; //clear the string:
sensor_string_complete = false;
}
terminal.println("Received");
}
else {
// Send it back
terminal.write(param.getBuffer(), param.getLength());
terminal.print(" is unknown command");
terminal.println();
}
// Ensure everything is sent
terminal.flush();
}
//----------END---------Receive command from Blynk terminal and excute accordingly----------------------------------
//
//-----------------Start get PH function-----------------//
void GetPH() {
if (sensor_string_complete == true) { //if a string from the Atlas Scientific product has been received in its entirety
//Serial.println(sensorstring); //send that string to the PC's serial monitor
if (isdigit(sensorstring[0])) { //if the first character in the string is a digit
pH = sensorstring.toFloat(); //convert the string to a floating point number so it can be evaluated by the Arduino
}
}
sensorstring = ""; //clear the string:
sensor_string_complete = false; //reset the flag used to tell if we have received a completed string from the Atlas Scientific product
}
//-----------------End get PH function-----------------//
//
//------START Water change function---------------------
void changeWater (int selectedwateramount)
{
terminal.println(selectedwateramount);
pulses = 0; //added code witout testing
liters = 0; //added code witout testing
if (selectedwateramount > 0) {
terminal.print("System will change ") ;
terminal.print(waterChangeAmount);
terminal.println(" liters") ;
tone(2, 3000, 3000);
terminal.println("Water started...") ;
while (liters < selectedwateramount) {
Blynk.run(); // run Blynk process
liters = pulses; //flow sensor
liters /= 7.5; //flow sensor
liters /= 60.0; //flow sensor
//Serial.print(liters); Serial.println(" Liters");
terminal.println("Draining water");
terminal.print(liters);
terminal.print(" ltr ");
//lcd.setCursor(9, 1);
terminal.print(liters / selectedwateramount * 100);
terminal.println("%");
//switch on sump pump
digitalWrite(9, LOW);
digitalWrite(10, HIGH);
delay(500);
}
sumpfloatswitch = digitalRead(3); //added code witout testing
while (liters >= selectedwateramount && sumpfloatswitch == LOW) {
Blynk.run(); // run Blynk process
sumpfloatswitch = digitalRead(3);
terminal.println("* Adding water *");
//switch on res pump
digitalWrite(9, HIGH);
digitalWrite(10, LOW);
//blinking adding water text
delay(500);
}
if (sumpfloatswitch == HIGH) {
//delay(2000); to eliminate sensor sensitivity should be added later somehow
Blynk.run(); // run Blynk process
terminal.println("Water change completed");
tone(2, 1000, 10000);
pulses = 0;
liters = 0;
selectedwateramount = 0;
digitalWrite(9, LOW);
digitalWrite(10, LOW);
}
}
else {
terminal.println("Please enter a valid amount");
}
}
//------END Water change function---------------------
The library does not try to refer to Serial objects, except those you point to… like BLYNK_PRINT.
Maybe, your shields use the same pins, or some other reason.
Also, you can check the source and try figuring out the reason.
Thanks vhymanskyy. My pH circuit is connected to TX/RX3 while my wifi module (ESP8266) is connected to TX/RX1. So i don’t this there is an issue with the pins. I also changed the pH circuit to serial 2, but this didn’t fix the issue.
I resolved the issue by using \r instead of /r which was a typo by the the Atlas technical service team. I have tried that many times but it didn’t work. After 2 days of debugging, I found out I had to add a delay of 100 ms before the Blynk run. I know its not recommended to use delays, but this was the only way to get it to work.
I am now using the terminal to send commands, so a big thank to the Blynk team for the great work that has been put in development as well as support.