Rev 2099 | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 2099 | Rev 2141 | ||
---|---|---|---|
1 | /*********************************************************************************/ |
1 | /*********************************************************************************/ |
2 | /* Attitude sense system (processing of gyro, accelerometer and altimeter data) */ |
2 | /* Attitude sense system (processing of gyro, accelerometer and altimeter data) */ |
3 | /*********************************************************************************/ |
3 | /*********************************************************************************/ |
4 | 4 | ||
5 | #ifndef _ATTITUDE_H |
5 | #ifndef _ATTITUDE_H |
6 | #define _ATTITUDE_H |
6 | #define _ATTITUDE_H |
7 | 7 | ||
8 | #include <inttypes.h> |
8 | #include <inttypes.h> |
9 | 9 | ||
10 | #include "analog.h" |
10 | #include "analog.h" |
- | 11 | #include "timer0.h" |
|
11 | 12 | ||
12 | // For debugging only. |
13 | // For debugging only. |
13 | #include "uart0.h" |
14 | #include "uart0.h" |
14 | 15 | ||
15 | /* |
16 | /* |
16 | * If you have no acc. sensor or do not want to use it, remove this define. This will cause the |
17 | * If you have no acc. sensor or do not want to use it, remove this define. This will cause the |
17 | * acc. sensor to be ignored at attitude calibration. |
18 | * acc. sensor to be ignored at attitude calibration. |
18 | */ |
19 | */ |
19 | //#define ATTITUDE_USE_ACC_SENSORS yes |
20 | //#define ATTITUDE_USE_ACC_SENSORS yes |
20 | 21 | ||
21 | /* |
22 | /* |
22 | * The frequency at which numerical integration takes place. 488 in original code. |
23 | * The frequency at which numerical integration takes place. 488 in original code. |
23 | */ |
24 | */ |
24 | #define INTEGRATION_FREQUENCY 488 |
25 | #define INTEGRATION_FREQUENCY (uint16_t)(F_MAINLOOP) |
25 | 26 | ||
26 | /* |
27 | /* |
27 | * Constant for deriving an attitude angle from acceleration measurement. |
28 | * Constant for deriving an attitude angle from acceleration measurement. |
28 | * |
29 | * |
29 | * The value is derived from the datasheet of the ACC sensor where 5g are scaled to VRef. |
30 | * The value is derived from the datasheet of the ACC sensor where 5g are scaled to VRef. |
30 | * 1g is (3V * 1024) / (5 * 3V) = 205 counts. The ADC ISR sums 2 acc. samples to each |
31 | * 1g is (3V * 1024) / (5 * 3V) = 205 counts. The ADC ISR sums 2 acc. samples to each |
31 | * [pitch/roll]AxisAcc and thus reads about acc = 410 counts / g. |
32 | * [pitch/roll]AxisAcc and thus reads about acc = 410 counts / g. |
32 | * We approximate a small pitch/roll angle v by assuming that the copter does not accelerate: |
33 | * We approximate a small pitch/roll angle v by assuming that the copter does not accelerate: |
33 | * In this explanation it is assumed that the ADC values are 0 based, and gravity is included. |
34 | * In this explanation it is assumed that the ADC values are 0 based, and gravity is included. |
34 | * The sine of v is the far side / the hypothenusis: |
35 | * The sine of v is the far side / the hypothenusis: |
35 | * sin v = acc / sqrt(acc^2 + acc_z^2) |
36 | * sin v = acc / sqrt(acc^2 + acc_z^2) |
36 | * Using that v is a small angle, and the near side is about equal to the the hypothenusis: |
37 | * Using that v is a small angle, and the near side is about equal to the the hypothenusis: |
37 | * sin v ~= acc / acc_z |
38 | * sin v ~= acc / acc_z |
38 | * Assuming that the helicopter is hovering at small pitch and roll angles, acc_z is about 410, |
39 | * Assuming that the helicopter is hovering at small pitch and roll angles, acc_z is about 410, |
39 | * and sin v ~= v (small angles, in radians): |
40 | * and sin v ~= v (small angles, in radians): |
40 | * sin v ~= acc / 410 |
41 | * sin v ~= acc / 410 |
41 | * v / 57.3 ~= acc / 410 |
42 | * v / 57.3 ~= acc / 410 |
42 | * v ~= acc * 57.3 / 410 |
43 | * v ~= acc * 57.3 / 410 |
43 | * acc / v ~= 410 / 57.3 ~= 7, that is: There are about 7 counts per degree. |
44 | * acc / v ~= 410 / 57.3 ~= 7, that is: There are about 7 counts per degree. |
44 | * |
45 | * |
45 | * Summary: DEG_ACC_FACTOR = (2 * 1024 * [sensitivity of acc. meter in V/g]) / (3V * 57.3) |
46 | * Summary: DEG_ACC_FACTOR = (2 * 1024 * [sensitivity of acc. meter in V/g]) / (3V * 57.3) |
46 | */ |
47 | */ |
47 | #define DEG_ACC_FACTOR 7 |
48 | #define DEG_ACC_FACTOR 7 |
48 | 49 | ||
49 | /* |
50 | /* |
50 | * Growth of the integral per degree: |
51 | * Growth of the integral per degree: |
51 | * The hiResXXXX value per deg / s * INTEGRATION_FREQUENCY samples / sec * correction / a number divided by |
52 | * The hiResXXXX value per deg / s * INTEGRATION_FREQUENCY samples / sec * correction / a number divided by |
52 | * HIRES_GYRO_INTEGRATION_FACTOR (why???) before integration. |
53 | * HIRES_GYRO_INTEGRATION_FACTOR (why???) before integration. |
53 | * The value of this expression should be about 1250 (by setting HIRES_GYRO_INTEGRATION_FACTOR to something suitable). |
54 | * The value of this expression should be about 1250 (by setting HIRES_GYRO_INTEGRATION_FACTOR to something suitable). |
54 | */ |
55 | */ |
55 | #define GYRO_DEG_FACTOR (GYRO_RATE_FACTOR * INTEGRATION_FREQUENCY * GYRO_CORRECTION) |
56 | #define GYRO_DEG_FACTOR (GYRO_RATE_FACTOR * INTEGRATION_FREQUENCY * GYRO_CORRECTION) |
56 | 57 | ||
57 | /* |
58 | /* |
58 | * This is ([gyro integral value] / degree) / (degree / acc. sensor value) = gyro integral value / acc.sensor value |
59 | * This is ([gyro integral value] / degree) / (degree / acc. sensor value) = gyro integral value / acc.sensor value |
59 | * = the factor an acc. sensor should be multiplied by to get the gyro integral |
60 | * = the factor an acc. sensor should be multiplied by to get the gyro integral |
60 | * value for the same (small) angle. |
61 | * value for the same (small) angle. |
61 | * The value is about 200. |
62 | * The value is about 200. |
62 | */ |
63 | */ |
63 | //#define GYRO_ACC_FACTOR ((GYRO_DEG_FACTOR_PITCHROLL) / (DEG_ACC_FACTOR)) |
64 | //#define GYRO_ACC_FACTOR ((GYRO_DEG_FACTOR_PITCHROLL) / (DEG_ACC_FACTOR)) |
64 | 65 | ||
65 | #define OVER180 ((int32_t)GYRO_DEG_FACTOR * 180) |
66 | #define OVER180 ((int32_t)(GYRO_DEG_FACTOR * 180.0f)) |
66 | #define OVER360 ((int32_t)GYRO_DEG_FACTOR * 360) |
67 | #define OVER360 ((int32_t)(GYRO_DEG_FACTOR * 360.0f)) |
67 | 68 | ||
68 | /* |
69 | /* |
69 | * Rotation rates |
70 | * Rotation rates |
70 | */ |
71 | */ |
71 | extern int16_t rate_PID[3], rate_ATT[3]; |
72 | extern int16_t rate_PID[3], rate_ATT[3]; |
72 | extern int16_t differential[3]; |
73 | extern int16_t differential[3]; |
73 | 74 | ||
74 | /* |
75 | /* |
75 | * Attitudes calculated by numerical integration of gyro rates |
76 | * Attitudes calculated by numerical integration of gyro rates |
76 | */ |
77 | */ |
77 | extern int32_t attitude[3]; |
78 | extern int32_t attitude[3]; |
78 | 79 | ||
79 | // extern volatile int32_t ReadingIntegralTop; // calculated in analog.c |
80 | // extern volatile int32_t ReadingIntegralTop; // calculated in analog.c |
80 | 81 | ||
81 | /* |
82 | /* |
82 | * Compass navigation |
83 | * Compass navigation |
83 | */ |
84 | */ |
84 | // extern int16_t compassHeading; |
85 | // extern int16_t compassHeading; |
85 | // extern int16_t compassCourse; |
86 | // extern int16_t compassCourse; |
86 | // extern int16_t compassOffCourse; |
87 | // extern int16_t compassOffCourse; |
87 | // extern uint8_t compassCalState; |
88 | // extern uint8_t compassCalState; |
88 | // extern int32_t yawGyroHeading; |
89 | // extern int32_t yawGyroHeading; |
89 | // extern int16_t yawGyroHeadingInDeg; |
90 | // extern int16_t yawGyroHeadingInDeg; |
90 | // extern uint8_t updateCompassCourse; |
91 | // extern uint8_t updateCompassCourse; |
91 | // extern uint16_t ignoreCompassTimer; |
92 | // extern uint16_t ignoreCompassTimer; |
92 | 93 | ||
93 | /* |
94 | /* |
94 | * Dynamic gyro offsets. These are signed values that are subtracted from the gyro measurements, |
95 | * Dynamic gyro offsets. These are signed values that are subtracted from the gyro measurements, |
95 | * to help canceling out drift and vibration noise effects. The dynamic offsets themselves |
96 | * to help canceling out drift and vibration noise effects. The dynamic offsets themselves |
96 | * can be updated in flight by different ways, for example: |
97 | * can be updated in flight by different ways, for example: |
97 | * - Just taking them from parameters, so the pilot can trim manually in a PC or mobile tool |
98 | * - Just taking them from parameters, so the pilot can trim manually in a PC or mobile tool |
98 | * - Summing up how much acc. meter correction was done to the gyro integrals over the last n |
99 | * - Summing up how much acc. meter correction was done to the gyro integrals over the last n |
99 | * integration, and then adding the sum / n to the dynamic offset |
100 | * integration, and then adding the sum / n to the dynamic offset |
100 | * - Detect which way the pilot pulls the stick to keep the copter steady, and correct by that |
101 | * - Detect which way the pilot pulls the stick to keep the copter steady, and correct by that |
101 | * - Invent your own... |
102 | * - Invent your own... |
102 | */ |
103 | */ |
103 | // extern int16_t dynamicOffset[2], dynamicOffsetYaw; |
104 | // extern int16_t dynamicOffset[2], dynamicOffsetYaw; |
104 | 105 | ||
105 | /* |
106 | /* |
106 | * For NaviCtrl use. |
107 | * For NaviCtrl use. |
107 | */ |
108 | */ |
108 | // extern int16_t averageAcc[2], averageAccCount; |
109 | // extern int16_t averageAcc[2], averageAccCount; |
109 | 110 | ||
110 | /* |
111 | /* |
111 | * Re-init flight attitude, setting all angles to 0 (or to whatever can be derived from acc. sensor). |
112 | * Re-init flight attitude, setting all angles to 0 (or to whatever can be derived from acc. sensor). |
112 | * To be called when the pilot commands gyro calibration (eg. by moving the left stick up-left or up-right). |
113 | * To be called when the pilot commands gyro calibration (eg. by moving the left stick up-left or up-right). |
113 | */ |
114 | */ |
114 | void attitude_setNeutral(void); |
115 | void attitude_setNeutral(void); |
115 | 116 | ||
116 | /* |
117 | /* |
117 | * Experiment. |
118 | * Experiment. |
118 | */ |
119 | */ |
119 | // void attitude_startDynamicCalibration(void); |
120 | // void attitude_startDynamicCalibration(void); |
120 | // void attitude_continueDynamicCalibration(void); |
121 | // void attitude_continueDynamicCalibration(void); |
121 | 122 | ||
122 | int32_t getAngleEstimateFromAcc(uint8_t axis); |
123 | int32_t getAngleEstimateFromAcc(uint8_t axis); |
123 | 124 | ||
124 | /* |
125 | /* |
125 | * Main routine, called from the flight loop. |
126 | * Main routine, called from the flight loop. |
126 | */ |
127 | */ |
127 | void calculateFlightAttitude(void); |
128 | void calculateFlightAttitude(void); |
128 | #endif //_ATTITUDE_H |
129 | #endif //_ATTITUDE_H |
129 | 130 |