element14 Community
element14 Community
    Register Log In
  • Site
  • Search
  • Log In Register
  • About Us
  • Community Hub
    Community Hub
    • What's New on element14
    • Feedback and Support
    • Benefits of Membership
    • Personal Blogs
    • Members Area
    • Achievement Levels
  • Learn
    Learn
    • Ask an Expert
    • eBooks
    • element14 presents
    • Learning Center
    • Tech Spotlight
    • STEM Academy
    • Webinars, Training and Events
    • Learning Groups
  • Technologies
    Technologies
    • 3D Printing
    • FPGA
    • Industrial Automation
    • Internet of Things
    • Power & Energy
    • Sensors
    • Technology Groups
  • Challenges & Projects
    Challenges & Projects
    • Design Challenges
    • element14 presents Projects
    • Project14
    • Arduino Projects
    • Raspberry Pi Projects
    • Project Groups
  • Products
    Products
    • Arduino
    • Avnet Boards Community
    • Dev Tools
    • Manufacturers
    • Multicomp Pro
    • Product Groups
    • Raspberry Pi
    • RoadTests & Reviews
  • Store
    Store
    • Visit Your Store
    • Choose another store...
      • Europe
      •  Austria (German)
      •  Belgium (Dutch, French)
      •  Bulgaria (Bulgarian)
      •  Czech Republic (Czech)
      •  Denmark (Danish)
      •  Estonia (Estonian)
      •  Finland (Finnish)
      •  France (French)
      •  Germany (German)
      •  Hungary (Hungarian)
      •  Ireland
      •  Israel
      •  Italy (Italian)
      •  Latvia (Latvian)
      •  
      •  Lithuania (Lithuanian)
      •  Netherlands (Dutch)
      •  Norway (Norwegian)
      •  Poland (Polish)
      •  Portugal (Portuguese)
      •  Romania (Romanian)
      •  Russia (Russian)
      •  Slovakia (Slovak)
      •  Slovenia (Slovenian)
      •  Spain (Spanish)
      •  Sweden (Swedish)
      •  Switzerland(German, French)
      •  Turkey (Turkish)
      •  United Kingdom
      • Asia Pacific
      •  Australia
      •  China
      •  Hong Kong
      •  India
      •  Korea (Korean)
      •  Malaysia
      •  New Zealand
      •  Philippines
      •  Singapore
      •  Taiwan
      •  Thailand (Thai)
      • Americas
      •  Brazil (Portuguese)
      •  Canada
      •  Mexico (Spanish)
      •  United States
      Can't find the country/region you're looking for? Visit our export site or find a local distributor.
  • Translate
  • Profile
  • Settings
Raspberry Pi
  • Products
  • More
Raspberry Pi
Blog PID based DC motor controller Project
  • Blog
  • Forum
  • Documents
  • Quiz
  • Events
  • Polls
  • Files
  • Members
  • Mentions
  • Sub-Groups
  • Tags
  • More
  • Cancel
  • New
Join Raspberry Pi to participate - click to join for free!
Featured Articles
Announcing Pi
Technical Specifications
Raspberry Pi FAQs
Win a Pi
GPIO Pinout
Raspberry Pi Wishlist
Comparison Chart
Quiz
  • Share
  • More
  • Cancel
Group Actions
  • Group RSS
  • More
  • Cancel
Engagement
  • Author Author: vsp
  • Date Created: 6 Feb 2019 1:52 PM Date Created
  • Views 9701 views
  • Likes 10 likes
  • Comments 3 comments
Related
Recommended
  • pid controller
  • motor drive module
  • raspbery pi
  • industrial automation
  • motor1
  • dcmotor

PID based DC motor controller Project

vsp
vsp
6 Feb 2019

This project demonstrates how to implement a PID based DC motor controller using Raspberry Pi. DC motor controller program is developed using Python. It consists of a GUI, RPM measuring, error detector, PID controller functions, and PWM generation function. The PID based closed-loop DC motor control system is one that determines a difference in the required speed and actual motor speed and creates a correction control signal to remove the error. To learn more about PID controller and DC Motor, go through PID based DC motor controller using Raspberry Pi and Motor Control 1 articles.

Required hardware:

Raspberry Pi

Raspberry Pi Display:

  • Farnell code: 2473872
  • Newark code: 49Y1712

RPM sensors:

   Slotted sensor:

  • Farnell code: 1386613
  • Newark code: 21M5159

Or

  PNP type proximity sensor: PR12-4DP

  • Farnell code: 1736862
  • Newark code: 10R6734

Procedure:

  • RPi.GPIO.22 is configured to get the feedback signal from the RPM sensor (voltage should less than 3.3V).
  • RPi.GPIO.23 is configured as an output. It provides PWM pulses for DC motor driver.
  • Connect the Raspberry Pi display and Input-Output pins.
  • Connect the Power adapter and power up the raspberry pi
  • Downloaded and install the GUIZERO library.
  • Download and run the DC motor controller code
  • GUI will open
  • If you are not connected feedback sensor to RPI, you can’t be able to set the PID gain values while running.
  • Adjust the required RPM using the sliders, now click the Start button.
  • Increase the P gain value.
  • The motor speed gradually increases, it will take some time to reach set RPM.
  • Increase the I-gain and D-gain values and see the system performance.
  • The speed of response depends on the PID gain values.
  • Load the motor using mechanical loading arrangement, and observe the set-RPM and run-RPM values, note load values to calculate the speed-torque characteristics of the motor.
  • Change the inputs (RPM and PID gain values) and observe the response of the motor.
  • After completion of your work press Stop button and close the project.

 

 

You don't have permission to edit metadata of this video.
Edit media
x
image
Upload Preview
image

 

DC motor controller code:

 

"""
       PID based DC motor controller
        thisproject is designed to control the DC motor at a constant speed
        Connect  one PPR(Pulse Per Rotation sensor to RPi.GPIO 22
        GPIO.23 providees PWM pulses to drive DC motor (DC motor drive between motor and RPi) 
"""

import threading
import RPi.GPIO as GPIO
import time
from guizero import App, Box, Text, TextBox, PushButton, Slider
""" Input Output  configaration """
GPIO.setmode(GPIO.BCM)
GPIO.setup(22, GPIO.IN, GPIO.PUD_DOWN)
GPIO.setup(23, GPIO.OUT)                  # PWM pulse for MOSFET/IGBT 
GPIO.output(23, 0)
""" Global variabels  """
Set_RPM =500                              # SET RPM value
feedback=0.0                          
previous_time =0.0
previous_error=0.0
Integral=0.0           
D_cycal=10
Kp=0                                       # Proportional controller Gain (0 to 100)
Ki=0                                       # Integral controller Gain (0 to 100)
Kd=0                                       # Derivative controller Gain (0 to 100)
RunRPM=0
Loop_value=0
a=0
avr=0
i=0
GatePulse = GPIO.PWM(23, 100)
""" PID control function """
def PID_function():
    
    global previous_time
    global previous_error
    global Integral
    global D_cycal
    global Kp
    global Ki
    global Kd
    
    error = int(Set_RPM) -feedback                    # Differnce between expected RPM and run RPM
    
    if (previous_time== 0):
         previous_time =time.time()
         
    current_time = time.time()
    delta_time = current_time - previous_time
    delta_error = error - previous_error
    
    Pout = (Kp/10 * error)              
    
    Integral += (error * delta_time)
    
    
    if Integral>10:      
        Integral=10
        
    if Integral<-10:
        Integral=-10
    
    Iout=((Ki/10) * Integral)
    
    
    Derivative = (delta_error/delta_time)         #de/dt
    previous_time = current_time
    previous_error = error
    
    Dout=((Kd/1000 )* Derivative)
    
    output = Pout + Iout + Dout                  # PID controller output
    
    if ((output>D_cycal)&(D_cycal<90)):           
        D_cycal+=1
        
    if ((output<D_cycal)&(D_cycal>10)):           
        D_cycal-=1
        
    return ()
"""   RPM calculation function   """
 
def RPM_function():      
    global feedback
    tc=time.time()
    
    
    while (GPIO.input(22)==False):               
        v=0
        ts=time.time()
        time_count=ts-tc
        
        if (time_count>7):
            print("Feedback failed, Please make proper feedback connection")
            feedback=0
            return ()         
               
    
    while (GPIO.input(22)==True):                  
        i=0
        ts=time.time()
        time_count=ts-tc
        if (time_count>7):
            print("Feedback failed, Please make proper feedback connection")
            feedback=0
            return ()
    
    v = time.time()                              # Stores the first pulse time
    while (GPIO.input(22)==False):               
        s=0                                     
    while (GPIO.input(22)==True):                  
        h=0                                            
    h=time.time()                                # Stores the next pulse time
                                        
    w=(60/(h-v))                                 # MOTOR speed in RPM  
    feedback = w
    
    return ()
def main_function():
    global D_cycal
    
    if Loop_value==1:
        
        t1 = threading.Thread(target=RPM_function)
        t1.start()
        t1.join()
        t2 = threading.Thread(target=PID_function)
        t2.start()
        t2.join()
        
        GatePulse.ChangeDutyCycle(D_cycal)
        
    else:
        GatePulse.ChangeDutyCycle(0)
print("Welcome To The Element14 Community!")
"""     GUI Functions     """
app = App(title="Welcome To The Element14 Community", height=700, width=500)
def change_Kp_value(slider_value):
    global Kp
    Proportional.value = slider_value
    Kp=int(slider_value)
    
def change_Ki_value(slider_value):
    global Ki
    Intregral.value = slider_value
    Ki= int(slider_value)
    
def change_Kd_value(slider_value):
    global Kd
    Deravative.value = slider_value
    Kd=int(slider_value)
def change_SetRPM_value(slider_value):
    global Set_RPM
    SetRPM.value = slider_value
    Set_RPM=int(slider_value)
      
def update_rpm():
    global avr
    global i
    global a
    global feedback
    if(Loop_value==1):
        if i<6:
            a+=feedback
            i+=1
        else:
                        
            Run_RPM.value = int(a/6)
            a=0
            i=0
    else:
        Run_RPM.value = 0
    
def start_funcdtion():
    global Loop_value
    print("MOTOR controller is ON ")
    GatePulse.start(25)
    Loop_value=1
    Startbutton.toggle()
    Startbutton.toggle()
    Startbutton.repeat(1, main_function)
        
def Stop_function():
    
    global Loop_value
    Loop_value=0
    Startbutton.cancel(main_function)
    Run_RPM.value=00
    D_cycal=0
    Stopbutton.toggle()
    Stopbutton.toggle()
    GatePulse.ChangeDutyCycle(0)
    print("Motor controller is Off")
def close_window():
    Stop_function()
    app.hide()
message = Text(app, text="PID based DC motor controller", color="saddle brown", size= 20)
Startbutton = PushButton(app, command = start_funcdtion, text="Start")
Startbutton.text_color="dark green"
Startbutton.text_size=15
Spase = Text(app, text= "  ")
SetRPM = Text(app, text= "Set_RPM")
SetRPM.text_color="blue"
SetRPM = Text(app, text= Set_RPM)
text_value = Slider(app, command=change_SetRPM_value, start=500, end=2000)
Spase = Text(app, text= "  ")
Proportional = Text(app, text= "Kp")
Proportional.text_color="DarkOliveGreen4"
Proportional = Text(app, text= Kp)
text_value = Slider(app, command=change_Kp_value, start=0, end=100)
pase = Text(app, text= "  ")
Intregral = Text(app, text= "Ki")
Intregral.text_color="DarkOliveGreen4"
Intregral = Text(app, text= Ki)
text_value = Slider(app, command=change_Ki_value, start=0, end=100)
pase = Text(app, text= "  ")
Deravative = Text(app, text= "Kd")
Deravative.text_color="DarkOliveGreen4"
Deravative = Text(app, text= Kd)
text_value = Slider(app, command=change_Kd_value, start=0, end=100)
pase = Text(app, text= "  ")
Run_RPM = Text(app, text= "RunRPM")
Run_RPM.text_color="tomato"
Run_RPM = Text(app, text= RunRPM)
Run_RPM.repeat(1, update_rpm) 
pase = Text(app, text= "  ")
Stopbutton = PushButton(app, command = Stop_function, text="Stop")
Stopbutton.text_color="red"
Stopbutton.text_size=15
pase = Text(app, text= "  ")
close_button = PushButton(app, text="Close Project", command=close_window)
#close_button.text_coller="yellow"
close_button.text_size=20
app.display()

  • Sign in to reply

Top Comments

  • rscasny
    rscasny over 6 years ago +3
    Thanks for this project. I was sure that the Pi could be used for a PID controller, but you showed it can. It would be interesting to see if anyone is using the PI is this mode. I appreciate your participation…
  • enesss
    enesss over 5 years ago +1
    Can you send the electronic diagram of the circuit please?
  • three-phase
    three-phase over 5 years ago

    Very neat project. Thanks for posting.

     

    Kind regards.

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • More
    • Cancel
  • enesss
    enesss over 5 years ago

    Can you send the electronic diagram of the circuit please?

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • More
    • Cancel
  • rscasny
    rscasny over 6 years ago

    Thanks for this project. I was sure that the Pi could be used for a PID controller, but you showed it can. It would be interesting to see if anyone is using the PI is this mode.

     

    I appreciate your participation in the element14 community.

     

    Randall

    • Cancel
    • Vote Up +3 Vote Down
    • Sign in to reply
    • More
    • Cancel
element14 Community

element14 is the first online community specifically for engineers. Connect with your peers and get expert answers to your questions.

  • Members
  • Learn
  • Technologies
  • Challenges & Projects
  • Products
  • Store
  • About Us
  • Feedback & Support
  • FAQs
  • Terms of Use
  • Privacy Policy
  • Legal and Copyright Notices
  • Sitemap
  • Cookies

An Avnet Company © 2025 Premier Farnell Limited. All Rights Reserved.

Premier Farnell Ltd, registered in England and Wales (no 00876412), registered office: Farnell House, Forge Lane, Leeds LS12 2NE.

ICP 备案号 10220084.

Follow element14

  • X
  • Facebook
  • linkedin
  • YouTube