Introduction: Another Easier Inverted Pendulum Robot
This is an improved version of my earlier instructable titled "A Simple and Very Easy Inverted Pendulum Balancing Robot". There are four advantages in this version.
- Easier to get a material
- Fewer materials needed
- Simpler program to balance itself
- Higher stability in balancing
I have published the original version in English and Japanese. I have gotten a considerable number of successful comments with videos (e.g. 1, 2, 3, 4, 5) to Japanese version but rare to English version. The first and the second points above are based on comments to the original version in English. These two improvements could eliminate a barrier from residents outside Japan. Under the introduction video below, some details for each these four points are described.
:
[Introduction Video]
:
(1) Digital Gyro Sensor
In the original version a gyro module with two analog output sensors (*1) is used. But outside Japan, it is not easy to get it or its equivalent product (*2). In this version a gyro module with a digital output sensor made by STMicroelectronics is used. It is easy to get it or its equivalent product either inside or outside Japan.
(*1) This analog output sensor has no constant value for the output at rest. Hence it is needed to measure the value of output in static state before balancing itself in the original version. But it is not needed in this version.
(*2) The gyro module used in the original version has angular acceleration contamination in angular velocity through its HPF. Therefore a fine soldering is required to cancel this contamination. However, it is not required in this improved version.
:
(2) Single Motor Driver IC
The inverted robot we would make here has two motors. In the original version two ICs drive them respectively. But in this version only an IC drives two motors.
:
(3) No Timer Library in Program
In the original version a timer library, Ms Timer2, is used in program for interrupt handling (*1). In this version no interrupt handling or no timer library is used in program (*2).
(*1) My original project was started with a numerical simulation on PC. The interrupt handling follows it.
(*2) See below.
:
(4) Noise Reduction Step in Program
In program, another revision is made also to reduce noise in output of gyro module (*2).
(*2) An alternative program with these revises was added to my original (earlier) instructable.
:
In following steps I will not avoid the same statements described in the original version to make this instractable a complete one.
* A Japanese version for this instructable is available.
Step 1: Gather Materials
Body (using TAMIYA's Educational Construction Series)
- A Universal Plate Set (2pcs.)
- A Universal Arm Set
- A Double Gearbox (Left/Right Independent 4-Speed, two DC motors included)
- A Slim Tire Set (36mm, 55mm Dia.)
Electrics
- An Arduino UNO
- A small solderless breadboard
- Some jumper wires
- A motor driver IC (STMicroelectoronics L298N)
- A gyro module (Akizuki-denshi AE-L3DG20: sensor L3GD20 on this module)
- Four AA batteries
- A 4AA battery holder
- A 9V battery (PP3)
- Two battery snaps
- Some rubber bands
:
[Tutorial for Step1]
:
[Commentary for Gyro Module]
Here a digital output gyro module is used instead of analog output one. This module is a L3GD20 carrier. The detail of L3GD20 is described subsequently. I have encountered with some troubles below while using it. So I recommend you to get 2 or 3 modules at once to isolate the problem.
:
(1) Inconsistent Sign of Gyro Output
I have tried two gyro modules with same model number alternatively to know individual difference of the module. Both of them are made by Akizuki-Denshi and they are L3GD20 carriers. I was surprised that signs of output of them are different around two axes. Therefore "R + ry" might have to be rewritten to "R - ry" in the line "DL29" in the program in Step 5.
:
(2) Abnormal Output of Gyro
A digital gyro module used here would begin to output strange data for some reason (*1). In that case, try to disconnect power supply to module or Arduino. If that fails, once upload a very simple program with the module to Arduino (*2), and upload the program for an inverted robot again.
(*1) I have seen non-zero value in a still state or constant value in motion, though I do not know the causes of them well.
(*2) The simple program is shown in the pdf file "dgtlGYRO_L3GD20_SPI_recover.pdf" attached to the end of Step 5.
:
(3) Equivalent or Alternative Gyro Module
In this instructable, a digital gyro module AE-L3GD20 made by Akizuki-Denshi is used as a carrier board for the L3GD20 three-axis gyroscope provided STMicroelectronics. It could be replaced by a near-equivalent module "item #: 2125" made by Pololu (*1), which is a carrier for the same gyroscope L3GD20. Outside Japan, it would be easier to get the latter. Pin mapping between each module and Arduino is shown below (*2).
- (Function: Pin of Akizuki's, [Pin of Pololu's], {Pin of Arduino})
- VIN: #1, [VIN], {3.3V}
- GND: #8, [GND], {GND}
- SPC: #2, [SCL], {D13}
- SDI: #3, [SDA], {D11}
- SDO: #4, [SDO], {D12}
- CS: #5, [CS], {D10}
(*1) I have not gotten or tried the Pololu's module. I do not know well the attaching direction of L3GD20 chip to the board of the Pololu's module. In this instructable with Akizuki's module, the angle around Y-axis is measured to balance. But when the Pololu's is used, other axis (X or Z) might be measured or sign of output might be inverted. If such the differences are recognized, the program in Step 5 should be corrected.
(*2) Pololu's module has not only VDD pin but also VIN pin. It is described in its website, "Never supply voltage to VDD when VIN is connected, and never supply more than 3.6 V to VDD".
Step 2: Solder Wires to Some Components
First you should solder wires and pins to some electrical components.
- Solder wire to each point of 2 motors (4 points in all)
- Cut 4 jumper wires in half (8 half jumpers gotten)
- Solder these half jumpers to 8 wires of 2 motors and 2 battery snaps
- Cover each point soldered with chip of tape for insulation
- Solder header pins to an Akizuki's gyro module
:
[Tutorial for Step2]
Step 3: Assemble the Body of Robot
To build the body of inverted robot, TAMIYA's Educational Construction Series are used.
- Make two V-shaped cuts to Universal Plate
- Attach 4 L-angles included in Universal Arm Set to this Plate
- Assemble Double Gearbox to make its gear ratio 114.7:1
- Set 2 motors with 4 wires in this Gearbox
- Attach this Gearbox to Universal Plate above
- Assemble Slim Tire Set (two 55mm Dia. wheels gotten)
- Install these wheels to shafts of Gearbox above
:
[Tutorial for Step3]
Step 4: Put Electrical Components Together
Put electrical components together and attach them to the body built in the former step. Then a robot without program is gotten.
- Referring to Note 1 below, adjust two lines of pins of motor driver IC (L298N) respectively
- Referring to the picture of breadboard above, plug a gyro module and motor driver IC into your breadboard
- Wind some rubber bands around the breadboard and attach it on the lower L-angles of body of robot
- According to a wiring diagram above, plug jumper wires into the breadboard
- Also plug both wires of the battery snap into breadboad, which will be connected to a 4AA battery holder
- Wind a small rubber band around Arduino and mount it on the upper L-angles of the body of robot
- According to a wiring diagram above, plug jumper wires into the pinholes of Arduino
- Insert four AA batteries to 4AA battery holder
- Wind a bigger rubber band around the body of robot and fix the battery holder to the back side of robot
:
[Tutorial for Step4]
:
[Note 1]
L298N should be plug into breadboard straddling over its center ditch. But two lines of pins of this IC are not fitted for this plugging. So we make two adjustments for these pins.
- Shorter pins: Shift the line of shorter pins to backside of IC by 2.5mm (making a wider distance to the line of longer pins)
- Longer pins: Shift the line of longer pins to right-hand side of IC by a little bit
:
[Note 2]
L298N has two pins (#1 and #15) to measure current flowing through each motor respectively. Here no current is measured. So both of them are connected to GND.
:
[Note 3]
The robot gotten here has no power switch. To turn on/off power, battery snap is connected/disconnected.
Step 5: Upload the Sample Sketch to Arduino
Using IDE, the sample Sketch for inverted robot is uploaded to Arduino.
- Connect Arduino to PC via a USB cable
- Disconnect the battery snap from 4AA battery holder
- Lay down robot on desktop or floor and leave it at rest
- Download (*) the pdf file attached to the next to the last line in this step (* You get a corrupted program if you open this file in web browser and copy its content)
- Open the file in proper reader and copy the whole of text in the file
- Paste the copy to IDE and correct misprints
- Upload corrected sketch to Arduino using IDE
:
[note 4]
To make an inverted pendulum balance itself, motor torque is controlled dynamically. This control method is expressed as a plane formula with 4 variables related to the state of pendulum.
"motor torque = k1 * angle of pendulum
+ k2 * angular velocity of pendulum
+ k3 * velocity of the lower end of pendulum
+ k4 * displacement of the lower end of pendulum from a reference point"
k1, k2, k3 and k4 are static coefficients with appropriate values. In a sample sketch in pdf file below, a long equation at line 72 expresses this formula. To make inverted robot balance itself, we have to select proper values for these 4 coefficients respectively and know right value of each of these 4 variables in real time.
The gyro sensor gives the second variable value, angular velocity of pendulum, dynamically by a 16-bit integer. And Arduino estimates the first variable value, angle of pendulum, contemporaneously by integrating the second variable.
On the other hand, the third or the fourth variable value cannot be measured by gyro sensor. So another kind of sensor or meter should be used to get them in real time. But our inverted robot has no more device than a gyro module. Thus it becomes a puzzle to estimate these 2 variables values dynamically. In a sample sketch in pdf file below, 2 masked equations at lines 76 and 77 should be used to estimate them. Here they are left masked not to spoil solving this puzzle.
:
[Note 5]
L3GD20 digital gyro sensor has three different measurement ranges; +/- 250dps, +/- 500dps and +/- 2000dps (dps: Degree per Second). This sensor outputs angular velocity as a 16bit integer. In this instructable the minimum range (+/- 250dps) is adopted, where a digit of output means 0.00875dps.
:
[Note 6]
The output of the gyro sensor is transmitted to Arduino by SPI interface. General technical discussion about SPI or wiring for it is not described here. If the gyro module made by Pololu were used instead of Akizuki’s one, see "(3) Equivalent or Alternative Gyro Module" [in Commentary for Gyro Module] in Step 1. I have not tried Pololu’s module. In the sample program attached to the end of this step, the angle around Y-axis is measured to balance. But when the Pololu's were used, other axis (X or Z) might be measured or sign of output might be inverted. For example, if the posture of robot were detected around X-axis of L3GD20 and sign of output is inverted, the right hand of line DL28 in the sample program should be rewritten “- ( (L3GD20_read(0x29) << 8) | L3GD20_read(0x28) )”.
:
[The Sample sketch (program) for inverted robot]
Copy whole text of "invertedRobot_v20d_noTimer.pdf" below, paste it to IDE and upload it to Arduino (**1-5).
(*1) Save the pdf file in your PC and open it in proper pdf-reader. Or you get a corrupted program by opening it in web-browser.
(*2) If "; //72" is not shown at the end of line 72, substitute whole a equation below for it. It is not the same as the original version.
powerScale = ( kAngle * thetaI / 100 ) + ( kOmega * omegaI / 100 ) + ( kSpeed * vE5 / 1000 ) + ( kDistance * xE5 / 1000 ); //72
(*3) Pasting the copy to IDE or editor, misprints such as "/ /" as "//" (an obstacle space inserted) might happen, then correct them.
(*4) The line number written in the sample sketch as comment (e.g. //DL2) is consistent with the earlier sketch ”invertedRobot.pdf” or ”invertedRobot_v20_noTimer.pdf” in the original version.
(*5) Copyright (C) 2015 ArduinoDeXXX All Rights Reserved.
:
[The sketch to restore L3GD20 carrier gyro module]
If the output of gyro module becomes strange, see "(2) Abnormal Output of Gyro" [in Commentary for Gyro Module] in Step 1. There two countermeasures are shown. The sketch used in the second measure, “dgtlGYRO_L3GD20_SPI_recover.pdf,” is attached to the last line of this step.
Step 6: Get an Inverted Following Robot
When the sample sketch uploaded to Arduino in the former step, you ought to get an inverted following robot. Though it needs your finger for standing, it follows your finger.
- After the upload finished, hold the body of your robot and pick it up (see picture 2)
- Connect battery snap to battery holder attached to the back side of robot
- Wheels of robot start spinning, hold both wheels tight and stop spinning (see picture 3)
- Set both wheels on desktop or floor and keep static standing to be made center of gravity of robot to be located on its wheel shafts
- After a few second, motor torque becomes down and faint noise or chirping "miii" is listened
- Then release your hands from robot gently (see picture 4) and put your finger on the top of the body of robot softly
- Move your finger forward and backward and see your robot following
- Release your finger and see your robot trying to balance but failing
:
[Tutorial for Step5 and 6]
:
[Note 7]
As turning on or resetting Arduino, the robot perceives its posture (angle of its body) and spins its wheels when the posture is changed. Then the robot has to study the proper posture in well inverted state. This robot is programmed that if it has been in static state for 0.05 seconds it deems itself well inverted.
Hence as its wheels starting spinning, you should hold both wheels tight and stop spinning. And execute line 4 to 8 above.
Further if you do not feel changes at line 5, torque down and faint noise of motors, for 10 seconds waiting, your gyro module might output wrong value temporarily or it might be inconsistent with the sample sketch in the former step.
In that case, you should see "(2) Abnormal Output of Gyro" [in Commentary for Gyro Module] in Step 1 first. And if you use some L3GD20 carrier other than Akizuki’s module, you should see "(3) Equivalent or Alternative Gyro Module" in Step 1 and Note 6 in Step 5 also.
:
[Troubleshooting 1]
If wheels of robot do not start spinning at line 3 above, some faulty wiring must be suspected first. Go back Step 4 and verify wiring carefully. Another doubt is a defective gyro module. If you suspect it, you should see "Commentary for Gyro Module" in Step 1.
On the other hand, if your robot does not follow your finger in spite of wheels starting spinning at line 3, three kinds of faulty wiring must be suspected: (1) Wires of a motor are set opposite, (2) Gyro module is set reversed, (3) Wiring to digital pins of Arduino is wrong. Go back Step 4 and verify wiring carefully.
Further if your gyro module outputs inconsistent value with the sample sketch in Step 5, your robot would not follow your finger despite correct wiring. If you suspect it, see "(1) Inconsistent Sign of Gyro Output" in Step 1. And if you use some L3GD20 carrier other than Akizuki’s module, you should see "(3) Equivalent or Alternative Gyro Module" in Step 1 and Note 6 in Step 5 also.
:
[Reference] Checking an Inverted Following Robot
Step 7: Challenge Yourself to Solve a Puzzle
Let's make your "following inversed robot" balance itself without your finger by modifying the sample sketch in Step 5. It might be a puzzle.
- Consider why it fails balancing
- Get plausible idea and modify the sample sketch
- Make your inverted robot try balancing
- If it balances itself you have solved a puzzle and your robot has become an inverted pendulum (Congratulation!)
- Or else turn back to line 1 or hesitate to see a solution in Step 8
Step 8: How to Get an Inverted Balancing Robot
Here you see how to get an inverted balancing robot. You need to modify only two lines in the sample sketch in Step 5.
- Copy 3 lines below and paste them over lines 76 and 77 in the sample sketch (overwriting them)
vE5 = sumPower; //76a
xE5 = sumSumP / 1000; //77a
// Copyright (C) 2014 ArduinoDeXXX All Rights Reserved.
- Execute Step 6 (without a finger support in lines 6 to 8)
- If center of gravity of robot is located on near its wheel shafts, your robot moves back and forward for a few seconds and gets well inverted posture
- See it keeps balancing itself
- If it moves with forward or backward bias, add to or submit from proper integer after "power" at the end of line 74 in the original sample sketch
:
[Tutorial for Step 8]
:
[Troubleshooting 2]
If your robot can not balance itself well in spite of executing Step 6 well, “low battery” in the battery holder on the back of robot should be suspected first. If it is not observed, constant values at lines 10 to 13 in the sample sketch should be changed. I think that line 12 is most critical.
Step 9: Operate Inverted Robot Via Serial Monitor
Now you have an inverted balancing robot. Then let’s control it by serial monitor. You could make it turn right/left and go forward/back.
- Update the modified sample program gotten in Step 8 according to the details below
- Upload the updated one to Arduino using IDE
- After the upload end, start serial monitor from IDE
- Select “Newline” and “115200 baud” at bottom right of serial monitor
- Make inverted robot balance itself according to Step 6 (without a finger support in lines 6 to 8)
- Input numerical values in upper left window of serial monitor and push the [Enter] key
- See action or change of action of your robot
:
[Tutorial for Step 9]
:
[Note 8]
You can control your robot dynamically by serial monitor from PC via USB cable. For example you input "00" in window of serial monitor and push the [Enter] key, then robot receive ‘0’ and ‘0’ separately. Hence it turns right at a regular angle below twice without stopping.
- A ‘0’ sent makes robot turn right at a regular angle on the spot
- A ‘1’ sent makes robot turn left at a regular angle on the spot
- A number (n) of ‘2’ sent make robot accelerate forward in proportion to the number (n)
- A number (n) of ‘3’ sent make robot accelerate backward in proportion to the number (n)
:
[Update on the sample sketch (for 4 places)]
(1) Copy the following 5 lines and paste them between lines 17 and 18 in the modified sketch gotten in Step 8.
int drct = 0;
boolean right = false;
boolean left = false;
int fwdBck = 0;
// Copyright (C) 2014 ArduinoDeXXX All Rights Reserved.
(2) Copy the following 26 lines and paste them over line 32 in the modified sketch gotten in Step 8, viz. substitute these lines for “if ( power > 0 ) {”.
if ( Serial.available() ) {
drct = Serial.read();
Serial.println(drct);
}
if( drct == 48 ) { right = true; }
else if ( drct == 49 ) { left = true; }
else if (drct == 50 ) { fwdBck++; drct = 0; }
else if (drct == 51 ) { fwdBck--; drct = 0; }
if ( right == true ) {
analogWrite( 6, 140 );
digitalWrite( 4, HIGH );
digitalWrite( 5, LOW );
analogWrite( 9, 140 );
digitalWrite( 7, LOW );
digitalWrite( 8, HIGH );
delay(40);
} else if ( left == true ) {
analogWrite( 6, 140 );
digitalWrite( 4, LOW );
digitalWrite( 5, HIGH );
analogWrite( 9, 140 );
digitalWrite( 7, HIGH );
digitalWrite( 8, LOW );
delay(40);
} else if ( power > 0 ) {
// Copyright (C) 2014 ArduinoDeXXX All Rights Reserved.
(3) Copy the following 4 lines and paste them between lines 55 and DL26 in the modified sketch gotten in Step 8.
drct = 0;
right = false;
left = false;
// Copyright (C) 2014 ArduinoDeXXX All Rights Reserved.
(4) Copy the following 2 lines and paste them over line 74 in the modified sketch gotten in Step 8, viz. substitute these lines for “sumPower = sumPower + power;”.
sumPower = sumPower + power + fwdBck * 4; // 74a
// Copyright (C) 2014 ArduinoDeXXX All Rights Reserved.
Step 10: Unplug the Cable
Substitute a battery (9V) for USB power (5V) for power supply to Arduino. Then Arduino is unplugged and your robot stands with no outer wire.
- Eject a USB cable from Arduino
- Connect the second battery snap to a battery (9V)
- Attach the battery to the back of robot by rubber band with a battery holder
- Plug the positive wire of this snap to Vin pin of Arduino
- Plug the negative wire of this snap to GND pin of Arduino
- Your robot starts spinning its wheels if the first snap is connected to battery holder
- Make your robot balance itself according to Step 6 (without a finger support in lines 6 to 8)
- See it stands with no outer wire as a completed inverted pendulum
:
[Tutorial for Step 10]
Step 11: Develop Robot Further
Let’s make your inverted robot or your knowledge evolve further. Here three ways are shown briefly. It would be hard to finish them within half a day.
:
(1) Remote Operation with No Wire
In Step 9 your robot is operated via USB cable. Now your robot is unplugged. So let’s operate it with no wire. In terms of simplicity, an infrared module would be the first choice.
:
[Demonstration of Operating Robot by a TV Remote]
:
(2) Simulating the Action of an Inverted Robot with Excel
Our inverted robot could be thought constructed from three parts: head, body and wheels. In this simplifying, an equation of motion of the robot can be written with a physics learned at High School. As getting it, the action of robot can be simulated using Excel. The near-proper values of two coefficients in Note 4 in Step 5, k1 and k2, could be gotten by this simulation.
:
(3) Capturing and Analyzing the Real Action of Inverted Robot
We can capture the state variables – posture and motion – of our robot in balancing. And it is possible to duplicate it on PC monitor in real time as a virtual 2D animation of balancing robot. Moreover, we can examine the effect of the sketch in detail by analyzing the time series of recorded state variables. An instructable in Japanese has been published, in which these capturing, duplicating and analyzing are described.
:
[Real Time 2D Animation by State Capturing]