Nuvoton Project: Numaker-PFM-M487 with Servo

Introduction
Hi, this is David Tseng of CAVEDU Education. This is the forth article of Nuvoton Numaker-PFM-M487. We’ve covered the introduction of this board and show you how to access common electrical components such as LED and button. If you are not familiar with M487 yet, please refer to the previous articles to grasp a basic understanding:
- All-in-one and Cloud-Supported Maker Solution: Nuvoton
- Nuvoton Project: RGB LED and Fading Effect
- Nuvoton Project: Analog Input with Potentiometer
In this topic, we are going to play with a common actuator, servo. This small motor can rotate precisely in limited range. You can use servos to achieve door lock or waving robot hands into your M487 projects. Considering of the purchase price, we will use a cheap servo, SG90 micro servo in this topic, you can of course use other servo like MG996R for better payload and control.
Hardware setup
This section will show you how to finish this example step by step with ARM mbed OS, let’s begin!
1. Get the parts ready
Prepare the parts below:
- NuMaker-PFM-M487 dev board, 1
- SG90 servo, 1
- Male-male jumper, 3
- PC (with Windows OS) with network connection to access mbed OS online IDE, 1
2. Driver setup
Refer to the M487 page or our previous example to setup the driver on your system. If everything is correct, your m487 will be recognized by your OS as a disk named as NuMicro MCU.
3. Quick introduction of servo
Unlike DC motors, servo allows for precise control of its position and speed. A servo consists of a motor coupled to a position sensor (or encoder) therefore it is recognized as a closed-loop control system.
A servo usually comes as with a 3-wire set while the wire colors are strongly self-explained. However, from my sg90, the wires are:
- red is for positive (Vcc).
- black (or the darkest color) is for negative (GND)
- the last one is for signal while it may have various color.
And for easier coupled with other material such as sticks or Lego parts, the servo often has servo horn of different shape as shown below:
For most servos, they can achieve precise positional control within a limited range like 0 to 180 degrees while other may have different control ranges. Although you an acquire a continuous rotation servo, but it is used in special scenario since its positional feedback is no longer available. You can see the servo is at its 0-degree position and 180-degree position in the below images:
4. Connect the SG90 servo to your M487
M487 provides Arduino UNO compatible interface, please refer to M487 page for detailed pin information. We use the Arduino pin D3 on the M487 board, which should be noticed that the pin you used should support PWM (Pulse-Width-Modulation). We use this pin to control the servo position with pulses of different width. For most RC servos, a 1500 µs pulse will make it go to the 90° position (or so-called neutral position).
To connect the sg90 servo to your M487, we use three male/male jumper wires to connect directly, as shown in below:
EX01 – servo sweep
If you had finished the previous LED example, your mbed console should already have the M487. If not, please refer to the previous article to finish the setup process.
Please follow the steps below to finish your first C++ example on the MBED OS website.
Step1:
Visit the MBED OS website, login with your account.
Step2:
After logged in, click the upper-right [Compiler] icon to enter the online compiler interface. Your NuMaker-PFM-M487 board should be there already, click the board to check all the details.
Step3:
In the M487 page, you can find the detailed information of this board and many starter examples from the right-hand side column.
Step4:
If you have not added M487 into your Mbed Compiler, click the [Add to you Mbed Compiler] to add this board into your compiler.
Step5:
Back to your compiler page, you can see the [NuMaker-PFM-M487] icon. Click [New] on the left-top menu and select [NuMaker-mbed-PWM1_DCservo] in the Template dropdown menu. This will import the example into your compiler directly. Click the link above for the quick review of this project.
Click to open main.cpp :
NuMaker-mbed-PWM1_DCservo / main.cpp
// NuMaker-PFM-NUC472 : PWM1 output to drive DC servo motor #include "mbed.h" /* NOTE: Most targets has UNO D3 for PWM. Check it for supporting new targets */ PwmOut pwm1(D3); int main() { Thread::wait(5000); int i=0; printf("...DCserv Start...\n\r"); #ifdef MBED_MAJOR_VERSION printf("Mbed OS version %d.%d.%d\r\n\n", MBED_MAJOR_VERSION, MBED_MINOR_VERSION, MBED_PATCH_VERSION); #endif pwm1.period_us(20000); // set PWM period to 20ms (50Hz) for (i=500; i<=2500; i=i+200) { // from 0.5ms to 2.5ms pwm1.pulsewidth_us(i); // set PWM pulse width to rotate motor #if MBED_MAJOR_VERSION >= 6 ThisThread::sleep_for(1000); #else Thread::wait(1000); // delay #endif printf("DCservo pulse width = %d\n\r", i); } printf("...DCserv End.....\n\r"); }
In the main.cpp, first we declare D3 as a PwmOut. and in the for loop, we increase the pulse width from 0.5 ms (500 µs) to 2.5 ms (2,500 µs) every one second by calling pwm1.pulsewidth_us(i). You can check the serial output for the related messages.
Step6:
Click the [Compile] icon to compile this project. After that, the compiled file will be downloaded to your PC as .bin extension. For our LED example, it should be “NuMaker-mbed-GPIO-button-buzzer-rgbled.NUMAKER_PFM_M487.bin” or other file name you’d like to have.
Step7 – play!
Drag the .bin file into the “NuMicro-MCU” disk drive and the servo should start rotating from one side to the other side after a few seconds.
Notice: DO NOT rotate the servo horn while the programing is running and the servo is still powered. You may damage the grearbox inside the servo!
EX02
You can also try to control the servo with the mbed cookbook example. Create a new project and enter the content in the main.cpp. This example will make the servo sweeping continuously.
NuMaker-mbed-PWM1_DCservo_new / main.cpp
// NuMaker-PFM-NUC472 : PWM1 output to drive DC servo motor #include "mbed.h" #include "Servo.h" Servo myservo(D3); int main() { for(float p=0; p<1.0; p += 0.1) { myservo = p; wait(0.2); } }
Challenge in 5 minutes
1. Modify EX02, try to control the servo position by rotating the potentiometer.
More examples you can try
● AudioPlayback
● AWS IoT
More info
● https://www.nuvoton.com/products/microcontrollers/arm-cortex-m4-mcus/m487-ethernet-series/?tab=4
● https://docs.aws.amazon.com/zh_tw/freertos/latest/userguide/getting-started-nuvoton-m487.html
Author
Dr. David Tseng, CAVEDU Education, MIT CSAIL Visiting Scientist.