.. note::

    Hello, welcome to the SunFounder Raspberry Pi & Arduino & ESP32 Enthusiasts Community on Facebook! Dive deeper into Raspberry Pi, Arduino, and ESP32 with fellow enthusiasts.

    **Why Join?**

    - **Expert Support**: Solve post-sale issues and technical challenges with help from our community and team.
    - **Learn & Share**: Exchange tips and tutorials to enhance your skills.
    - **Exclusive Previews**: Get early access to new product announcements and sneak peeks.
    - **Special Discounts**: Enjoy exclusive discounts on our newest products.
    - **Festive Promotions and Giveaways**: Take part in giveaways and holiday promotions.

    👉 Ready to explore and create with us? Click [|link_sf_facebook|] and join today!

.. _1.3.2_c:

1.3.2 Servo
=================

Introduction
--------------

In this project, we will learn how to make the servo rotate.

Required Components
------------------------------

In this project, we need the following components. 

.. image:: ../img/list_1.3.2.png

It's definitely convenient to buy a whole kit, here's the link: 

.. list-table::
    :widths: 20 20 20
    :header-rows: 1

    *   - Name	
        - ITEMS IN THIS KIT
        - LINK
    *   - Raphael Kit
        - 337
        - |link_Raphael_kit|

You can also buy them separately from the links below.

.. list-table::
    :widths: 30 20
    :header-rows: 1

    *   - COMPONENT INTRODUCTION
        - PURCHASE LINK

    *   - :ref:`cpn_gpio_extension_board`
        - |link_gpio_board_buy|
    *   - :ref:`cpn_breadboard`
        - |link_breadboard_buy|
    *   - :ref:`cpn_wires`
        - |link_wires_buy|
    *   - :ref:`cpn_servo`
        - |link_servo_buy|

Schematic Diagram
-----------------

.. image:: ../img/image337.png


Experimental Procedures
-----------------------

**Step 1:** Build the circuit.

.. image:: ../img/image125.png

**Step 2**: Go to the folder of the code.

.. raw:: html

   <run></run>

.. code-block::

    cd ~/raphael-kit/c/1.3.2

**Step 3**: Compile the code.

.. raw:: html

   <run></run>

.. code-block::

    gcc 1.3.2_Servo.c -lwiringPi

**Step 4**: Run the executable file.

.. raw:: html

   <run></run>

.. code-block::

    sudo ./a.out

After the program is executed, the servo will rotate from 
0 degrees to 180 degrees, and then from 180 degrees to 0 degrees, circularly.

.. note::

    If it does not work after running, or there is an error prompt: \"wiringPi.h: No such file or directory\", please refer to :ref:`install_wiringpi`.

**Code**

.. code-block:: c

    #include <wiringPi.h>
    #include <softPwm.h>
    #include <stdio.h>

    #define ServoPin    1       //define the servo to GPIO1
    long Map(long value,long fromLow,long fromHigh,long toLow,long toHigh){
        return (toHigh-toLow)*(value-fromLow) / (fromHigh-fromLow) + toLow;
    }
    void setAngle(int pin, int angle){    //Create a funtion to control the angle of the servo.
        if(angle < 0)
            angle = 0;
        if(angle > 180)
            angle = 180;
        softPwmWrite(pin,Map(angle, 0, 180, 5, 25));   
    } 

    int main(void)
    {
        int i;
        if(wiringPiSetup() == -1){ //when initialize wiring failed,print message to screen
            printf("setup wiringPi failed !");
            return 1; 
        }
        softPwmCreate(ServoPin, 0, 200);       //initialize PMW pin of servo
        while(1){
            for(i=0;i<181;i++){     // Let servo rotate from 0 to 180.            	setAngle(ServoPin,i);
                delay(2);
            }
            delay(1000);
            for(i=181;i>-1;i--){        // Let servo rotate from 180 to 0.            	setAngle(ServoPin,i);
                delay(2);
            }
            delay(1000);
        }
        return 0;
    }

**Code Explanation**

.. code-block:: c

    long Map(long value,long fromLow,long fromHigh,long toLow,long toHigh){
        return (toHigh-toLow)*(value-fromLow) / (fromHigh-fromLow) + toLow;
    }

Create a ``Map()`` function to map value in the following code.

.. code-block:: c

    void setAngle(int pin, int angle){    //Create a funtion to control the angle of the servo.
        if(angle < 0)
            angle = 0;
        if(angle > 180)
            angle = 180;
        softPwmWrite(pin,Map(angle, 0, 180, 5, 25));   
    } 

Create a funtion, ``setAngle()`` to write angle to the servo.

.. code-block:: c

    softPwmWrite(pin,Map(angle,0,180,5,25));  

This function can change the duty cycle of the PWM.

To make the servo rotate to 0 ~ 180 °, the pulse width should change
within the range of 0.5ms ~ 2.5ms when the period is 20ms; in the
function, ``softPwmCreate()`` , we have set that the period is
200x100us=20ms, thus we need to map 0 ~ 180 to 5x100us ~ 25x100us.

The prototype of this function is shown below.

.. code-block::

    int softPwmCreate（int pin，int initialValue，int pwmRange）;

* ``pin``: Any GPIO pin of Raspberry Pi can be set as PWM pin.
* ``initialValue``: The initial pulse width is that initialValue times 100us.
* ``pwmRange``: the period of PWM is that pwmRange times 100us.

Phenomenon Picture
------------------

.. image:: ../img/image126.jpeg

