Lesson 3: Sensing the Spin
CanSat NeXT has two sensor ICs on the CanSat NeXT board. One of them is the barometer we used in the last lesson, and the other one is inertial measurement unit LSM6DS3. The LSM6DS3 is a 6-axis IMU, which means that it is able to perform 6 different measurements. In this case, it is linear acceleration on three axis (x, y, z) and angular velocity on three axis.
In this lesson, we will look at the IMU example in the library, and also use the IMU to do a small experiment.
Library Example
Let's start by looking at how the library example works. Load it from File -> Examples -> CanSat NeXT -> IMU.
The initial setup is again the same - include the library, initialize serial and CanSat. So, let's focus on the loop. However, the loop also looks really familiar! We read the values just like in the last lesson, only this time there are many more of them.
float ax = readAccelX();
float ay = readAccelY();
float az = readAccelZ();
float gx = readGyroX();
float gy = readGyroY();
float gz = readGyroZ();
Each axis is actually read some hundreds of microseconds apart. If you need them to be updated simultaneously, check out the functions readAcceleration and readGyro.
After reading the values, we can print them as usually. This could be done using Serial.print and println just like in the last lesson, but this example shows an alternative way to print the data, with much less manual writing.
First, a buffer of 128 chars is created. Then this is first initialized so that each value is 0, using memset. After this, the values are written to the buffer using snprintf()
, which is a function that can be used to write strings with a specified format. Finally, this is just printed with Serial.println()
.
char report[128];
memset(report, 0, sizeof(report));
snprintf(report, sizeof(report), "A: %4.2f %4.2f %4.2f G: %4.2f %4.2f %4.2f",
ax, ay, az, gx, gy, gz);
Serial.println(report);
If the above feels confusing, you can just use the more familiar style using print and println. However, this gets a bit annoying when there are many values to print.
Serial.print("Ax:");
Serial.println(ay);
// etc
Finally, there is again a short delay before starting the loop again. This is mainly there to ensure that the output is readable - without a delay the numbers would be changing so fast that it is hard to read them.
The acceleration is read in Gs, or multiples of . The angular velocity is in units of .
Try to identify the axis based on the readings!
Free Fall detection
As an exercise, let's try to detect if the device is in free fall. The idea is that we would throw the board in the air, CanSat NeXT would detect the free fall and turn the LED on for couple of seconds after detecting a free fall event, so that we can tell that our check had triggered even after again catching it.
We can keep the setup just like it was, and just focus on the loop. Let's clear the old loop function, and start fresh. Just for fun, let's read the data using the alternative method.
float ax, ay, az;
readAcceleration(ax, ay, az);
Let's define free fall as an event when the total acceleration is below a treshold value. We can calculate the total acceleration from the individual axis as