功能代码
led1.c、灯
#include "led.h"
#include "sys.h"
void led_init(void)
{
GPIO_InitTypeDef gpio_initstruct;
__HAL_RCC_GPIOB_CLK_ENABLE();
gpio_initstruct.Pin = GPIO_PIN_8 | GPIO_PIN_9;
gpio_initstruct.Mode = GPIO_MODE_OUTPUT_PP;
gpio_initstruct.Pull = GPIO_PULLUP;
gpio_initstruct.Speed = GPIO_SPEED_FREQ_HIGH;
HAL_GPIO_Init(GPIOB,&gpio_initstruct);
led1_off();
led2_off();
}
void led1_on(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_8,GPIO_PIN_RESET);
}
void led1_off(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_8,GPIO_PIN_SET);
}
void led1_toggle(void)
{
HAL_GPIO_TogglePin(GPIO_PIN_8);
}
void led2_on(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_9,GPIO_PIN_RESET);
}
void led2_off(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_9,GPIO_PIN_SET);
}
void led2_Toggle(void)
{
HAL_GPIO_TogglePin(GPIO_PIN_9);
}
task.c、线程
写代码之前要么写状态机,要么写流程图
//如果处于允许通行的状态
//led1以1秒的频率闪烁
//led2不闪烁
//蜂鸣器不响
//开门
#include "tasks.h"
#include "led.h"
#include "beep.h"
#include "exti.h"
#include "lcd1602.h"
#include "gate.h"
#include "stdio.h"
enum //状态一般用枚举的方法 两种(允许和不允许) 工作中通常使用枚举,将工作状态定义出来
{
PASS_STATE,
WAIT_STATE
};
//时间计数
uint32_t led1_task1_cnt = 0;
uint32_t led2_task2_cnt = 0;
uint32_t wait_cnt = 0;
//乘客
uint32_t passager = 0;
// 灯线程
uint8_t led1_task1_flag = 0;
uint8_t led2_task2_flag = 0;
uint8_t state = PASS_STATE;//刚开始显示一个默认通行的状态
char message[16] = {0};//构造一个字符串,定义一个,----字符数组来实现
void systick_isr(void)
{
//如果处于允许通行的状态
if(state == PASS_STATE)
{
//led以1秒的频率闪烁
if(led1_task1_cnt < 1000)
led1_task1_cnt++;
else
{
led1_task1_flag = 1;
led1_task1_cnt = 0;
}
//led2不闪烁
led2_off();
//蜂鸣器不响
beep_off();
//开门
}
else if(state == WAIT_STATE)
{
//led以1秒的频率闪烁
if(led1_task2_cnt < 200)
led1_task2_cnt++;
else
{
led1_task1_flag = 1;
led1_task1_cnt = 0;
}
//led1不闪烁
led1_off();
//蜂鸣器响
beep1_off();
//关门
gate1_on();
if(wait_cnt < 3000)
wait_cnt++;
//进入允许通行的状态
else
{
wait_cnt = 0;
//进入允许通行的状态
state = PASS_STATE;.
//lcd显示状态
lcd1602_show_line(1,1,“PASS...”);
}
}
}
}
灯1线程
void led1_task1(void)
{
if(led1_task1_flag == 0)//
return ;
led1_task1_flag = 0;
led1_toggle();
}
灯2线程
void led2_task2(void)
{
if(led1_task2_flag == 0)//如果等于0表示计时还未结束,不执行后面的代码,反之执行
return ;
led1_task2_flag = 0;
led2_toggle();
}
//定义一个红外传感器的线程
void senser_task(void)
{
//检测到有人通过
//if(ia_flag_get() == TRUE && state == PASS_STATE)
//有人通过的同时也要处在通过状态才能允许继续计数,
{
passenger++;
sprintf(message, "PASS...%02d/05", passenger);//两位显示
lcd1602_show_line(1,1,message);//刷新显示
}
//如果通过的人数超过5个
if(passager >= 5)
{
//计数清零
passager = 0;
//进入不允许通行状态
state = WAIT_STATE;
//LCD显示状态
lcd1602_show_line(1,1,"WAIT...00/05");
}
}
exti.c 、外部事件中断
uint8_t ia_flag = FALSE; // 检测到震动标志位
void exti_init(void)
{
GPIO_InitTypeDef gpio_initstruct;
//打开时钟
__HAL_RCC_GPIOB_CLK_ENABLE(); // 使能GPIOA时钟
//调用GPIO初始化函数
gpio_initstruct.Pin = GPIO_PIN_4; // 震动传感器对应的引脚
gpio_initstruct.Mode = GPIO_MODE_IT_FALLING; // 下降沿触发
gpio_initstruct.Pull = GPIO_PULLUP; // 上拉
HAL_GPIO_Init(GPIOB, &gpio_initstruct);
HAL_NVIC_SetPriority(EXTI4_IRQn, 2, 0); // 设置EXTI0中断线的优先级
HAL_NVIC_EnableIRQ(EXTI4_IRQn); // 使能中断
}
void EXTI4_IRQHandler(void)
{
HAL_GPIO_EXTI_IRQHandler(GPIO_PIN_4);
}
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
delay_ms(20);
if (GPIO_Pin == GPIO_PIN_4)
{
if(HAL_GPIO_ReadPin(GPIOB, GPIO_PIN_4) == GPIO_PIN_RESET)
//led1_toggle();
ia_flag = TRUE;
}
}
uint8_t ia_flag_get(void)
{
uint8_t temp = ia_flag;
ia_flag = FALSE;
return temp;
}
void ia_flag_set(uint8_t value)
{
ia_flag = value;
}
gate.c、继电器控制门
#include "gate.h"
#include "sys.h"
void gate_init(void)
{
GPIO_InitTypeDef gpio_initstruct;
HAL_RCC_GPIOB_CLK_ENABLE();
gpio_initstruct.Pin = GPIO_PIN_6;
gpio_initstruct.Mode = GPIO_MODE_OUT_PP;
gpio_initstruct.Pull = GPIO_PULLUP;//低电平触发
gpio_initstruct.Speed = GPIO_SPEED_FREQ_HIGH;//速度随意不做要求
HAL_GPIO_Init(GPIOB,&gpio_initstruct);
gate1_off();
}
void gate1_on(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_6,GPIO_PIN_RESET);
}
void gate1_off(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_6,GPIO_PIN_SET);
}
void gate1_toggle(void)
{
HAL_GPIO_TogglePin(GPIO_PIN_6);
}
lcd1602.c、液晶屏显示
beep.c 蜂鸣器
#include "beep.h"
#include "sys.h"
void beep_init(void)
{
GPIO_InitTypeDef gpio_initstruct;
HAL_RCC_GPIOB_ENABLE();
gpio_initstruct.Pin = GPIO_PIN_5;
gpio_initstruct.Mode = GPIO_MODE_OUTPUT_PP;
gpio_initstruct.Pull = GPIO_PULLUP;//低电平触发
gpio_initstruct.Speed = GPIO_SPEED_FREG_HIGH;
beep_off();
}
void beep_on(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_5,GPIO_PIN_RESET);
}
void beep_off(void)
{
HAL_GPIO_WritePin(GPIOB,GPIO_PIN_5,GPIO_PIN_SET);
}
主函数
#include "tasks.h"
#include "gate.h"
#include "beep.h"
#include "exti.h"
#include "lcd1602.h"
int main(void)
{
HAL_Init(); /* 初始化HAL库 */
stm32_clock_init(RCC_PLL_MUL9); /* 设置时钟, 72Mhz */
led_init(); /* 初始化LED灯 */
gate_init(); /* 初始化继电器 */
beep_init(); /* 初始化蜂鸣器 */
exti_init(); /* 初始化红外传感器 */
lcd1602_init(); /* 初始化LCD1602 */
lcd1602_show_line(1, 1, "PASS...");
while(1)
{
led1_task();
led2_task();
sensor_task();
}
}
标签:led1,HAL,PIN,代码,排队,stm32,gpio,GPIO,void
From: https://blog.csdn.net/qq_65524926/article/details/142287953