一、项目简介
本项目是基于STM32微控制器的简单智能停车场收费系统。通过使用STM32的GPIO、串口通信、定时器等功能,实现了车辆入场、出场、计时计费等基本功能。
二、硬件连接
- 红外传感器连接
将红外传感器的输出引脚连接到STM32的一个GPIO引脚。当有车辆经过红外传感器时,传感器会输出高电平;否则输出低电平。
- LCD显示屏连接
将LCD显示屏的数据口和控制口分别连接到STM32的GPIO引脚。使用串行通信方式控制LCD显示内容。
- 按键连接
将两个按键分别连接到STM32的GPIO引脚。一个用于模拟车辆入场,一个用于模拟车辆出场。
- 电机控制连接
将电机的控制引脚连接到STM32的一个GPIO引脚。通过控制电机的正反转实现车辆入场和出场。
- 其他设备连接
根据具体需求,还可以连接其他设备,如蜂鸣器、红绿灯等。
三、软件设计
- 初始化设置
首先需要对STM32的相关外设进行初始化设置,包括GPIO、串口、定时器等。
- 红外传感器检测
使用GPIO来读取红外传感器的输出状态,如果检测到高电平,则说明有车辆经过传感器,进入车辆入场流程。
- 车辆入场
当检测到车辆入场时,先显示欢迎信息(如“Welcome!”),然后开始计时。使用定时器来实现计时功能,每隔一段时间(如1秒)更新计时时间并显示在LCD屏幕上。可以使用中断来触发定时器的更新。
- 车辆出场
当按下出场按键时,停止计时并显示计费信息(如“Total fee: xx”)。根据计时时间计算车辆的停车费用,并显示在LCD屏幕上。
- 电机控制
根据车辆入场和出场的状态来控制电机的正反转,实现车辆的进出。
- 其他功能
根据具体需求,可以添加其他功能,如蜂鸣器报警、红绿灯控制等。
四、代码示例
以下是一个简单的代码示例,实现了车辆入场、出场、计时计费等基本功能。请注意,该示例仅供参考,具体实现可能因硬件配置和需求差异而有所不同。
#include "stm32f10x.h"
// 定义GPIO和串口的引脚号
#define GPIO_INFRARED_PIN GPIO_Pin_0
#define GPIO_ENTER_PIN GPIO_Pin_1
#define GPIO_EXIT_PIN GPIO_Pin_2
#define USART_TX_PIN GPIO_Pin_9
#define USART_RX_PIN GPIO_Pin_10
// 定义LCD显示的行数和列数
#define LCD_ROWS 2
#define LCD_COLUMNS 16
// 定义计时器的频率、单位时间和最大计时值
#define TIMER_FREQ 1000 // 1ms
#define TIMER_UNIT_MS (1000 / TIMER_FREQ)
#define MAX_TIMER_VALUE 3600000 // 1小时
// 全局变量
volatile uint32_t timer_value = 0; // 计时器的当前值,单位ms
volatile uint8_t car_in_park = 0; // 车辆是否在停车场内
// 初始化函数
void GPIO_Configuration(void)
{
// 初始化GPIO
GPIO_InitTypeDef GPIO_InitStructure;
// 红外传感器
GPIO_InitStructure.GPIO_Pin = GPIO_INFRARED_PIN;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; // 输入,上拉
GPIO_Init(GPIOA, &GPIO_InitStructure);
// 入场按键
GPIO_InitStructure.GPIO_Pin = GPIO_ENTER_PIN;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; // 输入,上拉
GPIO_Init(GPIOA, &GPIO_InitStructure);
// 出场按键
GPIO_InitStructure.GPIO_Pin = GPIO_EXIT_PIN;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; // 输入,上拉
GPIO_Init(GPIOA, &GPIO_InitStructure);
}
void USART_Configuration(void)
{
// 初始化串口
USART_InitTypeDef USART_InitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
// 使能串口和GPIO的时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1 | RCC_APB2Periph_GPIOA, ENABLE);
// 连接串口引脚到GPIO端口
GPIO_InitStructure.GPIO_Pin = USART_TX_PIN;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; // 复用推挽输出
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = USART_RX_PIN;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; // 输入,浮空
GPIO_Init(GPIOA, &GPIO_InitStructure);
// 配置串口参数
USART_InitStructure.USART_BaudRate = 9600; // 波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b; // 数据位长度
USART_InitStructure.USART_StopBits = USART_StopBits_1; // 停止位
USART_InitStructure.USART_Parity = USART_Parity_No; // 校验位
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; // 硬件流控制
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; // 使能接收和发送
USART_Init(USART1, &USART_InitStructure);
// 使能串口
USART_Cmd(USART1, ENABLE);
}
void TIM_Configuration(void)
{
// 初始化定时器
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
NVIC_InitTypeDef NVIC_InitStructure;
// 使能定时器和中断的时钟
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
// 配置定时器参数
TIM_TimeBaseStructure.TIM_Period = TIMER_FREQ - 1; // 计时周期
TIM_TimeBaseStructure.TIM_Prescaler = SystemCoreClock / TIMER_FREQ - 1; // 预分频系数
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1; // 时钟分频
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; // 计数模式
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
// 使能定时器中断
TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);
// 配置NVIC中断优先级
NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
// 使能定时器
TIM_Cmd(TIM2, ENABLE);
}
void LCD_Configuration(void)
{
// 初始化LCD
// ...
}
// 定时器中断处理函数
void TIM2_IRQHandler(void)
{
if (TIM_GetITStatus(TIM2, TIM_IT_Update) != RESET) {
TIM_ClearITPendingBit(TIM2, TIM_IT_Update);
timer_value += TIMER_UNIT_MS;
}
}
// 显示字符串到LCD上
void LCD_ShowString(uint8_t row, uint8_t column, const char *str)
{
// ...
}
// 显示计时时间到LCD上
void LCD_ShowTime(uint32_t time)
{
uint8_t str[LCD_COLUMNS];
// ...
}
// 计算停车费用
uint32_t CalculateFee(uint32_t time)
{
// ...
}
// 主函数
int main(void)
{
// 初始化硬件配置
GPIO_Configuration();
USART_Configuration();
TIM_Configuration();
LCD_Configuration();
// 主循环
while (1) {
// 车辆入场流程
while (GPIO_ReadInputDataBit(GPIOA, GPIO_ENTER_PIN) == RESET) {
// 检测到车辆入场