基于RT-Thread的HC-SR04超聲波驅動

前言

本次驅動用的是這款超聲波,超聲波的驅動大同小異,均可參考
在這里插入圖片描述

一、引腳定義

引腳功能
VCC接直流5V
TRIG接外部電路的TRIG端,向此引腳輸入10us以上的高電平可觸發超聲波測距
ECHO接外部電路的ECHO端,測距結束時該引腳會輸出一個高電平,電平寬度為超聲波往返時間之和
GND

二、工作原理

1、采用 IO 觸發測距,給至少 10us 的高電平信號;
2、模塊自動發送 8 個 40khz 的方波,自動檢測是否有信號返回;
3、有信號返回,通過 IO 輸出一高電平,高電平持續的時間就是超聲波從發射到返回的時間
4、測試距離=(高電平時間*聲速(340M/S))/2;

三、引腳時序圖

建議測量周期在60ms以上,防止發射信號對回響信號的有影響

在這里插入圖片描述

四、創建RTT工程(開始動手

在這里插入圖片描述

五、打開CubeMX

在這里插入圖片描述

六、配置串行調試口

在這里插入圖片描述

七、配置使用外部高速晶振

在這里插入圖片描述

八、創建工程時默認使用了串口一,這里也打開串口一

在這里插入圖片描述

九、開啟定時器三,定時器三是用來給超聲波回波信號計時的,計算高電平時間從而得到測量距離

在這里插入圖片描述

十、配置時鐘線

在這里插入圖片描述

十一、生成代碼

在這里插入圖片描述

十二、打開定時器設備驅動程序

在這里插入圖片描述

十三、使能定時器模塊

在這里插入圖片描述

十四、打開定時器三的注釋(使用哪個定時器就打開哪個,沒有的就自己寫上去

在這里插入圖片描述

十五、在主函數中寫入如下代碼

/** Copyright (c) 2006-2024, RT-Thread Development Team** SPDX-License-Identifier: Apache-2.0** Change Logs:* Date           Author       Notes* 2024-05-10     先睡個好覺    first version*/#include <rtthread.h>
#include <rtdevice.h>  //加載設備驅動頭文件
#include <board.h>#include <hwtimer.h>#define HWTIMER_DEV_NAME   "timer3"     /* 定時器名稱 */
rt_device_t hw_dev;                     /* 定時器設備句柄 */rt_err_t ret = RT_EOK;    //返回值判斷是否成功
rt_uint32_t timer_cb_num = 0;           /*進定時器超調函數次數  */
rt_uint32_t level_flag = 1;         /*判斷超聲波接受引腳是否是第一個上升沿*/
rt_uint32_t echo_high_time = 0;     //超聲波接受引腳高電平總時間,單位為us
rt_uint32_t freq = 1000000;               /* 計數頻率 */
rt_hwtimer_mode_t mode;                 /* 定時器模式 */
rt_hwtimerval_t timeout_s;      /* 定時器超時值 */rt_uint32_t distance_cm = 0;     //超聲波測量出的距離#define SR04T_PIN_TRIG   GET_PIN(C, 9)  //獲取sr04t超聲波觸發引腳號
#define SR04T_PIN_ECHO   GET_PIN(C, 8)  //獲取sr04t超聲波接收引腳號/* 定時器3超時回調函數,每10us會進來一次*/
static rt_err_t timeout3_cb(rt_device_t dev, rt_size_t size)
{timer_cb_num++;//每進一次超調函數,該變量加一if((rt_pin_read(SR04T_PIN_ECHO) == PIN_HIGH)&&(level_flag)){timer_cb_num = 0;  //如果超聲波接收引腳被拉高了,重新進行計數level_flag = 0;}if ((rt_pin_read(SR04T_PIN_ECHO) == PIN_LOW)&&(level_flag == 0)){echo_high_time = timer_cb_num*10; //一個timer_cb_num是10uslevel_flag = 1;rt_kprintf("%d\n",timer_cb_num/9);}return 0;
}int sr04_Init(void)
{//設置sr04t超聲波引腳的模式rt_pin_mode(SR04T_PIN_TRIG, PIN_MODE_OUTPUT);//設置引腳為輸出模式rt_pin_mode(SR04T_PIN_ECHO, PIN_MODE_INPUT_PULLDOWN);//設置ECHO引腳為輸入模式rt_pin_write(SR04T_PIN_TRIG, PIN_LOW);//拉低引腳rt_pin_write(SR04T_PIN_ECHO, PIN_LOW);//拉低引腳/* 查找定時器設備 */hw_dev = rt_device_find(HWTIMER_DEV_NAME);if(hw_dev == RT_NULL){rt_kprintf("hwtimer sample run failed! can't find %s device! \n",HWTIMER_DEV_NAME);return RT_ERROR;}/* 以讀寫方式打開設備 */rt_device_open(hw_dev, RT_DEVICE_OFLAG_RDWR);if(ret != RT_EOK){rt_kprintf("open %s device failed!\n",RT_DEVICE_OFLAG_RDWR);return ret;}/* 設置超時回調函數 */rt_device_set_rx_indicate(hw_dev, timeout3_cb);/* 設置計數頻率(若未設置該項,默認為1Mhz 或 支持的最小計數頻率) */rt_device_control(hw_dev, HWTIMER_CTRL_FREQ_SET, &freq);/* 設置模式為周期性定時器(若未設置,默認是HWTIMER_MODE_ONESHOT)*/mode = HWTIMER_MODE_PERIOD;rt_device_control(hw_dev, HWTIMER_CTRL_MODE_SET, &mode);/* 設置定時器超時值為10us并啟動定時器 */timeout_s.sec = 0;      /* 秒 */timeout_s.usec = 10;     /* 微秒 */if (rt_device_write(hw_dev, 0, &timeout_s, sizeof(timeout_s)) != sizeof(timeout_s)){rt_kprintf("set timeout value failed\n");return RT_ERROR;}return RT_EOK;
}//信號觸發
void US_SendStartSignal(void)
{rt_pin_write(SR04T_PIN_TRIG, PIN_HIGH);//拉高引腳,觸發信號rt_hw_us_delay(20);   //給20us的延時//rt_thread_mdelay(5);rt_pin_write(SR04T_PIN_TRIG, PIN_LOW);//拉低引腳
}//數據處理
//count傳進去的參數是us
float SR04T_DataConversion(rt_uint32_t *count)
{float result = 0;result = (float)((float)(*count * 340) / 2000000.0);*count = 0;result = result*100.0; //將米轉化為厘米return result;
}//-------------------超聲波線程-----------------------------------------------
rt_thread_t Sr04Th_Handler;   //姿態解算線程句柄
#define Sr04_TH_PRIO    10    //姿態解算線程優先級
#define Sr04_STK_SIZE   700  //姿態解算線程堆棧大小
#define Sr04_TICK_LEN   5    //姿態解算線程執行時間void th_sr04_entry(void *parameter)
{rt_uint16_t num_trig_time=0;while(1){num_trig_time++;if(num_trig_time>12){num_trig_time = 0;US_SendStartSignal();//超聲波信號觸發}distance_cm = SR04T_DataConversion(&timer_cb_num);//超聲波數據處理//rt_kprintf("%d\n",echo_high_time/28);rt_thread_mdelay(5);}
}int sr04_th_creat(void)
{//超聲波線程Sr04Th_Handler = rt_thread_create("th_sr04_entry",th_sr04_entry,NULL,Sr04_STK_SIZE,Sr04_TH_PRIO,Sr04_TICK_LEN);if(Sr04Th_Handler == NULL){rt_kprintf("th_sr04_entry(create)failed...\n");return -ENOMEM;}return RT_EOK;
}void th_start(void)
{rt_thread_startup(Sr04Th_Handler);   //開啟超聲波線程線程調度
}int main(void)
{sr04_Init(); //超聲波初始化sr04_th_creat();//超聲波線程創建th_start();//開啟線程調度return RT_EOK;
}

十六、編譯,有如下報錯,先雙擊進入第一個錯誤

在這里插入圖片描述

十七、把這段代碼進行注釋

在這里插入圖片描述

十八、再編譯還剩這個報錯,找不到hwtimer.h文件

在這里插入圖片描述

十九、跳轉進入這個頭文件

在這里插入圖片描述

二十、找到它的文件路徑

在這里插入圖片描述

二十一、打開構建配置,進行路徑包含,應用后關閉

在這里插入圖片描述

二十二、再次編譯,報錯解決

在這里插入圖片描述

二十三、連接好硬件

在這里插入圖片描述

二十四、下載程序,查看串口一,有數據輸出,并且隨著遮擋物的遠近,數據大小有變化

在這里插入圖片描述

二十五、這里需要注意一下,如果你使用的定時器里面沒有,需要模仿里面的結構自行添加

在這里插入圖片描述

二十六、最后提醒一下,代碼中輸出的并不是準確的cm數,我只是隨意除了一個數字就輸出了,數據轉換函數在代碼中我也寫了,不過沒有使用,因為它輸出的是浮點數,rtthread要想打印浮點數需要另行配置,在這個工程里我沒有配置,所以要想得到精確的cm數,請自行數據轉換。

rtthread輸出浮點數,可以參考我的這篇文章
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?
RT-Thread(RTT)如何打印輸出浮點數
在這里插入圖片描述

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/10070.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/10070.shtml
英文地址,請注明出處:http://en.pswp.cn/web/10070.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Python框架Django入門教程

Django 是一個使用 Python 編程語言開發的、免費且開源的 Web 應用框架。它遵循 "DRY&#xff08;Dont Repeat Yourself&#xff09;" 原則&#xff0c;旨在簡化創建功能豐富的、高效率的 Web 網站。Django 提供了模型-視圖-控制器&#xff08;MVC&#xff09;架構的…

時尚圈的節制美學 — 奧柔拉 AVRALA的獨特設計理念

在這個多元化的時代&#xff0c;女性正在經歷一場前所未有的角色變革。她們不再僅僅滿足于傳統的社會角色&#xff0c;而是勇敢地追求個人職業發展和自我實現。在這樣的背景下&#xff0c;服飾不僅僅是外在的裝飾&#xff0c;更是內心故事的講述者、個性自我的表達者、身份歸屬…

KaiOS Data PDN 數據建立流程

代碼邏輯 APN創建 在 DataCallManager.jsm中,會對所有apnsetting創建一個datacall,其中會包含dataprofile的成員(通過apn參數來創建),在之后的流程用于直接發送到modem建立PDN。 PDN建立 1、DataCallManager.jsm -dcInterface.setupDataCall //RILNetworkInterface.c…

C語言內存泄漏及檢測方法

目錄 1. 內存泄漏概述 1.1 內存泄漏定義 1.2 內存泄漏的危害 1.3 內促泄漏的原因 2. C語言中的內存管理 2.1 C語言內存分配方式 2.2 C語言內存管理函數 2.3 動態內存管理注意事項 3. 內存泄漏的檢測與定位 3.1 內存泄漏檢測工具 3.2 內存泄漏定位方法 3.3 內存泄漏…

NX/UG二次開發—3D幾何—多邊形內部最大圓

多邊形內部最大圓&#xff0c;為什么不能說最大內切圓&#xff1f;如果正方形或正凸多邊形&#xff0c;最大內部圓是與邊相切的&#xff0c;但對于不規則多邊形&#xff0c;很多情況是正好經過一些凹點。 本次介紹在NX中計算封閉邊界內部最大圓&#xff1a; 1、首先按順序排序…

Spring、SpringMVC

一、Spring框架中的單例Bean是線程安全的嗎&#xff1f; 【默認單例的情況下】Spring Bean并沒有可變的狀態&#xff08;如Service類和DAO類&#xff09;&#xff0c;即只能查不能改&#xff0c;所以沒有并發問題&#xff0c;所以某種程度上來說Spring的單例Bean是線程安全的。…

【ZZULI數據結構實驗】壓縮與解碼的鑰匙:赫夫曼編碼應用

&#x1f4c3;博客主頁&#xff1a; 小鎮敲碼人 &#x1f49a;代碼倉庫&#xff0c;歡迎訪問 &#x1f680; 歡迎關注&#xff1a;&#x1f44d;點贊 &#x1f442;&#x1f3fd;留言 &#x1f60d;收藏 &#x1f30f; 任爾江湖滿血骨&#xff0c;我自踏雪尋梅香。 萬千浮云遮碧…

Faiss原理及使用總結

Faiss&#xff08;Facebook AI Similarity Search&#xff09;是一個用于高效相似性搜索和密集向量聚類的庫。 一、原理 向量表示與相似度度量&#xff1a;在Faiss中&#xff0c;數據通常被表示為高維向量&#xff0c;這些向量可以來自深度學習模型的特征提取&#xff0c;也可…

2024-05-11 問AI:在深度學習中,學習率是什么

文心一言 在深度學習中&#xff0c;**學習率&#xff08;Learning Rate&#xff09;**是一個非常重要的超參數&#xff0c;它控制著模型在訓練過程中參數更新的步長。具體來說&#xff0c;學習率決定了在每次迭代&#xff08;或稱為一個epoch&#xff09;中&#xff0c;模型根…

前端工程化之包管理器

這里寫目錄標題 什么是包包管理工具常用的包管理工具npmnpm 基本使用初始化搜索工具包下載安裝包導入 npm 包基本流程生產依賴與開發依賴全局安裝安裝全部依賴安裝指定版本的包刪除依賴包 cnpm全局安裝nrm 的使用 yarn全局安裝yarn 常用命令 pnpm 【推薦使用】全局安裝 什么是包…

我國吻合器市場規模不斷擴大 國產化率有所增長

我國吻合器市場規模不斷擴大 國產化率有所增長 吻合器是替代手工切除或縫合的一種醫療器械&#xff0c;其工作原理與訂書機十分相似&#xff0c;可利用鈦釘對組織進行離斷或吻合。經過多年發展&#xff0c;吻合器種類逐漸增多&#xff0c;根據手術方式不同&#xff0c;吻合器大…

【JavaEE 初階(三)】多線程代碼案例

?博主主頁: 33的博客? ??文章專欄分類:JavaEE?? &#x1f69a;我的代碼倉庫: 33的代碼倉庫&#x1f69a; &#x1faf5;&#x1faf5;&#x1faf5;關注我帶你了解更多線程知識 目錄 1.前言2.單例模式2.1餓漢方式2.2餓漢方式 3.阻塞隊列3.1概念3.2實現 4.定時器4.1概念4.…

支付寶小程序如何去除頁面下拉回彈

描述&#xff1a;支付寶小程序頁面下拉時會產生回彈&#xff0c;如果頁面上有拖拽功能&#xff0c;會有影響 解決方法&#xff1a; 頁面xx.config.js中設置&#xff1a;allowsBounceVertical: “NO” 官方文檔&#xff1a;https://opensupport.alipay.com/support/FAQ/7110b5d…

WT32-ETH01作為TCP Client進行通訊

目錄 模塊簡介WT32-ETH01作為TCP Client設置電腦作為TCP Server設置連接并進行通訊總結 模塊簡介 WT32-ETH01網關主要功能特點: 采用雙核Xtensa⑧32-bit LX6 MCU.集成SPI flash 32Mbit\ SRAM 520KB 支持TCP Server. TCP Client, UDP Server. UDP Client工作模式 支持串口、wif…

鴻蒙OpenHarmony技術:【Docker編譯環境】

Docker環境介紹 OpenHarmony為開發者提供了兩種Docker環境&#xff0c;以幫助開發者快速完成復雜的開發環境準備工作。兩種Docker環境及適用場景如下&#xff1a; 獨立Docker環境&#xff1a;適用于直接基于Ubuntu、Windows操作系統平臺進行版本編譯的場景。基于HPM的Docker環…

其他編程語言中調用 Python 腳本,如何設置Python腳本的相對路徑

import os# 假設 script_directory 是你的腳本所在的目錄 script_directory os.path.dirname(os.path.abspath(__file__))# 使用 os.path.join 來構建相對路徑 relative_path_to_image os.path.join(script_directory, 合并/figure_pic2.png)# 現在你可以使用這個相對路徑來加…

uni-app+vue3 +uni.connectSocket 使用websocket

前言 最近在uni-appvue3websocket實現聊天功能&#xff0c;在使用websocket還是遇到很多問題 這次因為是app手機應用&#xff0c;就沒有使用websocket對象&#xff0c;使用的是uni-app的uni.connectSocket 為了方便測試這次用的是node.js一個簡單的dom&#xff0c;來聯調模擬…

Apache Flume Agent內部原理

Apache Flume Agent內部原理 Apache Flume 是一個可擴展的、分布式的日志收集、聚合和傳輸系統。在 Flume 中&#xff0c;Agent 是一個獨立的進程&#xff0c;負責接收、傳輸和處理數據。Agent 內部包含多個組件&#xff0c;每個組件都有不同的功能和責任。 1. Source&#xff…

5個 Elasticsearch 核心組件

Elasticsearch 是一個基于 Lucene 的搜索引擎&#xff0c;它提供了分布式、高可用、多租戶的能力。Elasticsearch 的核心組件包括節點&#xff08;Node&#xff09;、集群&#xff08;Cluster&#xff09;、索引&#xff08;Index&#xff09;、分片&#xff08;Shard&#xff…

三下鄉社會實踐投稿攻略在這里

在當今信息爆炸的時代&#xff0c;如何讓自己的聲音被更多人聽到&#xff0c;成為許多人和企業所關心的問題。其中&#xff0c;向各大媒體網站投稿&#xff0c;成為了一種常見的宣傳方式。但是&#xff0c;如何投稿各大媒體網站&#xff1f;新聞媒體發文策略又有哪些呢&#xf…