Trying to operate relay based off 2 Virtual pins and RFID

The problem I’ve come across is that I can seem to only either be reading the RFID values, or the virtual pins, however my intention is to have both together in my if ( pinValue0 == 1 && pinValue4 ==1 && RFIDflag == 1) or something along those lines.

#include <MFRC522.h>
#define BLYNK_PRINT Serial
#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>

char auth[] = "g-zo8C8skr7RglPQneF7IlGRWVKscg2w";
char ssid[] = "75fennellwest";
char pass[] = "fennellhouse75";
int relay = 5;
int pinValue0=0;
int pinValue1=0;
int pinValue2=0;
int pinValue3=0;
int pinValue4=0;
const  int buttonPin = D2; // variable for D2 pin

constexpr uint8_t RST_PIN = 5;     // Configurable, see typical pin layout above
constexpr uint8_t SS_PIN = 4;     // Configurable, see typical pin layout above
 
MFRC522 rfid(SS_PIN, RST_PIN); // Instance of the class
 
MFRC522::MIFARE_Key key; 
 
// Init array that will store new NUID 
byte nuidPICC[4];

BLYNK_WRITE(V0)
{
   pinValue0 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $5 gas: ");
  Serial.println(pinValue0);
  delay(1000);
}


BLYNK_WRITE(V1)
{
   pinValue1 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $10 gas: ");
  Serial.println(pinValue1);
}

BLYNK_WRITE(V2)
{
   pinValue2 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $20 gas: ");
  Serial.println(pinValue2);
}


BLYNK_WRITE(V3)
{
   pinValue3 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $50 gas: ");
  Serial.println(pinValue3);
}

BLYNK_WRITE(V4)
{
   pinValue4 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Confirm Purchase: ");
  Serial.println(pinValue4);
}
 
void setup() { 
  Serial.begin(9600);
  Blynk.begin(auth, ssid, pass);
  SPI.begin(); // Init SPI bus
  rfid.PCD_Init(); // Init MFRC522 
  pinMode(relay, OUTPUT);
  pinMode (buttonPin, INPUT);  // Initialization of the variable "buttonPin" as INPUT (D2 pin)
  digitalWrite (buttonPin, HIGH);

   /*
  for (byte i = 0; i < 6; i++) {
    key.keyByte[i] = 0xFF;
  }
 
  Serial.println(F("This code scan the MIFARE Classsic NUID."));
  Serial.print(F("Using the following key:"));
  printHex(key.keyByte, MFRC522::MF_KEY_SIZE);
*/
  
}
void loop() {

   Blynk.run();
 
  // Look for new cards
  if ( ! rfid.PICC_IsNewCardPresent())
    return;
 
  // Verify if the NUID has been readed
  if ( ! rfid.PICC_ReadCardSerial())
    return;
 
  Serial.print(F("PICC type: "));
  MFRC522::PICC_Type piccType = rfid.PICC_GetType(rfid.uid.sak);
  Serial.println(rfid.PICC_GetTypeName(piccType));
 
  // Check is the PICC of Classic MIFARE type
  if (piccType != MFRC522::PICC_TYPE_MIFARE_MINI &&  
    piccType != MFRC522::PICC_TYPE_MIFARE_1K &&
    piccType != MFRC522::PICC_TYPE_MIFARE_4K) {
    Serial.println(F("Your tag is not of type MIFARE Classic."));
    return;
  }
 
  if (rfid.uid.uidByte[0] != nuidPICC[0] || 
    rfid.uid.uidByte[1] != nuidPICC[1] || 
    rfid.uid.uidByte[2] != nuidPICC[2] || 
    rfid.uid.uidByte[3] != nuidPICC[3] ) {
    Serial.println(F("A new card has been detected."));
 
    // Store NUID into nuidPICC array
    for (byte i = 0; i < 4; i++) {
      nuidPICC[i] = rfid.uid.uidByte[i];
    }
   
    Serial.println(F("The NUID tag is:"));
    Serial.print(F("In hex: "));
    printHex(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
    Serial.print(F("In dec: "));
    printDec(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
  }
  else Serial.println(F("Card read previously."));
 
  // Halt PICC
  rfid.PICC_HaltA();
 
  // Stop encryption on PCD
  rfid.PCD_StopCrypto1();

if ( pinValue0 == 1 && pinValue4 == 1)
{
  pinValue0 = 1;
  pinValue4 = 1;
  digitalWrite(relay, HIGH); 
  delay(1000);
  digitalWrite(relay, LOW); 
  Serial.println("Dispense $5 worth of gas");
  delay(1000);
  }
 else {
 digitalWrite(relay, LOW);
 }



if ( pinValue1 == 1 && pinValue4 == 1)
{
  digitalWrite(relay, HIGH);
    delay(1000);
  digitalWrite(relay, LOW); 
  Serial.println("Dispense $10 worth of gas");
   delay(1000);
}
 else {
 digitalWrite(relay, LOW);
 }



if ( pinValue2 == 1 && pinValue4 == 1)
{
  digitalWrite(relay, HIGH);
    delay(1000);
  digitalWrite(relay, LOW); 
  Serial.println("Dispense $20 worth of gas");
   delay(1000);
}
 else {
 digitalWrite(relay, LOW);
 }

 
if ( pinValue3 == 1 && pinValue4 == 1) 
{
  digitalWrite(relay, HIGH);
    delay(1000);
  digitalWrite(relay, LOW); 
  Serial.println("Dispense $50 worth of gas");
   delay(1000);
}
 else {
 digitalWrite(relay, LOW);
 }
  
}
 
 
/**
 * Helper routine to dump a byte array as hex values to Serial. 
 */
void printHex(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], HEX);
  }
}
 
/**
 * Helper routine to dump a byte array as dec values to Serial.
 */
void printDec(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], DEC);
  }
}```

Edit: I am using the RFID RC522 and the NodeMCU

@Adam_Baker is this project going to be part of a commercial applications?

Pete.

by no means so, just a project i’m putting together.

I re-formatted my code a little, but i’m no longer able to serial print

#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>
char auth[] = "YourAuthToken";
char ssid[] = "YourNetworkName";
char pass[] = "YourPassword";
BlynkTimer timer;

//RFID
#include <SPI.h>
#include <MFRC522.h>
constexpr uint8_t RST_PIN = 5;     // Configurable, see typical pin layout above
constexpr uint8_t SS_PIN = 4;     // Configurable, see typical pin layout above
MFRC522 rfid(SS_PIN, RST_PIN); // Instance of the class
MFRC522::MIFARE_Key key; 
byte nuidPICC[4];

//Project Code
int pinValue0;
int pinValue1;
int pinValue2;
int pinValue3;
int pinValue4;
int flag;

void setup()
{
  Serial.begin(9600);
  Blynk.begin(auth, ssid, pass);
  timer.setInterval(1000L, checkRFID);
  timer.setInterval(1000L, blynkREAD);
  timer.setInterval(1000L, relay);

//RFID
  SPI.begin(); // Init SPI bus
  rfid.PCD_Init(); // Init MFRC522 
    for (byte i = 0; i < 6; i++) {
    key.keyByte[i] = 0xFF;
  }
 
  Serial.println(F("This code scan the MIFARE Classsic NUID."));
  Serial.print(F("Using the following key:"));
  printHex(key.keyByte, MFRC522::MF_KEY_SIZE);
}

void loop()
{
  Blynk.run();
  timer.run();
}

void checkRFID()
{
    if ( ! rfid.PICC_IsNewCardPresent())
    return;
 
  // Verify if the NUID has been readed
  if ( ! rfid.PICC_ReadCardSerial())
    return;
 
  Serial.print(F("PICC type: "));
  MFRC522::PICC_Type piccType = rfid.PICC_GetType(rfid.uid.sak);
  Serial.println(rfid.PICC_GetTypeName(piccType));
 
  // Check is the PICC of Classic MIFARE type
  if (piccType != MFRC522::PICC_TYPE_MIFARE_MINI &&  
    piccType != MFRC522::PICC_TYPE_MIFARE_1K &&
    piccType != MFRC522::PICC_TYPE_MIFARE_4K) {
    Serial.println(F("Your tag is not of type MIFARE Classic."));
    return;
  }
 
  if (rfid.uid.uidByte[0] != nuidPICC[0] || 
    rfid.uid.uidByte[1] != nuidPICC[1] || 
    rfid.uid.uidByte[2] != nuidPICC[2] || 
    rfid.uid.uidByte[3] != nuidPICC[3] ) {
    Serial.println(F("A new card has been detected."));
 
    // Store NUID into nuidPICC array
    for (byte i = 0; i < 4; i++) {
      nuidPICC[i] = rfid.uid.uidByte[i];
    }
   
    Serial.println(F("The NUID tag is:"));
    Serial.print(F("In hex: "));
    printHex(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
    Serial.print(F("In dec: "));
    printDec(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
  }
  else Serial.println(F("Card read previously."));
 
  // Halt PICC
  rfid.PICC_HaltA();
 
  // Stop encryption on PCD
  rfid.PCD_StopCrypto1();
}

void blynkREAD()
{

}

void relay(){
 if (pinValue0 == 1 && pinValue1 ==4 && flag ==1){  
  
 }
 else if ( pinValue1 == 1 && pinValue4 == 1 && flag == 1){
  
 }
 else if ( pinValue2 == 1 && pinValue4 == 1 && flag == 1){
  
 } 
 else if ( pinValue3 == 1 && pinValue4 == 1 && flag == 1){
  
 } 
 
}

void printHex(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], HEX);
  }
}
 
/**
 * Helper routine to dump a byte array as dec values to Serial.
 */
void printDec(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], DEC);
  }
}```

Okay, I’ll take your word for that. The reason I asked is that your code talks about “customers” and pumping certain dollar values of gas. This implies to me that you’re trying to develop something for a commercial for business situation, which is illegal under the terms of the free version of Blynk that you’re using.
I can almost guarantee that if you do use this for business or commercial activity then that will be detected by the Blynk team and your account will be deleted without warning.

You have a number of topics on the forum recently, which all appear to be about the same project. Please don’t create any new topics about this project - it will get very difficult for you to make sense of advice given in different topics, and it will quickly frustrate forum members when they realise that the information they require to get the full picture of the project is spread across multiple locations.

Do you mean that you are getting no serial monitor output at all, or you get no serial information when an RFID tag is scanned?

I think you’re taking the wrong approach with your void relay() function, although its difficult to be certain, as the thing that’s missing from all of your posts on this project is an overview of what the project is meant to do, and what the purpose of the RFID, physical button, Blynk widget buttons, relay etc are and how you intend for them to interact together.
Based on your code, I think your ‘void relay()’ function should be called when something happens such as a physical button being pressed, an RFID tag is scanned, or a Blynk widget button changes state - rather than being called once per second, every second.

You’ve obviously taken out the actions that are to be performed if your various ‘if’ statements within the void relay() function evaluate to true, but I think your structure of these if logic tests is flawed.
Every if test contains && flag == 1) so for me, this should be your first test:

void relay()
{
  if (flag ==1)
  {
    // do the other if tests in here....
  } 
}

Pete.

Just would like to clarify again that this has nothing to do with real money and is only for a presentation. I have actually re formatted my code but I appreciate your help.

#include <SPI.h>
#include <MFRC522.h>
constexpr uint8_t RST_PIN = 5;     // Configurable, see typical pin layout above
constexpr uint8_t SS_PIN = 4;     // Configurable, see typical pin layout above
MFRC522 rfid(SS_PIN, RST_PIN); // Instance of the class
MFRC522::MIFARE_Key key; 
byte nuidPICC[4];

//Project Code
int pinValue0;
int pinValue1;
int pinValue2;
int pinValue3;
int pinValue4;
int flag;
int relay1;

//Blynk
#define BLYNK_PRINT Serial
#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>
char auth[] = "g-zo8C8skr7RglPQneF7IlGRWVKscg2w";
char ssid[] = "75fennellwest";
char pass[] = "fennellhouse75";
BlynkTimer timer;
WidgetLCD lcd(V5);

BLYNK_WRITE(V0){
   pinValue0 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $5 gas: ");
  Serial.println(pinValue0);
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Are you sure"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "you want $5 Gas?");
  delay(1000);
}
BLYNK_WRITE(V1){
   pinValue1 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $10 gas: ");
  Serial.println(pinValue1);
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Are you sure"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "you want $10 Gas?");
}
BLYNK_WRITE(V2){
   pinValue2 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $20 gas: ");
  Serial.println(pinValue2);
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Are you sure"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "you want $20 Gas?");
}
BLYNK_WRITE(V3){
   pinValue3 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Customer requests $50 gas: ");
  Serial.println(pinValue3);
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Are you sure"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "you want $50 Gas?");
}
BLYNK_WRITE(V4){
   pinValue4 = param.asInt(); // assigning incoming value from pin V1 to a variable
  Serial.print("Confirm Purchase: ");
  Serial.println(pinValue4);
}




void setup()
{
  Serial.begin(9600);
  Blynk.begin(auth, ssid, pass);
  timer.setInterval(1000L, checkRFID);
  timer.setInterval(1000L, relay);
  timer.setInterval(1000L, sendLCD);
  pinMode(D0, OUTPUT);

//Flow Rate
  

//RFID
  SPI.begin(); // Init SPI bus
  rfid.PCD_Init(); // Init MFRC522 
    for (byte i = 0; i < 6; i++) {
    key.keyByte[i] = 0xFF;
  }
 
  Serial.println(F("This code scan the MIFARE Classsic NUID."));
  Serial.print(F("Using the following key:"));
  printHex(key.keyByte, MFRC522::MF_KEY_SIZE);
}

void loop()
{
  Blynk.run();
  timer.run();
}

void checkRFID()
{
    if ( ! rfid.PICC_IsNewCardPresent())
    return;
 
  // Verify if the NUID has been readed
  if ( ! rfid.PICC_ReadCardSerial())
    return;
 
  Serial.print(F("PICC type: "));
  MFRC522::PICC_Type piccType = rfid.PICC_GetType(rfid.uid.sak);
  Serial.println(rfid.PICC_GetTypeName(piccType));
 
  // Check is the PICC of Classic MIFARE type
  if (piccType != MFRC522::PICC_TYPE_MIFARE_MINI &&  
    piccType != MFRC522::PICC_TYPE_MIFARE_1K &&
    piccType != MFRC522::PICC_TYPE_MIFARE_4K) {
    Serial.println(F("Your tag is not of type MIFARE Classic."));
    return;
  }
 
  if (rfid.uid.uidByte[0] != nuidPICC[0] || 
    rfid.uid.uidByte[1] != nuidPICC[1] || 
    rfid.uid.uidByte[2] != nuidPICC[2] || 
    rfid.uid.uidByte[3] != nuidPICC[3] ) {
    Serial.println(F("A new card has been detected."));
 
    // Store NUID into nuidPICC array
    for (byte i = 0; i < 4; i++) {
      nuidPICC[i] = rfid.uid.uidByte[i];
    }
   
    Serial.println(F("The NUID tag is:"));
    Serial.print(F("In hex: "));
    printHex(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
    Serial.print(F("In dec: "));
    printDec(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
    flag = 1;
    Serial.println("Flag 1");

  }
  else Serial.println(F("Card read previously."));
 
  // Halt PICC
  rfid.PICC_HaltA();
 
  // Stop encryption on PCD
  rfid.PCD_StopCrypto1();
}


void relay(){
 if (pinValue0 == 1 && pinValue4 ==1 && flag ==1)
 {  
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(4, 0, "Ya fuckin"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(4, 1, "Diditbud");
  digitalWrite(D0, HIGH); 
  delay(5000);
  digitalWrite(D0, LOW); 
  Serial.println("Dispense $5 worth of gas");
  flag = 0;
  Serial.println("flag = 0");
    lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "There she"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "Blows now leave");

 }
 else if ( pinValue1 == 1 && pinValue4 == 1 && flag == 1)
 {
    digitalWrite(D0, HIGH); 
  delay(7500);
  digitalWrite(D0, LOW); 
  Serial.println("Dispense $10 worth of gas");
  flag = 0;
 }
 else if ( pinValue2 == 1 && pinValue4 == 1 && flag == 1)
 {
    digitalWrite(D0, HIGH); 
  delay(10000);
  digitalWrite(D0, LOW); 
  Serial.println("Dispense $20 worth of gas");
  flag = 0;
 } 
 else if ( pinValue3 == 1 && pinValue4 == 1 && flag == 1)
 {
   digitalWrite(D0, HIGH); 
  delay(12000);
  digitalWrite(D0, LOW); 
  Serial.println("Dispense $50 worth of gas");
  flag = 0; 
 } 
 
}

void sendLCD()
{
   if (pinValue0 == 1 && pinValue4 ==1)
 {  
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Please park car"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "on marked location");
 }
 else if ( pinValue1 == 1 && pinValue4 == 1)
 {
    lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Please park car"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "on marked location");
 }
 else if ( pinValue2 == 1 && pinValue4 == 1)
 {
    lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Please park car"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "on marked location");
 }
 else if ( pinValue3 == 1 && pinValue4 == 1)
 {
    lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(0, 0, "Please park car"); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(0, 1, "on marked location");
 }
}

void printHex(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], HEX);
  }
}
 
/**
 * Helper routine to dump a byte array as dec values to Serial.
 */
void printDec(byte *buffer, byte bufferSize) {
  for (byte i = 0; i < bufferSize; i++) {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], DEC);
  }

void flow(){
  count = 0;
  interrupts();
  delay (1000);
  noInterrupts();

  flowRate = (count * 2.25);
  flowRate = flowRate * 60;
  flowRate = flowRate /1000;

  Serial.println(flowRate);
  Serial.print("L/min");
  Blynk.virtualWrite(V1, flowRate);
}
void Flow()

{
  count++;
}

}```

@Adam_Baker I’ve now locked the other two topics about this same project, and signposted community users to this one. Before locking the “Looking for assistance…” topic I explained why you are getting the "ISR not in IRAM message in your serial monitor, and how to fix that and the subsequent compiler message that you will then get.

As I think you can see, you aren’t making it easy for us!

I asked:

which you didn’t answer, but you did say:

I took that to mean that you had resolved your issues, but based on the serial output and details of the “ISR not in IRAM” issue you posted in the other topic, that’s not the case.

If you want us to help then I’d suggest you do the following…

  • Keep everything in this topic
  • When someone asks you a direct question then answer it
  • If you’ve made changes to your code buat are still having issues then explain what those changes are, what results you are seeing (or not seeing) and and post andy corresopinding serial monitor output
  • Tell us what the project is about, and how it’s supposed to work!

So far, it’s clear that there is an RFID reader, some widgets attached to pins V0-V4 (switches presumably?) for selecting a quantity, an LCD widget on V5, a flow sensor and maybe a physical switch attached somewhere?
What we don’t know is how the system is meant to function, what scenarios are acceptable or not, and not, and who operates the various bits of the process. Unless you tell us what the big picture use case is then we will struggle to see any flaws in your logic.
I’m not asking you this in an attempt to trick you into revealing that this is a commercial project - you’ve already said it isn’t, but unless we can see the big picture it’s very difficult to help.

Pete.

As @PeteKnight said, it’s frustrating for any forum member to help as nobody can have patience and time to get the full picture of your project spreading across seemingly unrelated topics.

Anyway, we all can see you have lot of patience in getting help, by trying your best in researching and modifying the code yourself.

So this is just a little bit of help. The most critical issues are

  1. The incorrect use of ISR (“ISR not in IRAM”)
  2. The use of delay() in wrong place to control the relay
  3. Many other problems as well

Here is the preliminary fix, based on your code. Hope you study it and improve.

#ifndef ESP8266
#error This code is intended to run on the ESP8266 platform! Please check your Tools->Board setting.
#endif

#define BLYNK_PRINT Serial

#define USE_BLYNK_WM      true

// Not use #define USE_SPIFFS  => using EEPROM for configuration data in WiFiManager
// #define USE_SPIFFS    false => using EEPROM for configuration data in WiFiManager
// #define USE_SPIFFS    true  => using SPIFFS for configuration data in WiFiManager
// Be sure to define USE_SPIFFS before #include <BlynkSimpleEsp8266_WM.h>

#define USE_SPIFFS                  false //true

#if (!USE_SPIFFS)
// EEPROM_SIZE must be <= 4096 and >= CONFIG_DATA_SIZE (currently 172 bytes)
#define EEPROM_SIZE    (4 * 1024)
// EEPROM_START + CONFIG_DATA_SIZE must be <= EEPROM_SIZE
#define EEPROM_START  0
#endif

// Force some params in Blynk, only valid for library version 1.0.1 and later
#define TIMEOUT_RECONNECT_WIFI                    10000L
#define RESET_IF_CONFIG_TIMEOUT                   true
#define CONFIG_TIMEOUT_RETRYTIMES_BEFORE_RESET    5
// Those above #define's must be placed before #include <BlynkSimpleEsp8266_WM.h>

#define USE_SSL   false

#if USE_BLYNK_WM
#if USE_SSL
#include <BlynkSimpleEsp8266_SSL_WM.h>        //https://github.com/khoih-prog/Blynk_WM
#else
#include <BlynkSimpleEsp8266_WM.h>            //https://github.com/khoih-prog/Blynk_WM
#endif
#else
#if USE_SSL
#include <BlynkSimpleEsp8266_SSL.h>
#else
#include <BlynkSimpleEsp8266.h>
#endif
char auth[] = "*";
char ssid[] = "*";
char pass[] = "*";
#endif

#include <SPI.h>
#include <MFRC522.h>

#define RST_PIN       5     // Configurable, see typical pin layout above
#define SS_PIN        4     // Configurable, see typical pin layout above

MFRC522 rfid(SS_PIN, RST_PIN); // Instance of the class
MFRC522::MIFARE_Key key;

byte nuidPICC[4];

//Project Code
bool pinValue5;
bool pinValue10;
bool pinValue20;
bool pinValue50;
bool pinValueConfirm;

bool flag;

//Flow Rate
int limitType, tap_limit_value, timer1, timer2, timer3, rowIndex = 0, month_old;
volatile uint32_t pulseCount = 0;

float flowRate = 0.00, waterCost, waterCost_month;
float flowLitres;
float totalLitres, totalLitres_month;

#define vPIN_VALUE_5              V0
#define vPIN_VALUE_10             V1
#define vPIN_VALUE_20             V2
#define vPIN_VALUE_50             V3
#define vPIN_CONFIRM              V4
#define vPIN_LVD                  V5

#define vPIN_TAP_LED              V7
#define vPIN_TAP_LIMIT            V14
#define vPIN_TAP_MANUAL           V18
#define vPIN_TAP_ACTIVATE         V19
#define vPIN_WATER_TOTAL          V25
#define vPIN_WATER_TOTAL_MONTH    V21
#define vPIN_WATER_FLOW           V26
#define vPIN_WATER_COST           V28
#define vPIN_WATER_COST_MONTH     V11
#define vPIN_WATER_TAP            V27
#define vPIN_TERMINAL             V31
#define vPIN_LIMITMENU            V9
#define vPIN_LAST_MONTH           V10

#define FLOW_SENSOR               D3  // D2
#define FLOW_CALIBRATION          4.5
#define WATER_PRICE               0.1444

bool relayActive      = false;
bool parkCarDisplayed = false;

BlynkTimer timer;
WidgetLCD lcd(vPIN_LVD);

// Use true to bypass RFID validation
#define TESTING_WITHOUT_RFID      true

void displayLCD(uint8_t X1, uint8_t Y1, String msg1, uint8_t X2, uint8_t Y2, String msg2)
{
  parkCarDisplayed = false;
  lcd.clear(); //Use it to clear the LCD Widget
  lcd.print(X1, Y1, msg1); // use: (position X: 0-15, position Y: 0-1, "Message you want to print")
  lcd.print(X2, Y2, msg2);
}

BLYNK_CONNECTED()
{
  displayLCD(0, 0, "Welcome to", 0, 1, "Bakers got Gas");
}

BLYNK_WRITE(vPIN_VALUE_5)
{
  if ( param.asInt() )
  {
    pinValue10 = pinValue20 = pinValue50 = pinValueConfirm = false;
    pinValue5 = true;
  }

  if (pinValue5 && !param.asInt())
  {
    Serial.println("Customer requests $5 gas");
    displayLCD(0, 0, "5? Please park", 0, 1, "at pump. Confirm");
  }
}

BLYNK_WRITE(vPIN_VALUE_10)
{
  if ( param.asInt() )
  {
    pinValue5 = pinValue20 = pinValue50 = pinValueConfirm = false;
    pinValue10 = true;
  }

  if (pinValue10 && !param.asInt())
  {
    Serial.println("Customer requests $10 gas");
    displayLCD(0, 0, "10? Please park", 0, 1, "at pump. Confirm");
  }
}

BLYNK_WRITE(vPIN_VALUE_20)
{
  if ( param.asInt() )
  {
    pinValue5 = pinValue10 = pinValue50 = pinValueConfirm = false;
    pinValue20 = true;
  }

  if (pinValue20 && !param.asInt())
  {
    Serial.println("Customer requests $20 gas");
    displayLCD(0, 0, "20? Please park", 0, 1, "at pump. Confirm");
  }
}

BLYNK_WRITE(vPIN_VALUE_50)
{
  if ( param.asInt() )
  {
    pinValue5 = pinValue10 = pinValue20 = pinValueConfirm = false;
    pinValue50 = true;
  }

  if (pinValue50 && !param.asInt())
  {
    Serial.println("Customer requests $50 gas");
    displayLCD(0, 0, "50? Please park", 0, 1, "at pump. Confirm");
  }
}

BLYNK_WRITE(vPIN_CONFIRM)
{
  if ( param.asInt() && (pinValue5 || pinValue10 || pinValue20 || pinValue50) )
    pinValueConfirm = true;

  if (pinValueConfirm && !param.asInt())
  {
    Serial.println("Purchase Confirmed");
  }
}

void checkRFID()
{
  if ( ! rfid.PICC_IsNewCardPresent())
    return;

  Serial.println();
  flag = true;
  Serial.println("Flag OK");

  // Verify if the NUID has been readed
  if ( ! rfid.PICC_ReadCardSerial())
    return;

  Serial.print(F("PICC type: "));
  MFRC522::PICC_Type piccType = rfid.PICC_GetType(rfid.uid.sak);
  Serial.println(rfid.PICC_GetTypeName(piccType));

  // Check is the PICC of Classic MIFARE type
  if (piccType != MFRC522::PICC_TYPE_MIFARE_MINI &&
      piccType != MFRC522::PICC_TYPE_MIFARE_1K &&
      piccType != MFRC522::PICC_TYPE_MIFARE_4K)
  {
    Serial.println(F("Your tag is not of type MIFARE Classic."));
    return;
  }

  if (rfid.uid.uidByte[0] != nuidPICC[0] ||
      rfid.uid.uidByte[1] != nuidPICC[1] ||
      rfid.uid.uidByte[2] != nuidPICC[2] ||
      rfid.uid.uidByte[3] != nuidPICC[3] )
  {
    Serial.println(F("A new card has been detected."));

    // Store NUID into nuidPICC array
    for (byte i = 0; i < 4; i++)
    {
      nuidPICC[i] = rfid.uid.uidByte[i];
    }

    Serial.println(F("The NUID tag is:"));
    Serial.print(F("In hex: "));
    printHex(rfid.uid.uidByte, rfid.uid.size);
    Serial.println();
    Serial.print(F("In dec: "));
    printDec(rfid.uid.uidByte, rfid.uid.size);
  }
  else Serial.println(F("Card read previously."));

  // Halt PICC
  rfid.PICC_HaltA();

  // Stop encryption on PCD
  rfid.PCD_StopCrypto1();
}

void clickRelay(int relayPin, uint32_t timeout)
{
  static int pinRelay = relayPin;

  digitalWrite(pinRelay, HIGH);

  timer.setTimeout(timeout, []()
  {
    digitalWrite(pinRelay, LOW);
    relayActive = false;
    Serial.println("Stop pumping gas");
    displayLCD(0, 0, "Welcome to", 0, 1, "Bakers got Gas");
  });
}

void pumpControl()
{
  if (!relayActive )
  {
#if TESTING_WITHOUT_RFID
    flag = true;
#endif

    if (flag && pinValue5 && pinValueConfirm)
    {
      pinValue5 = pinValueConfirm = false;
      relayActive = true;
      clickRelay(D0, 5000);

      flag = false;
      displayLCD(0, 0, "Dispense $5", 0, 1, "worth of gas");
      Serial.println("Dispense $5 worth of gas");
    }
    else if (flag && pinValue10 && pinValueConfirm)
    {
      pinValue10 = pinValueConfirm = false;

      relayActive = true;
      clickRelay(D0, 7500);

      flag = false;
      displayLCD(0, 0, "Dispense $10", 0, 1, "worth of gas");
      Serial.println("Dispense $10 worth of gas");
    }
    else if (flag && pinValue20 && pinValueConfirm)
    {
      pinValue20 = pinValueConfirm = false;

      relayActive = true;
      clickRelay(D0, 10000);

      flag = false;
      displayLCD(0, 0, "Dispense $20", 0, 1, "worth of gas");
      Serial.println("Dispense $20 worth of gas");
    }
    else if (flag && pinValue50 && pinValueConfirm)
    {
      pinValue50 = pinValueConfirm = false;

      relayActive = true;
      clickRelay(D0, 12000);

      flag = false;
      displayLCD(0, 0, "Dispense $50", 0, 1, "worth of gas");
      Serial.println("Dispense $50 worth of gas");
    }
    else if ( !parkCarDisplayed && pinValueConfirm && (pinValue5 || pinValue10 || pinValue20 || pinValue50 ) )
    {
      displayLCD(0, 0, "Park car on", 0, 1, "marked location");
      parkCarDisplayed = true;
    }
  }
}

void printHex(byte *buffer, byte bufferSize)
{
  for (byte i = 0; i < bufferSize; i++)
  {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], HEX);
  }
}

/**
   Helper routine to dump a byte array as dec values to Serial.
*/
void printDec(byte *buffer, byte bufferSize)
{
  for (byte i = 0; i < bufferSize; i++)
  {
    Serial.print(buffer[i] < 0x10 ? " 0" : " ");
    Serial.print(buffer[i], DEC);
  }
}

void ICACHE_RAM_ATTR pulseCounter()
{
  pulseCount++;
}

void flowSensor()
{
  noInterrupts();
  flowRate = pulseCount / FLOW_CALIBRATION;
  pulseCount = 0;
  interrupts();

  //calc totals
  flowLitres = (flowRate / 60);
  totalLitres += flowLitres;
  totalLitres_month += flowLitres;

  Blynk.virtualWrite(vPIN_WATER_TOTAL, (float) totalLitres);
  Blynk.virtualWrite(vPIN_WATER_FLOW,  String((float) flowLitres, 0));
  Blynk.virtualWrite(vPIN_WATER_TOTAL_MONTH, (float) totalLitres_month);

  waterCost = waterCost + ( ( ( (float) flowLitres ) * WATER_PRICE ) / 100);
  Blynk.virtualWrite(vPIN_WATER_COST, String(waterCost, 6));

  waterCost_month = waterCost_month + ( ( ( (float) flowLitres ) * WATER_PRICE ) / 100);
  Blynk.virtualWrite(vPIN_WATER_COST_MONTH, String(waterCost_month, 6));
}

void setup()
{
  pinMode(D0, OUTPUT);
  Serial.begin(115200);

  //Flow Rate
  pulseCount   = 0;
  flowRate     = 0.0;
  flowLitres   = 0;
  totalLitres  = 0;

  //RFID
  SPI.begin(); // Init SPI bus
  rfid.PCD_Init(); // Init MFRC522
  for (byte i = 0; i < 6; i++)
  {
    key.keyByte[i] = 0xFF;
  }

  Serial.println(F("This code scan the MIFARE Classsic NUID."));
  Serial.print(F("Using the following key:"));
  printHex(key.keyByte, MFRC522::MF_KEY_SIZE);

#if USE_BLYNK_WM
  Blynk.begin("RFIC_System");
#else
  Blynk.begin(auth, ssid, pass);
#endif

  timer.setInterval(100L,  checkRFID);
  timer.setInterval(500L,  pumpControl);
  timer.setInterval(5000L, flowSensor);

  attachInterrupt(FLOW_SENSOR, pulseCounter, FALLING);
}

void loop()
{
  Blynk.run();
  timer.run();
}

and the terminal output of a test using Blynk_WM library library

217] Calc Cksum = 0x2ea9, Read Cksum = 0x2ea9
[219] Header = ESP8266, Board Name = RFID-Gas
[223] SSID = ****, PW =****
[226] SSID1 = ****, PW1 = ****
[230] Server = ****.duckdns.org, Token = ****
[236] Server1 = 192.168.2.110, Token1 = ****
[243] Port = 8080
[244] Connecting MultiWifi...
[4602] WiFi connected after time: 1
[4602] SSID: ****, RSSI = -36
[4602] Channel: 10, IP address: 192.168.2.46
[4602] bg: WiFi connected. Try Blynk
[4604] 
    ___  __          __
   / _ )/ /_ _____  / /__
  / _  / / // / _ \/  '_/
 /____/_/\_, /_//_/_/\_\
        /___/ v0.6.1 on NodeMCU

[4617] BlynkArduinoClient.connect: Connecting to ****.duckdns.org:8080
[4646] Ready (ping: 5ms).
[4914] Connected to Blynk Server = ****.duckdns.org, Token  = ****
[4914] bg: WiFi+Blynk connected
Customer requests $5 gas
Customer requests $10 gas
Purchase Confirmed
Dispense $10 worth of gas
Stop pumping gas
Customer requests $50 gas
Purchase Confirmed
Dispense $50 worth of gas
Stop pumping gas
Customer requests $5 gas
Customer requests $10 gas
Customer requests $10 gas
Customer requests $20 gas
Customer requests $50 gas
Customer requests $50 gas
Customer requests $10 gas
Customer requests $10 gas
Purchase Confirmed
Dispense $10 worth of gas
Stop pumping gas

We’re here as volunteers, and are not interested in compensation. If we have to live by that, it might be very high to pay.

2 Likes