恒美微站 Logo 恒美微站
  • 首页
  • 关于我们
  • 建站服务
  • 主题模板
  • 案例展示
  • 资讯中心
  • 联系我们

四、SysTick+(红外传感器+LCD1602显示器)模块+智能排队系统项目

  • 首页
  • 资讯中心
  • /
  • 四、SysTick+(红外传感器+LCD1602显示器)模块+智能排队系统项目

相关资讯

【RDMA】rdma指令 2026/8/19 21:11:47
基于LF唤醒与BLE的智能眼镜防丢器:硬件设计与低功耗实现 2026/8/19 21:11:47
挪威2万亿美元主权基金欲购8000亿美元OpenAI,是想象力还是空想? 2026/8/19 21:06:47

最新资讯

抖音无水印下载完整指南:从安装到批量保存作者主页的实测全记录
深挖C语言:深入理解指针(2)
主流APP广告变现平台推荐:APP变现平台选型指南
蓝桥杯webJS
光度立体成像全栈拆解 | 多视角光影法向量求解+梯度积分重建,助力漫反射工件微划痕凹坑褶皱高速高精度2.5D缺陷检测
TypeScript工程化AI应用开发:从配置管理到流式响应实战

今日推荐

Windows 安卓应用安装终极方案:5分钟上手免费APK安装器,三步告别模拟器
WarcraftHelper 魔兽争霸3优化实战指南
抖音批量下载实战手册:用douyin-downloader把6小时手工劳动压缩到15分钟

本周热门

【文章复现】非线性值迭代自适应动态规划(ADP):离散时间非线性系统的策略迭代自适应动态规划算法研究附Matlab代码
【双层规划,节点出清价,绿证交易,CVaR方法】两级电力市场环境下计及风险的省间交易商最优购电模型附Matlab代码
隐式mpc+自适应mpc+时变mpc,线性时变模型预测控制附Simulink仿真

本月精选

如何用DamaiHelper实现演唱会门票的智能自动化抢购:完整技术解决方案指南
第4篇:59 倍性能差距的索引瓶颈定位——一次教科书级的全表扫描调优
终极歌词批量下载神器:5分钟解决离线音乐库歌词同步难题

四、SysTick+(红外传感器+LCD1602显示器)模块+智能排队系统项目

发布时间:2026/8/19 21:11:47
四、SysTick+(红外传感器+LCD1602显示器)模块+智能排队系统项目 1. SysTick介绍1.1什么是SysTickSystick即滴答定时器是内核中的一个特殊定时器用于提供系统级的定时服务。该定时器是一个24位的 递减计数器具有自动重载值寄存器的功能。当计数器到达自动重载值时它会自动重新加载并开始新的计 数周期。Systick定时器的主要功能包括实现简单的延时、生成定时中断以及进行精确定时和周期定时操作。此外 Systick定时器还可以被用于其他目的例如作为操作系统的时基如FreeRTOS或者用于软件看门狗等系统调度操作。在STM32中Systick通常以HCLKAHB时钟或HCLK/8作为运行时钟。1.2 SysTick工作原理在使用Systick定时器进行延时操作时可以设定初值并使能后每经过一个系统时钟周期计数值就减1。 当计数到0时Systick计数器自动重装初值并继续计数同时内部的COUNTFLAG标志会置位触发中断 如果中断使能。这样可以在中断处理函数中实现特定的延时逻辑。时钟来源是HCLK72M之后一分频或者八分频VAL递减计数器递减到0之后countflag置1触发中断重装载值再次进入到VAL中进行下一轮计数。2. SysTick寄存器介绍SysTick控制及状态寄存器CTRLTICKINT会不会产生中断的一个标志位。ENABLE置1时计时器开始工作。SysTick重装载数值寄存器LOADSysTick当前数值寄存器VAL递减计数器3.手撸延时函数3.1HAL_Delay底层实验原理随便打开我们之前做过的一个程序发现我们之前用的延时函数都是delay_ms延时函数。我们F12进去。这个函数实际上是我们自己编写的中文的注释而不是ST公司自带的。 当然ST公司也给了延时函数。weak类型的可以有我们进行修改重写。那我们为什么还要进行其他的延时函数编写呢 是因为ST公司自带的只能实现毫秒级别的延时而我们有许多时候要求微秒的延时级别。我们现在看HAL_Delay是如何用systick实现的。选中HAL_Delay 依次ctrl cfv。这里就是实现的一个底层代码。3.2手撸原理首先我们看delay.c中的函数 有delay_us、delay_ms、delay_s。单位直接都是1000的进制关系我们只需写出us级别的延时函数需要用到其他单位的时候我们就进行while循环即可。我们上文说了systick的三种寄存器都需要我们来进行配置。VAL--当前计数器的值LOAD--重装载值--我们要计多少个数countflag--延时完成 还有要进行几分频。理一下思路1.确定要计多少个数 2.清空当前的计数 3.配置分频系数 4.开启定时器1.之前说过滴答定时器的时钟来源是HCLK72M、1秒会数72M个数1s1000ms1Mμs。对应就是1μs读了72个数。所以72*nμs个数需要读存放LOAD寄存器。SysTick-LOAD 72 * nμs2.清除掉之前有可能残留下来的值SysTick-VAL 0x003.在CTRL中第2位段进行分频SysTick-CTRL|1 2用或等的方式吧某一位 置11左移两位从第0位到第二位或等保证了怎么移 都会使第二位置14.开启定时器在CTRL中第0位段SysTick-CTRL|1 01左移0位当计数完成后 countflag将置为1。在CTRL第16位段SysTick-CTRL|1 16.在while循环的条件中temp 0x01使能位一直为1后者temp116 。我们要当countflag位置1时该退出while循环所以取个反。当计数未结束时 后者取0 加个反为1再和前者1 与的关系while循环继续。计数结束时后者为1 取反为0再与前者1 取与 总结果为0 退出while循环。结束之后 我们该关闭定时器使ENABLE那位至0。SysTick-CTRL~10;使用与等置第0位为0因为0与任何位与 都是0。4.手撸带操作系统的延时函数通常的滴答定时器会进行频繁的启动和关闭。但在操作系统如FreeRTOS中作为时基。就不能频繁的启动关闭。while循环结束的条件就是tcnt已经计的数ticks需要计多少数。通过不断的读取二者的值进行判断递减计数器VAL左----右由于读取间隔的问题可能会出现图左下方的两种情况。在流程图中也有体现其分别的计算方法。可以按照流程图的顺序来写。小实验SysTick模拟多线程较难实验目的使用SysTick模拟多线程实现流水灯实验。硬件清单上官二号ST-Link像之前我们的流水灯实验是单线程的。一般我们要进行多线程就要是移植一个操作系统比如RTOS但如果不移植的情况下如何模拟一个多线程。就要用到systick定时器。现在我们基于这个实验带操作系统的一个延时函数做一个复制。此处为systick的中断服务函数。task.c的内容在此之前要在BSP文件夹中分别新建task.c.h文件然后在“品”和魔法棒中添加对应文件和头文件。task.h 声明包含.c中的函数名称。主函数HAL_Init()打开并配置了 SysTick 定时器后硬件每 1ms 产生一次中断CPU 被打断后自动执行SysTick_Handler/systick_isr执行完再回到main的while(1)。模块红外传感器红外跟随避障模块详解 | 良许嵌入式如果红外接收管接收到了红外线OUT引脚就输出一个低电平否则就一直保持高电平。原理跟振动传感器相似。小实验红外点灯实验目的用手遮挡红外传感器LED1点亮2秒之后熄灭。硬件清单红外传感器上官二号ST-Link硬件接线对应的.h文件声明也要修改。模块LCD1602显示器LCD1602显示模块详解 | 良许嵌入式LCD1602 Liquid Crystal Display 1602一种常见的字符型液晶显示模块。虽然它接线多但是LCD1602是每个嵌入式工程师的必经之路。它能够显示16列2行共32个字符字符每个字符都由5x8像素点阵构成是一种专门用来显示字母、数字、符号等的液晶显示模块。LCD1602 的基本的操作分为读操作和写操作。其中读操作可以分为读状态和读数据写操作可以分为写指令和写数据。读状态输入 RS0、RW1、E1输出D0~7 读出为状态字读数据输入 RS1、RW1、E1输出D0~7 读出为数据写指令输入 RS0、RW0、E上升沿写入控制指令写数据输入 RS1、RW0、E上升沿写入需要显示的字符。LCD1602 的读写操作、屏幕和光标的操作都是通过指令编程来实现的。LCD1602 内部的控制器共有11条控制指令如表所示指令1清显示指令码 01H光标复位到地址 00H 位置。指令2光标复位光标返回到地址00H。指令3I/D光标和显示模式设置光标移动方向高电平右移低电平左移​ S屏幕上所有文字是否左移或者右移。高电平表示有效低电平则无效。指令4显示开关控制。​ D控制整体显示的开与关高电平表示开显示低电平表示关显示​ C控制光标的开与关高电平表示有光标低电平表示无光标​ B控制光标是否闪烁高电平闪烁低电平不闪烁。指令5S/C高电平时移动显示的文字低电平时移动光标​ R/L高电平时右移低电平时左移。指令6功能设置命令 DL高电平时为4位总线低电平时为8位总线​ N低电平时为单行显示高电平时双行显示​ F低电平时显示5x7的点阵字符高电平时显示5x10的点阵字符。指令7字符发生器RAM地址设置。指令8DDRAM地址设置。指令9读忙信号和光标地址BF为忙标志位高电平表示忙此时模块不能接收命令或者数据如果为低电平表示不忙。指令10写数据。指令11读数据。要在屏上显示有两个部分需要确定首先是显示的地址其次是显示的内容。显示的地址的设定呢是由指令8DDRAM地址来确定的。我们可以看到D7的位置始终是1。LCD1602 的控制器内置有 80 个 byte 的显存 而 LCD1602 只有两行 × 16 个字符的显示区域所以 显存中有些地址是无法对应上 LCD 屏的下图为显存地址对应图80H0x80不是数学上随便加个数字而是在告诉 LCD“这是一条‘设置地址’指令”。80H 给地址命令加上“标志位 D71”让控制器认出这是“设置显示地址”而不是普通数据或其它指令。接下来就是显示的内容。这个模块的显示的内容是有限的只能显示对应字符表中的内容。例如我们要显示1对应的输入就是00110001对应的十进制数是49对应的ASCII码就是1。实际上是于ASCII码是一一对应的所以在后续编写代码时直接把对应的字符直接输入进去即可LCD1602呢有一个初始化的流程那么我们在写程序的时候呢也要把这个初始化考虑进去。小实验驱动LCD1602显示内容实验目的1.使用LCD1602显示一个字符2.使用LCD1602显示一个字符串。硬件清单LCD1602上官二号ST-Link硬件接线首先我们还是要在Drivers--BSP中建立对应的文件夹其中都包括对应的.c和.h文件。依旧是老规矩在“品”中添加对应的文件。和在魔法棒中的C/C中添加对应的头文件。这些都是必要的步骤。之后来编写代码之后编译lcd1602.h将会出现。在lcd1602.c中先构想一下到底要写一些什么函数首先每个模块都是有一个初始化init函数的所以接下来还要有对应的读和写在讲时序图的时候说过要让LCD1602显示什么内容的话要首先把数据发送过去。那么写包含写数据和写命令既然有写肯定要有一个读read。但在LCD 1602模块里读数据寄存器用处不是非常大。所以一般来讲我们不会读它的数据寄存器或者说指令寄存器的所以我们读read这种相关函数的话就省略的不写了。到这儿我们初始化的部分就结束了。接下来进行写指令和写数据的函数封装。在时序图中我们也看过写数据和写指令的区别就是RS这个引脚是置0还是1来选择寄存器0就是指令寄存器1就是数据寄存器。那么在这个时序图的过程中呢我们需要不断去设置引脚的状态那我们就需要用到HAL_GPIO_WritePin这个函数经常写这个函数的话就会变得很不方便所以我们进行进一步的通过宏定义来进行封装。通过时序图写出写指令的代码。RS-0,RW-0。Output Data Register输出数据寄存器GPIOA-ODR cmd 把命令字节并行输出到 PA0~PA7作为 LCD 的 低 8 位数据线电平。把指令字节cmd的 8 位一次性写到 GPIOA 的输出数据寄存器ODR里从而出现在 PA0-PA7 引脚上交给 LCD 的 DB0-DB7。同样的写数据的代码类似。显示的地址和内容 show。在我们的.h文件中全部进行一个声明。main现在是显示一个字符接下来我们看看如何显示字符串。char *string 传入一个“字符指针”指向字符串的首地址。项目智能排队控制系统项目需求1.红外传感器检测有人通过并计数2.计数值显示在LCD16023.允许通过时LED1闪烁蜂鸣器不响继电器不闭合4.不允许通过时LED2闪烁蜂鸣器响继电器闭合5.每次允许通过5个人之后转为不允许通过3秒后再转为允许通过硬件清单继电器模拟匣机蜂鸣器红外避障模块LCD1602上官二号ST-Link硬件接线先把项目工程的框架搭起来。这个项目的需求是稍微复杂的所以我们会用到systick去模拟一个操作系统。在实验12的基础上进行修改。之后根据框图中所用到的模块在Drivers-BSP中建立对应的文件夹。之后在“品”中添加各个的.c文件在魔法棒中C/C添加头文件。由于之前我们的继电器的实验的命名是alarm在进入之后要将alarm换成gate。可以ctrlf找到replace进行替换。.h文件开头处的为大写需要手动敲一下。gate继电器的引脚变成了GPIOB B6所以在.c文件中要进行一个改动。之后依次检查各个模块是否正常编译运行看继电器是否正常。接下来看LED模块是否正常。beef蜂鸣器我们此次实验接的是B5所以对应的引脚代码也要修改一下。之后main中运行一下看是否正常。#include beep.h别忘加上。和beep_init。之后就是我们的红外传感器 对应的是exti.c。接到的是B4所以引脚还是要确定一下。之后测试一下。#include exti.h和exti_init。#include lcd1602.hlcd1602_init();目前确保了模块和接线是没有问题的后续就可以专注在逻辑上面的编写了。具体项目在下面说完状态机的知识后继续。状态机状态机State Machine是一种用于描述系统行为或功能行为的数学模型。它通常包含一组状态、一组转换条件以及动作执行。状态机通过在不同状态之间进行转换来模拟系统的行为。每个状态都代表系统的一个特定配置或情况而转换规则则定义了从一个状态转换到另一个状态的条件和动作。状态机广泛应用于多个领域包括但不限于计算机科学、电子工程、通信、自动化和机器人技术等。在计算机科学中状态机常用于描述软件系统的行为特别是在硬件设计、编译器设计、网络协议以及用户界面交互等方面。状态机的主要特点包括1.有限状态状态机通常具有有限数量的状态。这些状态可以是有序的、离散的或层次化的。2.转换条件状态之间的转换是基于特定条件触发的。当满足某个条件时状态机会从当前状态转换到下一个状态。3.动作执行在状态转换过程中状态机可能会执行某些动作或操作。这些动作可以包括计算、数据更新、输出信号等。4.确定性和非确定性状态机可以是确定性的每个条件唯一对应一个转换或非确定性的一个条件可能导致多个可能的转换。状态机的实现方式多种多样可以使用编程语言中的条件语句、循环结构或专门的状态机库来实现。此外硬件设计领域中的有限状态机Finite State Machine, FSM也是状态机的一种重要应用。图中所演示的状态不多如果以后状态多的话可以使用switch case语句。switch (表达式) {case 常量1:语句块1;break;case 常量2:语句块2;break;// ... 可以有多个casedefault: // 可选所有case都不匹配时执行默认语句块;break;}项目具体的实现由于我们要用到systick模拟操作系统来构建一个多任务的调度框架。从底层原理看它做了三件事产生固定时间中断配置SysTick定时器让它每间隔固定时间例如1ms产生一次中断。充当“时间基准”在中断服务函数中对一个全局变量如Tick进行累加这个变量就是整个模拟系统的“逻辑时间”所有延时、超时都基于它。实现“任务切换”在中断中或者在主循环中检测时间到然后保存当前任务的状态寄存器恢复下一个任务的寄存器让CPU去执行另一个任务。这模拟了操作系统的上下文切换。所以我们的项目代码呢主要写在task.c当中。原本我们的task.c当中也有一部分内容有两个task其中task1是以1秒的速度将LED1进行翻转task2是500毫秒的频率将LED2进行一个翻转。为了方便区分我们将名字进行一个改动将task1-led1_tasktask2-led2_task。这样命名就很清晰一下就可以看出哪个task是干嘛用的。包括最上方变量的定义和代码的其他地方也要同步改过来。编译一下出现task.h后其中的也不要忘了改。之后在main函数中测试一下可以看到LED12按给定频率闪烁的现象。用上我们上面说的状态机的知识那么首先要进行状态变量的定义。一般使用枚举enum来将每个变量依次枚举出来。 在我们的项目中 有两个状态分别是允许通行和不允许。之后通过systick的回调函数来检测状态。在我们写继续的代码的时候最好是有一个流程图把整个思路理清楚。通过注释一步步的去编写代码。要调用sprintf要包含#include stdio.h这个头文件。sprintf的标准用法就是把格式化后的字符串写进一个字符数组里不打印到屏幕。嵌入式里 LCD 不能直接printf所以先sprintf到缓冲区再拿message去显示。必须保证数组够大sprintf不会检查message够不够长写超了会踩内存。这句最多写出PASS...05/05 \012个字符 结束符 \0 13 字节char message[16]16个字节装得下。规范写法更推荐sprintf(message, sizeof(message), PASS...%02d/05, passenger);snprintf会限制最多写sizeof(message)个字节避免溢出。教学/小项目里sprintf很常见知道这个风险即可。sprintf(message, PASS...%02d/05, passenger);参数作用message结果写到这里PASS...%02d/05模板固定文字 占位符passenger填进%02d的那个数%02d是格式说明符从右往左读最清楚部分含义%这里要替换成变量d按有符号十进制整数打印对应int/uint32_t这类整数2至少占 2 位0位数不够时左边补 0所以passenger%d%2d%02d333前面空格0312121212这里用%02d是为了和后面的/05对齐。常见占位符顺带记%d // 整数 sprintf(buf, %d, 3); → 3%02d // 两位、不足补0 sprintf(buf, %02d, 3); → 03%s // 字符串 sprintf(buf, hi %s, stm); → hi stm%f // 浮点 sprintf(buf, %.1f, 3.14); → 3.1%x // 十六进制 sprintf(buf, %02X, 10); → 0A

关于恒美微站

恒美微站专注于为个体商户、工作室提供极简自助建站服务,让每个人都能轻松拥有专业网站。

快速链接

  • 关于我们
  • 建站服务
  • 主题模板
  • 案例展示
  • 资讯中心

服务项目

  • 可视化建站
  • 拖拽编辑
  • 主题定制
  • SEO 优化
  • 网站托管

联系方式

  • 📍 地址:北京市朝阳区建国路 88 号
  • 📞 电话:400-888-8888
  • ✉️ 邮箱:info@hmyw.cn
  • 🕐 时间:周一至周日 9:00-18:00

© 2024 恒美微站 hmyw.cn 版权所有 | 京 ICP 备 12345678 号