【单片机开发】智能小车工程 (超声波测距HC-SR04)
发布日期:2021-05-08 05:11:04 浏览次数:21 分类:原创文章

本文共 3699 字,大约阅读时间需要 12 分钟。

项目相关链接:



在这里插入图片描述
测距原理:PA5 trig 产生超声波
PA4 ECHO 记录从发出到接收的时间
思路1 采用定时器的输入捕获
思路2 在trig=1 时人为打开定时器 收到后关闭定时器

我们看思路2 //参照野火例程

length.h

#ifndef __LENGTH_H#define	__LENGTH_H#include "stm32f10x.h"#include <stdio.h>void Distance_Config();    //测距用到的引脚初始化#endif #include<length.h>

length.c

//ECHO PA4//TRIG PA5void Distance_Config(){       GPIO_InitTypeDef GPIO_InitStructure;    	  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);  //开启IO口对应的时钟	  	  GPIO_InitStructure.GPIO_Pin=GPIO_Pin_4;	 // GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IN_FLOATING;  //引脚的模式设置为浮空输入模式		GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IPD;	  GPIO_Init(GPIOA,&GPIO_InitStructure);		  GPIO_InitStructure.GPIO_Pin=GPIO_Pin_5;	  GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; //配置为通用推挽输出模式    GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;		  GPIO_Init(GPIOA,&GPIO_InitStructure);}

tick.h

//配置时钟#ifndef __TIM3TICK_H#define	__TIM3TICK_H#include "stm32f10x.h"#include "misc.h"#include "stm32f10x_tim.h"//#include <stdio.h>void Tim3_Config();  //配置定时器TIM3static void NVIC_Configuration();  //配置定时器中断,当计数时间到时触发中断#endif /* __USART1_H */

tick.c

#include"tick.h"void Tim3_Config(){       TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;	  NVIC_Configuration();  //配置中断函数	  //使能TIM3时钟    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);	  	     	  TIM_TimeBaseStructure.TIM_Period =49999;	  TIM_TimeBaseStructure.TIM_Prescaler=71;  //设置分频系数为71	  TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;	  TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up;  //设置为向上计数模式		  TIM_TimeBaseInit(TIM3,&TIM_TimeBaseStructure);		 // TIM_ARRPreloadConfig(TIM3,ENABLE);  //使能TIM3重载寄存器	  TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE);  //注意这里函数的意思是打开中断,溢出中断	  }static void NVIC_Configuration(){     NVIC_InitTypeDef NVIC_InitStructure;    /* Configure one bit for preemption priority */  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);    /* 配置中断源 */  NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;  NVIC_Init(&NVIC_InitStructure);}

main.c

#include "stm32f10x.h"#include "usart.h"#include "length.h"#include "tick.h"//注意这里的超声波模块的VCC必须是+5V,如果是+3V的话会导致测距不准#define CLI()      __set_PRIMASK(1)		/* 关闭总中断 */  #define SEI() __set_PRIMASK(0)		/*开总中断*/void Delay(unsigned short int time);  //粗略的延时函数float ChangeDistance(unsigned int cout1);  //时间转为距离函数//ECHO PA4//TRIG PA5int main(void){   	  unsigned int count=0;	  float distance=0;	  float distancebuf[]={   0};      uart_init(9600);    Distance_Config();  //测距模块对应的引脚初始化    CLI() ;//关闭总中断	  SEI(); //开总中断	  Tim3_Config();  //定时器的初始化		  	  GPIO_ResetBits(GPIOA,GPIO_Pin_5);  //先拉低电平		  while(1)		{         //  printf("测距开始\n");			  GPIO_SetBits(GPIOA,GPIO_Pin_5);  //拉高电平			  Delay(30);  //延时20个微秒			//  Delay(20);			//  Delay(20);			 GPIO_ResetBits(GPIOA,GPIO_Pin_5);        TIM3->CNT=0;  //TIM3的计数器清0       while(GPIO_ReadInputDataBit(GPIOA,GPIO_Pin_4) == 0); //等待ECHO的高电平		       TIM_Cmd(TIM3,ENABLE);  //运行TIM3进行计时       			while((GPIO_ReadInputDataBit(GPIOA,GPIO_Pin_4) == 1) && (TIM3->CNT < TIM3->ARR-10));			 			  TIM_Cmd(TIM3,DISABLE);         		        count=TIM3->CNT;        printf("count=%d",count);						  distance=ChangeDistance(count);			  printf(" 当前距离为:%f\n",distance);			  Delay(20000); 				Delay(20000); 			  while(1);				     }}void Delay(unsigned short int time)  //粗略的延时函数{       unsigned char i=0;	  while(time--)		{           i=10;			  while(i--);    }}float ChangeDistance(unsigned int cout1){       float distance=0;	  printf("cou1=%d\n",cout1);	  distance=cout1/58.0;		  return distance;}

最后一部分关于测速的程序经过无数次尝试仍然没有调通,各位大哥要是有的话跟小弟分享一下感激不尽。

上一篇:【单片机开发】智能小车工程(经验总结)
下一篇:【单片机开发】智能小车工程 (蓝牙遥控JDY-31)

发表评论

最新留言

能坚持,总会有不一样的收获!
[***.219.124.196]2025年04月03日 20时20分50秒