# Values from BNO055 are drifting when measuring for a longer period of time (IMU)

#### anziboy

Joined Mar 25, 2019
4
Hello, I am a master thesis student at LTH who is currently working on creating a prototype which can measure the human knee joint angle for 24 hours. I am using two BNO055 sensors which are placed on the shank and thigh.

I get the quaternion values and find the absolute value from both in which i get the angle value. I tried running some measurements on humans and they seem to be really fine, however, when i do the measurements for a longer period of time (for example more than 20 minutes), my readings get drifted. Now my guess is that the drifting is coming from the gyroscope. I tried the different operational modes : IMUPLUS, NDOF in which i can measure the relative angle and absolute angle. Both are giving me the same error. When measure for a short period of time, it does not seem to be any problem.
I will post some screenshots where you can see how my drift values look (x-axis is time in seconds since arduino started, and y-axis the knee joint angle)

Now I am wondering if you can help me with that. What operational mode do you think i should try? I tried IMU and NDOF, but they both seem to be giving me the same error for a longer period of time.

I also tried placing the sensors in a stationary position for 30 minutes and they did not seem to get any drifting problems. I just get that once i start walking around with the sensors.

Any help or tips would be really appreciated! Thank you! I will also post my arduino code.

best wishes,
Anza

Code:
Adafruit_BNO055 bno = Adafruit_BNO055(55, BNO055_ADDRESS_A);
SdFat SD;
//SdFile myFile;
File myFile;
unsigned long id = 1;
const int chipSelect = SS;
#define SD_CS_PIN SS
unsigned long time;
long timeInterval = 10000;
long previousTime = 0;
const int buttonPin = 9;
int buttonState = 0;
long previousMillis = 0;
unsigned long StartTime = millis();
int LED = 6;
const uint8_t BASE_NAME_SIZE = sizeof(FILE_BASE_NAME) -1;
char fileName[] = FILE_BASE_NAME "00.txt";

void setup(void)
{
//115200
Serial.begin(115200);
Serial.println(F("Relative angle measurement")); Serial.println("");
Serial.print(F("Initializing SD card..."));

/* Initialise the sensor */
if(!bno.begin())
{
/* There was a problem detecting the BNO055 ... check your connections */
while(1);
}

if(!bno1.begin())
{
/* There was a problem detecting the BNO055 ... check your connections */
Serial.print(F("Ooops, no BNO055 second detected ... Check your wiring or I2C ADDR!"));
while(1);
}

pinMode(SS, OUTPUT);
//  if (!SD.begin(10)) {
//    Serial.println("initialization failed, program stopped!");
//    exit(0);
//SD.begin(SD_CS_PIN, SPI_FULL_SPEED);
if (!SD.begin(SD_CS_PIN)) {
Serial.println(F("initialization failed!"));
exit(0);

}
Serial.println(F("initialization done."));

//For creating a text file in SD card.
while(SD.exists(fileName)) {
if(fileName[BASE_NAME_SIZE +1] != '9'){
fileName[BASE_NAME_SIZE +1]++;
} else if (fileName[BASE_NAME_SIZE] != '9') {
fileName[BASE_NAME_SIZE +1] = '0';
fileName[BASE_NAME_SIZE]++;
} else {
Serial.println(F("Can't create file name"));
return;
}
}
myFile = SD.open(fileName, O_CREAT | O_WRITE);
if(!myFile) {
Serial.println(F("Open failed"));
return;
}
Serial.print(F("Opened: "));
Serial.println(fileName);

bno.setMode(bno.OPERATION_MODE_NDOF);
bno1.setMode(bno.OPERATION_MODE_NDOF);
bno.setExtCrystalUse(true);
bno1.setExtCrystalUse(true);

void loop(void)
{
unsigned long CurrentTime = millis();
unsigned long ElapsedTime = CurrentTime - StartTime;

sensors_event_t event;
bno.getEvent(&event);
bno1.getEvent(&event);

//Get quaternion values.
imu::Quaternion quat = bno.getQuat();
imu::Quaternion quat2 = bno1.getQuat();

quat.normalize();
quat2.normalize();
//Formula for the absolute angle between two quaternions.
double relDeg = 57.2958*2*acos(abs(quat.w()*quat2.w() + quat.x()*quat2.x() + quat.y()*quat2.y()+quat.z()*quat2.z()));

#### Attachments

• 73.1 KB Views: 2
• 69.2 KB Views: 2
• 65.3 KB Views: 2
• 75 KB Views: 2