STM32:两种方式实现超声波测距

这篇具有很好参考价值的文章主要介绍了STM32:两种方式实现超声波测距。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

超声波模块HC-SR04的工作原理很简单,有很多办法可以完成超声波测距,这里简单介绍两种。

1.定时器中断法

配置定时器的中断并声明一个Time的变量,在中断中先判断标志位,然后检查echo端口是否为高电平,如果是,Time++,然后变量time乘以定时时间就能得到echo端口高电平持续的时间,经过计算就可以得到距离。

Timer.c

#include "stm32f10x.h"                  // Device header
#include "Timer.h"

extern uint16_t Time;   //Time变量在HCSR04.c文件中定义

void Timer_Init()
{
 	Time = 0;
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);	//选择APB1总线下的定时器Timer3
	
	TIM_InternalClockConfig(TIM3);		//TIM3使用内部时钟
										//默认使用内部时钟,不写这句代码也没关系
	
	TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
	
	TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;		//时钟1分频
	TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;		//计数模式,此处为向上计数
	TIM_TimeBaseInitStructure.TIM_Period = 7200 - 1;		//ARR 1 = 0.0001S,自动重装器的值
	TIM_TimeBaseInitStructure.TIM_Prescaler = 0;		//PSC,预分频器的值
	TIM_TimeBaseInitStructure.TIM_RepetitionCounter = 0;		//高级计时器特有,重复计数
	TIM_TimeBaseInit(TIM3, &TIM_TimeBaseInitStructure);
	
	TIM_ClearFlag(TIM3, TIM_FLAG_Update);
	TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);		//使能中断
	
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);		//将中断优先级分为两组,即组1和组2。

	
	NVIC_InitTypeDef NVIC_InitStructure;// 定义一个NVIC_InitTypeDef结构体变量,用于初始化中断控制器
	NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;// 设置中断通道为TIM3的IRQn中断
	NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;// 使能中断通道
	NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;// 设置中断优先级为2,表示高优先级
	NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;// 设置中断子优先级为1,表示低优先级
	NVIC_Init(&NVIC_InitStructure);// 使用NVIC_Init函数初始化中断控制器
	
	TIM_Cmd(TIM3, ENABLE);// 使能定时器TIM3

}

void TIM3_IRQHandler(void)		// 定时器3的中断函数
{
    if(TIM_GetITStatus(TIM3, TIM_IT_Update) == SET) // 检查定时器3的更新中断标志位是否被设置
    {
        if (GPIO_ReadInputDataBit(Echo_Port, Echo_Pin) == 1) // 读取回声传感器端口上的引脚状态
        {
            Time++; // 如果引脚状态为高电平,则增加时间计数器
        }
        TIM_ClearITPendingBit(TIM3, TIM_IT_Update);		// 清空标志位,表示中断已经处理完毕
    }
}

Timer.h

#ifndef __TIMER_H
#define __TIMER_H

#define Trig_Port 		GPIOA
#define Trig_Pin 		GPIO_Pin_5
#define Trig_RCC		RCC_APB2Periph_GPIOA

#define Echo_Port 		GPIOA
#define Echo_Pin 		GPIO_Pin_6
#define Echo_RCC		RCC_APB2Periph_GPIOA

void Timer_Init(void);

#endif

2.输入捕获法

配置定时器的输入捕获,在echo端口的上升沿捕获一次,下降沿捕获一次,通过“TIM_GetCapture2(TIM3)”这句代码直接可以将时间读取出来。

IC.c

#include "stm32f10x.h"                  // Device header

void IC_Init(void)
{
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);  	// TIM3->使用引脚PA6
	
	//在超声波模块已经配置过
//	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
//	GPIO_InitTypeDef GPIO_InitStructure;
//	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
//	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6;//PB6引脚,接入超声波Echo引脚
//	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
//	GPIO_Init(GPIOA, &GPIO_InitStructure);
	
	TIM_InternalClockConfig(TIM3);
	
	TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;//配置时基单元
	TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
	TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;
	TIM_TimeBaseInitStructure.TIM_Period = 65536 - 1;		//ARR
	TIM_TimeBaseInitStructure.TIM_Prescaler = 72 - 1;		//PSC分频系数
	TIM_TimeBaseInitStructure.TIM_RepetitionCounter = 0;
	TIM_TimeBaseInit(TIM3, &TIM_TimeBaseInitStructure);
	
	
	//通道一
	TIM_ICInitTypeDef TIM_ICInitStructure;
	TIM_ICInitStructure.TIM_Channel = TIM_Channel_1;//TIM3的通道1
	TIM_ICInitStructure.TIM_ICFilter = 0xF;//配置滤波器,参数决定滤波效果,高频滤波
	TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising;//极性选择,选择上升沿触发
	TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;//每次都触发捕获
	TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//通道触发选择
	
	
	//通道二
//	TIM_ICInitStructure.TIM_Channel=TIM_Channel_2;//捕获通道二
//	TIM_ICInitStructure.TIM_ICFilter=0xF;//滤除高频波动
//	TIM_ICInitStructure.TIM_ICPolarity=TIM_ICPolarity_Falling;//下降触发捕获
//	TIM_ICInitStructure.TIM_ICPrescaler=TIM_ICPSC_DIV1;//不分频
//	TIM_ICInitStructure.TIM_ICSelection=TIM_ICSelection_IndirectTI;//交叉通道输入
//	TIM_ICInit(TIM3,&TIM_ICInitStructure);
	 
	TIM_PWMIConfig(TIM3, &TIM_ICInitStructure);//pwmi模式配置通道2,效果相当于上面的代码
	
	TIM_SelectInputTrigger(TIM3, TIM_TS_TI1FP1);
	TIM_SelectSlaveMode(TIM3, TIM_SlaveMode_Reset);
	
	TIM_Cmd(TIM3, ENABLE);
}

IC.h

#ifndef __IC_H
#define __IC_H

void IC_Init(void);

#endif

#超声波部分

这里将展示如何将获取到的时间值计算得到距离,定时器中断和输入捕获两种方法的实现都在下面的文件中,我们正确添加完文件后,在main文件中直接调用就可以实现测距的功能了。

HCSR04.c

#include "stm32f10x.h"                  // Device header
#include "HCSR04.h"
#include "Timer.h"
#include "Delay.h"

uint16_t Time;

void HCSR04_Init()
{
	RCC_APB2PeriphClockCmd(Trig_RCC, ENABLE);
	
	GPIO_InitTypeDef GPIO_InitStruct;
	
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStruct.GPIO_Pin = Trig_Pin;
	GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(Trig_Port, &GPIO_InitStruct);
	
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IPD;
	GPIO_InitStruct.GPIO_Pin = Echo_Pin;
	GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(Echo_Port, &GPIO_InitStruct);
	
	GPIO_ResetBits(Trig_Port, Trig_Pin);//Trig引脚给低电平,为后续启动做准备
	
}

void HCSR04_Start(void)
{
	GPIO_SetBits(Trig_Port, Trig_Pin);
	Delay_us(40);
	GPIO_ResetBits(Trig_Port, Trig_Pin);
	
	Timer_Init();//定时器初始化
}

uint16_t HCSR04_GetValue(void) //定时器中断测距
{
	HCSR04_Start();
	Delay_ms(100);
	return ((Time * 0.0001) * 34000) / 2;
//	return Time;                          
}


float GetLength(void) //输入捕获测距
{
	int i=0;
	float length=0;
	float sum=0;
	float Length;
	for(i=0;i<5;i++)
	{
		//减小误差,计算五次
		GPIO_SetBits(GPIOA,GPIO_Pin_5);
		Delay_us(20);//发送一段40us的高电平
		GPIO_ResetBits(GPIOA,GPIO_Pin_5);
		Time=TIM_GetCapture2(TIM3); //获取捕获值
		length=(Time/58.0);//固定计算超声波距离公式:时间/58.0;单位厘米
		sum=sum+length;
	}
	
	Length=sum/5.0;
	return Length;
}

HCSR04.h文章来源地址https://www.toymoban.com/news/detail-852813.html

#ifndef __HCSR04_H
#define __HCSR04_H

#define Trig_Port 		GPIOA
#define Trig_Pin 		GPIO_Pin_5
#define Trig_RCC		RCC_APB2Periph_GPIOA

#define Echo_Port 		GPIOA
#define Echo_Pin 		GPIO_Pin_6
#define Echo_RCC		RCC_APB2Periph_GPIOA

void HCSR04_Init(void);
uint16_t HCSR04_GetValue(void);
float GetLength(void);
	
#endif 

到了这里,关于STM32:两种方式实现超声波测距的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 基于STM32超声波测距系统设计

    随着社会的发展和科技的进步,人们对测距的要求越来越高,特别是在一些要求实时测距的场合,传统的测距方式已经无法满足人们的需求,而超声波测距由于其非接触和实时反馈的特点在生活中得到广泛应用。 本系统硬件部分由电源模块、控制模块、显示模块、报警模块、

    2024年02月04日
    浏览(55)
  • stm32之14.超声波测距代码

           -------------------- 源码  

    2024年02月11日
    浏览(50)
  • STM32超声波测距(OLED显示距离)

    超声波原理: 利用声音测距,声音在空气中的速度是340m/s(15℃) 当声音传播时,若遇到障碍物时,就会被反弹回来,通过计时反弹回来的时间就可以计算出从发射端到障碍物的距离 引脚定义: 工作电压:3V-5.5V宽电压供电 测距盲区:2cm最小盲区 接口定义如图 序号 接口定义

    2024年02月04日
    浏览(44)
  • 最详细STM32,cubeMX 超声波测距

    这篇文章将详细介绍 STM32使用 cubeMX驱动超声波测距 。 实验材料:STM32F103C8T6开发板, HC-SR04 超声波模块。 所需软件:keil5 , cubeMX ,AiThinker Serial Tool 串口助手。 实验目的:了解 STM32使用 cubeMX驱动超声波 。 实验:超声波测距。 HC-SR04 超声波测距模块可提供 2cm-400cm 的非接触

    2024年02月08日
    浏览(52)
  • 手把手教你,通过HAL库实现STM32的超声波测距--以SR-04为例

    目录 0、SR-04基本原理 1、准备工作 2、连线  3、STM32CUBEMX设置 3.1新建工程 3.2芯片通用设置 3.3定时器捕获设置 ​3.4其他设置 3.5生成工程  4、程序完善 4.1完善打印输出函数  4.2完善tim.c 4.3完善gpio.c  4.4完善main函数   5、总结 声波遇到障碍物会反射,而声波的速度已知,所以

    2024年02月14日
    浏览(50)
  • STM32F103驱动HCSR04超声波测距显示

    超声波模块在电子DIY作品中实现小车避障测距等方面均应用广泛,在大学生智能车DIY爱好者中尤为显眼。 点击图片购买 HC-SR04超声波测距模块可提供2cm-400cm的非接触式距离感测功能,测距精度可达3mm,包括发射器、接收器与控制电路,它是一种压电式传感器,利用电致伸缩现

    2024年02月02日
    浏览(47)
  • stm32-CS100A 超声波测距芯片原理及代码解读

            CS100A 是苏州顺憬志联新材料科技有限公司(www.100sensor.com)推出的一款工 业级超声波测距芯片,CS100A 内部集成超声波发射电路,超声波接收电路,数字处理电 路等,单芯片即可完成超声波测距,测距结果通过脉宽的方式进行输出,通信接口兼容 现有超声波模块

    2024年02月04日
    浏览(164)
  • 【STM32篇】驱动HC_SR04超声波测距模块

    CH_SR04 HC_SR04超声波测距模块可提供 2cm-400cm 的非接触式测距感测功能,测距精度高达3mm;模块包括超声波发射器,接收器与控制电路。 基本工作原理: (1)采用IO口TRIG触发测距,需要给最少10us的高电平。 (2)模块自动发送8个40kHz的方波,自动检测是否有信号返回。 (3)有

    2024年02月17日
    浏览(54)
  • 基于STM32F103C8T6的超声波测距应用

    #一、超声波HC_SR04简介 #二、超声波工作原理 #三、超声波测距步骤 #四、硬件接线 #五、项目代码 一、超声波HC_SR04简介 超声波传感器模块上面通常有两个超声波元器件,一个用于发射,一个用于接收。电路板上有四个引脚:VCC、GND、Trig(触发)、Echo(回应) 工作电压与电流

    2024年02月03日
    浏览(47)
  • STM32系列(HAL库)——F103C8T6通过HC-SR04超声波模块实现测距

    (1)编程平台:Keil5 (2)CubeMX (3)XCOM(串口调试助手) (1)某宝买的超声波模块   (2)F1的板子,本例使用经典F103C8T6 (3)ST-link 下载器 (4)USB-TTL模块 (5)杜邦线若干 (1)模块简介:         超声波是振动频率高于20kHz的机械波。它具有频率高、波长短、绕射现象小、方向性好、能够成为射

    2024年02月02日
    浏览(50)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包