Raspberry Pi - Stepper Motor Limit Switch

This tutorial instructs you how to use Raspberry Pi to control a stepper motor via a limit switch and an L298N driver. Specifically, we will cover:

Hardware Preparation

1×Raspberry Pi 4 Model B
1×Limit Switch (KW12-3)
1×Limit Switch (V-156-1C25)
1×Stepper Motor Nema 17
1×L298N Motor Driver Module
1×12V Power Adapter
1×DC Power Jack
1×Jumper Wires
1×(Optional) Screw Terminal Adapter for Raspberry Pi

Or you can buy the following sensor kit:

1×DIYables Sensor Kit 30 types, 69 units
Disclosure: Some of the links provided in this section are Amazon affiliate links. We may receive a commission for any purchases made through these links at no additional cost to you. We appreciate your support.

Overview of Stepper Motor and Limit Switch

If you are unfamiliar with stepper motor and limit switch (including pinout, functionality, programming, etc.), the following tutorials can help:

Wiring Diagram

This tutorial provides the wiring diagram for two cases: One stepper motor + one limit switch, One stepper motor + two limit switches.

  • Wiring Diagram between Raspberry Pi, stepper motor and, and a limit switch
The wiring diagram between Raspberry Pi and stepper motor and limit switch

This image is created using Fritzing. Click to enlarge image

  • Wiring Diagram between Raspberry Pi, stepper motor and, and two limit switches
The wiring diagram between Raspberry Pi and stepper motor and two limit switches

This image is created using Fritzing. Click to enlarge image

※ NOTE THAT:

The wiring connection between the stepper motor and L298N may vary depending on the type of stepper motor. Carefully examine the Raspberry Pi - Stepper Motor tutorial to learn how to properly link the stepper motor to the L298N motor driver.

Raspberry Pi Code - Stop Stepper Motor by a Limit Switch

A stepper motor is programmed to spin continuously with the following code, and will stop instantly when a limit switch is touched, and resume moving if the limit switch is released.

Detailed Instructions

  • Make sure you have Raspbian or any other Raspberry Pi compatible operating system installed on your Pi.
  • Make sure your Raspberry Pi is connected to the same local network as your PC.
  • Make sure your Raspberry Pi is connected to the internet if you need to install some libraries.
  • If this is the first time you use Raspberry Pi, See how to set up the Raspberry Pi
  • Connect your PC to the Raspberry Pi via SSH using the built-in SSH client on Linux and macOS or PuTTY on Windows. See to how connect your PC to Raspberry Pi via SSH.
  • Make sure you have the RPi.GPIO library installed. If not, install it using the following command:
sudo apt-get update sudo apt-get install python3-rpi.gpio
  • Create a Python script file stepper_limit_switch.py and add the following code:
# This Raspberry Pi code was developed by newbiely.com # This Raspberry Pi code is made available for public use without any restriction # For comprehensive instructions and wiring diagrams, please visit: # https://newbiely.com/tutorials/raspberry-pi/raspberry-pi-stepper-motor-limit-switch import RPi.GPIO as GPIO import time # Define GPIO pins for L298N driver and limit switch IN1 = 12 IN2 = 16 IN3 = 20 IN4 = 21 LIMIT_SWITCH_PIN = 27 # Set GPIO mode and configure pins GPIO.setmode(GPIO.BCM) GPIO.setup(IN1, GPIO.OUT) GPIO.setup(IN2, GPIO.OUT) GPIO.setup(IN3, GPIO.OUT) GPIO.setup(IN4, GPIO.OUT) GPIO.setup(LIMIT_SWITCH_PIN, GPIO.IN, pull_up_down=GPIO.PUD_UP) # Define constants DEG_PER_STEP = 1.8 STEPS_PER_REVOLUTION = int(360 / DEG_PER_STEP) # Function to move the stepper motor one step forward def step_forward(delay): GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) # Function to check the limit switch status def is_limit_switch_pressed(): return GPIO.input(LIMIT_SWITCH_PIN) == GPIO.LOW try: # Set the delay between steps delay = 0.001 while not is_limit_switch_pressed(): # Move the stepper motor forward endlessly step_forward(delay) except KeyboardInterrupt: print("\nExiting the script.") finally: # Clean up GPIO settings GPIO.cleanup()
  • Save the file and run the Python script by executing the following command in the terminal:
python3 stepper_limit_switch.py
  • If the wiring is correct, the motor should rotate in a clockwise direction.
  • When the limit switch is touched, the motor should stop immediately.
  • Then if the limit switch is released, the motor rotates again.

The script runs in an infinite loop continuously until you press Ctrl + C in the terminal.

By changing the value of delay variable in the code, you can change the speed of the stepper motor.

Code Explanation

Check out the line-by-line explanation contained in the comments of the source code!

Raspberry Pi Code - Change Direction of Stepper Motor by a Limit Switch

A stepper motor will be set in motion continuously and its direction will be altered when a limit switch is touched.

Detailed Instructions

  • Create a Python script file stepper_direction.py and add the following code:
# This Raspberry Pi code was developed by newbiely.com # This Raspberry Pi code is made available for public use without any restriction # For comprehensive instructions and wiring diagrams, please visit: # https://newbiely.com/tutorials/raspberry-pi/raspberry-pi-stepper-motor-limit-switch import RPi.GPIO as GPIO import time # Define GPIO pins for L298N driver and limit switch IN1 = 12 IN2 = 16 IN3 = 20 IN4 = 21 LIMIT_SWITCH_PIN = 27 # Set GPIO mode and configure pins GPIO.setmode(GPIO.BCM) GPIO.setup(IN1, GPIO.OUT) GPIO.setup(IN2, GPIO.OUT) GPIO.setup(IN3, GPIO.OUT) GPIO.setup(IN4, GPIO.OUT) GPIO.setup(LIMIT_SWITCH_PIN, GPIO.IN, pull_up_down=GPIO.PUD_UP) # Define constants DEG_PER_STEP = 1.8 STEPS_PER_REVOLUTION = int(360 / DEG_PER_STEP) # Global variable to store the previous state of the limit switch prev_limit_switch_state = GPIO.HIGH # Function to move the stepper motor one step forward def step_forward(delay): GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) # Function to move the stepper motor one step backward def step_backward(delay): GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.HIGH) time.sleep(delay) GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.HIGH) time.sleep(delay) try: # Set the delay between steps delay = 0.001 # Set the initial direction direction = 'forward' while True: # Check if the limit switch state changes limit_switch_state = GPIO.input(LIMIT_SWITCH_PIN) # Change direction if the limit switch changes from HIGH to LOW if limit_switch_state == GPIO.LOW and prev_limit_switch_state == GPIO.HIGH: direction = 'backward' if direction == 'forward' else 'forward' # Move the stepper motor based on the direction if direction == 'forward': step_forward(delay) elif direction == 'backward': step_backward(delay) # Update the previous state of the limit switch prev_limit_switch_state = limit_switch_state except KeyboardInterrupt: print("\nExiting the script.") finally: # Clean up GPIO settings GPIO.cleanup()
  • Save the file and run the Python script by executing the following command in the terminal:
python3 stepper_direction.py
  • If the wiring is correct, the motor should spin in a clockwise direction.
  • When you touch the limit switch, the stepper motor's direction will change to counterclockwise.
  • Touch the limit switch again and the stepper motor's direction will go back to clockwise.

Raspberry Pi Code - Change Direction of Stepper Motor by two Limit Switches

Let's see the code that makes a stepper motor spin continuously, and when either of two limit switches is touched, switches the motor's direction.

Detailed Instructions

  • Create a Python script file stepper_two_limit_switches.py and add the following code:
# This Raspberry Pi code was developed by newbiely.com # This Raspberry Pi code is made available for public use without any restriction # For comprehensive instructions and wiring diagrams, please visit: # https://newbiely.com/tutorials/raspberry-pi/raspberry-pi-stepper-motor-limit-switch import RPi.GPIO as GPIO import time # Define GPIO pins for L298N driver and limit switches IN1 = 12 IN2 = 16 IN3 = 20 IN4 = 21 LIMIT_SWITCH1_PIN = 27 LIMIT_SWITCH2_PIN = 19 # Set GPIO mode and configure pins GPIO.setmode(GPIO.BCM) GPIO.setup(IN1, GPIO.OUT) GPIO.setup(IN2, GPIO.OUT) GPIO.setup(IN3, GPIO.OUT) GPIO.setup(IN4, GPIO.OUT) GPIO.setup(LIMIT_SWITCH1_PIN, GPIO.IN, pull_up_down=GPIO.PUD_UP) GPIO.setup(LIMIT_SWITCH2_PIN, GPIO.IN, pull_up_down=GPIO.PUD_UP) # Define constants DEG_PER_STEP = 1.8 STEPS_PER_REVOLUTION = int(360 / DEG_PER_STEP) # Global variables to store the previous state of the limit switches prev_limit_switch_1 = GPIO.HIGH prev_limit_switch_2 = GPIO.HIGH # Function to move the stepper motor one step forward def step_forward(delay): GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.LOW) time.sleep(delay) # Function to move the stepper motor one step backward def step_backward(delay): GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.HIGH) time.sleep(delay) GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.HIGH) time.sleep(delay) try: # Set the delay between steps delay = 0.001 # Set the initial direction direction = 'forward' while True: # Check if limit switch 1 state changes limit_switch_1 = GPIO.input(LIMIT_SWITCH1_PIN) if limit_switch_1 == GPIO.LOW and prev_limit_switch_1 == GPIO.HIGH: direction = 'backward' # Check if limit switch 2 state changes limit_switch_2 = GPIO.input(LIMIT_SWITCH2_PIN) if limit_switch_2 == GPIO.LOW and prev_limit_switch_2 == GPIO.HIGH: direction = 'forward' # Move the stepper motor based on the direction if direction == 'forward': step_forward(delay) elif direction == 'backward': step_backward(delay) # Update the previous states of the limit switches prev_limit_switch_1 = limit_switch_1 prev_limit_switch_2 = limit_switch_2 except KeyboardInterrupt: print("\nExiting the script.") finally: # Clean up GPIO settings GPIO.cleanup()
  • Save the file and run the Python script by executing the following command in the terminal:
python3 stepper_two_limit_switches.py

The script runs in an infinite loop continuously until you press Ctrl + C in the terminal.

  • If the wiring is correct, the motor should spin in a clockwise direction.
  • When you touch limit switch 1, the stepper motor's direction will be reversed to anti-clockwise.
  • Touching limit switch 2 will cause the stepper motor to rotate clockwise again.