STM8L之ADC
STM8L之ADC
/*******************************************************************************
*名 ? ?稱: Hal_Comm_GetBatADC
*功 ? ?能: 獲取電池電量信息
*入口參數: 無
*出口參數: 電量AD值
*說 ? ?明:?
*******************************************************************************/
unsigned int Hal_Comm_GetBatADC(void)
{
unsigned int Result = 0, value_adc = 0;
unsigned char index = 0;
? GPIO_Init(VOL_ADC_PORT,VOL_ADC_PIN,GPIO_Mode_In_FL_No_IT);//VOL_ADC
? ADC1->CR1 |= 0x01;//使能AD
? ADC1->CR3 &= ~0x1F;// ?選擇采樣時間 384 周期 ?通道清空?
? ADC1->CR3 |= 0x00; ?// channel 0 is selected?
? ADC1->SQR[0] = ADC1->SQR[1] = ADC1->SQR[2] = ADC1->SQR[3] = 0x00;
? ADC1->SQR[3] = 0x01;// 選擇通道0掃描 ?
? ADC1->SR &= 0x00;// conversion not complete?
? ADC1->SR = 0; ? ?// conversion 標識清空
? ADC1->CR1 |= 0x03;//使能AD并開始轉換?
??
? while(!(ADC1->SR & 0x01)); //waitloop ? bit0: 1 complete ? 0 not complete?
?
? for(index = 0; index < 10; index++)
? {
? ? ADC1->SR = 0; ?// conversion 標識清空?
? ? ADC1->CR1 |= 0x03;//使能AD ?開始轉換
? ? while(!(ADC1->SR & 0x01));//waitloop ?conversion ?complete?
? ? Result = ADC1->DRH; ? ? //總共計算16bit的值,但ADC為12 bit 長度
? ? Result <<= 8; ? ? ? ? ? //ADC1->DRH為高8位,
? ? Result += ADC1->DRL; ? ?//ADC1->DRL為低8位
? ? value_adc += Result;
if(index != 0)value_adc = value_adc/2; ?//獲取多次數據,計算平均值 ?
? ? index++;
? }
? ADC1->CR1 &= 0xFE;//關閉AD?
? ADC1->CR3 &= ~0x1F;//選擇通道?
? ADC1->CR3 |= 0x11;?
return value_adc;
}
我們一般在設計原理圖的時候會把ADC的輸入電壓范圍設定在:0~3.3v,如果設置ADC為12位的,那么12位滿量程對應的就是3.3V,12位滿量程對應的數字值是:2^12。數值0對應的就是0V。如果轉換后的ADC數值為X,X對應的模擬電壓為Y,那么會有這么一個等式成立:2^12/3.3=X/Y,=>Y=(3.3*X)/2^12
在我們的智能鎖項目中,滿量程Vref為3.31V,總電壓(M6V)/測試電壓(VOL_ADC) = 3
4096/3.31 = value_adc/Va
Va = value_adc * 3.31 / 4096
總電壓 = Va * 3
即程序中的vin = value_adc * 3.31 * 3 / 4096?
/*******************************************************************************
*名 ? ?稱: Hal_Comm_GetBatADC
*功 ? ?能: 獲取電池電量信息
*入口參數: 無
*出口參數: 電量AD值
*說 ? ?明:?
*******************************************************************************/
unsigned int Hal_Comm_GetBatADC(void)
{
unsigned int Result = 0, value_adc = 0;
unsigned char index = 0;
? GPIO_Init(VOL_ADC_PORT,VOL_ADC_PIN,GPIO_Mode_In_FL_No_IT);//VOL_ADC
? ADC1->CR1 |= 0x01;//使能AD
? ADC1->CR3 &= ~0x1F;// ?選擇采樣時間 384 周期 ?通道清空?
? ADC1->CR3 |= 0x00; ?// channel 0 is selected?
? ADC1->SQR[0] = ADC1->SQR[1] = ADC1->SQR[2] = ADC1->SQR[3] = 0x00;
? ADC1->SQR[3] = 0x01;// 選擇通道0掃描 ?
? ADC1->SR &= 0x00;// conversion not complete?
? ADC1->SR = 0; ? ?// conversion 標識清空
? ADC1->CR1 |= 0x03;//使能AD并開始轉換?
??
? while(!(ADC1->SR & 0x01)); //waitloop ? bit0: 1 complete ? 0 not complete?
?
? for(index = 0; index < 10; index++)
? {
? ? ADC1->SR = 0; ?// conversion 標識清空?
? ? ADC1->CR1 |= 0x03;//使能AD ?開始轉換
? ? while(!(ADC1->SR & 0x01));//waitloop ?conversion ?complete?
? ? Result = ADC1->DRH; ? ? //總共計算16bit的值,但ADC為12 bit 長度
? ? Result <<= 8; ? ? ? ? ? //ADC1->DRH為高8位,
? ? Result += ADC1->DRL; ? ?//ADC1->DRL為低8位
? ? value_adc += Result;
if(index != 0)value_adc = value_adc/2; ?//獲取多次數據,計算平均值 ?
? ? index++;
? }
? ADC1->CR1 &= 0xFE;//關閉AD?
? ADC1->CR3 &= ~0x1F;//選擇通道?
? ADC1->CR3 |= 0x11;?
return value_adc;
}
我們一般在設計原理圖的時候會把ADC的輸入電壓范圍設定在:0~3.3v,如果設置ADC為12位的,那么12位滿量程對應的就是3.3V,12位滿量程對應的數字值是:2^12。數值0對應的就是0V。如果轉換后的ADC數值為X,X對應的模擬電壓為Y,那么會有這么一個等式成立:2^12/3.3=X/Y,=>Y=(3.3*X)/2^12
在我們的智能鎖項目中,滿量程Vref為3.31V,總電壓(M6V)/測試電壓(VOL_ADC) = 3
4096/3.31 = value_adc/Va
Va = value_adc * 3.31 / 4096
總電壓 = Va * 3
即程序中的vin = value_adc * 3.31 * 3 / 4096?
總結
- 上一篇: STM8L之低功耗
- 下一篇: STM8L之外部中断