Overview
In this post we will learn how to Measure Tilt Angle using MPU6050 & Arduino. This can be done by simply interfacing MPU6050 6 axis Gyro/Accelerometer Sensor. The Accelerometer sends X, Y, and Z acceleration forces. We need to convert the forces into X, Y, Z 3D angle to determine the 3D Orientation of the sensor.
The gyroscope measures rotational velocity or rate of change of the angular position over time, along the X, Y, and Z-axis. It uses MEMS technology and the Coriolis Effect for measuring. The outputs of the gyroscope are in degrees per second, so in order to get the angular position, we just need to integrate the angular velocity.
The accelerometer can measure gravitational acceleration along the 3 axes and using some trigonometry math we can calculate the angle at which the sensor is positioned. So, if we fuse, or combine the MPU6050 accelerometer and gyroscope data we can get very accurate information about the sensor orientation. Hence MPU6050 with Arduino can measure tilt angle.
Check this post:
1. Interfacing MPU6050 Accelerometer & Gyroscope with Arduino
2. DC Motor Control using MPU6050 Gyro/Accelerometer Sensor & Arduino
3. ESP8266 & MPU6050 Tilt Angle Monitor on IoT Blynk
Components Required
|
1 2 3 4 |
1. Arduino Board 2. MPU6050 Gyro/Accelerometer Sensor 3. Breadboard 4. Connecting Wires |
MPU6050 Gyro/Accelerometer Sensor
Introduction:
The InvenSense MPU-6050 sensor contains a MEMS accelerometer and a MEMS gyro in a single chip. It is very accurate, as it contains a 16-bits analog to digital conversion hardware for each channel. Therefor it captures the x, y, and z channel at the same time. The sensor uses the I2C-bus to interface with the Arduino.
The MPU-6050 is not expensive, especially given the fact that it combines both an accelerometer and a gyro.
MPU6050 Pinout:
The MPU-6050 module has 8 pins:
INT: Interrupt digital output pin.
AD0: I2C Slave Address LSB pin. This is the 0th bit in the 7-bit slave address of the device. If connected to VCC then it is read as logic one and slave address changes.
XCL: Auxiliary Serial Clock pin. This pin is used to connect other I2C interface enabled sensors SCL pin to MPU-6050.
XDA: Auxiliary Serial Data pin. This pin is used to connect other I2C interface enabled sensors SDA pin to MPU-6050.
SCL: Serial Clock pin. Connect this pin to the microcontrollers SCL pin.
SDA: Serial Data pin. Connect this pin to the microcontrollers SDA pin.
GND: Ground pin. Connect this pin to the ground connection.
VCC: Power supply pin. Connect this pin to +5V DC supply.
3-Axis Gyroscope:
The MPU6050 consists of a 3-axis Gyroscope with Micro Electro Mechanical System(MEMS) technology. It is used to detect rotational velocity along the X, Y, Z axes as shown in the below figure.
3-Axis Accelerometer:
The MPU6050 consist of 3-axis Accelerometer with Micro Electro Mechanical (MEMs) technology. It used to detect the angle of tilt or inclination along the X, Y, and Z axes as shown in the below figure.
Circuit Diagram & Connection
MPU6050 has I2C Pins. So it needs to be connected to I2C pins of Arduino. So connect SDA pins of MPU6050 to A4 of Arduino and SCL to A5. Supply a 5V input to MPU6050 and also connect the GND as shown in the figure below.
Source Code/Program
Below is the code to measure the tilt angle using MPU6050 & Arduino. Copy the code and upload it to the Arduino board.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 |
#include<Wire.h> const int MPU_addr=0x68; int16_t AcX,AcY,AcZ,Tmp,GyX,GyY,GyZ; int minVal=265; int maxVal=402; double x; double y; double z; void setup(){ Wire.begin(); Wire.beginTransmission(MPU_addr); Wire.write(0x6B); Wire.write(0); Wire.endTransmission(true); Serial.begin(9600); } void loop(){ Wire.beginTransmission(MPU_addr); Wire.write(0x3B); Wire.endTransmission(false); Wire.requestFrom(MPU_addr,14,true); AcX=Wire.read()<<8|Wire.read(); AcY=Wire.read()<<8|Wire.read(); AcZ=Wire.read()<<8|Wire.read(); int xAng = map(AcX,minVal,maxVal,-90,90); int yAng = map(AcY,minVal,maxVal,-90,90); int zAng = map(AcZ,minVal,maxVal,-90,90); x= RAD_TO_DEG * (atan2(-yAng, -zAng)+PI); y= RAD_TO_DEG * (atan2(-xAng, -zAng)+PI); z= RAD_TO_DEG * (atan2(-yAng, -xAng)+PI); Serial.print("AngleX= "); Serial.println(x); Serial.print("AngleY= "); Serial.println(y); Serial.print("AngleZ= "); Serial.println(z); Serial.println("-----------------------------------------"); delay(400); } |
Output/Results
So once the code is uploaded, you can click on the serial monitor to check the outputs. You need to tilt the MPU6050 Gyro/Accelerometer to detect the angular position of X, Y & Z-axis.
You can check this project as well: Measure Tilt Angle with MPU6050 & STM32 Microcontroller












13 Comments
why we use this boundary value
int minVal=265;
int maxVal=402;
Can you mount the sensor anyway you want (likevertically) or does it have to be a default orientation?
Thanks
Have run the code successfully
Now I want to find the max and min tilt angle for repeated movements
I can find tilt max using an ‘IF’ loop but it only provides max value not repeated max values
tilt[i]=x; // create a ’tilt’ array
if (tilt[i] > tiltmax) // check if tilt array value from the calculated X degrees is increasing
tiltmax = tilt[i]; // if increasing assign the new value to tiltmax
then print tiltmax. But it all stops when I use :
if (tilt[i] < tiltmax) // if tilt array value is dereasing then print the value
tiltmaxx = tilt[i];
then print tiltmaxx
Also the tilt array tilt[i] from a ‘FOR’ loop
for (int i=0; i
Hello, I am trying to write a ‘if’ statement to activate led and buzzer at 180deg , 50 deg, ? In that order , I would grateful if you could help
Thank you
Robin
Hi Robin
I have been struggling with max and min values and working with if statements
So in my experience the IF statement you might be able to use :
if ( x = 180 ){
// activate the pins for the LED and the buzzer
}
if ( x = 50 ){
// activate the pins for the LED and the buzzer
}
This still might not give you the correct order –
if it’s on a reducing angle after an increasing angle then you can add :
x = current_angle;
if ( current_angle < previous _angle && x = 180 ){
// pins high
}
if ( current_angle < previous_angle && x = 50 ){
//pins high
}
previous_angle = current_angle;
}
I am still very new to coding so unless I run the code with the prototype hardware (set-up) I will not see if I have made a mistake
BW
Charles
Do you have any other pictures of the completed bread board? The layout of your jumper wires is not easily comprehendable. I’m trying to recreate this exact project but i KNOW i don’t have the jumper wires connected correctly. PLEASE HELP WITH MORE PICTURES!
H i want to built a tilt alarm for a car and use this code how would i do this as if the car was parked on a hill it would go off i need it to accept the incline of the hill while parked up thank you for any help with this project
Doesn’t work for me; I get this kind of readings no matter the position of the MPU6050; I modified the code to print the raw data for x, y, z:
RawRead x:-17188 y:-2108 z:-26186
AngleX= 354.04
AngleY= 323.13
AngleZ= 187.93
RawRead x:-17212 y:-2134 z:-26200
AngleX= 353.97
AngleY= 323.08
AngleZ= 188.00
RawRead x:-17190 y:-2096 z:-26188
AngleX= 354.06
AngleY= 323.12
AngleZ= 187.89
RawRead x:-17176 y:-2152 z:-26198
AngleX= 353.92
AngleY= 323.13
AngleZ= 188.08
RawRead x:-17138 y:-2108 z:-26152
AngleX= 354.04
AngleY= 323.25
AngleZ= 187.95
Doesn’t work for me; I get this kind of readings no matter the position of the MPU6050; I modified the code to print the raw data for x, y, z:
RawRead x:-17188 y:-2108 z:-26186
AngleX= 354.04
AngleY= 323.13
AngleZ= 187.93
RawRead x:-17212 y:-2134 z:-26200
AngleX= 353.97
AngleY= 323.08
AngleZ= 188.00
RawRead x:-17190 y:-2096 z:-26188
AngleX= 354.06
AngleY= 323.12
AngleZ= 187.89
RawRead x:-17176 y:-2152 z:-26198
AngleX= 353.92
AngleY= 323.13
AngleZ= 188.08
RawRead x:-17138 y:-2108 z:-26152
AngleX= 354.04
AngleY= 323.25
AngleZ= 187.95
You are calculating the tilt using only the Accelerator data but I don’t see where you are using the Gyroscope data, am I missing anything?
you can calculate angles about x and y axis only using above data but, not angle about z axis.
thanks heaps – I assume you need to calibrate this initially if measuring tilt (atitude) so horitontal is 0 degrees? If yes, how long will it remain calibrated for? Do you need to have a user interface or an approach so that it will “calibrate” each time the device is started, so that horitonal will be 0 degress?
This code uses only an accelerometer; there is no data fusion here, although the post stated, “So, if we fuse, or combine the MPU6050 accelerometer and gyroscope data, we can get very accurate information about the sensor orientation.” This is very misleading.