6.1 ADC简介
ADC,Analog-to-Digital Converter的缩写,指模数转换器 。是指将连续变化的模拟信号转换为离散的数字信号。
STM32F4的ADC可以设置为6位,8位,12位的模式,位数越高,分辨率越高。
6.2 ADC的作用
得到测量点的电压值,进而可以转换为所需要的数据。比如温度传感器,不同温度会有不同电阻值,则固定电压串联上一个固定电阻后,采集到的电压值会根据温度不同而发生变化,则可以根据采集到的电压计算出温度。
AD值转电压值计算方法:
比如12位的ADC,参考电压为3.3V,则采集值 4096(2的12次方)代表3.3V,每个值为3.3除以4096,通常0-5的值会存在比较大的误差。
6.3 ADC初始化代码
//初始化ADC
void AdcInit()
{
GPIO_InitTypeDef GPIO_InitStructure;
ADC_CommonInitTypeDef ADC_CommonInitStructure;
ADC_InitTypeDef ADC_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);//使能GPIOA时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE); //使能ADC1时钟
//先初始化ADC1通道5 IO口
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;//PA5 通道5
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AN;//模拟输入
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL ;//不带上下拉
GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化
RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC1,ENABLE); //ADC1复位
RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC1,DISABLE); //复位结束
ADC_CommonInitStructure.ADC_Mode = ADC_Mode_Independent; //独立模式
ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_5Cycles; // 两个采样阶段之间的延迟5个时钟
ADC_CommonInitStructure.ADC_DMAAccessMode = ADC_DMAAccessMode_Disabled; //DMA失能
ADC_CommonInitStructure.ADC_Prescaler = ADC_Prescaler_Div4; //预分频4分频。ADCCLK=PCLK2/4=84/4=21Mhz,ADC时钟最好不要超过36Mhz
ADC_CommonInit(&ADC_CommonInitStructure); //初始化
ADC_InitStructure.ADC_Resolution = ADC_Resolution_12b; //12位模式
ADC_InitStructure.ADC_ScanConvMode = DISABLE; //非扫描模式
ADC_InitStructure.ADC_ContinuousConvMode = DISABLE; //关闭连续转换
ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_None;//禁止触发检测,使用软件触发
ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; //右对齐
ADC_InitStructure.ADC_NbrOfConversion = 1; //1个转换在规则序列中 也就是只转换规则序列1
ADC_Init(ADC1, &ADC_InitStructure); //ADC初始化
ADC_Cmd(ADC1, ENABLE); //开启AD转换器
}
u16 GetAdcValue(u8 ch) //设置指定ADC的规则组通道,一个序列,采样时间
{
ADC_RegularChannelConfig(ADC1, ch, 1, ADC_SampleTime_480Cycles ); //ADC1,ADC通道,480个周期,提高采样时间可以提高精确度
ADC_SoftwareStartConv(ADC1); //使能指定的ADC1的软件转换启动功能
while(!ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC ));//等待转换结束
return ADC_GetConversionValue(ADC1); //返回最近一次ADC1规则组的转换结果
}
// 得到通道ch的值
u16 Get_Adc_Average(u8 ch,u8 times)
{
u32 uADvalue=0;
u8 t;
for(t=0;t<times;t++)
{
uADvalue += GetAdcValue(ch);
delay_ms(5);
}
return uADvalue/times;
}