国产STC8H_ADC配置代码解释
国产STC8H_ADC配置代码解释
/* ADC配置 */
void ADC_Init(void)
{
ADC_InitTypeDef ADC_InitStructure; //结构定义
ADC_InitStructure.ADC_SMPduty = 31; //ADC 模拟信号采样时间控制, 0~31(注意: SMPDUTY 一定不能设置小于 10)
ADC_InitStructure.ADC_CsSetup = 0; //ADC 通道选择时间控制 0(默认),1
ADC_InitStructure.ADC_CsHold = 1; //ADC 通道选择保持时间控制 0,1(默认),2,3
ADC_InitStructure.ADC_Speed = ADC_SPEED_2X16T; //设置 ADC 工作时钟频率 ADC_SPEED_2X1T~ADC_SPEED_2X16T
ADC_InitStructure.ADC_AdjResult = ADC_RIGHT_JUSTIFIED; //ADC结果调整, ADC_LEFT_JUSTIFIED,ADC_RIGHT_JUSTIFIED
ADC_Inilize(&ADC_InitStructure); //初始化
ADC_PowerControl(ENABLE); //ADC电源开关, ENABLE或DISABLE
NVIC_ADC_Init(DISABLE,Priority_0); //中断使能, ENABLE/DISABLE; 优先级(低到高) Priority_0,Priority_1,Priority_2,Priority_3
}
国产8位单片机(CH55x系列,CH551/CH552/CH554) 的ADC初始化代码,CH55x自带10位ADC,库函数是沁恒官方库。
/* ADC配置 */
void ADC_Init(void)
{
ADC_InitTypeDef ADC_InitStructure; //结构定义
定义 ADC_InitTypeDef 类型的结构体变量 ADC_InitStructure,这个结构体用来一次性存放ADC所有配置参数,是嵌入式库常见写法。
ADC_InitStructure.ADC_SMPduty = 31; //ADC 模拟信号采样时间控制, 0~31(注意: SMPDUTY 一定不能设置小于 10)
ADC_SMPduty:采样保持时间(采样周期),范围0~31。
- 数值越大,采样时间越长,ADC采样越稳定;但转换速度变慢。
- 注释提醒:不要小于10,否则采样时间太短,电压采集不准,容易跳变。这里设最大值31,采样最稳,速度最低。
ADC_InitStructure.ADC_CsSetup = 0; //ADC 通道选择时间控制 0(默认),1
ADC_CsSetup:通道建立时间(切换ADC通道之后,等待模拟通道稳定的延时)
- 0:默认;1:增加建立延时。
- 多通道轮询采集时,如果通道电压差异很大,可以改成1;单通道采集保持0即可。
ADC_InitStructure.ADC_CsHold = 1; //ADC 通道选择保持时间控制 0,1(默认),2,3
ADC_CsHold:通道保持时间,选中通道后维持稳定的时间。
- 0~3可选,当前=1(默认值)。
- 作用:保证多路切换时,模拟开关稳定,防止串扰。
ADC_InitStructure.ADC_Speed = ADC_SPEED_2X16T; //设置 ADC 工作时钟频率 ADC_SPEED_2X1T~ADC_SPEED_2X16T
ADC_Speed:ADC时钟分频,ADC_SPEED_2X16T 代表ADC时钟 = 系统时钟 / 16。
- 可选:
ADC_SPEED_2X1T(最快)~ADC_SPEED_2X16T(最慢) - 速度越快,转换越快,但噪声变大;低速采样精度更好。当前配置是低速高精度模式。
ADC_InitStructure.ADC_AdjResult = ADC_RIGHT_JUSTIFIED; //ADC结果调整, ADC_LEFT_JUSTIFIED,ADC_RIGHT_JUSTIFIED
ADC_AdjResult:ADC采样数据对齐方式(CH55x是10位ADC,结果存放在16bit寄存器)
ADC_RIGHT_JUSTIFIED:右对齐
低10位是有效ADC数据,高6位=0。读取时直接拿
(u16)ADCRH << 8 | ADCRL就是真实采样值,最常用。
- 左对齐:10位数据放在高10位,低6位无效,适合直接做8位粗略采样。
ADC_Inilize(&ADC_InitStructure); //初始化
ADC_Inilize()(官方库函数,注意拼写不是Initialize):把上面结构体里所有参数写入ADC硬件寄存器,完成ADC内核配置。
ADC_PowerControl(ENABLE); //ADC电源开关, ENABLE或DISABLE
打开ADC模块电源。必须在配置完成之后再上电,顺序不能颠倒;如果DISABLE就是关闭ADC,降低功耗。
NVIC_ADC_Init(DISABLE,Priority_0); //中断使能, ENABLE/DISABLE; 优先级(低到高) Priority_0,Priority_1,Priority_2,Priority_3
}
NVIC_ADC_Init:ADC中断配置
- 第一个参数
DISABLE:关闭ADC中断,采用查询方式读取ADC结果(转换完成后软件手动查询标志位)。 - 第二个参数
Priority_0:中断优先级。当前中断没开,优先级参数无效;如果改成ENABLE才会生效。 - CH55x中断优先级:Priority_0最低,Priority_3最高。
整体总结
这个初始化函数最终效果:
- ADC采样时间拉满(SMPduty=31),低速模式,追求采样精度、抗噪声
- 右对齐输出,方便读取10位原始采样值
- ADC电源开启,不开启ADC中断,程序用查询方式读取AD值
- 通道建立/保持时间使用默认配置,适合单通道或者慢速多通道采集
配套读取ADC示例(CH55x)
u16 Get_ADC(u8 ch)
{
ADC_ChannelCfg(ch); //选择ADC通道 ch=0~7
ADC_Start(); //启动转换
while(!ADC_GetFlagStatus()); //等待转换完成(查询标志)
ADC_ClearFlag(); //清除标志位
return (u16)ADCRH << 8 | ADCRL; //右对齐读取10bit结果
}
/* ADC采集部分,仅P10有效 */
for(i=0; i<1; i++) // i从0~15,一共16路ADC通道(这里只选择1路 P10)
{
delay_ms(260); // 每采集一路,等待260ms,采样电容已经充分充放电
Get_ADCResult(i); // 参数0~15,查询方式做一次ADC, 丢弃一次,做高速连续采集(无延时)需打开注释
j = Get_ADCResult(i); // 参数0~15,查询方式做一次ADC, 返回值就是结果, 4096 为错误
if(j > 1800 && 0 == i) // ADC0通道_采集的信号阈值高于1800,给出有效信号
{
Fan_Count++;
if(Fan_Count > 5) // 确保 Fan_Count <= 5
{
Fan_Count = 0;
}
}
if(5 == Fan_Count && En_loca != 1) // 累计到5次有效信号,且不在低位触发
{
Fan_Flag = 1; // 信号标志位置高
}
}
注意事项
ADC_Inilize是沁恒库函数拼写,不是笔误。- 顺序:先配置结构体 → 调用ADC_Inilize → 再打开ADC电源。
- SMPduty <10 会出现采样跳动,尤其高阻抗传感器。
/* ADC模拟量采集 */
//P0_MODE_IN_HIZ(GPIO_Pin_LOW | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6); // P0.0~P0.6 设置为高阻输入
P1_MODE_IN_HIZ(GPIO_Pin_0); // P1.0 设置为高阻输入
浙公网安备 33010602011771号