footPDR.c 27 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119
  1. #include <stdio.h>
  2. #include <string.h>
  3. #include <stdlib.h>
  4. #include <math.h>
  5. #include <stdint.h>
  6. #define ZUPT_threshold 0.81
  7. #define SIGMA 0.01
  8. #define SIGMA_V 0.001
  9. #define PI 3.1416
  10. #define RUN 1
  11. #define STAND 0
  12. //当地的重力加速度
  13. float g = 9.788f;
  14. float dt = 0.01f;
  15. float P[81], acc_n[3];
  16. float Temporary_array1[9], Temporary_array2[9];
  17. float K[27], P_prev[81], delta_x[9];
  18. float C[9], C_prev[9];
  19. float vel_n[3], pos_n[3];
  20. float last_pos_n[3];
  21. float pos_offset[3];
  22. int frame_index = 0;
  23. int stand_num = 0;
  24. float gyr_norm_window[10];
  25. float gyr_z_window[10];
  26. float gyr_extreme[6];
  27. float gyr_mean[3];
  28. float num_peak;
  29. float acc_mean[3];
  30. float gyrBias[3];
  31. float accSum;
  32. float accSize;
  33. int press_data[6];
  34. int ZUPT_STATUS;
  35. int HAS_RESULT;
  36. int IS_DOWN;
  37. int press_index;
  38. float gyr_temp[3];
  39. float acc_temp[3];
  40. int last_move_index;
  41. int down_pass1;
  42. int down_pass2;
  43. enum _CMD_MOTION{
  44. MOTION_STOP = 0,
  45. MOTION_RUN = 1,
  46. MOTION_JUMP = 2,
  47. MOTION_DOWN = 3,
  48. MOTION_LEFT = 4,
  49. MOTION_RIGHT = 5,
  50. MOTION_FRONT = 6,
  51. MOTION_BACK = 7,
  52. };
  53. void invert3x3(float * src, float * dst)
  54. {
  55. float det;
  56. /* Compute adjoint: */
  57. dst[0] = +src[4] * src[8] - src[5] * src[7];
  58. dst[1] = -src[1] * src[8] + src[2] * src[7];
  59. dst[2] = +src[1] * src[5] - src[2] * src[4];
  60. dst[3] = -src[3] * src[8] + src[5] * src[6];
  61. dst[4] = +src[0] * src[8] - src[2] * src[6];
  62. dst[5] = -src[0] * src[5] + src[2] * src[3];
  63. dst[6] = +src[3] * src[7] - src[4] * src[6];
  64. dst[7] = -src[0] * src[7] + src[1] * src[6];
  65. dst[8] = +src[0] * src[4] - src[1] * src[3];
  66. /* Compute determinant: */
  67. det = src[0] * dst[0] + src[1] * dst[3] + src[2] * dst[6];
  68. /* Multiply adjoint with reciprocal of determinant: */
  69. det = 1.0f / det;
  70. dst[0] *= det;
  71. dst[1] *= det;
  72. dst[2] *= det;
  73. dst[3] *= det;
  74. dst[4] *= det;
  75. dst[5] *= det;
  76. dst[6] *= det;
  77. dst[7] *= det;
  78. dst[8] *= det;
  79. }
  80. void multiply3x3(float *a, float *b, float *dst)
  81. {
  82. dst[0] = a[0] * b[0] + a[1] * b[3] + a[2] * b[6];
  83. dst[1] = a[0] * b[1] + a[1] * b[4] + a[2] * b[7];
  84. dst[2] = a[0] * b[2] + a[1] * b[5] + a[2] * b[8];
  85. dst[3] = a[3] * b[0] + a[4] * b[3] + a[5] * b[6];
  86. dst[4] = a[3] * b[1] + a[4] * b[4] + a[5] * b[7];
  87. dst[5] = a[3] * b[2] + a[4] * b[5] + a[5] * b[8];
  88. dst[6] = a[6] * b[0] + a[7] * b[3] + a[8] * b[6];
  89. dst[7] = a[6] * b[1] + a[7] * b[4] + a[8] * b[7];
  90. dst[8] = a[6] * b[2] + a[7] * b[5] + a[8] * b[8];
  91. }
  92. void multiply3x1(float *a, float *b, float *dst)
  93. {
  94. dst[0] = a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
  95. dst[1] = a[3] * b[0] + a[4] * b[1] + a[5] * b[2];
  96. dst[2] = a[6] * b[0] + a[7] * b[1] + a[8] * b[2];
  97. }
  98. void init_attitude_matrix(float *C, float *acc)
  99. {
  100. float pitch = asin(-acc[0] / g);
  101. float roll = atan2(acc[1], acc[2]);
  102. float pitch_sin = sin(pitch);
  103. float pitch_cos = cos(pitch);
  104. float roll_sin = sin(roll);
  105. float roll_cos = cos(roll);
  106. C[0] = cos(pitch);
  107. C[1] = pitch_sin * roll_sin;
  108. C[2] = pitch_sin * roll_cos;
  109. C[4] = roll_cos;
  110. C[5] = -roll_sin;
  111. C[6] = -pitch_sin;
  112. C[7] = pitch_cos * roll_sin;
  113. C[8] = pitch_cos * roll_cos;
  114. }
  115. void reset_yaw_C(float *C)
  116. {
  117. float pitch = asin(-C[6]);
  118. float roll = atan2(C[7], C[8]);
  119. float pitch_sin = sin(pitch);
  120. float pitch_cos = cos(pitch);
  121. float roll_sin = sin(roll);
  122. float roll_cos = cos(roll);
  123. C[0] = pitch_cos;
  124. C[1] = pitch_sin * roll_sin;
  125. C[2] = pitch_sin * roll_cos;
  126. C[3] = 0.0;
  127. C[4] = roll_cos;
  128. C[5] = -roll_sin;
  129. }
  130. // F * P * F'
  131. void State_covariance_matrix_update(float *P, float *acc_n)
  132. {
  133. // P2 + P3*dt,
  134. P[3] = P[3] + P[6] * dt;
  135. P[4] = P[4] + P[7] * dt;
  136. P[5] = P[5] + P[8] * dt;
  137. P[12] = P[12] + P[15] * dt;
  138. P[13] = P[13] + P[16] * dt;
  139. P[14] = P[14] + P[17] * dt;
  140. P[21] = P[21] + P[24] * dt;
  141. P[22] = P[22] + P[25] * dt;
  142. P[23] = P[23] + P[26] * dt;
  143. //P4 + P7*dt,
  144. P[27] = P[27] + P[54] * dt;
  145. P[28] = P[28] + P[55] * dt;
  146. P[29] = P[29] + P[56] * dt;
  147. P[36] = P[36] + P[63] * dt;
  148. P[37] = P[37] + P[64] * dt;
  149. P[38] = P[38] + P[65] * dt;
  150. P[45] = P[45] + P[72] * dt;
  151. P[46] = P[46] + P[73] * dt;
  152. P[47] = P[47] + P[74] * dt;
  153. // P5 + P8*dt + dt*(P6 + P9*dt)
  154. P[30] = P[30] + P[57] * dt + dt * (P[33] + P[60] * dt);
  155. P[31] = P[31] + P[58] * dt + dt * (P[34] + P[61] * dt);
  156. P[32] = P[32] + P[59] * dt + dt * (P[35] + P[62] * dt);
  157. P[39] = P[39] + P[66] * dt + dt * (P[42] + P[69] * dt);
  158. P[40] = P[40] + P[67] * dt + dt * (P[43] + P[70] * dt);
  159. P[41] = P[41] + P[68] * dt + dt * (P[44] + P[71] * dt);
  160. P[48] = P[48] + P[75] * dt + dt * (P[51] + P[78] * dt);
  161. P[49] = P[49] + P[76] * dt + dt * (P[52] + P[79] * dt);
  162. P[50] = P[50] + P[77] * dt + dt * (P[53] + P[80] * dt);
  163. //P6 + P9*dt + matr*(P4 + P7*dt)
  164. P[33] = P[33] + P[60] * dt + acc_n[2] * dt * P[28] - acc_n[1] * dt * P[29];
  165. P[34] = P[34] + P[61] * dt - acc_n[2] * dt * P[27] + acc_n[0] * dt * P[29];
  166. P[35] = P[35] + P[62] * dt + acc_n[1] * dt * P[27] - acc_n[0] * dt * P[28];
  167. P[42] = P[42] + P[69] * dt + acc_n[2] * dt * P[37] - acc_n[1] * dt * P[38];
  168. P[43] = P[43] + P[70] * dt - acc_n[2] * dt * P[36] + acc_n[0] * dt * P[38];
  169. P[44] = P[44] + P[71] * dt + acc_n[1] * dt * P[36] - acc_n[0] * dt * P[37];
  170. P[51] = P[51] + P[78] * dt + acc_n[2] * dt * P[46] - acc_n[1] * dt * P[47];
  171. P[52] = P[52] + P[79] * dt - acc_n[2] * dt * P[45] + acc_n[0] * dt * P[47];
  172. P[53] = P[53] + P[80] * dt + acc_n[1] * dt * P[45] - acc_n[0] * dt * P[46];
  173. //P7 + P1*matr
  174. P[54] = P[54] + P[9] * acc_n[2] * dt - P[18] * acc_n[1] * dt;
  175. P[55] = P[55] + P[10] * acc_n[2] * dt - P[19] * acc_n[1] * dt;
  176. P[56] = P[56] + P[11] * acc_n[2] * dt - P[20] * acc_n[1] * dt;
  177. P[63] = P[63] - P[0] * acc_n[2] * dt + P[18] * acc_n[0] * dt;
  178. P[64] = P[64] - P[1] * acc_n[2] * dt + P[19] * acc_n[0] * dt;
  179. P[65] = P[65] - P[2] * acc_n[2] * dt + P[20] * acc_n[0] * dt;
  180. P[72] = P[72] + P[0] * acc_n[1] * dt - P[9] * acc_n[0] * dt;
  181. P[73] = P[73] + P[1] * acc_n[1] * dt - P[10] * acc_n[0] * dt;
  182. P[74] = P[74] + P[2] * acc_n[1] * dt - P[11] * acc_n[0] * dt;
  183. //P8 + P2*matr + dt*(P9 + P3*matr),
  184. P[57] = P[57] + dt * P[60] + P[12] * acc_n[2] * dt - P[21] * acc_n[1] * dt;
  185. P[58] = P[58] + dt * P[61] + P[13] * acc_n[2] * dt - P[22] * acc_n[1] * dt;
  186. P[59] = P[59] + dt * P[62] + P[14] * acc_n[2] * dt - P[23] * acc_n[1] * dt;
  187. P[66] = P[66] + dt * P[69] - P[3] * acc_n[2] * dt + P[21] * acc_n[0] * dt;
  188. P[67] = P[67] + dt * P[70] - P[4] * acc_n[2] * dt + P[22] * acc_n[0] * dt;
  189. P[68] = P[68] + dt * P[71] - P[5] * acc_n[2] * dt + P[23] * acc_n[0] * dt;
  190. P[75] = P[75] + dt * P[78] + P[3] * acc_n[1] * dt - P[12] * acc_n[0] * dt;
  191. P[76] = P[76] + dt * P[79] + P[4] * acc_n[1] * dt - P[13] * acc_n[0] * dt;
  192. P[77] = P[77] + dt * P[80] + P[5] * acc_n[1] * dt - P[14] * acc_n[0] * dt;
  193. // P9 + P3*matr + matr*(P7 + P1*matr)
  194. P[60] = P[60] + P[15] * acc_n[2] * dt - P[24] * acc_n[1] * dt + acc_n[2] * dt * P[55] - acc_n[1] * dt * P[56];
  195. P[61] = P[61] + P[16] * acc_n[2] * dt - P[25] * acc_n[1] * dt - acc_n[2] * dt * P[54] + acc_n[0] * dt * P[56];
  196. P[62] = P[62] + P[17] * acc_n[2] * dt - P[26] * acc_n[1] * dt + acc_n[1] * dt * P[54] - acc_n[0] * dt * P[55];
  197. P[69] = P[69] - P[6] * acc_n[2] * dt + P[24] * acc_n[0] * dt + acc_n[2] * dt * P[64] - acc_n[1] * dt * P[65];
  198. P[70] = P[70] - P[7] * acc_n[2] * dt + P[25] * acc_n[0] * dt - acc_n[2] * dt * P[63] + acc_n[0] * dt * P[65];
  199. P[71] = P[71] - P[8] * acc_n[2] * dt + P[26] * acc_n[0] * dt + acc_n[1] * dt * P[63] - acc_n[0] * dt * P[64];
  200. P[78] = P[78] + P[6] * acc_n[1] * dt - P[15] * acc_n[0] * dt + acc_n[2] * dt * P[73] - acc_n[1] * dt * P[74];
  201. P[79] = P[79] + P[7] * acc_n[1] * dt - P[16] * acc_n[0] * dt - acc_n[2] * dt * P[72] + acc_n[0] * dt * P[74];
  202. P[80] = P[80] + P[8] * acc_n[1] * dt - P[17] * acc_n[0] * dt + acc_n[1] * dt * P[72] - acc_n[0] * dt * P[73];
  203. //P3 + P1 * matr
  204. P[6] = P[6] + P[1] * acc_n[2] * dt - P[2] * acc_n[1] * dt;
  205. P[7] = P[7] - P[0] * acc_n[2] * dt + P[2] * acc_n[0] * dt;
  206. P[8] = P[8] + P[0] * acc_n[1] * dt - P[1] * acc_n[0] * dt;
  207. P[15] = P[15] + P[10] * acc_n[2] * dt - P[11] * acc_n[1] * dt;
  208. P[16] = P[16] - P[9] * acc_n[2] * dt + P[11] * acc_n[0] * dt;
  209. P[17] = P[17] + P[9] * acc_n[1] * dt - P[10] * acc_n[0] * dt;
  210. P[24] = P[24] + P[19] * acc_n[2] * dt - P[20] * acc_n[1] * dt;
  211. P[25] = P[25] - P[18] * acc_n[2] * dt + P[20] * acc_n[0] * dt;
  212. P[26] = P[26] + P[18] * acc_n[1] * dt - P[19] * acc_n[0] * dt;
  213. float noise = SIGMA * SIGMA * dt *dt;
  214. for (int i = 0; i < 9; i++)
  215. {
  216. P[i * 9 + i] += noise;
  217. }
  218. }
  219. void Kalfman_gain(float *P, float *Temporary_array, float *Temporary_array1, float *K)
  220. {
  221. Temporary_array[0] = P[60] + SIGMA_V * SIGMA_V;
  222. Temporary_array[1] = P[61];
  223. Temporary_array[2] = P[62];
  224. Temporary_array[3] = P[69];
  225. Temporary_array[4] = P[70] + SIGMA_V * SIGMA_V;
  226. Temporary_array[5] = P[71];
  227. Temporary_array[6] = P[78];
  228. Temporary_array[7] = P[79];
  229. Temporary_array[8] = P[80] + SIGMA_V * SIGMA_V;
  230. invert3x3(Temporary_array, Temporary_array1);
  231. memcpy(Temporary_array, Temporary_array1, 9 * sizeof(float));
  232. K[0] = P[6] * Temporary_array[0] + P[7] * Temporary_array[3] + P[8] * Temporary_array[6];
  233. K[1] = P[6] * Temporary_array[1] + P[7] * Temporary_array[4] + P[8] * Temporary_array[7];
  234. K[2] = P[6] * Temporary_array[2] + P[7] * Temporary_array[5] + P[8] * Temporary_array[8];
  235. K[3] = P[15] * Temporary_array[0] + P[16] * Temporary_array[3] + P[17] * Temporary_array[6];
  236. K[4] = P[15] * Temporary_array[1] + P[16] * Temporary_array[4] + P[17] * Temporary_array[7];
  237. K[5] = P[15] * Temporary_array[2] + P[16] * Temporary_array[5] + P[17] * Temporary_array[8];
  238. K[6] = P[24] * Temporary_array[0] + P[25] * Temporary_array[3] + P[26] * Temporary_array[6];
  239. K[7] = P[24] * Temporary_array[1] + P[25] * Temporary_array[4] + P[26] * Temporary_array[7];
  240. K[8] = P[24] * Temporary_array[2] + P[25] * Temporary_array[5] + P[26] * Temporary_array[8];
  241. K[9] = P[33] * Temporary_array[0] + P[34] * Temporary_array[3] + P[35] * Temporary_array[6];
  242. K[10] = P[33] * Temporary_array[1] + P[34] * Temporary_array[4] + P[35] * Temporary_array[7];
  243. K[11] = P[33] * Temporary_array[2] + P[34] * Temporary_array[5] + P[35] * Temporary_array[8];
  244. K[12] = P[42] * Temporary_array[0] + P[43] * Temporary_array[3] + P[44] * Temporary_array[6];
  245. K[13] = P[42] * Temporary_array[1] + P[43] * Temporary_array[4] + P[44] * Temporary_array[7];
  246. K[14] = P[42] * Temporary_array[2] + P[43] * Temporary_array[5] + P[44] * Temporary_array[8];
  247. K[15] = P[51] * Temporary_array[0] + P[52] * Temporary_array[3] + P[53] * Temporary_array[6];
  248. K[16] = P[51] * Temporary_array[1] + P[52] * Temporary_array[4] + P[53] * Temporary_array[7];
  249. K[17] = P[51] * Temporary_array[2] + P[52] * Temporary_array[5] + P[53] * Temporary_array[8];
  250. K[18] = P[60] * Temporary_array[0] + P[61] * Temporary_array[3] + P[62] * Temporary_array[6];
  251. K[19] = P[60] * Temporary_array[1] + P[61] * Temporary_array[4] + P[62] * Temporary_array[7];
  252. K[20] = P[60] * Temporary_array[2] + P[61] * Temporary_array[5] + P[62] * Temporary_array[8];
  253. K[21] = P[69] * Temporary_array[0] + P[70] * Temporary_array[3] + P[71] * Temporary_array[6];
  254. K[22] = P[69] * Temporary_array[1] + P[70] * Temporary_array[4] + P[71] * Temporary_array[7];
  255. K[23] = P[69] * Temporary_array[2] + P[70] * Temporary_array[5] + P[71] * Temporary_array[8];
  256. K[24] = P[78] * Temporary_array[0] + P[79] * Temporary_array[3] + P[80] * Temporary_array[6];
  257. K[25] = P[78] * Temporary_array[1] + P[79] * Temporary_array[4] + P[80] * Temporary_array[7];
  258. K[26] = P[78] * Temporary_array[2] + P[79] * Temporary_array[5] + P[80] * Temporary_array[8];
  259. }
  260. void multiply9x3(float *K, float *vel_n, float* delta_x)
  261. {
  262. int i = 0;
  263. for (i = 0; i < 9; i++)
  264. {
  265. delta_x[i] = K[i * 3] * vel_n[0] + K[i * 3 + 1] * vel_n[1] + K[i * 3 + 2] * vel_n[2];
  266. }
  267. }
  268. void State_covariance_matrix_corr(float *P, float *P_tmp, float *K)
  269. {
  270. int i = 0;
  271. int j = 0;
  272. for (i = 0; i < 9; i++) {
  273. for (j = 0; j < 9; j++) {
  274. P_tmp[i * 9 + j] = P[i * 9 + j] - K[3 * i] * P[54 + j] - K[3 * i + 1] * P[63 + j] - K[3 * i + 2] * P[72 + j];
  275. }
  276. }
  277. memcpy(P, P_tmp, 81 * sizeof(float));
  278. }
  279. void Att_matrix_corr(float *C, float *C_prev, float *Temporary_array, float *Temporary_array1, float *delta_x)
  280. {
  281. Temporary_array[0] = 2.0;
  282. Temporary_array[1] = -delta_x[2];
  283. Temporary_array[2] = delta_x[1];
  284. Temporary_array[3] = delta_x[2];
  285. Temporary_array[4] = 2.0;
  286. Temporary_array[5] = -delta_x[0];
  287. Temporary_array[6] = -delta_x[1];
  288. Temporary_array[7] = delta_x[0];
  289. Temporary_array[8] = 2.0;
  290. invert3x3(Temporary_array, Temporary_array1);
  291. Temporary_array[0] = 2.0;
  292. Temporary_array[1] = delta_x[2];
  293. Temporary_array[2] = -delta_x[1];
  294. Temporary_array[3] = -delta_x[2];
  295. Temporary_array[4] = 2.0;
  296. Temporary_array[5] = delta_x[0];
  297. Temporary_array[6] = delta_x[1];
  298. Temporary_array[7] = -delta_x[0];
  299. Temporary_array[8] = 2.0;
  300. multiply3x3(Temporary_array, Temporary_array1, C_prev);
  301. memcpy(Temporary_array, C_prev, 9 * sizeof(float));
  302. multiply3x3(Temporary_array, C, C_prev);
  303. memcpy(C, C_prev, 9 * sizeof(float));
  304. }
  305. void pos_n_corr(float *pos_n, float *delta_x)
  306. {
  307. pos_n[0] -= delta_x[3];
  308. pos_n[1] -= delta_x[4];
  309. pos_n[2] -= delta_x[5];
  310. }
  311. void vel_n_corr(float *vel_n, float *delta_x)
  312. {
  313. vel_n[0] -= delta_x[6];
  314. vel_n[1] -= delta_x[7];
  315. vel_n[2] -= delta_x[8];
  316. }
  317. void State_covariance_matrix_orthogonalization(float *P)
  318. {
  319. int i = 0;
  320. int j = 0;
  321. float temp;
  322. for (i = 0; i < 9; i++)
  323. for (j = i + 1; j < 9; j++)
  324. {
  325. temp = 0.5f*(P[i * 9 + j] + P[j * 9 + i]);
  326. P[i * 9 + j] = temp;
  327. P[j * 9 + i] = temp;
  328. }
  329. }
  330. void Initialize(float *gyr, float *acc)
  331. {
  332. frame_index = 1;
  333. stand_num = 0;
  334. accSize = 1.0f;
  335. accSum = 0.0f;
  336. ZUPT_STATUS = 0;
  337. HAS_RESULT = 0;
  338. memset(last_pos_n, 0, 3 * sizeof(float));
  339. memset(pos_offset, 0, 3 * sizeof(float));
  340. memset(gyr_norm_window, 0, 10 * sizeof(float));
  341. memset(gyr_z_window, 0, 10 * sizeof(float));
  342. memset(P, 0, 81 * sizeof(float));
  343. memset(acc_n, 0, 3 * sizeof(float));
  344. memset(vel_n, 0, 3 * sizeof(float));
  345. memset(pos_n, 0, 3 * sizeof(float));
  346. memset(Temporary_array1, 0, 9 * sizeof(float));
  347. memset(Temporary_array2, 0, 9 * sizeof(float));
  348. memset(K, 0, 27 * sizeof(float));
  349. memset(P_prev, 0, 81 * sizeof(float));
  350. memset(delta_x, 0, 9 * sizeof(float));
  351. memset(C, 0, 9 * sizeof(float));
  352. memset(Temporary_array1, 0, 9 * sizeof(float));
  353. memset(Temporary_array2, 0, 9 * sizeof(float));
  354. memset(press_data, 0, 6 * sizeof(int));
  355. init_attitude_matrix(C, acc);
  356. memcpy(C_prev, C, 9 * sizeof(float));
  357. }
  358. void attitude_matrix_update(float *C, float *Temporary_array1, float *Temporary_array2, float *gyr)
  359. {
  360. Temporary_array1[0] = 2.0;
  361. Temporary_array1[1] = dt * gyr[2];
  362. Temporary_array1[2] = -dt * gyr[1];
  363. Temporary_array1[3] = -dt * gyr[2];
  364. Temporary_array1[4] = 2.0;
  365. Temporary_array1[5] = dt * gyr[0];
  366. Temporary_array1[6] = dt * gyr[1];
  367. Temporary_array1[7] = -dt * gyr[0];
  368. Temporary_array1[8] = 2.0;
  369. invert3x3(Temporary_array1, Temporary_array2);
  370. memset(Temporary_array1, 0, 9 * sizeof(float));
  371. Temporary_array1[0] = 2 * C[0] + C[1] * dt * gyr[2] - C[2] * dt * gyr[1];
  372. Temporary_array1[1] = 2 * C[1] - C[0] * dt * gyr[2] + C[2] * dt * gyr[0];
  373. Temporary_array1[2] = 2 * C[2] + C[0] * dt * gyr[1] - C[1] * dt * gyr[0];
  374. Temporary_array1[3] = 2 * C[3] + C[4] * dt * gyr[2] - C[5] * dt * gyr[1];
  375. Temporary_array1[4] = 2 * C[4] - C[3] * dt * gyr[2] + C[5] * dt * gyr[0];
  376. Temporary_array1[5] = 2 * C[5] + C[3] * dt * gyr[1] - C[4] * dt * gyr[0];
  377. Temporary_array1[6] = 2 * C[6] + C[7] * dt * gyr[2] - C[8] * dt * gyr[1];
  378. Temporary_array1[7] = 2 * C[7] - C[6] * dt * gyr[2] + C[8] * dt * gyr[0];
  379. Temporary_array1[8] = 2 * C[8] + C[6] * dt * gyr[1] - C[7] * dt * gyr[0];
  380. multiply3x3(Temporary_array1, Temporary_array2, C);
  381. }
  382. float max_window_val(float *window, int window_size)
  383. {
  384. float val = window[0];
  385. for (int i = 0; i < window_size; i++)
  386. {
  387. if (window[i] > val)
  388. val = window[i];
  389. }
  390. return val;
  391. }
  392. int max_window_int(int *window, int window_size)
  393. {
  394. int val = window[0];
  395. for (int i = 0; i < window_size; i++)
  396. {
  397. if (window[i] > val)
  398. val = window[i];
  399. }
  400. return val;
  401. }
  402. float min_window_val(float *window, int window_size)
  403. {
  404. float val = window[0];
  405. for (int i = 0; i < window_size; i++)
  406. {
  407. if (window[i] < val)
  408. val = window[i];
  409. }
  410. return val;
  411. }
  412. int min_window_int(int *window, int window_size)
  413. {
  414. int val = window[0];
  415. for (int i = 0; i < window_size; i++)
  416. {
  417. if (window[i] < val)
  418. val = window[i];
  419. }
  420. return val;
  421. }
  422. unsigned char footPDR(int num, float *gyr, float *acc, int press, float* pos_res)
  423. {
  424. unsigned char movement_e = 0;
  425. for (int i = 0; i < 3; i++)
  426. {
  427. gyr[i] *= (PI / 180);
  428. acc[i] *= g;
  429. }
  430. if(num_peak == 0)
  431. {
  432. for(int i = 0; i < 3; i++)
  433. {
  434. gyr_extreme[2 * i] = gyr[i];
  435. gyr_extreme[2 * i + 1] = gyr[i];
  436. }
  437. }
  438. for (int i = 0; i < 3; i++)
  439. {
  440. if (gyr[i] < gyr_extreme[2 * i])
  441. {
  442. gyr_extreme[2 * i] = gyr[i];
  443. }
  444. if (gyr[i] > gyr_extreme[2 * i + 1])
  445. {
  446. gyr_extreme[2 * i + 1] = gyr[i];
  447. }
  448. }
  449. accSum += sqrt(acc[0] * acc[0] + acc[1] * acc[1] + acc[2] * acc[2]);
  450. for (int i = 0; i < 3; i++)
  451. {
  452. gyr_mean[i] += gyr[i];
  453. }
  454. num_peak++;
  455. if (num_peak > 500)
  456. {
  457. if (gyr_extreme[1] - gyr_extreme[0] < 0.02f && gyr_extreme[3] - gyr_extreme[2] < 0.02f && gyr_extreme[5] - gyr_extreme[4] < 0.02f)
  458. {
  459. gyrBias[0] = gyr_mean[0] / num_peak;
  460. gyrBias[1] = gyr_mean[1] / num_peak;
  461. gyrBias[2] = gyr_mean[2] / num_peak;
  462. accSize = g * num_peak /accSum;
  463. }
  464. num_peak = 0;
  465. accSum = 0.0f;
  466. memset(gyr_mean, 0, 3 * sizeof(float));
  467. }
  468. gyr[0] -= gyrBias[0];
  469. gyr[1] -= gyrBias[1];
  470. gyr[2] -= gyrBias[2];
  471. acc[0] *= accSize;
  472. acc[1] *= accSize;
  473. acc[2] *= accSize;
  474. float gyr_norm_xyz = sqrt(gyr[0]*gyr[0] + gyr[1]*gyr[1] + gyr[2]*gyr[2]);
  475. if (frame_index > 6 && press - min_window_int(press_data, 6) > 100000)
  476. {
  477. ZUPT_STATUS = 1;
  478. if(down_pass1 == 2)
  479. {
  480. down_pass1 = 0;
  481. }
  482. if(fabs(gyr[1]) > 1.0f || fabs(gyr[2]) > 0.3f)
  483. {
  484. down_pass1 = 1;
  485. }
  486. }
  487. else if (frame_index > 6 && press - max_window_int(press_data, 6) < -100000)
  488. {
  489. ZUPT_STATUS = 2;
  490. if(down_pass2 == 2)
  491. {
  492. down_pass2 = 0;
  493. }
  494. if(fabs(gyr[1]) > 1.0f || fabs(gyr[2]) > 0.3f)
  495. {
  496. down_pass2 = 1;
  497. }
  498. }
  499. else if (frame_index > 6 && ZUPT_STATUS == 2)
  500. {
  501. ZUPT_STATUS = 3;
  502. if(down_pass1 == 0 && down_pass2 == 0)
  503. {
  504. IS_DOWN = 1;
  505. }
  506. down_pass1 = 2;
  507. down_pass2 = 2;
  508. }
  509. press_data[(frame_index - 1) % 6] = press;
  510. //需要一个滑动窗口来判断脚步是否在地上
  511. frame_index++;
  512. //下面为惯导解算
  513. if (num == 1)
  514. {
  515. Initialize(gyr, acc);
  516. return movement_e;
  517. }
  518. attitude_matrix_update(C, Temporary_array1, Temporary_array2, gyr);
  519. multiply3x1(C, acc, acc_n);
  520. vel_n[0] = vel_n[0] + acc_n[0] * dt;
  521. vel_n[1] = vel_n[1] + acc_n[1] * dt;
  522. vel_n[2] = vel_n[2] + (acc_n[2] - g) * dt;
  523. pos_n[0] = pos_n[0] + vel_n[0] * dt;
  524. pos_n[1] = pos_n[1] + vel_n[1] * dt;
  525. pos_n[2] = pos_n[2] + vel_n[2] * dt;
  526. //P = F*P*F' + Q;
  527. State_covariance_matrix_update(P, acc_n);
  528. int window_index = (frame_index - 1) % 10;
  529. //这里用X轴 Z轴为依据,Y轴朝上的很难作为参考(特别是剧烈运动的时候)
  530. float gyr_norm_xz = sqrt(gyr[0] * gyr[0] + gyr[2] * gyr[2]);
  531. gyr_norm_window[window_index] = gyr_norm_xz;
  532. //RUN_ZUPT mean detect on floor when running
  533. int RUN_ZUPT = 0;
  534. if((frame_index > 10 && ZUPT_STATUS == 1))
  535. RUN_ZUPT = 1;
  536. //STAND_ZUPT mean detect on floor when no any moving
  537. int STAND_ZUPT = 0;
  538. if((frame_index > 15 && gyr_norm_window[window_index] < 0.5f && fabs(min_window_val(gyr_norm_window, 10) - max_window_val(gyr_norm_window, 10)) < 0.2f))
  539. STAND_ZUPT = 1;
  540. //zupt
  541. if (RUN_ZUPT || STAND_ZUPT)
  542. {
  543. stand_num = stand_num + 1;
  544. //K = P*H'/(H*P*H' + R);
  545. Kalfman_gain(P, Temporary_array1, Temporary_array2, K);
  546. //delta_x = K * [vel_n(:,i);];
  547. multiply9x3(K, vel_n, delta_x);
  548. State_covariance_matrix_corr(P, P_prev, K);
  549. //这里先从设置 delta_x(3) = atan2(C(2,1),C(1,1));
  550. //意味着每一步的参考方向是IMU X轴方向
  551. delta_x[2] = atan2(C[3], C[0]);
  552. Att_matrix_corr(C, C_prev, Temporary_array1, Temporary_array2, delta_x);
  553. pos_n_corr(pos_n, delta_x);
  554. vel_n_corr(vel_n, delta_x);
  555. last_pos_n[0] = pos_n[0];
  556. last_pos_n[1] = pos_n[1];
  557. last_pos_n[2] = pos_n[2];
  558. HAS_RESULT = 1;
  559. }
  560. else
  561. {
  562. stand_num = 0;
  563. }
  564. State_covariance_matrix_orthogonalization(P);
  565. /*theta = -0.61;
  566. temp = [cos(theta), sin(theta); -sin(theta), cos(theta)];
  567. pos_temp = temp * [pos_result(1); pos_result(2)];
  568. pos_result(1) = pos_temp(1);
  569. pos_result(2) = pos_temp(2);*/
  570. float pos_offset_temp0 = pos_n[0] - last_pos_n[0];
  571. float pos_offset_temp1 = pos_n[1] - last_pos_n[1];
  572. float pos_offset_temp2 = pos_n[2] - last_pos_n[2];
  573. pos_offset[0] = -0.7949f * pos_offset_temp0 - 0.6067f * pos_offset_temp1;
  574. pos_offset[1] = 0.6067f * pos_offset_temp0 - 0.7949f * pos_offset_temp1;
  575. // pos_offset[0] = pos_offset_temp0;
  576. // pos_offset[1] = pos_offset_temp1;
  577. pos_offset[2] = pos_offset_temp2;
  578. // memcpy(pos_res, acc_n, 3 * sizeof(float));
  579. memcpy(pos_res, pos_offset, 3 * sizeof(float));
  580. if(HAS_RESULT == 1)
  581. {
  582. if(pos_offset[1] > 0.15f)
  583. {
  584. movement_e = MOTION_LEFT;
  585. HAS_RESULT = 0;
  586. }
  587. else if(pos_offset[1] < -0.15f)
  588. {
  589. movement_e = MOTION_RIGHT;
  590. HAS_RESULT = 0;
  591. }
  592. else if(pos_offset[2] > 0.2f)
  593. {
  594. movement_e = MOTION_JUMP;
  595. HAS_RESULT = 0;
  596. }
  597. else if(IS_DOWN == 1)
  598. {
  599. movement_e = MOTION_DOWN;
  600. stand_num = 0;
  601. IS_DOWN = 0;
  602. }
  603. // else if(stand_num > 100)
  604. // {
  605. // movement_e = MOTION_STOP;
  606. // stand_num = 0;
  607. // }
  608. }
  609. return movement_e;
  610. }
  611. //int main()
  612. //{
  613. // FILE *fp = NULL;
  614. //
  615. // FILE *out = NULL;
  616. //
  617. // char *line, *record;
  618. //
  619. // char buffer[1024];
  620. //
  621. // int num = 0;
  622. // float *gyr = (float *)malloc(3 * sizeof(float));
  623. // float *acc = (float *)malloc(3 * sizeof(float));
  624. //
  625. // out = fopen("F:\\work\\matlab\\result.txt", "a+");
  626. //
  627. // if ((fp = fopen("F:\\work\\matlab\\FootRight8_CalInertialAndMag.csv", "r")) != NULL)
  628. //
  629. // {
  630. //
  631. // fseek(fp, 170L, SEEK_SET); //定位到第二行,每个英文字符大小为1
  632. //
  633. // char delims[] = ",";
  634. //
  635. // char *result = NULL;
  636. //
  637. // int j = 0;
  638. //
  639. // while ((line = fgets(buffer, sizeof(buffer), fp)) != NULL)//当没有读取到文件末尾时循环继续
  640. //
  641. // {
  642. //
  643. // record = strtok(line, ",");
  644. //
  645. // while (record != NULL)//读取每一行的数据
  646. //
  647. // {
  648. //
  649. // if (strcmp(record, "Ps:") == 0)//当读取到Ps那一行时,不再继续读取
  650. //
  651. // return 0;
  652. //
  653. //
  654. //
  655. //
  656. // switch (j) {
  657. //
  658. // case 1:
  659. // gyr[0] = atof(record);
  660. // break;
  661. // case 2:
  662. // gyr[1] = atof(record);
  663. // break;
  664. // case 3:
  665. // gyr[2] = atof(record);
  666. // break;
  667. // case 4:
  668. // acc[0] = atof(record);
  669. // break;
  670. // case 5:
  671. // acc[1] = atof(record);
  672. // break;
  673. // case 6:
  674. // acc[2] = atof(record);
  675. // break;
  676. // default:
  677. // break;
  678. // }
  679. //
  680. //
  681. // if (j == 6) //只需读取前9列
  682. //
  683. // break;
  684. //
  685. // record = strtok(NULL, ",");
  686. //
  687. // j++;
  688. //
  689. // }
  690. //
  691. //
  692. //
  693. // if (num > 0)
  694. // {
  695. //
  696. // footPDR(num, gyr, acc);
  697. //
  698. // for (int i = 0; i < 3; i++)
  699. // {
  700. // fprintf(out, "%f ", angle_out[i]);
  701. // }
  702. // fprintf(out, "\n ");
  703. //
  704. //
  705. //
  706. // }
  707. //
  708. // num++;
  709. // j = 0;
  710. //
  711. //
  712. // }
  713. //
  714. // fclose(fp);
  715. //
  716. // fp = NULL;
  717. //
  718. // }
  719. //
  720. // /*
  721. // float *gyr = (float *)malloc(3 * sizeof(float));
  722. // float *acc = (float *)malloc(3 * sizeof(float));
  723. //
  724. // int num;
  725. // float gyr_x, gyr_y, gyr_z, acc_x, acc_y, acc_z, mag_x, mag_y, mag_z;
  726. // while (fscanf(file, "%d%f%f%f%f%f%f%f%f%f", &num, &gyr_x, &gyr_y, &gyr_z, &acc_x, &acc_y, &acc_z, &mag_x, &mag_y, &mag_z)) {
  727. // printf("%d %f %f %f %f %f %f %f %f %f", gyr_x, gyr_y, gyr_z, acc_x, acc_y, acc_z, mag_x, mag_y, mag_z);
  728. //
  729. // }
  730. // fclose(file);
  731. //
  732. // return 0;
  733. // */
  734. //
  735. //}
  736. /*
  737. int main()
  738. {
  739. float acc_x = 0.0;
  740. float acc_y = 0.1;
  741. float acc_z = 9.75;
  742. float acc[] = { acc_x , acc_y, acc_z };
  743. float gyr_x = 0.01;
  744. float gyr_z = 0.02;
  745. float gyr_y = 0.03;
  746. float gyr[] = { gyr_x , gyr_y, gyr_z };
  747. P = (float *)malloc(81*sizeof(float));
  748. memset(P, 0, 81*sizeof(float));
  749. P_prev = (float *)malloc(81*sizeof(float));
  750. memset(P_prev, 0, 81*sizeof(float));
  751. C = (float *)malloc(9);
  752. float* C_inv = (float *) malloc(9 * sizeof(float));
  753. memset(C_inv, 0, 9 * sizeof(float));
  754. acc_n = (float *) malloc(3 * sizeof(float));
  755. memset(acc_n, 0, 3 * sizeof(float));
  756. vel_n = (float *) malloc(3 * sizeof(float));
  757. memset(vel_n, 0, 3 * sizeof(float));
  758. pos_n = (float *) malloc(3 * sizeof(float));
  759. memset(pos_n, 0, 3 * sizeof(float));
  760. K = (float *)malloc(27 * sizeof(float));
  761. memset(K, 0, 27 * sizeof(float));
  762. Temporary_array1 = (float *)malloc(9 * sizeof(float));
  763. memset(Temporary_array1, 0, 9 * sizeof(float));
  764. Temporary_array2 = (float *)malloc(9 * sizeof(float));
  765. memset(Temporary_array2, 0, 9 * sizeof(float));
  766. delta_x = (float *)malloc(9 * sizeof(float));
  767. memset(delta_x, 0, 9 * sizeof(float));
  768. C_inv[0] = 2.0;
  769. C_inv[1] = dt*gyr_z;
  770. C_inv[2] = -dt*gyr_y;
  771. C_inv[3] = -dt*gyr_z;
  772. C_inv[4] = 2.0;
  773. C_inv[5] = dt*gyr_x;
  774. C_inv[6] = dt*gyr_y;
  775. C_inv[7] = -dt*gyr_x;
  776. C_inv[9] = 2.0;
  777. float* C_res =(float *) malloc(9 * sizeof(float));
  778. memset(C_res, 0, 9 * sizeof(float));
  779. invert3x3(C_inv, C_res);
  780. memset(C_inv, 0, 9 * sizeof(float));
  781. C_inv[0] = 2 * C[0] + C[1] * dt * gyr_z - C[2] * dt * gyr_y;
  782. C_inv[1] = 2 * C[1] - C[0] * dt * gyr_z + C[2] * dt * gyr_x;
  783. C_inv[2] = 2 * C[2] + C[0] * dt * gyr_y - C[1] * dt * gyr_x;
  784. C_inv[3] = 2 * C[3] + C[4] * dt * gyr_z - C[5] * dt * gyr_y;
  785. C_inv[4] = 2 * C[4] - C[3] * dt * gyr_z + C[5] * dt * gyr_x;
  786. C_inv[5] = 2 * C[5] + C[3] * dt * gyr_y - C[4] * dt * gyr_x;
  787. C_inv[6] = 2 * C[6] + C[7] * dt * gyr_z - C[8] * dt * gyr_y;
  788. C_inv[7] = 2 * C[7] - C[6] * dt * gyr_z + C[8] * dt * gyr_x;
  789. C_inv[8] = 2 * C[8] + C[6] * dt * gyr_y - C[7] * dt * gyr_x;
  790. multiply3x3(C_inv, C_res, C);
  791. //C*acc
  792. multiply3x1(C, acc, acc_n);
  793. vel_n[0] = vel_n[0] + acc_n[0] * dt;
  794. vel_n[1] = vel_n[1] + acc_n[1] * dt;
  795. vel_n[2] = vel_n[2] + (acc_n[2] - g) * dt;
  796. pos_n[0] = pos_n[0] + vel_n[0] * dt;
  797. pos_n[1] = pos_n[1] + vel_n[1] * dt;
  798. pos_n[2] = pos_n[2] + vel_n[2] * dt;
  799. float P_copy[] = { 0.0095, -0.0000 , 0.0020, 0.0003, -0.0015, 0.0000 , 0.0002 , - 0.0401, - 0.0011,
  800. -0.0000 ,0.0094 ,-0.0002, 0.0020 ,-0.0000, -0.0005 , 0.0410, -0.0001 ,-0.0051
  801. ,0.0020 , -0.0002 , 0.0830 , 0.0115 , 0.0238 , 0.0006 ,0.0077 , 0.0420 , 0.0000
  802. ,0.0003 , 0.0020 , 0.0115 , 0.6790 , 0.0047 , 0.0009 , 0.1350 , 0.0059 , -0.0015
  803. , -0.0015 , -0.0000 ,0.0238 , 0.0047 , 0.6851 , 0.0012 , 0.0023 , 0.1462 , 0.0006
  804. ,0.0000 , -0.0005 , 0.0006 , 0.0009 , 0.0012 , 0.5172 ,-0.0027 ,-0.0004 , 0.0850
  805. ,0.0002 , 0.0410 , 0.0077 , 0.1350 , 0.0023, -0.0027 , 0.3347 , 0.0040, -0.0270
  806. , -0.0401, -0.0001 , 0.0420 , 0.0059 , 0.1462 , -0.0004 , 0.0040 , 0.3562 , 0.0046
  807. , -0.0011 ,-0.0051 , 0.0000, -0.0015 , 0.0006 , 0.0850 ,-0.0270 , 0.0046 , 0.0384 };
  808. for (int i = 0; i < 81; i++)
  809. {
  810. if (i % 9 == 0)
  811. printf("\n");
  812. printf("%6.8f ", P_copy[i]);
  813. P_copy[i] /= 10000;
  814. }
  815. printf("\n");
  816. Kalfman_gain(P_copy, Temporary_array1, Temporary_array2, K);
  817. for (int i = 0; i < 27; i++)
  818. {
  819. if (i % 3 == 0)
  820. printf("\n");
  821. printf("%6.4f ", K[i]);
  822. }
  823. //inv
  824. return 0;
  825. }
  826. */