Arduino library · Sensors

MPU6050_light: angles, offsets and a status code

MPU6050_light by Romain Fetick turns an MPU-6050 into three angles in degrees with a complementary filter inside update(). It adds a few things that make faults easier to see: begin() returns 0 when the chip acknowledged and the I2C error code when it did not, the gyro and accelerometer ranges can be chosen, and the accelerometer can be calibrated alongside the gyro.

Built in on Mokxi: #include <MPU6050_light.h> and it builds, with nothing to install. Free, and no account needed.

What MPU6050_light does

calcOffsets() averages 500 readings with the sensor at rest. With no arguments it calibrates both, and it assumes the board is lying flat, so whatever tilt it has at that moment becomes level. That suits a robot that always starts flat and misleads one that does not. The example below starts the part pitched 30 degrees and calls calcOffsets(true, false), calibrating only the gyro, so the angle reads 30 rather than 0.

Units are plain: accelerations in g, rates in degrees a second, angles in degrees. The filter gives the gyro 0.98 unless setFilterGyroCoef() changes it. Like the tockn library, the class is called MPU6050, so it cannot share a sketch with another MPU6050 driver. In Mokxi, tilt the mpu6050 part and the printed angles move with it.

Library Manager nameMPU6050_light
AuthorRomain Fetick
Include#include <MPU6050_light.h>
Boardsevery board Mokxi compiles for but ATtiny85
In the simulatorSimulated: it runs against the part the way it does on the bench.
Parts it drivesAccelerometer and gyroscope, MPU6050

Install it

It builds on every board Mokxi compiles for but ATtiny85.

In Mokxi it is built in: #include <MPU6050_light.h> and the sketch compiles, with no download, no zip and no Library Manager.

On a real board, install "MPU6050_light" by Romain Fetick from the Arduino IDE’s Library Manager (Sketch, Include Library, Manage Libraries), or add MPU6050_light to lib_deps in PlatformIO. Mokxi follows the calls of release 1.2.1, so a sketch written here builds there too.

The calls you will use

In the order a sketch meets them.

MPU6050 mpu(Wire)

Creates the driver on a TwoWire bus. The address is 0x68 unless setAddress() changes it.

byte status = mpu.begin()

Configures and wakes the chip and returns 0 on success. begin(1, 0), the default, means ±500 °/s and ±2 g; each number runs 0 to 3 for the four ranges.

mpu.calcOffsets(true, false)

Averages 500 still readings into the gyro offsets only. calcOffsets() with no arguments also zeroes the accelerometer, which assumes the board is flat.

mpu.update()

Reads the sensor and moves the filter one step. Call it on every pass of loop().

mpu.getAngleX()

The filtered angle about X in degrees; getAngleY() and getAngleZ() for the others, Z from the gyro alone.

mpu.setFilterGyroCoef(0.95)

How much the filter trusts the integrated gyro on each step. getFilterGyroCoef() reads it, and setFilterAccCoef() sets the other side of the same split.

mpu.getAccX()

Acceleration on X in g after the offsets; getGyroX() is the rate in degrees a second.

mpu.upsideDownMounting(true)

For a sensor mounted chip side down, so calcOffsets() expects -1 g on Z instead of +1 g.

mpu.setAddress(0x69)

Talks to a module with AD0 pulled high. Call it before begin().

Example: Tilt angles with MPU6050_light

On the Arduino Uno R3. It runs in the browser exactly as printed.

sketch.ino · Arduino Uno R3
#include "Wire.h"
#include <MPU6050_light.h>

MPU6050 mpu(Wire);
unsigned long timer = 0;

void setup() {
  Serial.begin(9600);
  Wire.begin();
  byte status = mpu.begin();
  Serial.print(F("MPU6050 status: "));
  Serial.println(status);
  while (status != 0) {}
  Serial.println(F("Calculating offsets, do not move MPU6050"));
  mpu.calcOffsets(true, false);   // the gyro only: the board starts tilted
  Serial.println("Done!");
}

void loop() {
  mpu.update();
  if ((millis() - timer) > 300) {
    Serial.print("X : ");
    Serial.print(mpu.getAngleX());
    Serial.print("\tY : ");
    Serial.println(mpu.getAngleY());
    timer = millis();
  }
}

Wiring

  • Arduino Uno R3 A4 to Accelerometer and gyroscope, MPU6050 SDA
  • Arduino Uno R3 A5 to Accelerometer and gyroscope, MPU6050 SCL
  • Arduino Uno R3 5V to Accelerometer and gyroscope, MPU6050 VCC
  • Arduino Uno R3 GND to Accelerometer and gyroscope, MPU6050 GND

Open it in the editor, wired and ready to run

Common errors and how to fix them

MPU6050 status: 2, and the sketch stops there

begin() returned the Wire error for an address nobody acknowledged. Check the bus wiring and the address: 0x68 by default, 0x69 when AD0 is high, which needs setAddress(0x69).

The angle reads 0 although the board is plainly tilted

calcOffsets() with no arguments zeroed the accelerometer while it was tilted, so that tilt became level. Calibrate only the gyro with calcOffsets(true, false), or start with the board flat.

The angle lags fast moves, or shakes with vibration

Tune the filter: a coefficient near 0.99 smooths vibration, one near 0.9 pulls toward the accelerometer faster. Also keep update() on every pass rather than after a long delay().

Questions and answers

Why does the example wait for status to be 0?

A nonzero status means the chip did not acknowledge, and every angle after that would be meaningless. The while loop holds the sketch so the status line stays on screen.

Is MPU6050_light the same as MPU6050_tockn?

Same idea, different details: this one reports a status from begin(), lets you pick ranges and calibrate the accelerometer, and averages 500 samples instead of 3000.

Try MPU6050_light without installing anything

Open the example, change the sketch, and keep your version in a free account.