超声波模块

超声波用于避障,测距之类的,是比较简单的传感器


datasheet 下载地址

外观

HC-SR04超声波测距模块可提供约2cm400厘米的非接触式距离感测功能,测距精度可达高到3毫米;模块包括超声波发射器,接收器与控制电路像智能小车的测距以及转向,或是一些项目中,常常会用到。智能小车测距可以及时发现前方的障碍物,使智能小车可以及时转向,避开障碍物。
在这里插入图片描述
在这里插入图片描述
HC-SR04有4个引脚:VCC,GND,TRIG和ECHO。

  1. VCC是5v电源。这应该来自微控制器
  2. GND是接地引脚。在微控制器上接地。
  3. TRIG应连接到可设置为HIGH的GPIO引脚
    ECHO有点困难。HC-SR04输出5v,可能会破坏许多微控制器GPIO引脚(最大允许电压变化)。为了降压,使用单个电阻器或分压器电路。这又取决于您使用的特定微控制器,您需要找出其GPIO最大电压并确保低于该值。(只限于FT引脚),也就是ECHO对于stm32只能连在FT引脚上!!
    在这里插入图片描述

基本原理

TRIG引脚负责发送超声波脉冲串。此引脚应设置为高电平10μs,此时HC-SR04将以40 kHZ发出8个周期的声波脉冲。发出声波爆发后,ECHO引脚将变为高电平。 ECHO引脚是数据引脚 - 用于进行距离测量。发送超声波脉冲串后, ECHO引脚将变为高电平,它将保持高电平,直到检测到超声波脉冲串为止,此时它将变为低电平。
在这里插入图片描述
就是TRIG引脚给一个持续10us的高电平,触发超声波模块自动发送8个40khz的方波,发出声波后,ECHO引脚会被拉高,待接收到之后,ECHO引脚拉低,我们只要测出ECHO引脚从拉高到拉低的时间就可以知道距离了

计算公式

我们知道声速是340m/s
根据x=vt
因为超声波发送出去和回来是测量距离的两倍,所以假设距离是L
2L=344xt
t我们用定时器测出来
一般都是us
所以就是tx172x10的-6次方=L,L单位为cm
最终的出 L= t(us) * 0.0172(cm/us)
0.0172=1/58
所以 L= t(us)/58(cm)

对于51单片机,12mhz的周期时间为1us
所以11.059200mzh的计算公式为
L = 计数 x(12/11.0592) x (1/58)
= 计数 x 0.0187
= (计数 x 1.87)/100
(cm)

测试代码

51&15

//#include <reg52.h>
#include "stc15.h"
#include <intrins.h>
#include <stdio.h>

typedef unsigned char u8;
typedef unsigned int u16;
typedef unsigned long u32;
sbit Echo=P3^2;//超声波模块echo脚定义
sbit Trig=P3^3;//超声波模块trig脚定义

u16 time=0;
float Distance=0;
bit flag=0;//定时器0溢出标志位

void Config_UARTimer(u16 Baud);//配置串口,定时器
void Delay10us_15(void);//15延时10us程序
void Delay10us_51(void);//51延时10us程序
void delayms(u16 ms);//ms延时程序
void StartModule();//打开超声波测距	 
void Count_Distance();//计算距离

void main()
{
	Config_UARTimer(9600);
	
	while(1)
	{
		StartModule();
		while(!Echo);
		TR0=1;
		while(Echo);
		TR0=0;
		 
		Count_Distance();
		delayms(100);
		
	}

}

//15延时10us程序
void Delay10us_15(void)
{
	u8 i=30;
	_nop_();
	while(--i);
}

//51延时10us程序
void Delay10us_51(void)
{
	u8 i=15;
	_nop_();
	while(--i);
}
//ms延时程序
void delayms(unsigned int ms)
{
	unsigned char i=100,j;
	for(;ms;ms--) 
	{
		while(--i)
		{
			j=10;
			while(--j);
		}
	}
}

//打开超声波测距
void StartModule()
{
	Trig=1;
	Delay10us_51();
	Trig=0;
		
}

void Count_Distance()
{
	time=TH0*256+TL0;
	TH0=0;
	TL0=0;
	
	Distance = (time*1.87)/100;
	if(flag==1)		    //超出测量
	{
	  flag=0;
	  printf("-----\n"); 
	}
	else
	{
	 
	  printf("Distance = %f CM\n",Distance); 
	}
}

void Config_UARTimer(u16 Baud)
{
	//需要配置串口,定时器0,定时器1

//	//15单片机配置
//    PCON &= 0x7F;  //不倍速
//    SCON  = 0x50;  //工作方式1,8位异步
//	AUXR &= 0xBF;  //定时器1时钟为Fosc/12,即12T
//    AUXR &= 0xFE;  //串口1选择定时器1为波特率发生器
//    TMOD &= 0x0F;  
//    TMOD|=0X21;//定时器1工作方式2(8位定时器),定时器0工作方式1(16位定时器)
//
//	TH0=0;
//	TL0=0;//定时器0初值赋值
//
//	TH1=256-(11059200/12/32)/Baud;
//	TL1=TH1;//定时器1初值赋值
//
//	ET0=1;//定时中断0打开
//	ET1=0;//定时中断1禁止
//	TR0=1;//定时器0打开
//	TR1=1;//定时器1打开
//	TI=1;

	//51单片机配置程序
	PCON&=0X7F;//不倍速
	SCON=0X50;//工作方式1,8位异步
	
	
	TMOD=0X21;//定时器1工作方式2(8位定时器),定时器0工作方式1(16位定时器)

	TH0=0;
	TL0=0;//定时器0初值赋值

	TH1=256-(11059200/12/32)/Baud;
	TL1=TH1;//定时器1初值赋值

	ET0=1;//定时中断0打开
	ET1=0;//定时中断1禁止
	TR0=1;//定时器0关闭
	TR1=1;//定时器1打开
	TI=1;
	EA=1;//打开总中断
}


void timer0()interrupt 1
{
	flag=1;	
}

stm32

hcsr04.c

#include "hcsr04.h"
#include "delay.h"

u16 overcount=0;//溢出计数

//中断配置
void NVIC_Config(void)
{
		NVIC_InitTypeDef NVIC_InitStruct;
		//设置中断优先级
		NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
		//中断初始化
		NVIC_InitStruct.NVIC_IRQChannel=TIM2_IRQn;
		NVIC_InitStruct.NVIC_IRQChannelCmd=ENABLE;
		NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority=0;
		NVIC_InitStruct.NVIC_IRQChannelSubPriority=0;
		NVIC_Init(&NVIC_InitStruct);
}
//超声波初始化
void HCSR04_Init(void)
{
		GPIO_InitTypeDef GPIO_InitStruct;
		TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;
		//时钟使能
		RCC_APB2PeriphClockCmd(HCSR04,ENABLE);
		RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2,ENABLE);
		//trig脚-推挽输出
		GPIO_InitStruct.GPIO_Mode=GPIO_Mode_Out_PP;
		GPIO_InitStruct.GPIO_Pin=HCSR04_TRIG;
		GPIO_InitStruct.GPIO_Speed=GPIO_Speed_50MHz;
		GPIO_Init(HCSR04_PORT,&GPIO_InitStruct);
		GPIO_ResetBits(HCSR04_PORT,HCSR04_TRIG);
		//echo脚-浮空输入
		GPIO_InitStruct.GPIO_Mode=GPIO_Mode_IN_FLOATING;
		GPIO_InitStruct.GPIO_Pin=HCSR04_ECHO;
		GPIO_Init(HCSR04_PORT,&GPIO_InitStruct);
		GPIO_ResetBits(HCSR04_PORT,HCSR04_ECHO);
		//定时器TIM2初始化
		TIM_DeInit(TIM2);
		TIM_TimeBaseInitStruct.TIM_Period=1000-1;
		TIM_TimeBaseInitStruct.TIM_Prescaler=72-1;
		TIM_TimeBaseInitStruct.TIM_ClockDivision=TIM_CKD_DIV1;
		TIM_TimeBaseInitStruct.TIM_CounterMode=TIM_CounterMode_Up;
		TIM_TimeBaseInit(TIM2,&TIM_TimeBaseInitStruct);
		//定时器中断配置_更新中断
		TIM_ITConfig(TIM2,TIM_IT_Update,ENABLE);
		//中断配置
		NVIC_Config();
		//关闭定时器使能
		TIM_Cmd(TIM2,DISABLE);
}


//打开定时器
void OpenTimeForHc(void)
{
		//计数器清空
		TIM_SetCounter(TIM2,0);
		overcount=0;
		TIM_Cmd(TIM2,ENABLE);
}

//关闭定时器
void CloseTimeForHc(void)
{
		TIM_Cmd(TIM2,DISABLE);
}

//获取定时器时间
u32 GetEchoTimer(void)
{
		u32 t=0;
		t=overcount*1000;
		t+=TIM_GetCounter(TIM2);
		//计数器清0
		TIM2->CNT=0;
		delay_ms(50);
	
		return t;
}

//超声波测距
float Hcsr04GetLength(void)
{
		u32 t=0;
		int i=0;
		float lengthTemp=0;
		float sum=0;
		while(i!=5)
		{
				TRIG_Send=1;
				delay_ms(20);
				TRIG_Send=0;
				while(ECHO_Reci==0);
				OpenTimeForHc();
				i=i+1;
				while(ECHO_Reci==1);
				CloseTimeForHc();
				t=GetEchoTimer();
				lengthTemp=((float)t/58.0);
				sum+=lengthTemp;
		}
		lengthTemp=sum/5;
		return lengthTemp;
}

//定时器2中断
void TIM2_IRQHandler(void)
{
		if(TIM_GetITStatus(TIM2,TIM_IT_Update)!=RESET)
		{
				//清除中断标志位
				TIM_ClearITPendingBit(TIM2,TIM_IT_Update);
				overcount++;
		}
}

hcsr04.h

#ifndef __HCSR04_H
#define __HCSR04_H 
#include "sys.h"

#define HCSR04_PORT GPIOB  
#define HCSR04 RCC_APB2Periph_GPIOB
#define HCSR04_TRIG GPIO_Pin_5
#define HCSR04_ECHO GPIO_Pin_6

#define TRIG_Send PBout(5)
#define ECHO_Reci PBin(6)



void NVIC_Config(void);//中断配置
void HCSR04_Init(void);//超声波初始化
float Hcsr04GetLength(void);//超声波测距
	

#endif

  • 45
    点赞
  • 211
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值