![](/media/cache/img/default_profile.jpg.50x50_q85.jpg)
Self-Balancing bot for MAX32630 and two wheel car.
Dependencies: mbed BMI160 SDFileSystem max32630fthr
Diff: main.cpp
- Revision:
- 6:9712c04e13bf
- Parent:
- 5:f66e4666de56
- Child:
- 7:337faf16a8d6
--- a/main.cpp Fri Jan 13 07:29:19 2017 +0000 +++ b/main.cpp Sun Jan 15 22:11:22 2017 +0000 @@ -39,6 +39,9 @@ * Reading a IMU Without Kalman: The Complementary Filter * http://www.pieter-jan.com/node/11 * +* The Balance Filter +* http://d1.amobbs.com/bbs_upload782111/files_44/ourdev_665531S2JZG6.pdf +* */ @@ -47,9 +50,11 @@ #include "bmi160.h" #include "SDFileSystem.h" + +float compFilter(float K, float pitch, float gyroX, float accY, float accZ, float DT); void saveData(uint32_t numSamples, float * loopCoeffs, float * gyroX, - float * accY, float * accZ, float * pw); + float * accY, float * accZ, int32_t * pw); //Setup interrupt in from imu @@ -156,7 +161,7 @@ float accYaxisBuff[N]; float accZaxisBuff[N]; float gyroXaxisBuff[N]; - float pulseWidthBuff[N]; + int32_t pulseWidthBuff[N]; //Setup I2C bus for IMU I2C i2cBus(P5_7, P6_0); @@ -167,10 +172,10 @@ BMI160::AccConfig accConfig; BMI160::AccConfig accConfigRead; - accConfig.range = BMI160::SENS_2G; + accConfig.range = BMI160::SENS_4G; accConfig.us = BMI160::ACC_US_OFF; accConfig.bwp = BMI160::ACC_BWP_2; - accConfig.odr = BMI160::ACC_ODR_12; + accConfig.odr = BMI160::ACC_ODR_11; if(imu.setSensorConfig(accConfig) == BMI160::RTN_NO_ERROR) { if(imu.getSensorConfig(accConfigRead) == BMI160::RTN_NO_ERROR) @@ -209,7 +214,7 @@ BMI160::GyroConfig gyroConfigRead; gyroConfig.range = BMI160::DPS_2000; gyroConfig.bwp = BMI160::GYRO_BWP_2; - gyroConfig.odr = BMI160::GYRO_ODR_12; + gyroConfig.odr = BMI160::GYRO_ODR_11; if(imu.setSensorConfig(gyroConfig) == BMI160::RTN_NO_ERROR) { if(imu.getSensorConfig(gyroConfigRead) == BMI160::RTN_NO_ERROR) @@ -273,13 +278,12 @@ BMI160::SensorTime sensorTime; //Complementary Filter vars, filter weight K - static const float K = 0.99995F; + static const float K = 0.999F; float pitch = 0.0F; //PID coefficients - //Kc = 2.5, Pc = 0.1; Critical gain and period of osc - //when adjusting KP until marginally stable - static const float DT = 0.000625F; + + static const float DT = 0.00125F; static const float KP = 2.0F; static const float KI = (0.0F*DT); static const float KD = (0.0F/DT); @@ -343,7 +347,7 @@ rLED = LED_ON; gLED = LED_ON; - while(offsetCount < 3200) + while(offsetCount < 1600) { if(drdy) { @@ -353,9 +357,8 @@ //Read feedback sensors imu.getGyroAccXYZandSensorTime(accData, gyroData, sensorTime, accConfig.range, gyroConfig.range); - //Feedback Block, Complementary filter. - //Pitch estimate in degrees - pitch = ((K * (pitch + (gyroData.xAxis.scaled * DT))) + ((1.0F - K) * accData.yAxis.scaled)); + //Feedback Block, pitch estimate in degrees + pitch = compFilter(K, pitch, gyroData.xAxis.scaled, accData.yAxis.scaled, accData.zAxis.scaled, DT); //Accumalate pitch measurements setPoint += pitch; @@ -388,10 +391,9 @@ //Read feedback sensors imu.getGyroAccXYZandSensorTime(accData, gyroData, sensorTime, accConfig.range, gyroConfig.range); - //Feedback Block, Complementary filter. - //Pitch estimate in degrees - pitch = ((K * (pitch + (gyroData.xAxis.scaled * DT))) + ((1.0F - K) * accData.yAxis.scaled)); - + //Feedback Block, pitch estimate in degrees + pitch = compFilter(K, pitch, gyroData.xAxis.scaled, accData.yAxis.scaled, accData.zAxis.scaled, DT); + //PID Block //Error signal currentError = (setPoint - pitch); @@ -472,7 +474,7 @@ accYaxisBuff[samples] = accData.yAxis.scaled; accZaxisBuff[samples] = accData.zAxis.scaled; gyroXaxisBuff[samples] = gyroData.xAxis.scaled; - pulseWidthBuff[samples] = pulseWidth; + pulseWidthBuff[samples] = static_cast<int32_t>(pulseWidth); samples++; } @@ -524,7 +526,7 @@ //***************************************************************************** void saveData(uint32_t numSamples, float * loopCoeffs, float * gyroX, - float * accY, float * accZ, float * pw) + float * accY, float * accZ, int32_t * pw) { SDFileSystem sd(P0_5, P0_6, P0_4, P0_7, "sd"); // mosi, miso, sclk, cs FILE *fp; @@ -543,21 +545,21 @@ float accPitch = 0.0F; float gyroDegrees = 0.0F; float pitch = 0.0F; - float k = loopCoeffs[1]; - float dt = loopCoeffs[5]; + float K = loopCoeffs[1]; + float DT = loopCoeffs[5]; for(uint32_t idx = 0; idx < numSamples; idx++) { - fprintf(fp, "%f,", idx*dt); + fprintf(fp, "%f,", idx*DT); fprintf(fp, "%5.4f,", accY[idx]); fprintf(fp, "%6.2f,", gyroX[idx]); - gyroDegrees += (gyroX[idx] * dt); + gyroDegrees += (gyroX[idx] * DT); fprintf(fp, "%5.2f,", gyroDegrees); accPitch = ((180.0F/3.14159F) * atan(accY[idx]/accZ[idx])); fprintf(fp, "%5.2f,", accPitch); - pitch = ((k * (pitch + (gyroX[idx] * dt))) + ((1.0F - k) * accY[idx])); + pitch = compFilter(K, pitch, gyroX[idx], accY[idx], accZ[idx], DT); fprintf(fp, "%5.2f,", pitch); - fprintf(fp, "%f", pw[idx]); + fprintf(fp, "%d", pw[idx]); fprintf(fp, "\n"); } fprintf(fp, "\n"); @@ -568,3 +570,10 @@ printf("Failed to open file\n"); } } + + +//***************************************************************************** +float compFilter(float K, float pitch, float gyroX, float accY, float accZ, float DT) +{ + return ((K * (pitch + (gyroX * DT))) + ((1.0F - K) * ((180.0F / 3.1459F) * atan(accY/accZ)))); +}