Tuesday, February 9, 2016

How do accelerometer and gyroscope work - an example with MPU6050 and raspberry pi

MPU6050 provides an affordable option for providing accelerometer and gyroscope data for DIY electronics.

1) how does an electronic accelerometer work? The common one is based on piezoelectric effect: this type of material generates a voltage when being applied pressure. Imagine a small mass in the middle of the device. According to Newton's second law F= m a, if there is a finite acceleration a, it will press on the contact piezoelectric material and generate an electric signal. The acceleration is a vector, which has x, y, z components. If you suddenly move the device, generating an acceleration, this will be picked up by accelerometer. But remember, if the device is moving at a constant velocity, this does not have a finite acceleration.  Naturally, there is gravity, or acceleration is g. This will be always picked up by the accelerometer. So, accelerometer measures accelerations (in unit of meter/second^2 or g).

2) how to interpret the MPU6050 accelerometer data? MPU6050 provides acceleration data in x, y, z directions (0x3b, 3d, 3f). Each data has two bytes, or range from [-32768, +32767], which can be calibrated in units of +- 2, 4, 8, 16g.
Let's say the default setting 2g, if MPU6050 is laying flat on a surface, a_x=a_y=0. a_z = g. You should get a reading of a_x=a_y=0, a_z = 16384.

3) how to use the accelerometer data to identify the orientation of the device? Let's start with xy in horizontal plane. The simplest case is to tilt an angle theta along x-axis (x remains horizontal, yz are tilted). Here, the gravity is no longer points to z direction, but certain direction in yz plane. A little trigonometry, a_z = g cos(theta), a_y= g sin(theta), and therefore theta = atan(a_y/a_z).  So we can use a_y and a_z reading to determine the tilt angle from vertical direction. A generic case is to tilt along an arbitrary axis in xy plane. Still, a_z = g cos(theta), sqrt(a_x^2 + a_y^2) = g sin(theta), we have theta = atan(sqrt(a_x^2+a_y^2)/a_z).
In real applications, say an accelerometer in a cell phone or Pad, the chip plane is aligned with LCD monitor (z is perpendicular to LCD), assume x is pointing up in landscape. We can use the following criterion to decide the orientation:
a_x > 0.5g AND |a_y|<0.4g AND |a_z| < 0.4g: pointing up
a_x < -0.5g AND |a_y|<0.4g AND |a_z| < 0.4g: pointing down
a_y < -0.5g AND |a_x|<0 .4g AND |a_z| < 0.4g: left portrait
a_y > 0.5g AND |a_x|<0 .4g AND |a_z|<0.4g portrait right
4) how to determine yaw, pitch, roll? Let me assume roll is an angle to rotate along the airplane direction from head to tail (x-axis), pitch is an angle to rotate along the wing-wing direction(y-axis), yaw is to rotate along the z-axis perpendicular to the airplane. Strictly speaking, pitch, roll, yaw are impossible to determine from accelerometer data due to the order of these rotations are performed. To simplify, let's just do one rotation. For example, for pitch (theta) , if y-axis is horizontal, pitch = atan(a_x/a_z). If we add a roll (phi), a_x = g sin(theta) (still), a_z = g cos(theta) cos(phi), a_y = g cos(theta) sin(phi). So, we estimate pitch(theta) = atan(a_x/ sqrt(a_y^2+a_z^2)).  roll (phi) in this case is atan(a_y/a_z).  Let's say, if we do roll phi first, a_z = g cos(phi), a_y = g sin(phi), and do a pitch theta, a_z=gcos(phi) cos(theta), a_x = g cos(phi)sin(theta). The pitch theta = atan(a_y/a_z) and roll phi = atan(a_y/sqrt(a_x^2+a_y^2). So people normally use atan(a_y/sqrt(a_x^2+a_z^2)) to estimate roll and ... for pitch. It is just an estimation and only applies to small angle. Also, yaw is not really captured by accelerometer. Instead, we use magnetometer(compass) or gyroscope.

5) how does an electronic gyroscope work? MPU6050 uses a MEMS gyroscope. It uses the Coriolis effect, i.e. F= -2 m Omega x V, where F omega V are vectors. The idea is to drive the mass moving along one direction (say x), if there is an angular velocity omega along z direction, a force is generated along y direction, which again can be picked by piezoelectric device.  

6) how to interpret gyroscopic data? So, gyroscope measures the angular velocity, or omega, in unit of degree/second or rad/second). It is also a vector, whose xyz components are the rate change of roll,pitch,yaw angles. The latter are obtained through proper integration. MPU6050 again uses two bytes for each component, or range from [-32768, +32767]. It can be programmed to scale as +-250, 500, 1000, 2000 degrees per second. For the default setting 250 deg/s, 32767/250 ~ 131, and for a reading g_x, the angular speed is g_x*250/32767 or gx/131 deg/s. For example, if the device rotates once in 2 seconds, or 180 deg/s, the reading is 180*131~23600.

7) how to combine accelerometer and gyroscopic data to get a better angle information? Accelerometer has a problem with noisy small-amplitude signals. MEMS gyro has the problem with drifting. A better solution is to combine them
angle = percentage x angle_by_gyro + (1-percentage) x angle_by_accel.
Notice yaw cannot be obtained by accelerometer, but can be done by compass. Also, certain filters can be used to filter out the noisy signals. So, consider to buy an additional magnetometer, or IMU with accel+gyro+compass.

8) programming, there are many excellent resources, such as http://www.invensense.com/products/motion-tracking/6-axis/mpu-6050/ (check the register maps), i2cdevlib.