[SOLVED] Triggered cycle counter

Hello everybody,
I’m trying to automate my swing gates in which I need a sequence to be as follows:
for opening both halves there must be a pause between powering the left and right motors
closing is done in reverse order
I did this for arduino but arduino’s interrupt goes crazy near AC magnetic interference

#define BLYNK_PRINT Serial    // Comment this out to disable prints and save space
#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>
int setdelay = 500;
int setdelay1 = 10;
int counter1 = 0;
static unsigned long last_interrupt_time1 = 0;
volatile int  counter = 0;
int LampState = HIGH;
const int lampPin = 1;
const int leftopenPin = 7;
const int leftclosePin=6;
const int rightopenPin = 4;
const int rightclosePin = 5;

unsigned long TimerA;
unsigned long PreviousTimer = 0;

// You should get Auth Token in the Blynk App.
// Go to the Project Settings (nut icon).
char auth[] = "";

// Your WiFi credentials.
// Set password to "" for open networks.
char SSID[] = "Linksys";
char pass[] = "3";
BLYNK_WRITE(V1)
{
  int pinValue = param.asInt(); // assigning incoming value from pin V1 to a variable
  counter == counter + pinValue;
}
BLYNK_WRITE(V2)
{
  int setdelay1 = param.asInt(); // assigning incoming value from pin V1 to a variable
}
void setup()
{
  Serial.begin(9600);
  Blynk.begin(auth, SSID, pass, IPAddress(192, 168, 2, 199));
}

void loop()
{
  Blynk.run();
  while ((counter == 1) || (counter == 3)) {
    TimerA = millis();
    if (TimerA - PreviousTimer > setdelay) {
      PreviousTimer = TimerA;
      if (LampState == LOW) {
        LampState = HIGH;
      } else {
        LampState = LOW;
      }
      digitalWrite(lampPin, LampState);
      counter1++;
      if (counter1 > setdelay1) {
        counter1 = 0;
        //digitalWrite lampPin, HIGH);
      }
    }
    switch (counter) {
      case 0:
        digitalWrite (leftopenPin, HIGH);
        digitalWrite(rightopenPin, HIGH);
        digitalWrite (leftclosePin, HIGH);
        digitalWrite(rightclosePin, HIGH);
        break;
      case 1:
        digitalWrite (leftopenPin, LOW);
        if (counter1 > 8) {
          digitalWrite(rightopenPin, LOW);
        }
        if (counter1 >= setdelay1) {
          digitalWrite (leftopenPin, HIGH);
          digitalWrite(rightopenPin, HIGH);
          digitalWrite (leftclosePin, HIGH);
          digitalWrite(rightclosePin, HIGH);
          counter++;
        }
        break;
      case 3:
        digitalWrite (rightclosePin, LOW);
        if (counter1 > 8) {
          digitalWrite(leftclosePin, LOW);
        }
        if (counter1 >= setdelay1) {
          digitalWrite (leftclosePin, HIGH);
          digitalWrite(rightclosePin, HIGH);
          digitalWrite (leftopenPin, HIGH);
          digitalWrite(rightopenPin, HIGH);
          counter++;
        }
        break;
    }
  }
}

It compiles but no reaction to the trigger

@Viktor_Guroma you can’t simply use the same code for an Arduino on an ESP.

const int leftopenPin = 7;
const int leftclosePin=6;

These pins simply don’t exist on an ESP and even though pin 1 exists it is very rare it is used because it’s used for Serial comms.

Look up the pinout for your hardware.

Sure, I’ve seen some funny pics like this. I will not use my gate while using TXD or RXD and vice versa.
What bothers me most is the fact that GPIO 4 and 5 are silent which are D1 and D2 in NODEMCU. .

@Viktor_Guroma were you aware that most Blynk sketches have just 2 lines in loop() and the reason for this?

Affirmative, Sir. But I did not find any place to put the ticker. maybe you can

Use SimpleTimer.

The PushData example provided by Blynk will help you learn how it works.

Blynk’s Simple Timer runs all the, Jamin. I need something that allow triggering certain relays in a sequence: one relay ON- pause 2 sec (relay still on) - second relay ON - all 2 relays off after 15 seconds from first action.
Other ideas are welcome.

SimpleTimer to the rescue!

void actionRelays(){
  relay1_ON(); // turn on relay1
  timer.setTimeout(2000, relay2_ON); // delay 2sec then turn on relay2
  timer.setTimeout(15000, relays_OFF); // delay 15sec from first action and turn off both relays
}

void relay1_ON(){
  digitalWrite(relay1,HIGH); // turn on relay1
  Blynk.virtualWrite(V10, 255); // turn on an LED widget (optional)
}

void relay2_ON(){
  digitalWrite(relay2,HIGH); // turn on relay2
  Blynk.virtualWrite(V20, 255); // turn on an LED widget (optional)
}

void relays_OFF(){
  digitalWrite(relay1,LOW); // turn off relay1
  digitalWrite(relay2,LOW); // turn off relay2
  Blynk.virtualWrite(V10, 0); // turn off an LED widget (optional)
  Blynk.virtualWrite(V20, 0); // turn off an LED widget (optional)
}

Run actionRelays() anywhere in your code and it will automatically do the timed sequence without blocking.

1 Like

Just what I need too. But if I want to repeat it, say 45 times and then stop, what do you suggest?
I could calculate all the intervals and just continue the scetch 45 times, but there must be an easier way, right?

// O.C.

If you want to repeat the entire thing 45 times, then you would just tell it to run again at the end of the sequence.

int repeatCounter;
void relays_OFF(){
  digitalWrite(relay1,LOW); // turn off relay1
  digitalWrite(relay2,LOW); // turn off relay2
  Blynk.virtualWrite(V10, 0); // turn off an LED widget (optional)
  Blynk.virtualWrite(V20, 0); // turn off an LED widget (optional)
  repeatCounter++;
  if(repeatCounter >= 45){ 
    actionRelays();
    repeatCounter = 0;
  }
}

Or run another timer set for 45 cycles.

https://playground.arduino.cc/Code/SimpleTimer

int setTimer(long d, timer_callback f, int n)
Call function f every d milliseconds for n times. The callback function must be declared as void f(). After f has been called the specified number of times, the interval is deleted, therefore the value timerId is no longer valid.

void repeatMeFortyFiveTimes() {
    // do something
}

timerId = timer.setTimer(1000, repeatMeFortyFiveTimes, 45);

To use that type of trigger he would run out of available space in his timer node.
He only get 10 timers which can be stored at once. After 6 seconds all slots would be full and all new timers would be ignored.
You could set the interval to exactly 15 seconds to match the timed sequence and then it might be fine.

Whilst you were “away” Blynk increased it to 16 :slight_smile:

1 Like

mind blown

:open_mouth: