蓝桥杯嵌入式STM32学习笔记(四)——ADC的学习与配置

蓝桥杯ADC的学习

ADC就是模数转换,咱们要将电压大小的模拟量,通过采样量化为数字量获得一个数字的电压值。
通过查看原理图,咱们发现R37是一个滑动变阻器,而咱们能够经过软件把PB0设置成ADC输入引脚,就能够采集PB0引脚上的电压数据了
步骤以下:
1.使能时钟
这里咱们须要使能GPIOB和ADC1上的时钟,而且因为STM32的ADC最大转换速率为1Mhz,也就是转换时间为1us,不要让ADC的时钟超过14M,因此咱们须要对系统时钟进行分频。
web

RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1 | RCC_APB2Periph_GPIOB, ENABLE);
RCC_ADCCLKConfig(RCC_PCLK2_Div6);

2.初始化GPIO,ADC
而后咱们对GPIO和ADC进行初始化
svg

/* Configure PB.0 (ADC Channel 8) as analog input -------------------------*/
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB, &GPIO_InitStructure);

这里咱们把GPIO的模式设置为模拟输入函数

ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;
  ADC_InitStructure.ADC_ScanConvMode = DISABLE;
  ADC_InitStructure.ADC_ContinuousConvMode = DISABLE;
  ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;
  ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;
  ADC_InitStructure.ADC_NbrOfChannel = 1;
  ADC_Init(ADC1, &ADC_InitStructure);

ADC的模式设置为独立模式,ADC_ScanConvMode是设置是否连续扫描,其实这里也能够设置为连续扫描。ADC_ContinuousConvMode是设置是否连续转换,这里选否。
咱们把硬件编译关上,让数据向右对齐,设置序列规则长度为1。
3.使能ADC并校准
而后咱们ADC还须要一个重校准的步骤
学习

/* Enable ADC1 */
  ADC_Cmd(ADC1, ENABLE);
  ADC_ResetCalibration(ADC1);
  while(ADC_GetResetCalibrationStatus(ADC1));
  ADC_StartCalibration(ADC1);
  while(ADC_GetCalibrationStatus(ADC1));

咱们先要使能ADC,这很关键,若是不先使能的话,后面的操做将没法执行。
而后咱们须要重启校准,记住咱们每次进行校准以后须要等待校准结束。这里是经过获取校准状态来判断是否校准是否结束的。
4.编写函数读取ADC值
我以为编写函数读取ADC的这个步骤是,配置ADC中比较关键的,由于其余的步骤咱们能够借鉴官方给咱们的固件库的代码,惟有这个是须要咱们从无到有打上去的,因此咱们要理解这个思路。
ui

U16 Getadc(u8 channel)
{
	U16 Temp;
	ADC_RegularChannelConfig(ADC1, channel, 1, ADC_SampleTime_239Cycles5);
	ADC_SoftwareStartConvCmd(ADC1, ENABLE);
	While(ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC)==0);
	Temp= ADC_GetConversionValue(ADC1);
	ADC_SoftwareStartConvCmd(ADC1, DISABLE);
	Return Temp;
}

void ADC_RegularChannelConfig(ADC_TypeDef* ADCx, uint8_t ADC_Channel, uint8_t Rank, uint8_t ADC_SampleTime);
是用来配置通道的环境的一个函数,第一个入口参数为选的配置的ADC,第二个入口参数为选择配置的通道,第三个入口参数则配置ADC编号(例如使用ADC1,那么就写1),第四个入口参数则表明单次采样的时钟周期数。
然后咱们就能够经过软件去启动咱们的AD转换了
void ADC_SoftwareStartConvCmd(ADC_TypeDef* ADCx, FunctionalState NewState);
转换开启后咱们能够根据标志位EOC判断转换是否完成
在这里插入图片描述
这里能够得知咱们须要等待EOC从0变到1才能执行下一步,因此咱们就用while去判断EOC是否为0,是0的时候等待,不为0的时候跳出
而后这时候咱们就能够读取AD的值了,咱们用这个函数:
uint16_t ADC_GetConversionValue(ADC_TypeDef* ADCx);
能够得到AD的值而后把它赋给Temp,而后返回Temp便可
es5