树莓派31/100 - Pico连接HC-SR04超声波传感器,为自动避障智能小车打好基础

超声波传感器,英文ultrasonic sensor,既可以发射超声波,也可以接收超声波,它有一个重要作用,可以提前探测到附近的物体,而且通过声波速度,能够推算出附近物体离传感器的大概距离。

HC-SR04是一种非常流行的、很便宜的超声波传感器,非常适合进行嵌入式编程的技术试验,它是智能避障小车的一个关键部件,可以提前发现小车前方的障碍物,相应做出转弯或后退的动作。

HC-SR04长的模样见下图,它的工作电压为5V,据说HC-SR04P或HC-SR04+新型号可以工作在3V电压下。
在这里插入图片描述
现在我们的任务是把它接入树莓派Pico里,来感知位于它前方物体的距离。

电路连接

先观察它的针脚,只有4个,左边是Vcc,接5V正极,右侧 GND接地。我手里的HC-SR04是5V版本的,Vcc接Pico的VBUS即可。

在这里插入图片描述
现在还剩下2个针脚,Trig和Echo。

Trig负责控制是否发射超声波,如果给它高电位,则发射;如果低电位,则停止发射。这里,我们要把它接到Pico的一个GPIO引脚,让Pico控制它,我把它直接连接到GP18引脚。

在这里插入图片描述
Echo的连接稍微复杂一点,Echo的英文意思是“回声”,意思是接收超声波信号。如果接收到超声波,则高电位;如果没收到,则为低电位。

重要提醒:

我的HC-SR04的工作电压为5V,那么echo针脚的电位也相应是5V,而Pico的工作电压为3.3V,如果直接把echo的输出信号连接到GPIO引脚上,会超过Pico的工作电压,有损坏Pico的可能性,所以需要做降压处理。

网上有些教程没有说明这个问题,把echo输出直接连到GPIO引脚上,比如这篇文章

一种解决方案是加入3.3V-5.5V电平转换器,一个非常便宜的小元件,比如这篇文章

还有一种解决方案,只需要增加2个电阻,再加上清晰的头脑和认真的连线即可,我参考了这篇文章的说明。
在这里插入图片描述
用到高中物理知识,得到电阻的计算公式。我们这里的Vin=5,Vout=3.3,所以R1/R2 = 0.515,如果R1选1000欧,那么R2约为2000欧。

所以,从Echo串上一个1000Ω的电阻,接到GP26引脚,再串一个2000Ω的电阻接地,就可以有效保护Pico的引脚。最后的逻辑连线图:
在这里插入图片描述

实际连接图(电阻丝非常细,又比较长,拍摄角度不容易看清楚连接关系):
在这里插入图片描述

学习原理,编写程序

看懂代码,需要了解一下超声波测距的基本原理。传感器的T端(Transmitter)发出超声波,遇到障碍物之后,超声波返回,被传感器的R端(Receiver)接收到,根据时间差和声音的速度,可以求出距离。

在这里插入图片描述

HC-SR04就是这样工作的:
1)Trigger收到一个长达10us的方波后,开始发出超声波
2)传感器内部发出8组40KHz的方波,然后接收回声
3)方波发送完成后,ECHO变为高电位,收到回声的时候,ECHO为低电位
在这里插入图片描述

下面这段代码,一开始的2us是把电位置零,再产生10us的方波。

trigger.low()
utime.sleep_us(2)
trigger.high()
utime.sleep_us(10)
trigger.low()

然后把ECHO处于高电位的时间段计算出来,乘以声音的速度,由于超声波跑了双程,所以还要除以2,最后求出距离,这里的单位是厘米。

while echo.value() == 0:
    start = utime.ticks_us()
while echo.value() == 1:
    end = utime.ticks_us()
d = (end - start) * 0.0343 / 2

最后的所有源代码:

from machine import Pin
import utime

# 超声波测距,单位:厘米
def getDistance(trigger, echo):
    # 产生10us的方波
    trigger.low()
    utime.sleep_us(2)
    trigger.high()
    utime.sleep_us(10)
    trigger.low()
    
    while echo.value() == 0:
        start = utime.ticks_us()
    while echo.value() == 1:
        end = utime.ticks_us()
    d = (end - start) * 0.0343 / 2 
    return d

# 主程序
trigger = Pin(18, Pin.OUT)
echo = Pin(26, Pin.IN)

while True:
    distance = getDistance(trigger, echo)
    print("距离:{:.2f} cm".format(distance))
    utime.sleep(1)

看HC-SR04的规格说明书,它能判断出传感器前方15度范围内的2厘米~5米距离的障碍物,分辨率达3毫米。
在这里插入图片描述

这里的计算距离的函数已经非常简化,有时会不太准确,可以多取几次求平均,另外,如果你对距离精度有更高的要求,那就要换其它的传感器了。

推荐阅读:
树莓派Pico开发系列文章

版权声明:本文为CSDN博主「申龙斌」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/slofslb/article/details/120700357

生成海报
点赞 0

申龙斌

我还没有学会写个人说明!

暂无评论

发表评论

相关推荐

nodemcu 模块用mciropython 使用SD卡

使用sd卡可以扩大8266的存储器,使用时候很重要的是接线。 其他很容易。下面程序就是初始化、挂载sd卡、读sd卡里面main.cpp里面的代码行。 import machine, sdcard, os from machine

Keil MDK5 STM32F103C8T6开发环境配置

Windows下使用Keil MDK5进行stm32f103c8t6的开发和编译, 配合ST-LINK工具进行烧录, 使用原生(非HAL)的方式. 所需硬件 stm32f103系列开发板 stm32f103c8t6核心板 参数 ARM 32-b

Arduino与Proteus仿真实例-DHT11温度湿度传感器驱动仿真

DHT11温度湿度传感器驱动仿真 DHT11 是一款基本的超低成本数字温度和湿度传感器。 它使用电容式湿度传感器和热敏电阻来测量周围的空气,并在数据引脚上吐出数字信号(不需要模拟输入引脚)。 它使用起来相当简单,但需要仔细定时来抓取数据。

九轴运动传感器--BMX160,硬件开发与程序设计

九轴运动传感器–BMX160,硬件开发与程序设计 前言 和之前OPT3001传感器一块板子上的九轴传感器的代码我写完啦,和大家分享一下 硬件部分介绍 BMX160介绍 BMX160是博世的九轴运动传感器&#xff