hal_battery_NoPowerEnPin - 副本.c 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285
  1. /*********************************************************************
  2. * INCLUDES
  3. */
  4. #include "usr_config.h"
  5. #include "hal_battery.h"
  6. #include "cli.h"
  7. #define PRINTBLE 0
  8. int16_t ADC_GetValue(uint32_t channel)
  9. {
  10. int16_t temp=0;
  11. ADC_Read(channel, &temp);
  12. return temp;
  13. }
  14. //返回5V信号,有5V的话返回1,没有的话返回0
  15. static char charge_in(void)
  16. {
  17. uint32_t ch = nrf_gpio_pin_read(PIN_CHARGING);
  18. if(ch)return 1;
  19. else return 0;
  20. }
  21. static float filter(float value, float kg, float* preBestResult)
  22. {
  23. float new_v = value;
  24. new_v = *preBestResult * (1.0f - kg) + value * kg;
  25. *preBestResult = new_v;
  26. return new_v;
  27. }
  28. //负载测量仪
  29. //const float poo1o[]={5.10168165379740,5.34733044915476,5.61704724780813,5.91504952455148,6.24538762712249,6.61232594416931,7.01953712767654,7.46935265033756,7.96335122494516,8.50358200192486,9.09281468086492,9.73412484740972,10.4325753748233,11.1947240789575,12.0279998795062,12.9374916137117,13.9260172775225,14.9884510507725,16.1112400764950,17.2842706470249,18.5004202529463,19.7491314797588,21.0185653416731,22.2986943158191,23.5786963439054,24.8484876852771,26.0960349502041,27.3050010170951,28.4610454562188,29.5600116621742,30.6034682628590,31.5984702746944,32.5538106818571,33.4783670170583,34.3806559960012,35.2670128624846,36.1402606107567,36.9999854839693,37.8491813155179,38.6980882892879,39.5608382688438,40.4501589172903,41.3790038698800,42.3638365959298,43.4226235933126,44.5726867709324,45.8261573855592,47.1820084404052,48.6371187751347,50.1935842257010,51.8472994098979,53.5916193269800,55.4227167186607,57.3375320331711,59.3313953215555,61.3855139357523,63.4578870950691,65.4854598022728,67.4115262370806,69.2059495638218,70.8663781140949,72.4135268452713,73.8842849282509,75.3217897769173,76.7641290674375,78.2395953684845,79.7625546270391,81.3527328594521,83.0420141741465,84.8459239717299,86.7331023820235,88.6178189933847,90.3918821756187,91.9708771194967,93.3175662114905,94.4438984171043,95.3852594026215,96.1782551857171,96.8552759200241,97.4399007649065,97.9470337398631,98.3861216083791,98.7637272009236,99.0856995099079,99.3556936180377,99.5764952915733,99.7517164714185,99.8847888907893,99.9783503988427,100.038705667285,100.073274028685,100.088914482705,100.091844988568,100.087235862329,100.078726223926,100.068495717630,100.057471632431,100.046085695070,100.034540863310,100.022996031552,100.011610094200};
  30. //鞋子ADC
  31. static const float poo1o[] = {0, 0, 0.0279893723606430, 0.174605323652602, 0.325796538285416, 0.495164949358988, 0.661918800578876, 0.829024800123971, 1.00225498989324, 1.17936073685608, 1.37258677752597, 1.56525700069634, 1.78680072433224, 2.00361106262195, 2.24466616203811, 2.46699160701705, 2.77834696254638, 3.12186809827754, 3.58442625993982, 4.15025435558636, 4.75855743544068, 5.51189718744822, 6.35834306864975, 7.38461196888009, 8.48997478633724, 9.43096936165977, 10.3817319764220, 11.4116388420216, 12.3939372566211, 13.5048186806524, 14.5904959858255, 15.5237940825920, 16.4790857938893, 17.8137595522187, 18.9982251103467, 20.3392608271850, 21.5817542329461, 22.7218253119165, 23.9444316340532, 25.2939077624602, 26.6264082603126, 27.6802415218000, 29.0022881606974, 30.1783424265851, 31.1179209268523, 32.2887764986448, 33.3732790985050, 34.2380544358441, 35.2041112278740, 36.0163848326001, 36.8624779801428, 37.6634899287154, 38.5186413495501, 39.4878256764553, 40.2471232681709, 41.2081417271725, 42.3322924899204, 43.7047997876243, 44.9058976548061, 46.5044971286874, 47.8927266715832, 49.8558978793141, 51.9022338412845, 54.2586141300707, 56.3903798469888, 58.7696803719223, 60.8764981712366, 62.2358527791606, 63.8383633243999, 65.5021323737117, 67.1556090613014, 69.0159229136298, 70.1420773342446, 71.2282683025524, 72.4548338447843, 73.6556507850819, 74.8128040906371, 75.8695501837768, 77.1323517287879, 78.6365237973046, 80.3752005495001, 82.8468947240450, 86.6163997907370, 91.2910588313494, 93.9702969410882, 95.4930183746766, 96.9114001488224, 97.8493292727541, 98.7169169431273, 99.3270162091455, 99.6869018017068, 99.9917942993789, 99.9689500363163, 99.97, 99.98, 99.98, 99.98, 99.98, 99.99, 99.99, 99.99};
  32. static float interp1(float x)
  33. {
  34. int absx = (int)x - 320;
  35. float max = poo1o[absx + 1];
  36. float min = poo1o[absx];
  37. float temp = x - (float)absx - 320.0f;
  38. return (max - min) * temp + min;
  39. }
  40. //返回电压百分比
  41. static float preBestResult_Voltage2power = 0;
  42. static float Voltage2power(float mV)
  43. {
  44. float rev = 0;
  45. float k = 0;
  46. static char init = 1;
  47. if (init)
  48. {
  49. preBestResult_Voltage2power = mV / 10;
  50. init = 0;
  51. }
  52. k = filter(mV / 10, 0.01, &preBestResult_Voltage2power);
  53. if (k < 320.0f)
  54. {
  55. rev = 0;
  56. }
  57. else if (k > 420.0f)
  58. {
  59. rev = 100;
  60. }
  61. else
  62. {
  63. rev = interp1(k);
  64. }
  65. return rev;
  66. }
  67. static const float chargeV2P[] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0.606184684199367, 0.938307744774148, 1.30769659743727, 1.87378869014097, 2.39210582883903, 2.92471759425620, 3.79782257541779, 4.54241638183623, 5.09886597521223, 5.98930945903392, 6.49613916536905, 7.57967916311061, 8.42757721701290, 9.26589943580526, 10.3408809248851, 11.4278317273525, 12.3098089504989, 13.8095299712012, 15.4373756551577, 16.8805115746597, 18.4871688551768, 20.0578462608782, 21.6336381358003, 22.9916066660508, 24.4652374859292, 25.6565902258290, 26.8453581267414, 27.9070922567514, 28.9713295466563, 30.0209078713242, 30.9380166385130, 32.0419258329631, 33.1827748787620, 33.8691297160915, 34.8949274023278, 35.8840553861847, 36.9638277084030, 37.8687458690322, 38.9939274175310, 40.4336758333268, 41.1114865403869, 42.6160733592240, 44.2493873543177, 45.6026105469954, 47.4664557187522, 49.0734043728910, 51.2998758679562, 52.8880367841713, 54.7587352342972, 57.0178625862682, 58.8608281071146, 60.3657347075748, 62.4281274954232, 64.3086188700345, 65.8044424890286, 68.6475622104224, 72.7352289117192, 76.9893033499930, 84.0930819869950, 92.2923770276700, 96.3286261252036, 99.7542287364423};
  68. static float interp1_chargeV2P(float x)
  69. {
  70. int absx = (int)x - 350;
  71. float max = chargeV2P[absx + 1];
  72. float min = chargeV2P[absx];
  73. float temp = x - (float)absx - 350.0f;
  74. return (max - min) * temp + min;
  75. }
  76. //返回电压百分比
  77. static float preBestResult_chargeV2P_f = 0;
  78. static float chargeV2P_f(float mV)
  79. {
  80. float rev = 0;
  81. float k = 0;
  82. static char init = 1;
  83. if (init)
  84. {
  85. preBestResult_chargeV2P_f = mV / 10;
  86. init = 0;
  87. }
  88. k = filter(mV / 10, 0.05, &preBestResult_chargeV2P_f);
  89. if (k < 350.0f)
  90. {
  91. rev = 0;
  92. }
  93. else if (k > 420.0f)
  94. {
  95. rev = 100;
  96. }
  97. else
  98. {
  99. rev = interp1_chargeV2P(k);
  100. }
  101. return rev;
  102. }
  103. //返回电量百分比
  104. static float Voltage2mah(float mah, float storage_capacity)
  105. {
  106. return mah / storage_capacity * 100.0f;
  107. }
  108. //返回电压剩余绝对容量
  109. static float mah2Voltage(float P, float storage_capacity)
  110. {
  111. return storage_capacity * P / 100.0f;
  112. }
  113. static void Charge(float mV, float* mAh, float interval_s)
  114. {
  115. float A = mV / 3000.0f * 1.1f;
  116. float dmAh = A * 1000.0f * interval_s / 3600.0f;
  117. *mAh = *mAh + dmAh;
  118. }
  119. static float Power_management(float mV_Battery, float mV_Charge)
  120. {
  121. static float P1 = 100;
  122. static float P2 = 0;
  123. float P_mAh = 0;
  124. float storage_capacity = 350;
  125. static float mAh = 0;
  126. static char sta = 0;
  127. static float kg = 0;
  128. switch (sta)
  129. {
  130. case 0:
  131. if (mV_Charge > 20)
  132. {
  133. sta = 2; //充电过程
  134. P1=chargeV2P_f(mV_Battery);
  135. }
  136. else
  137. {
  138. P1 = Voltage2power(mV_Battery);
  139. sta = 1; //放电过程
  140. }
  141. break;
  142. case 1:
  143. if (mV_Charge > 20)
  144. {
  145. sta = 2; //充电过程
  146. kg = 0;
  147. //解决插上充电没接电池状态下突然接上电池时电量不衔接的问题
  148. if((mV_Battery<4000)&&(P1>95.0f))
  149. {
  150. P1=chargeV2P_f(mV_Battery);
  151. }
  152. }
  153. else
  154. {
  155. //---------------------------------------------------
  156. P2 = Voltage2power(mV_Battery);
  157. if (P1 > P2) //过滤刚拔掉充电线时候的虚高
  158. {
  159. P1 = P2;
  160. }
  161. //解决充满电后充电器不拔出来的情况显示不到100%的情况
  162. if(charge_in()&&(P1>95.0f))
  163. {
  164. P1=100.0f;
  165. }
  166. //---------------------------------------------------
  167. //---------------------------------------------------
  168. }
  169. break;
  170. case 2:
  171. if (mV_Charge < 20)
  172. {
  173. sta = 1; //放电过程
  174. //初始化滤波器波器
  175. preBestResult_Voltage2power = mV_Battery / 10;
  176. if (P1 > 99.1f)
  177. {
  178. P1 = 100.0f;
  179. }
  180. // //解决大电流充电的时候突然把电池拔掉
  181. // if(mV_Battery>4100)
  182. // {
  183. // P1=Voltage2power(mV_Battery);
  184. // }
  185. }
  186. else
  187. {
  188. //---------------------------------------------------
  189. mAh = mah2Voltage(P1, storage_capacity);
  190. Charge(mV_Charge, &mAh, 1);
  191. P_mAh = Voltage2mah(mAh, storage_capacity);
  192. P2 = chargeV2P_f(mV_Battery);
  193. kg = mV_Charge / 1000.0f;
  194. if (kg > 1.0f)
  195. {
  196. kg = 1.0f;
  197. }
  198. P2 = (1.0f - kg) * P2 + kg * P_mAh;
  199. if (P1 < P2) //过滤刚插上充电线时候的虚低
  200. {
  201. P1 = P2;
  202. }
  203. if (P1 > 100)
  204. {
  205. P1 = 99.9;
  206. }
  207. //---------------------------------------------------
  208. // P2=chargeV2P_f(mV_Battery);
  209. // if(P1<P2)//过滤刚插上充电线时候的虚低
  210. // P1=P2;
  211. //---------------------------------------------------
  212. }
  213. break;
  214. }
  215. return P1;
  216. }
  217. static float adc_tp4056_power = 0;
  218. static void hal_battery_Process(void)
  219. {
  220. #if PRINTBLE
  221. char buff[256];
  222. unsigned char len = 0;
  223. #endif
  224. int16_t adcVal;
  225. int16_t CHARGMEASURE;
  226. int16_t volTemp;
  227. int16_t volTemp_CHARGMEASURE;
  228. adcVal = ADC_GetValue(PIN_ADC_BAT_CHANNEL);
  229. volTemp = ADC_RESULT_IN_MILLI_VOLTS(adcVal) * 5 / 3; // 电池电压转换计算
  230. CHARGMEASURE = ADC_GetValue(PIN_ADC_CHARGMEASURE_CHANNEL);
  231. volTemp_CHARGMEASURE = ADC_RESULT_IN_MILLI_VOLTS(CHARGMEASURE);// 电池电压转换计算
  232. adc_tp4056_power = Power_management((float)volTemp, (float)volTemp_CHARGMEASURE);
  233. #if PRINTBLE
  234. len = sprintf(buff, "%4d ,%4d ,%4d,%f\r\n",TIME_GetTicks(), volTemp, volTemp_CHARGMEASURE, adc_tp4056_power);
  235. send_bytes_client((unsigned char*)buff, len);
  236. #endif
  237. // cli_process(&clirtt);
  238. // uint8_t persent = 0;
  239. // persent = (uint8_t)(adc_tp4056_power+0.5f);
  240. // DEBUG_LOG("hal_battery_Process:%d,%d\n",persent,volTemp);
  241. }
  242. //返回的电量范围: 0~100 表示电量百分比
  243. uint8_t GetBatteryPersent(void)
  244. {
  245. uint8_t persent = 0;
  246. persent = (uint8_t)(adc_tp4056_power+0.5f);
  247. if(persent > 100)persent =100;
  248. return persent;
  249. }
  250. //void battydeb_pcs(cli_t *p_cli, unsigned short argc, char **argv)
  251. //{
  252. // cli_printf(p_cli, "GetBatteryPersent %d",GetBatteryPersent());
  253. //}
  254. //CLI_CMD_REGISTER(battydeb, "Cli cmd history", battydeb_pcs);
  255. void hal_battery_init(void){
  256. hal_battery_Process();
  257. Process_Start(1000,"hal_battery_Process",hal_battery_Process);
  258. }