STM32 ADC多通道采样实验

一、实验现象

每次循环连续采集3个ADC样本,每个样本间隔500毫秒。每次采集时,程序会启动ADC转换,等待转换完成,然后将12位ADC原始值(0-4095)转换为对应的电压值(0.000V-3.300V),并通过串口实时输出。在串口调试工具上,会看到每1.5秒输出一组3个电压值,每组内的3个数值间隔0.5秒显示。

二、示例代码

1. ADC初始化

复制代码
void MX_ADC1_Init(void)
{
  ADC_ChannelConfTypeDef sConfig = {0};  // 定义ADC通道配置结构体并初始化为0

  /** ADC通用配置 */
  hadc1.Instance = ADC1;                          // 设置ADC实例为ADC1
  hadc1.Init.ScanConvMode = ADC_SCAN_ENABLE;      // 启用扫描模式(多通道)
  hadc1.Init.ContinuousConvMode = DISABLE;        // 禁用连续转换模式(单次转换)
  hadc1.Init.DiscontinuousConvMode = ENABLE;      // 启用间断模式
  hadc1.Init.NbrOfDiscConversion = 1;             // 每个间断序列包含1个转换
  hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START; // 使用软件触发转换
  hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;     // 数据右对齐
  hadc1.Init.NbrOfConversion = 3;                 // 转换序列数为3(3个通道)
  
  // 初始化ADC,如果失败则调用错误处理函数
  if (HAL_ADC_Init(&hadc1) != HAL_OK)
  {
    Error_Handler();
  }

  /** 配置规则通道1 */
  sConfig.Channel = ADC_CHANNEL_4;          // 设置ADC通道4
  sConfig.Rank = ADC_REGULAR_RANK_1;        // 设置通道在规则组中的排名为第1个
  sConfig.SamplingTime = ADC_SAMPLETIME_1CYCLE_5;  // 设置采样时间为1.5个ADC时钟周期
  
  // 配置ADC通道4,如果失败则调用错误处理函数
  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }

  /** 配置规则通道2 */
  sConfig.Channel = ADC_CHANNEL_5;          // 设置ADC通道5
  sConfig.Rank = ADC_REGULAR_RANK_2;        // 设置通道在规则组中的排名为第2个
  // 采样时间保持与通道4相同(1.5个ADC时钟周期)
  
  // 配置ADC通道5,如果失败则调用错误处理函数
  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }

  /** 配置规则通道3 */
  sConfig.Channel = ADC_CHANNEL_6;          // 设置ADC通道6
  sConfig.Rank = ADC_REGULAR_RANK_3;        // 设置通道在规则组中的排名为第3个
  // 采样时间保持与前面通道相同
  
  // 配置ADC通道6,如果失败则调用错误处理函数
  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }
}

2. 主函数

复制代码
uint16_t adc_get[3] = {0};  // 定义ADC原始值数组,用于存储3个通道的转换结果
float vol[3] = {0.0f};      // 定义电压值数组,用于存储3个通道计算得到的电压值

// 系统时钟配置函数声明
void SystemClock_Config(void);

/**
  * @brief  应用程序主函数
  * @retval int
  */
int main(void)
{
  // HAL库初始化
  HAL_Init();

  // 系统时钟配置
  SystemClock_Config();

  // 初始化所有配置的外设
  MX_GPIO_Init();           // GPIO初始化
  MX_ADC1_Init();           // ADC1初始化(配置为3通道扫描模式)
  MX_USART1_UART_Init();    // USART1串口初始化
  HAL_ADCEx_Calibration_Start(&hadc1);  // 执行ADC校准

  // 主循环
  while (1)
  {
    // 循环采集3个通道的数据
    for(int i = 0; i < 3; i++)
    {
        // 启动ADC转换(每次触发转换一个通道)
        HAL_ADC_Start(&hadc1);
        
        // 等待转换完成,超时时间50ms
        if(HAL_ADC_PollForConversion(&hadc1, 50) == HAL_OK)
        {
            // 获取当前通道的ADC转换结果
            adc_get[i] = HAL_ADC_GetValue(&hadc1);
            
            // 将ADC值转换为电压值(假设参考电压3.3V,12位分辨率)
            vol[i] = (float)adc_get[i] / 4095 * 3.3f;
            
            // 通过串口打印当前通道的电压值,保留3位小数
            printf("%.3f\r\n", vol[i]);
        }
        
        // 延时500ms后采集下一个通道
        HAL_Delay(500);
    }
  }
}
相关推荐
sramdram8 小时前
基于32位微控制器的FOC汽车水泵方案
单片机·嵌入式硬件·汽车·微控制器·32位微控制器
十月的皮皮10 小时前
stm20260720-从新手 C 到量产 STM32 工程:程序设计推导指南
c语言·开发语言·stm32·stm32cubemx·hal库
开发笔记-阿牛11 小时前
解析一款有意思的产品||CK6159A语音芯片设计的儿童专注力训练机-舒尔特玩具
stm32·单片机·嵌入式硬件·音频
残影飞雪12 小时前
ESP32-C5下载烧录固件失败报错的原因
单片机·嵌入式硬件
搞全栈小苏13 小时前
SIMetrix_simplis8.4安装教程——附安装包
stm32·单片机·嵌入式硬件·电力电子
qq_5739678214 小时前
STM32控制器
stm32·单片机·嵌入式硬件
某林21215 小时前
履带小车底盘stm32F103RCT6开发
人工智能·stm32·单片机·嵌入式硬件·架构·人机交互·ros2
sramdram16 小时前
低功耗MCU微控制器在动态血糖仪(CGM)中的应用方案
单片机·嵌入式硬件·mcu·mcu微控制器
Dlrb121116 小时前
ARM--IMX6ULL的SDK学习,BSP开发工程管理,以及链接脚本与Makefile的编写
单片机·嵌入式硬件·arm·sdk·链接脚本·i.mx6ull·cortex-a7
李永奉16 小时前
杰理可视化SDK开发-配置ANC主动降噪功能模块教程
单片机·嵌入式硬件·物联网