STM32 ADC基础与多通道采样
12位ADC是一种逐次逼近型模拟数字数字转换器。它有多达18个通道,可测量16个外部和2个内部信号源。ADC的输入时钟不得超过14MHZ,它是由PCLK2经分频产生。如果被ADC转换的模拟电压低于低阀值或高于高阀值,AWD模拟看门狗状态位被设置。
ADC通常要与DMA一起使用 这里只是简单的用库配置ADC 不断扫描来实现ADC的应用。
配置DMA:
- void DMA_Config(void)
- {
- DMA_InitTypeDef DMA_InitStructure;//定义DMA初始化结构体
- DMA_DeInit(DMA_Channel1);//复位DMA通道1
- DMA_InitStructure.DMA_PeripheralBaseAddr = ADC1_DR_Address; //定义 DMA通道外设基地址=ADC1_DR_Address
- DMA_InitStructure.DMA_MemoryBaseAddr = (u32)&ADC_ConvertedValue; //定义DMA通道存储器地址
- DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;//指定外设为源地址
- DMA_InitStructure.DMA_BufferSize = ;//定义DMA缓冲区大小1
- DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;//当前外设寄存器地址不变
- DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Disable;//当前存储器地址不变
- DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;//定义外设数据宽度16位
- DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord; //定义存储器数据宽度16位
- DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;//DMA通道操作模式位环形缓冲模式
- DMA_InitStructure.DMA_Priority = DMA_Priority_High;//DMA通道优先级高
- DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;//禁止DMA通道存储器到存储器传输
- DMA_Init(DMA_Channel1, &DMA_InitStructure);//初始化DMA通道1
- DMA_Cmd(DMA_Channel1, ENABLE); //使能DMA通道1
- }
配置ADC的运行:
- void ADC_Config(void)
- {
- ADC_InitTypeDef ADC_InitStructure;//定义ADC初始化结构体变量
- ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;//ADC1和ADC2工作在独立模式
- ADC_InitStructure.ADC_ScanConvMode = ENABLE; //使能扫描
- ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;//ADC转换工作在连续模式
- 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_RegularChannelConfig(ADC1, ADC_Channel_14, , ADC_SampleTime_28Cycles5); //ADC1选择信道14,音序器等级1,采样时间239.5个周期
- ADC_DMACmd(ADC1, ENABLE);//使能ADC1模块DMA
- ADC_Cmd(ADC1, ENABLE);//使能ADC1
- ADC_ResetCalibration(ADC1); //重置ADC1校准寄存器
- while(ADC_GetResetCalibrationStatus(ADC1));//等待ADC1校准重置完成
- ADC_StartCalibration(ADC1);//开始ADC1校准
- while(ADC_GetCalibrationStatus(ADC1));//等待ADC1校准完成
- ADC_SoftwareStartConvCmd(ADC1, ENABLE); //使能ADC1软件开始转换
- }
(1) 第一个参数是ADC_Mode,这里设置为独立模式:
ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;
在这个模式下,双ADC不能同步,每个ADC接口独立工作。所以如果不需要ADC同步或者只是用了一个ADC的时候,就应该设成独立模式了。
(2) 第二个参数是ADC_ScanConvMode,这里设置为DISABLE。
ADC_InitStructure.ADC_ScanConvMode = DISABLE;
如果只是用了一个通道的话,DISABLE就可以了,如果使用了多个通道的话,则必须将其设置为ENABLE。
(3) 第三个参数是ADC_ContinuousConvMode,这里设置为ENABLE,即连续转换。如果设置为DISABLE,则是单次转换。两者的区别在于连续转换直到所有的数据转换完成后才停止转换,而单次转换则只转换一次数据就停止,要再次触发转换才可以。所以如果需要一次性采集1024个数据或者更多,则采用连续转换。
(4) 第四个参数是ADC_ExternalTrigConv,即选择外部触发模式。这里只讲三种:
1、第一种是最简单的软件触发,参数为ADC_ExternalTrigConv_None。设置好后还要记得调用库函数:
ADC_SoftwareStartConvCmd(ADC1, ENABLE);
这样触发才会启动。
2、第二种是定时器通道输出触发。共有这几种:ADC_ExternalTrigConv_T1_CC1、ADC_ExternalTrigConv_T1_CC2、ADC_ExternalTrigConv_T2_CC2、
ADC_ExternalTrigConv_T3_T以及ADC_ExternalTrigConv_T4_CC4。定时器输出触发比较麻烦,还需要设置相应的定时器。以
ADC_ExternalTrigConv_T2_CC2触发为例设置相应的定时器:
- void TIM2_Configuration(void){
- TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
- TIM_OCInitTypeDef TIM_OCInitStructure;
- TIM_TimeBaseStructure.TIM_Prescaler = ;
- TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
- TIM_TimeBaseStructure.TIM_Period = 0XFF;
- TIM_TimeBaseStructure.TIM_ClockDivision = ;
- TIM_TimeBaseStructure.TIM_RepetitionCounter = ;
- TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
- TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
- TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
- TIM_OCInitStructure.TIM_Pulse = 0X7F;
- TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_Low;
- TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set;
- TIM_OC2Init(TIM2, &TIM_OCInitStructure);
- TIM_Cmd(TIM2, ENABLE);
- TIM_CtrlPWMOutputs(TIM2, ENABLE);
- }
这样设置之后就可以用定时器2的输出触发了,至于触发的周期,设置TIM2的时间即可。这里不再赘述。
3、第三种是外部引脚触发,对于规则通道,选择EXTI线11和TIM8_TRGO作为外部触发事件;而注入通道组则选择EXTI线15和TIM8_CC4作为外部触发事件。
(5) 第五个参数是ADC_DataAlign,这里设置为ADC_DataAlign_Right右对齐方式。建议采用右对齐方式,因为这样处理数据会比较方便。当然如果要从高位开始传输数据,那么采用左对齐优势就明显了。
(6) 第六个参数是ADC_NbrOfChannel,顾名思义:通道的数量。要是到多个通道采集数据的话就得设置一下这个参数。此外在规则通道组的配置函数中也许将各个通道的顺序定义一下,如:
- ADC_RegularChannelConfig(ADC1,ADC_Channel_13,,ADC_SampleTime_13Cycles5);
- ADC_RegularChannelConfig(ADC1,ADC_Channel_14,,ADC_SampleTime_13Cycles5);
多通道数据传输时有一点还要注意:若一个数组为ADC_ValueTab[4],且设置了两个通道:通道1和通道2,则转换结束后,ADC_ValueTab[0]和ADC_ValueTab[2]存储的是通道1的数据,而ADC_ValueTab[1]和ADC_ValueTab[3]存储的是通道2的数据。如果数组容量大则依次类推。
补充一点:在使用DMA传输数据的时候,需要设置外设地址和存储器地址,外设地址当然就是ADC的地址了,而存储器的地址如果使用8位数据的话,存储器必须定义为8位缓冲区;如果使用16位数据格式的话,存储器则为16位缓冲器,不可定义为32位或更多,否则,数据将出错。
STM32 ADC基础与多通道采样的更多相关文章
- STM32 ADC多通道规则采样和注入采样
layout: post tags: [STM32] comments: true 文章目录 layout: post tags: [STM32] comments: true 什么是ADC? STM ...
- 关于Stm32定时器+ADC+DMA进行AD采样的实现
Stm32的ADC有DMA功能这都毋庸置疑,也是我们用的最多的!然而,如果我们要对一个信号(比如脉搏信号)进行定时采样(也就是隔一段时间,比如说2ms),有三种方法: 1.使用定时器中断每隔一定时间进 ...
- STM32 ADC多通道转换DMA模式与非DMA模式两种方法(HAL库)
一.非DMA模式(转) 说明:这个是自己刚做的时候百度出来的,不是我自己做出来的,因为感觉有用就保存下来做学习用,原文链接:https://blog.csdn.net/qq_24815615/arti ...
- 【STM32H7教程】第46章 STM32H7的ADC应用之DMA方式多通道采样
完整教程下载地址:http://www.armbbs.cn/forum.php?mod=viewthread&tid=86980 第46章 STM32H7的ADC应用之DMA方式多 ...
- Hi3518EV200平台ADC多通道采样
Hi3518EV200平台ADC多通道采样流程 Hi3518EV200 ADC 本文针对Hi3518EV200平台处理器,通过ADC单次采样方式,实现对多通道(1~4通道)ADC进行采样控制.本文仅仅 ...
- STM32 ADC 采样 频率的确定
一 STM32 ADC 采样频率的确定 1. : 先看一些资料,确定一下ADC 的时钟: (1),由时钟控制器提供的ADCCLK 时钟和PCLK2(APB2 时钟)同步.CLK 控制器为A ...
- STM32 ADC多通道转换
描述:用ADC连续采集11路模拟信号,并由DMA传输到内存.ADC配置为扫描并且连续转换模式,ADC的时钟配置为12MHZ.在每次转换结束后,由DMA循环将转换的数据传输到内存中.ADC可以连续采集N ...
- STM32 ADC详细篇(基于HAL库)
一.基础认识 ADC就是模数转换,即将模拟量转换为数字量 l 分辨率,读出的数据的长度,如8位就是最大值为255的意思,即范围[0,255],12位就是最大值为4096,即范围[0,4096] l ...
- STM32.ADC
ADC实验 原理图: 1.ADC配置函数 /* enable adc1 and config adc1 to dma mode */ ADC1_Init(); /** * @brief ADC1初始化 ...
随机推荐
- js模块化编程之CommonJS和AMD/CMD!
有了模块,我们就可以更方便地使用别人的代码,想要什么功能,就加载什么模块. 但是,这样做有一个前提,那就是大家必须以同样的方式编写模块,否则你有你的写法,我有我的写法,岂不是乱了套! 于是下面三个模块 ...
- [19/05/17-星期五] HTML_body标签(内嵌标签)和框架标签
一.内嵌标签 <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <!- ...
- python基础循环语句练习
1.使用while循环输入 1 2 3 4 5 6 8 9 10 n = 1 while n < 11: if n == 7: pass else: print(n) n = n + 1 ...
- Java-集合第二篇Set集合
1.Set集合与Collection基本相同,没有提供额外的方法.实际上Set就是Collection,只是行为略有所不同(Set不允许有重复元素). Set下的HashSet.TreeSet.Enu ...
- 面试一个 3 年 Java 程序员,一个问题都不会!
大家周末愉快,当你看到这篇文章的时候,事情已经过去几天了. 刚从洽谈室走出来,心情很复杂! 栈长面试过很多人,不乏知识渊博.技能顶尖的选手,但从未遇到过工作了三年,却一个问题都答不上来.. 这场史无前 ...
- JDK11 | 第四篇 : 增强API
文章首发于公众号<程序员果果> 地址 : https://mp.weixin.qq.com/s/O0xntC-JfeSBk-9x2QfwnA 一.简介 JDK 9~11 在语言语法方面有一 ...
- PTA第二题
#include<string.h> #include<stdio.h> #include<malloc.h> ]; ][]={"ling",& ...
- .net easyui Tree树
原文:https://www.cnblogs.com/hantianwei/archive/2012/03/19/2407118.html Tree 树 用 $.fn.tree.defaults ...
- 解决Vscode编辑器不能打开多标签页问题
问题描述:编辑代码时,初用vscode,不能打开多个文件:每打开一个文件,都会替换前面一个文件标签,很不方便切换编码: 想要的效果: 解决方式: 方法一: 找到setting.json文件,最外层花括 ...
- 将Java对象序列化成JSON和XML格式
1.先定义一个Java对象Person: public class Person { String name; int age; int number; public String getName() ...