Reed switch and stepper motor

Hi All,

I am using a stepper motor with arduino Mega 2560 board and would like the motor to stop moving when it reaches a reed switch .
The motor doesnt run if it senses the reed switch initially , which is good .
But I want the motor to stop running as soon as it reached the reed switch .
Any idea what I have to change in my code ? or would someone tell me how to implement my while loop properly . (I have // it )

#include <AccelStepper.h>
#define SWITCH 7   //input for REED SWITCH
#define LED 13     //pin for the LED
int incomingByte = 0;
int val = 0;       //used to store input value

// stepper motor pins: STEP, DIRECTION, STEPPER ON/OFF
AccelStepper Stepper1(1,2,3);



void setup() {
  
  for(int i = 0;i <54;i++) {
    pinMode(i,OUTPUT);
    digitalWrite(i,LOW);
  }
  
  pinMode(SWITCH, INPUT);   //SWITCH is input
  pinMode(LED, OUTPUT);   //tell arduino LED is an output
  
   //Start Serial for debuging purposes	
  Serial.begin(115200); // USB comm with PC

  
  // switch stepper chips off 
  digitalWrite(4,HIGH);
 
  Stepper1.setMaxSpeed(500);
  Stepper1.setAcceleration(500);
  spam();
 
}

void spam() {
  Serial.println("--------------------");
  
  Serial.println("1: Stepper1 FORWARD");

  Serial.println("2: STOP");
}



// main loop
void loop() {
  
      if (Serial.available() > 0) {
      incomingByte = Serial.read()-48;
      Serial.print("  Selection:");Serial.println(incomingByte);
      switch(incomingByte) {
          case 1: 
                  Stepper1.setCurrentPosition(0);
                  
                  val=digitalRead(SWITCH);   //read input value and store it
                  
                  
                  if (val == 0)     //switch is open
                  { digitalWrite(4,LOW); digitalWrite(3,HIGH); digitalWrite(2,HIGH); //Serial.println("Stepper1: forward"); 
                    digitalWrite(LED, LOW);
                    Stepper1.moveTo(4000);
                    
                    //while(Stepper1.currentPosition() !=Stepper1.targetPosition())
                    
                    for(int i =4000 ; i>0 ;i--)
                    { 
                      val=digitalRead(SWITCH); 
                      if(val == HIGH)   //switch is closed
                      {
                        digitalWrite(4,HIGH);
                        digitalWrite(LED, HIGH);
                      }
                    }
                    
                  }
                   if(val== HIGH)
                   digitalWrite(4,HIGH);
                  
                  break;
                
          case 2 : digitalWrite(4,HIGH);
                   Serial.println(Stepper1.currentPosition());
                   break;
                  
          
          default :spam();
                   break;
          
        }
      }  
     
    Stepper1.run();
    if(Stepper1.run() ==0)
    digitalWrite(4,HIGH);
    
    
} // main loop
                    for(int i =4000 ; i>0 ;i--)
                    { 
                      val=digitalRead(SWITCH); 
                      if(val == HIGH)   //switch is closed
                      {
                        digitalWrite(4,HIGH);
                        digitalWrite(LED, HIGH);
                      }
                    }

How long do you think it will take to race through this block of code? Will the stepper motor have caused the switch to be closed by then?

                    //while(Stepper1.currentPosition() !=Stepper1.targetPosition())

Uncomment this. Get rid of the for loop and the opening and closing brace, but not the code inside the braces.

Add a break statement to the if block, so the while loop is terminated.

You will also need tell the Stepper1 instance to go to the current position, so it stops trying to get to the target position. That is, the new target position is the current position.

Hi Paul

Please check if the following is how you described it . I am not able to get it running with the below changes I've made

                  if (val == 0)     //switch is open
                  { digitalWrite(4,LOW); digitalWrite(3,HIGH); digitalWrite(2,HIGH); //Serial.println("Stepper1: forward"); 
                    digitalWrite(LED, LOW);
                    Stepper1.moveTo(4000);
                    
                     while(Stepper1.currentPosition() !=Stepper1.targetPosition())
                     {
                     val=digitalRead(SWITCH); 
                      
                      if(val == HIGH)   //switch is closed
                      {
                        digitalWrite(4,HIGH);
                        digitalWrite(LED, HIGH);
                        Stepper1.targetPosition()==Stepper1.currentPosition();
                        break;
                      }
                      
                     }
                   }
                        Stepper1.targetPosition()==Stepper1.currentPosition();

This is a (useless) comparison, not any kind of assignment. You use the Stepper1.moveTo() method to define a target position. I don't know what method you use to abort a move in progress. That is what you need to figure out.

Hi
Seems to get it workin the way I want it now . I am able to stop the motion abruptly when the reed switch is encountered.
I have pasted my code below .
Thanks Paul

#include <AccelStepper.h>
#define SWITCH 7   //input for REED SWITCH
#define LED 13     //pin for the LED
int incomingByte = 0;
int val = 0;       //used to store input value

// stepper motor pins: STEP, DIRECTION, STEPPER ON/OFF
AccelStepper Stepper1(1,2,3);



void setup() {
  
  for(int i = 0;i <54;i++) {
    pinMode(i,OUTPUT);
    digitalWrite(i,LOW);
  }
  
  pinMode(SWITCH, INPUT);   //SWITCH is input
  pinMode(LED, OUTPUT);   //tell arduino LED is an output
  
   //Start Serial for debuging purposes	
  Serial.begin(115200); // USB comm with PC

  
  // switch stepper chips off 
  digitalWrite(4,HIGH);
 
  Stepper1.setMaxSpeed(500);
  Stepper1.setAcceleration(500);
  spam();
 
}

void spam() {
  Serial.println("--------------------");
  
  Serial.println("1: Stepper1 FORWARD");

  Serial.println("2: STOP");
}



// main loop
void loop() {
  
      if (Serial.available() > 0) {
      incomingByte = Serial.read()-48;
      Serial.print("  Selection:");Serial.println(incomingByte);
      switch(incomingByte) {
          case 1: 
                  Stepper1.setCurrentPosition(0);
                  
                  val=digitalRead(SWITCH);   //read input value from reed switch and store it
                  
                  if(val == 0)     //switch is open
                    { 
                     digitalWrite(4,LOW); digitalWrite(3,HIGH); digitalWrite(2,HIGH); //Serial.println("Stepper1: forward"); 
                     digitalWrite(LED, LOW);
                     Stepper1.moveTo(30000);
                    }
                  
                  if(val == HIGH)
                    {
                     digitalWrite(4,HIGH);
                     Serial.println(Stepper1.currentPosition());
                    }
                  break;
                
          case 2 : digitalWrite(4,HIGH);
                   Serial.println(Stepper1.currentPosition());
                   break;
                  
          
          default :spam();
                   break;
          
        }
      }  
                    
                    
     while(Stepper1.currentPosition() !=Stepper1.targetPosition())
          {
           Stepper1.run();
           val=digitalRead(SWITCH); 
           if(val == HIGH)   //switch is closed
             {
              digitalWrite(4,HIGH);
              digitalWrite(LED, HIGH);
              Stepper1.moveTo(Stepper1.currentPosition());
              Serial.println(Stepper1.currentPosition());
             } 
            
           } 
    
    if(Stepper1.run() ==0)
    digitalWrite(4,HIGH);
    
    
} // main loop

I have pasted my code below .

Using Tools + Auto Format would be a really good idea.

I like each { on a new line, too.

Consistent use of curly braces after if statements would be good, too.

    if(Stepper1.run() ==0)
    digitalWrite(4,HIGH);

You may decide that there are two things that need to be done when some condition is met. Adding the curly braces later is much more effort, in my opinion, than adding them in the first place.

Function names that reflect what they do are good.

  spam();

It's not possible to even guess what this function does, in a motor control program. In a e-mail generating application, maybe, but not here.

If you can't decide what the name ought to be, then you haven't thought enough about what the function is going to do.

A judicious amount of white space is good. More is not.

  Stepper1.setMaxSpeed(500);
  Stepper1.setAcceleration(500);
  spam();
 
}

That blank line does NOT improve the readability of the code. Lose it, and the other ones like it.

Just my final 2 cents.