当前位置:   article > 正文

STM32学习笔记(7) 超声波HSR04模块详解

hsr04
超声波硬件详解

  • 硬件参数
参数说明
产品名称HC-SR04超声波模块
工作电压DC 5V
工作电流15mA
工作频率40KHz
射程范围2cm — 400cm
测量角度<= 15度
输入触发信号10us的TTL脉冲
输出回响信号输出TTL电平信号,与射程成正比
二 工作原理

超声波信号时序图

  1. 采用(IO触发测距,至少给10us的高电平)
  2. 模块自动发送8个40kHz的方波,自动检测是否有信号返回
  3. 有信号返回时,通过IO输出一高电平、高电平持续时间就是超声波从发射到返回的时间
三 代码编写
  • 程序流程图
  1. GPIO结构体的初始化
  2. EXTI外部中断结构体的初始化
  3. NVIC中断结构体的初始化
  4. TimeBase时基结构体的初始化
  5. 超声波Trig发送信号
  6. 外部中断服务函数接收返回信号并计算出距离(全局变量)
  • 关键代码
/**
 * 函数名:HSR04_Init()
 * 功能:超声波的初始化
 * 引脚:PB5(Trig) | PB4(Echo)
 * 占用的内设资源:TIM6,EXTI_Line4
 */
void HSR04_Init()
{
    GPIO_InitTypeDef  GPIO_InitSture;
	EXTI_InitTypeDef  EXTI_InitSture;
	NVIC_InitTypeDef  NVIC_InitSture;
    TIM_TimeBaseInitTypeDef   TIM_TimeBaseInitSture;
	
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);//打开外部中断exti挂载时钟线
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6,ENABLE);
	GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE);
	
    /**************************GPIO结构体的初始化**********************************/
	GPIO_InitSture.GPIO_Mode=GPIO_Mode_Out_PP;   
	GPIO_InitSture.GPIO_Pin=Trig;             
	GPIO_InitSture.GPIO_Speed=GPIO_Speed_10MHz;  
	GPIO_Init(Trig_Port,&GPIO_InitSture);
	
	GPIO_InitSture.GPIO_Mode=GPIO_Mode_IN_FLOATING;    
	GPIO_InitSture.GPIO_Pin=Echo;               
	GPIO_Init(Echo_Port,&GPIO_InitSture);

    /**************************EXTI外部中断结构体的初始化***************************/
	GPIO_EXTILineConfig(GPIO_PortSourceGPIOB,GPIO_PinSource4);//将外部中断引脚重映射到GPIO
	EXTI_InitSture.EXTI_Line=EXTI_Line4;
	EXTI_InitSture.EXTI_LineCmd=ENABLE;
	EXTI_InitSture.EXTI_Mode=EXTI_Mode_Interrupt;//选择中断方式
	EXTI_InitSture.EXTI_Trigger=EXTI_Trigger_Rising;
	EXTI_Init(&EXTI_InitSture);

    /**************************NVIC中断结构体的初始化*******************************/
	NVIC_InitSture.NVIC_IRQChannel=EXTI4_IRQn;
	NVIC_InitSture.NVIC_IRQChannelCmd=ENABLE;
	NVIC_InitSture.NVIC_IRQChannelPreemptionPriority=2;
	NVIC_InitSture.NVIC_IRQChannelSubPriority=2;
	NVIC_Init(&NVIC_InitSture);
	
    /***********************TimeBase时基结构体的初始化*******************************/
	TIM_TimeBaseInitSture.TIM_CounterMode=TIM_CounterMode_Up;
	TIM_TimeBaseInitSture.TIM_Period=5000;
	TIM_TimeBaseInitSture.TIM_Prescaler=7199;
	TIM_TimeBaseInitSture.TIM_ClockDivision=0;//无需分频
	TIM_TimeBaseInit(TIM6,&TIM_TimeBaseInitSture);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
四 知识点分析

观察以下两段代码

 TIM_SetCounter(TIM6,0);
 TIM_Cmd(TIM6,ENABLE);
 while(GPIO_ReadInputDataBit(GPIOB,Echo)==1)
 TIM_Cmd(TIM6,DISABLE);
 Distance_test=TIM_GetCounter(TIM6)*340/200;
  • 1
  • 2
  • 3
  • 4
  • 5
 TIM_SetCounter(TIM6,0);
 TIM_Cmd(TIM6,ENABLE);
 while(GPIO_ReadInputDataBit(GPIOB,Echo)==1);
 TIM_Cmd(TIM6,DISABLE);
 Distance_test=TIM_GetCounter(TIM6)*340/200;
  • 1
  • 2
  • 3
  • 4
  • 5

第三行的while循环中,第一个无分号(),第二个有分号(;).

所以第一段代码中,由于没有分号,所以相当于

 while(GPIO_ReadInputDataBit(GPIOB,Echo)==1)
 {
 	 TIM_Cmd(TIM6,DISABLE);
 }
  • 1
  • 2
  • 3
  • 4

所以在高电平的时间段,定时器一直在关闭,那么超声波测出来的距离始终为0

而第二段代码则是可以正常运行的

改了好久的bug,权当纪念~

相关代码超声波模块的使用

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/知新_RL/article/detail/479291
推荐阅读
相关标签
  

闽ICP备14008679号