STM32F4之ADC1【库函数操作】

2023-11-19

折腾了两天ADC多通道采样,采样的结果都很乱,完全不是预期值。在amobbs求助也没有找到结果。于是决定从简单开始,一步步折腾着破ADC。

【ADC试验1实验说明】

            1、这个实验仅仅是初始化一个ADC,对其输入进行采样。

            2、使用STM32F4的ADC1进行采样,采样值不输出之在编译器里边观察。

            3、使用ST外设库进行实验

            4、本实验只为采集到数据,采样周期、采样间隔设置为最大。

【ADC试验1实验结果】

             成功采集到了ADC1,通道1引脚PA1上的输入。数据稳定不跳变。

【ADC试验1实验步骤】

1、首先怀疑是工程中使用的USART、EXTI什么的影响了ADC的。重建工程,加入ST外设库,添加引用位置。这一步就不说了。

2、开启GPIOA、ADC时钟。因为使用ADC1的通道1,对应的PA1引脚作为输入。

ADC挂接在APB2时钟上,GPIOA挂接在AHB1时钟上。所以要开启这两个时钟。

代码如下:

RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1,ENABLE);

3、输入引脚配置

          输入端口PA,引脚1.模拟输入,引脚时钟100M

//PA1 PA2 PA3,模拟输入
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
GPIO_InitStructure.GPIO_Pin = GPIO_PinSource1 | GPIO_PinSource2 | GPIO_PinSource3;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_Init(GPIOA,&GPIO_InitStructure);

4、ADC通用的初始化

        这是F4系列新出来的东西,与F1不同。这里通过库函数配置一个新增的寄存器ADC_CCR,这个配置将影响片上所有的ADC。

//ADC通用配置
ADC_CommonInitStructure.ADC_DMAAccessMode = ADC_DMAAccessMode_Disabled;  //不用DMA
ADC_CommonInitStructure.ADC_Mode = ADC_Mode_Independent;  //独立采样
ADC_CommonInitStructure.ADC_Prescaler = ADC_Prescaler_Div8;  //速度尽可能低
ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_20Cycles;
ADC_CommonInit(&ADC_CommonInitStructure);

5、ADC1初始化

        之后对单独的ADC1进行配置,设定一些参数。最后的ADC_RegularChannelConfig完成通道选择和扫描顺序设置

主要参数:连续采样/数据右对齐/不用外部触发/采样通道数1/12位精度

//ADC1配置
ADC_InitStructyre.ADC_ContinuousConvMode = ENABLE;
ADC_InitStructyre.ADC_DataAlign = ADC_DataAlign_Right;
ADC_InitStructyre.ADC_ExternalTrigConv = ADC_ExternalTrigConvEdge_None;
ADC_InitStructyre.ADC_NbrOfConversion = 1;  //通道数
ADC_InitStructyre.ADC_Resolution = ADC_Resolution_12b;
ADC_InitStructyre.ADC_ScanConvMode = ENABLE;
ADC_Init(ADC1,&ADC_InitStructyre);
 
ADC_Cmd(ADC1,ENABLE);
ADC_RegularChannelConfig(ADC1,ADC_Channel_1,1,ADC_SampleTime_144Cycles);

6、手动开始ADC采样,由于配置为连续扫描所有只需要开启一次即可:

     使用函数ADC_SoftwareStartConv(ADC1);完成

7、获取ADC采样数据:

    可以通过读ADC的DR或者使用库函数ADC_GetConversionValue来完成。我使用的是库函数。

adcvalue1 = ADC_GetConversionValue(ADC1);

adcvota = adcvalue1 *3300 / 0xfff;

8、最后加上串口功能,让数据回显

while(1)
{
   adcvalue1 = ADC_GetConversionValue(ADC1);
   adcvota = adcvalue1 *3300 / 0xfff;
 
  for(i = 0;i<10000;i++)
  {
      sum += adcvota;
    if(i ==9999)
    {
       avgvota = sum/10000;
       sum = 0;
      printf("avg vota is: %d\r\n",avgvota);
    }
  }
}

9、完整的代码:

#include <stm32f4xx.h>
#include "stm32f4xx_rcc.h"
#include "stm32f4xx_gpio.h"
#include "stm32f4xx_adc.h"
#include "stm32f4xx_conf.h"

#include "usart.h"

#include <stdio.h>

NVIC_InitTypeDef NVIC_InitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
ADC_CommonInitTypeDef ADC_CommonInitStructure;
ADC_InitTypeDef ADC_InitStructyre;

int adcvalue1,adcvalue2,adcvalue3;
int adcvota ;

int i,sum,avgvota;

int main()
{
  USART_Config();
  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE);
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1,ENABLE);
  //PA1 PA2 PA3,模拟输入
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
//   GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
  GPIO_InitStructure.GPIO_Pin = GPIO_PinSource1 | GPIO_PinSource2 | GPIO_PinSource3;
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
  GPIO_Init(GPIOA,&GPIO_InitStructure);
  //ADC通用配置
  ADC_CommonInitStructure.ADC_DMAAccessMode = ADC_DMAAccessMode_Disabled;  //不用DMA
  ADC_CommonInitStructure.ADC_Mode = ADC_Mode_Independent;  //独立采样
  ADC_CommonInitStructure.ADC_Prescaler = ADC_Prescaler_Div8;  //速度尽可能低
  ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_20Cycles;
  ADC_CommonInit(&ADC_CommonInitStructure);
 
  //ADC1配置
  ADC_InitStructyre.ADC_ContinuousConvMode = ENABLE;
  ADC_InitStructyre.ADC_DataAlign = ADC_DataAlign_Right;
  ADC_InitStructyre.ADC_ExternalTrigConv = ADC_ExternalTrigConvEdge_None;
  ADC_InitStructyre.ADC_NbrOfConversion = 1;
  ADC_InitStructyre.ADC_Resolution = ADC_Resolution_12b;
  ADC_InitStructyre.ADC_ScanConvMode = ENABLE;
  ADC_Init(ADC1,&ADC_InitStructyre);
   
  ADC_Cmd(ADC1,ENABLE);
  ADC_RegularChannelConfig(ADC1,ADC_Channel_1,1,ADC_SampleTime_144Cycles);
 
  ADC_SoftwareStartConv(ADC1);
 
  sum = 0;
  while(1)
  {
     adcvalue1 = ADC_GetConversionValue(ADC1);
     adcvota = adcvalue1 *3300 / 0xfff;
   
    for(i = 0;i<10000;i++)
    {
        sum += adcvota;
      if(i ==9999)
      {
         avgvota = sum/10000;
         sum = 0;
        printf("avg vota is: %d\r\n",avgvota);
      }
    }
  }
}
 
  //重定义printf
int fputc(int ch,FILE *f)
{
  //检查发送寄存器为空之后再往里边放数据
  while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET)
  {}
  //USART发送一个字符
  USART_SendData(USART1, (uint8_t) ch);
  return ch;
}

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

STM32F4之ADC1【库函数操作】 的相关文章

  • 2020.11.13 奇偶链表

    2020 11 13 奇偶链表 题目描述 给定一个单链表 把所有的奇数节点和偶数节点分别排在一起 请注意 这里的奇数节点和偶数节点指的是节点编号的奇偶性 而不是节点的值的奇偶性 请尝试使用原地算法完成 你的算法的空间复杂度应为 O 1 时间

随机推荐

  • Java:List<Map>指定Key去重,差集(针对集合里面只有Map非实体对象)

    ListMap去重 差集 针对集合里面只有Map非实体对象 问题 由于业务需求 接口的入参出参都是List格式 对于有些查出来的数据 为了防止重复的数据 需要对集合去重 以下分享一种去重的方法 该方法可根据指定字段对List
  • 最全 VxLAN 知识详解

    什么是VXLAN VXLAN Virtual eXtensible Local Area Network 虚拟扩展局域网 是由IETF定义的NVO3 Network Virtualization over Layer 3 标准技术之一 是对
  • 容器修改完成的镜像打包到自己的docker hub

    容器修改完成的镜像打包到自己的docker hub 一 步骤 首先 我们基于当前的容器进行了修改 比如 我们首先创建了一个Ubuntu的容器 然后在容器当中安装了python3 安装了Django框架 安装NGINX服务器 安装了mysql
  • rt-thread中使用WebClient WebNet总结 http学习

    HTTP学习资料 1 需求背景 WebClient主要用来传输文件 WebNet用来支持cgi接口 需要支持get post put delete方式 2 webnet中使用 2 1 webnet存在问题 2 11 rt thread 使用
  • Web基础 HTML标签 六种超链接标签的使用方式

    超链接标签 重点 1 链接的语法格式 a href 跳转目标链接 target self 文本或图像 a a 标签里的a是单词anchor的的缩写 意为 锚 两个属性的作用如下 属性 作用 href 用于指定链接目标的url地址 必须属性
  • 【物联网毕设基础】NBIOT 窄带物联网

    文章目录 1 简介 2 NBIOT简介 3NB的型号介绍 3 1 BC95 3 2 BC35 3 3 BC28 3 4 BC26 3 5 BC20 3 6 BC30 4 NB物联网卡 5 OpenCPU 6 BC260模块详解 6 1 基本
  • 【周末闲谈】二进制VS三进制

    个人主页 个人主页 系列专栏 周末闲谈 周末闲谈 第一周 二进制VS三进制 文章目录 周末闲谈 前言 一 效率 二 三进制计算机 三进制计算机的最后 总结 前言 作为计算机是20世纪最先进的科学技术发明之一 对人类的生产活动和社会活动产生了
  • yolov7 onnx tensorrt 批量预测 全网首发

    目录 deepstream yolov7 mask yolov5的TensorRT部署 动态batch 开源tensorrt 调研笔记 tensorrt 加载模型batch size为 1的原因
  • JS解混淆-AST还原案例

    目录 一 js混淆了解 1 为什么要混淆 2 常见的混淆模样 ob sojson jsfuck AAencode jjEncode eval 二 AST初步认识 三 解混淆常用的方法 一 js混淆了解 1 为什么要混淆 js混淆的作用 为了
  • 为什么计算机中的整数要用补码表示?补码表示有什么好处?

    为什么计算机中的整数要用补码表示 补码表示有什么好处 在计算机中 补码可谓是十分神奇而又重要的存在 我们知道整数在计算机内部的机器数一般都是补码表示的 这里给出几个这样表示的好处 符号位可以和数值为一起参加运算 比如俩个负数相加 只要结果在
  • 风投平台

    一 天使湾创投 http www tisiwi com 二 天使汇 http angelcrunch com 三 蚂蚁天使 https www mayiangel com index htm 四 梦想小镇孵化器平台 http www dre
  • docker+jenkins+git搭建java自动化部署

    一 杂言 首先今天在写这篇文章的时候 刚好LOL洲际赛 RW赛前不被看好的情况下 为LPL扳回一城 RNG成功的在BO5最后一场拿下AFS LPL成功的拿下了洲际赛的冠军 恭喜LPL 田忌赛马的故事大家都耳熟能详 但是不可避免的也会出现逆转
  • pandas读取和存储CSV文件

    import pandas as pd import numpy as np read csv data pd read csv data temp 0 csv header None data DataFrame object data
  • 前端核心手写面试题(看你的马步扎实不扎实)

    防抖 防抖
  • c++类和对象--封装--属性和行为做整体

    封装的意义 1 将属性和行为当做一个整体来表现对象 类中的属性和行为统称为成员 属性又叫成员属性或成员变量 行为又叫成员函数或成员方法 案例 设计一个圆类 求圆的周长 include
  • 华为OD机试真题 Java 实现【机器人活动区域】【2023Q1 200分】

    一 题目描述 现有一个机器人 可放置于 M N的网格中任意位置 每个网格包含一个非负整数编号 当相邻网格的数字编号差值的绝对值小于等于 1 时 机器人可在网格间移动 问题 求机器人可活动的最大范围对应的网格点数目 说明 1 网格左上角坐标为
  • QT+ OpenGL学习

    文章目录 QT OpenGL QOpenGLWidget 不需要GLFW QOpenGLFunction X X Core 不需要GLAD 你好 三角形 顶点输入 顶点着色器 片段着色器 链接着色器 本节代码 元素缓冲对象EBO QT交互
  • haxm-windows_v7_5_6下载

    下载地址 https github com intel haxm releases download v7 5 6 haxm windows v7 5 6 zip 我已经下载好上传了 想自己去下载的小伙伴可以去上面的网站自己下载哦
  • 当今职场,正在加速淘汰 “巨婴员工”

    我担任过多家上市公司的技术高管职位 在工作中经常会遇到巨婴型员工 他们外在的表现是 不能够很好地管理自己 缺乏自律 缺乏起码的抗挫折能力和抗压能力 需要领导呵护着 同事们忍让着 作为一名管理者 绝不能放任团队中的巨婴存在 必须时刻保持团队的
  • STM32F4之ADC1【库函数操作】

    折腾了两天ADC多通道采样 采样的结果都很乱 完全不是预期值 在amobbs求助也没有找到结果 于是决定从简单开始 一步步折腾着破ADC ADC试验1实验说明 1 这个实验仅仅是初始化一个ADC 对其输入进行采样 2 使用STM32F4的A