Loop certain number of times then do action

I am having trouble getting my code to work properly. It is supposed to run a loop if I have a signal from a relay. The loop is supposed to run a set amount of times and once it is done it will send a signal to another relay. Right now it is constantly pulsing a signal to cutPin. Any advice would be appreciated.

const int relayPin = 2;
const int stepPin = 7;
const int cutPin = 4;
const int directionPin = 13;
const int numberOfSteps = 50000;
int relayState = digitalRead(relayPin);

void setup()
{
   pinMode(relayPin, INPUT);
   pinMode(stepPin, OUTPUT);
   pinMode(cutPin, OUTPUT);
   pinMode(directionPin, OUTPUT);
}

void loop()
{
  if (relayState == HIGH){ 
    for (int i=0; i < numberOfSteps; i++){
       digitalWrite(stepPin, HIGH);
       delayMicroseconds(100);
       digitalWrite(stepPin, LOW);
       delayMicroseconds(100);
      }
    {
     digitalWrite(cutPin, HIGH);
     delay(500);
     digitalWrite(cutPin, LOW);
     delay(100);
    }
   }
 else
 {
   delay(20);
 }
}

Welcome to the forum

You have this line of code in the loop() function

    if (relayState == HIGH)

but the value of relayState is not changed in loop() so the condition is either always true or always false. You need to read the state of relayPin in the loop() function

1 Like

I forgot to mention, I am trying to communicate this with another PLC. That is supposed to read if there is a signal coming from the PLC and run the program when there is.

It does not matter where the input is coming from if you don't read the state of the input at the right place in the code

1 Like

Put another way, when do you think this:

int relayState = digitalRead(relayPin);

executes? Hint, it's not in loop(), it's not in setup(), so?

I changed it to if(relayPin == HIGH); is there any other changes that need to be made?

That is not the solution. relayPin will always be HIGH as its value is fixed at 2

You need to read the state of relayPin in loop() using digitalRead()

1 Like

This

int relayState = digitalRead(relayPin);

may work to set the value of a variable, but if it does would be once, before any of your code ran.

That statement does not establish a magic connection between the variable the current state of the pin when you use the variable later.

It's a common misconception.Think in terms of how the code works line by line; the only way for a variable to get a new value is with an assignment statement. In this case it means you must digitalRead() the relayPon whenever you want to know what's on the pin at that point.

a7

Just move the statement where you read the pin inside loop()

const int relayPin = 2;
const int stepPin = 7;
const int cutPin = 4;
const int directionPin = 13;
const int numberOfSteps = 50000;

void setup()
{
  pinMode(relayPin, INPUT);
  pinMode(stepPin, OUTPUT);
  pinMode(cutPin, OUTPUT);
  pinMode(directionPin, OUTPUT);
}

void loop()
{
  int relayState = digitalRead(relayPin);
  
  if (relayState == HIGH) {
    for (int i = 0; i < numberOfSteps; i++) {
      digitalWrite(stepPin, HIGH);
      delayMicroseconds(100);
      digitalWrite(stepPin, LOW);
      delayMicroseconds(100);
    }
    digitalWrite(cutPin, HIGH);
    delay(500);
    digitalWrite(cutPin, LOW);
    delay(100);
  }
  else
  {
    delay(20);
  }
}

I made the change and what Im hoping is that the code will cycle through quickly enough when the relaystate is low that it will loop and read it again. And I am still confused why each time the code loops it runs the section of code below while its in the if statement
{
digitalWrite(cutPin, HIGH);
delay(500);
digitalWrite(cutPin, LOW);
delay(100);

Where does the code that you posted read the state of relayPin ?

Did you post the changed code ?

const int relayPin = 2;
const int stepPin = 7;
const int cutPin = 4;
const int directionPin = 13;
const int numberOfSteps = 50000;

void setup()
{
   pinMode(relayPin, INPUT);
   pinMode(stepPin, OUTPUT);
   pinMode(cutPin, OUTPUT);
   pinMode(directionPin, OUTPUT);
}

void loop()
{
  int relayState = digitalRead(relayPin);
  if (relayState == HIGH){ 
    for (int i=0; i < numberOfSteps; i++){
       digitalWrite(stepPin, HIGH);
       delayMicroseconds(100);
       digitalWrite(stepPin, LOW);
       delayMicroseconds(100);
      }
    //{
     //digitalWrite(cutPin, HIGH);
     //delay(500);
     //digitalWrite(cutPin, LOW);
     //delay(100);
    //}
   }
 else
 {
   delay(20);
 }
}

That looks better but it is not obvious what you are trying to do. How long do you want the stepper motor to run when relayPin becomes HIGH ?

Is there anything keeping relayPin LOW before the relay operates or is it floating at an unknown voltage, maybe HIGH, maybe LOW ?

The stepper motor is supposed to do a certain amount of steps which is equal to numberOfSteps so for now it is 50000 steps. I have 5 volts going to the positive post on the output side of the relay and then the other post on the output side of the relay is connected to pin 2.

What is connected on relayPin?

So there is not a pulldown resistor keeping relayPin LOW when the relay is not energised

I have a PLC that operates at 24V that is suppose to initiate the program

I do not have a pulldown resistor

Then how can you be sure of the state of relayPin when the relay is not turned on ?

We are now nearly 20 replies into this topic and you have made changes to the sketch. Is it doing what you want ? If not, then describe what it does and what you want it to do

What action do you want to take after the "certain number of steps" ? I ask, because there is no such action in your sketch

The main problem i came here for is that the program is looping and only running the program section that controls the cutpin. I need the cutpin program to only run once the for statement is complete. Right now it will skip the for statement and run the section of code that controls the cutPin