Interfacing Servo Motor with PIC Microcontroller

Interfacing Servo Motor with PIC Microcontroller

Servo Motor

Servo Motor uses error sensing negative feedback to control the precise angular position. Servos are used for precise positioning in robotic arms, legs, RC Aeroplanes, Helicopters etc. Please read the article Servo Motor for more information about its working and construction. Hobby Servo Motors have three wires, two of them (RED and BLACK) are used to given power and the third one is used to give control signals. Servo can be easily be controlled using microcontrollers using Pulse Width Modulated (PWM) signals on  the control wire. Here we are using a servo whose angular rotation is limited to 0 – 180°. We can control the exact angular position by using  a pulse, whose width varying from 1 millisecond to 2 millisecond on the control wire. The actual behavior of a particular motor depends upon its manufacture, please refer the datasheet of the particular motor for that.

Here I am using VIGOR VS-10A servo motor.

Servo Angular Rotation Pulse Width Modulation
Servo Angular Rotation Pulse Width Modulation

Circuit Diagram

Interfacing Servo Motor with PIC Microcontroller
Interfacing Servo Motor with PIC Microcontroller

Note: VDD and VSS of the pic microcontroller is not shown in the circuit diagram. VDD should be connected to +5V and VSS to GND.


MikroC Programming

void servoRotate0() //0 Degree
{
  unsigned int i;
  for(i=0;i<50;i++)
  {
    PORTB.F0 = 1;
    Delay_us(800);
    PORTB.F0 = 0;
    Delay_us(19200);
  }
}

void servoRotate90() //90 Degree
{
  unsigned int i;
  for(i=0;i<50;i++)
  {
    PORTB.F0 = 1;
    Delay_us(1500);
    PORTB.F0 = 0;
    Delay_us(18500);
  }
}

void servoRotate180() //180 Degree
{
  unsigned int i;
  for(i=0;i<50;i++)
  {
    PORTB.F0 = 1;
    Delay_us(2200);
    PORTB.F0 = 0;
    Delay_us(17800);
  }
}

void main()
{
  TRISB = 0; // PORTB as Ouput Port
  do
  {
    servoRotate0(); //0 Degree
    Delay_ms(2000);
    servoRotate90(); //90 Degree
    Delay_ms(2000);
    servoRotate180(); //180 Degree
  }while(1);
}

Control wire of the Servo  is connected to RB0 of the PIC Microcontroller. Delay_ms() is used to make delay in milliseconds during the program execution while Delay_us() is used to make delay in microsecond during the program execution.

Download

You can download MikroC Code, Proteus files etc here…..
Interfacing Servo Motor with PIC Microcontroller

Want to See the Output ?

Share this post

  • Ithu avril work akunilallo… clockwise 90° anu servo turn akunne… real aytm proteusilm athe…. Oscilloscopeil wide pulse width anu kanikunath with the same code

  • in video it is recommended to use separate supplies for PIC and Servo. how to use filter capacitors if using same supply for both servo and PIC? where to connect capacitors?

  • I’m doing a project using PIC16F887, which is gonna remotely control a crane using servos. Kind of lost , will this code above be a helpful aid for this type of project?

  • i’m trying this code in mplab v8.10 ide it throws following error —- Error [500] ; . undefined symbols:

    ___delay_ms (se.obj)___delay_us (se.obj), i’ve tried following commands delay_ms(1000);,delay(1000);_delay_ms(1000); someone help me to solve this problem ,i’m new to pic

  • what if i want to have a push button switch ..

    portb.f0=1 // my input

    when my button is active the motor will be on 90 and if not active the motor will be back on 0 degree

  • @Ligo
    Hi i been trying to make this code turn 0 then 90 then 0 then -90
    but all i am getting is 0 then 45 then 90 then 0
    here is my code
    Thank you
    void servoRotate0() //0 Degree
    {
    unsigned int i;
    for(i=0;i<50;i++)
    {
    PORTC.F0 = 1;
    Delay_us(1500);
    PORTC.F0 = 0;
    Delay_us(18500);
    }
    }

    void servoRotate90() //90 Degree
    {
    unsigned int i;
    for(i=0;i<50;i++)
    {
    PORTC.F0 = 1;
    Delay_us(2000);
    PORTC.F0 = 0;
    Delay_us(18000);
    }
    }

    void servoRotate_90() //-90 Degree
    {
    unsigned int i;
    for(i=0;i<50;i++)
    {
    PORTC.F0 = 1;
    Delay_us(1000);
    PORTC.F0 = 0;
    Delay_us(19000);
    }
    }

    void main()
    {
    TRISC = 0; // PORTB as Ouput Port
    do
    {
    servoRotate90(); //90 Degree
    servoRotate0(); //0 Degree
    servoRotate_90(); //-90 Degree

    }while(1);
    }

  • Dear Sir,
    You r right but in this project i don’t wanna display any current value,instead,it’s a rotary pneumatic actuator,so i wanna show the pneumatic moments with servo motor,plz guide me,thanks

  • You cannot control the speed of servo motor….Try using another servo..
    But I think your Idea is a bad one… Microcontroller is a digital device.. So you are going to make an analog display using digital components ?

  • Dear Sir, i wanna build a 4-20 mA analog display with servo motor. I had succeeded moving the motor in both way with PIC 16F887, But it is not moving precisely when i give same pulse to it, may be the FUTABA S3003 motor is not precise or i am making some mistakes,also wanna control the speed,plz do the needful

  • Hello LIGO Gearge

    I can control it in simulation Proteus. It is Ok.

    But i can’t control it in real time.

    Tell me please where is wrong?

    Code C is ok.

    I have used quartz crystal 20Mhz.

    I use servomotor (DF25MG made in china).

  • hi i use those codes for servo sg 91r servo but my motor does not move it goes some 30-45 degree and stops what can i do please help ………

  • Hi, I want to use a mikroE 4×4 matrix keypad to input a specific angle that the servo should go to. Do you know how I can code the keypad and servo to do this in MikroC? Or a good tutorial that could help? Thanks

  • What if i want to servo motor to turn 270 degrees? i mean first 0 degree…then 90 deg…then 180…then 270 degree?? coz my bot requires complete circular rotation…need help!

  • So…what is the values that i need to use to bring back to the older position, for example, im using a servo to open and and close a claw, so i need to run the motor for a side and after run againt to another size….how can i do this? whats the values that i need to put? Thanks!

  • As indicated above, you need a frequency of about 50Hz, to control the servo motor…. thus you need to use a very low clock frequency to produce that frequency using ccp module…

  • why is that the signal of the servo is connected to the interrupt port of the microcontroller not the ccp port?

  • In your program you have given like this,
    PORTB.F0 = 1;
    Delay_us(1000);//1ms Delay
    PORTB.F0 = 0;
    Delay_ms(1000);
    but as per the diagram of the input pulses it should be like this right?
    PORTB.F0 = 1;
    Delay_us(1000);//1ms Delay
    PORTB.F0 = 0;

    Delay_ms(20);

  • Hi!!! can you please give me a sample program for five degree freedom robotic arm using servo motor? we are using mikroc in 16f84a as our pic and we are having a hard time solving it. thanks! 😀

  • maybe you have some microC code which can do the same servo control via uart? (pic to pic communication)


  • >