18_ADC单通道
1、硬件
定义:ADC可以将引脚上连续变化的模拟电压转换为内存中存储的数字变量

1.1独立的8位逐次逼近型ADC
通道选择开关:选择输入通道
DAC:数模转换器,输出最大最小值由Vref+,Vref-决定,也决定了ADC 的输入范围
比较寄存器:选择的通道模拟量通过比较器与DAC输出的模拟量进行比较,直到数值相同为止(采用二分法进行逐次逼近)
逐次比较寄存器:将比较值传回DAC使DAC继续输出值比较,将最终值传到锁存器中
clock:提供ADC时钟
start:发出开始触发信号
1.2STM32的ADC框图

参考电压Vref+、Vref-由模拟电路电源VDDA、VSSA提供
本实验选用的STM32F103C8T6能选用的ADC通道有10个

转换的数据存储在ADC数据寄存器中,注入通道有4个数据寄存器,规则通道仅一个,在多通道的情况下需采用DMA进行数据转运,避免前面的数据被后边数据覆盖
设置模拟看门狗可观察数据的异常情况,设置阈值高限与低限。超过范围就会发出警告
ADCCLK来源于RCC,最大就只能14Mhz,采用6分频时为12Mhz
状态标志位显示转换是否完成,可通过是否完成转换设置中断
其余与独立ADC类似
1.3 ADC配置结构与顺序

1、开启RCC时钟,包括ADC时钟,GPIO时钟,ADCCLK分频器时钟
2、配置GPIO,将输入改为模拟输入
3、多路开关控制,包括通道选择,转换模式选择等
4、配置ADC转换器
5、使能ADC1
6、校准ADC1
7、软件触发ADC1
8、判断转换完毕后获取ADC1数值
2、接线图
通过调节电位器查看不断变化的电压值

3、程序
单通道模块程序
1 #include "stm32f10x.h" 2 3 4 void adc_init(void) 5 { 6 /*开启RCC时钟*/ 7 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);//本实验使用PA0,开启GPIOA时钟 8 RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE);//本实验使用ADC1,开启ADC1时钟 9 RCC_ADCCLKConfig(RCC_PCLK2_Div6);//ADCCLK分频器采用6分频,频率为12Mhz 10 /*配置GPIO结构体*/ 11 GPIO_InitTypeDef GPIO_InitStructure; 12 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;//选择模拟输入 13 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;//选择PA0 14 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; 15 GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化GPIO结构体 16 /*配置多路开关*/ 17 ADC_RegularChannelConfig(ADC1,ADC_Channel_0,1,ADC_SampleTime_55Cycles5);//选择ADC1的通道0,RANK在非扫描模式下无效,只取一通道,采样时间选择55 18 /*配置ADC转换器*/ 19 ADC_InitTypeDef ADC_InitStructure;//定义一个ADC结构体 20 ADC_InitStructure.ADC_Mode=ADC_Mode_Independent;//选择独立模式,本实验仅涉及1个ADC 21 ADC_InitStructure.ADC_ScanConvMode=DISABLE;//选择单通道模式 22 ADC_InitStructure.ADC_ContinuousConvMode=DISABLE;//选择单模式还是连续模式,本实验选择单模式 23 ADC_InitStructure.ADC_ExternalTrigConv =ADC_ExternalTrigConv_None;//触发源选择软件触发 24 ADC_InitStructure.ADC_DataAlign=ADC_DataAlign_Right;//选择右对齐 25 ADC_InitStructure.ADC_NbrOfChannel=1;//选择1通道 26 ADC_Init( ADC1, &ADC_InitStructure); 27 /*使能ADC1*/ 28 ADC_Cmd(ADC1,ENABLE); 29 /*ADC校准*/ 30 ADC_ResetCalibration(ADC1); 31 while( ADC_GetResetCalibrationStatus(ADC1)==SET); 32 ADC_StartCalibration( ADC1); 33 while(ADC_GetCalibrationStatus(ADC1)==SET); 34 } 35 36 uint16_t get_adcvalue(void) 37 { 38 ADC_SoftwareStartConvCmd(ADC1,ENABLE);//软件触发ADC 39 while(ADC_GetFlagStatus(ADC1,ADC_FLAG_EOC) == RESET );//如果转换完毕,则可获取最终的结构,状态标志位在数据获取后自动置0 40 return ADC_GetConversionValue(ADC1); 41 42 43 }

浙公网安备 33010602011771号