【STM32项目开源】STM32单片机物联网门禁控制系统

目录

一、设计背景和意义

1.1设计背景:

1.2设计意义:

二、实物展示

三、硬件功能介绍

[2.1 硬件清单:](#2.1 硬件清单:)

[2.2 功能介绍:](#2.2 功能介绍:)

四、软件设计流程图

五、硬件PCB展示

六、软件主函序展示

七、单片机实物资料

[资料获取 查看主页介绍:兆龙电子单片机设计](#资料获取 查看主页介绍:兆龙电子单片机设计)


一、设计背景和意义

1.1设计背景:

在商业办公园区、住宅小区、工业园区及智慧楼宇的出入管理场景中,权限精准管控、安全预警与高效运维是核心需求。传统门禁系统存在明显局限:一方面,高端智能门禁设备(如品牌定制化安防门禁平台、多模态生物识别门禁系统)功能虽全但成本高昂,安装调试复杂,依赖专业技术人员操作与特定品牌售后支持,难以普及到中小型企业、老旧小区及基层办公场景,且设备兼容性差,更换或升级成本高,无法灵活满足不同人群(如员工、访客、运维人员)的权限管理需求;另一方面,普通简易门禁装置(如机械锁、单一 IC 卡门禁、密码锁)虽操作简单,但功能单一,仅能通过人工登记或固定凭证验证通行,缺乏身份精准识别、异常行为监测、远程授权及实时报警等功能,无法满足现代化安防场景下对出入安全、精准管理的需求。

现有关禁控制方案还存在功能割裂与集成度低的问题:部分高端门禁设备虽具备多模式认证与安全监测功能,但依赖复杂的软硬件架构与专业维护,后期使用成本高,难以覆盖预算有限的中小型场所或基层管理场景;而低成本门禁装置又在功能完整性与智能化上存在欠缺,无法实现出入数据与管理平台、移动端 APP 的联动,导致身份冒用、非法闯入、权限管理混乱等安全风险,无法为出入记录追溯及管理人员工作效率优化提供数据支撑。基于此,本设计以 STM32 单片机为核心,融合高精度识别与监测模块(如人脸识别模块、RFID 射频传感器、门磁状态传感器、防拆检测传感器)、LCD 显示模块、数据存储模块及电磁锁控制与报警模块,构建低成本、高集成度的物联网门禁控制系统,以解决传统门禁设备功能单一、智能化程度低、安全风险高及管理效率低的问题。

1.2设计意义:

本设计通过整合 STM32 单片机的高效数据处理能力与多模块协同工作机制,在出入安全管理领域具有多重实用价值,具体体现在以下三方面:

从使用体验与管理效率角度,该系统突破了传统门禁设备的局限:一是实现了多方式认证与多功能联动(如支持人脸、IC 卡、密码、远程授权认证,联动电磁锁控制模块、异常报警模块),无需管理人员现场值守或人工登记,减少人工操作繁琐性与失误率;二是配备 OLED 实时显示模块,直观呈现当前认证状态、出入时间、权限等级及运行模式,同时支持数据自动存储(可通过蓝牙或 WiFi 传输至管理平台 / 移动端 APP),方便管理人员长期追溯出入记录,为安防方案优化及日常管理流程规范提供完整数据支撑;三是新增异常预警与自动调控功能,当监测到某项参数超出安全范围(如非法闯入、设备被拆、门未关严),系统自动触发声光报警(同时向管理终端发送预警信息),并联动电磁锁锁闭、启动视频抓拍或切断非法操作通路,无需人工干预即可及时处理异常,大幅提升了门禁管理的便捷性与安全性。

从技术实践与成本控制角度,本设计以 STM32 单片机为核心,充分利用其低功耗、高性价比的优势,搭配低成本的高精度识别与监测模块及通用外围模块,在保证识别精度(人脸识别准确率可控制在 99.5% 以上,权限验证响应时间可控制在 0.5 秒以内)的前提下,有效降低了系统整体成本,相比同功能的高端智能门禁设备成本降低 40%-60%,更易普及到中小型企业、老旧小区、社区服务中心及基层办公等场景。同时,系统支持模块化扩展(如后续可新增语音交互模块、访客预约授权功能、电梯联动控制功能),为后续功能升级预留了空间,具备良好的灵活性与可扩展性。

从应用场景与行业价值角度,该系统可广泛适配多类出入管理场景:在商业办公园区中,可作为人员出入的智能管理终端,实时管控权限、监测安全状态,减轻管理人员值守压力;在高校电子信息、自动化相关专业教学中,可作为单片机与物联网设备结合的实践案例,帮助学生理解嵌入式系统在安防场景中的应用原理;在老旧小区或中小型商铺场景中,可为用户提供低成本的安全出入方案,减少安全事故风险与管理人员工作负担。此外,本设计探索了 STM32 单片机在低成本物联网门禁设备领域的应用方案,推动传统门禁装置从 "人工登记、固定认证" 向 "多方式识别、智能控制、自动预警" 升级,为低成本智能化门禁设备的开发提供了可参考的集成思路,具有较好的实践应用与行业推广价值。c

**二、**实物展示

下方为实物演示视频连接

点击下方链接跳转演示视频https://www.bilibili.com/video/BV1XcayzGELQ/?spm_id_from=333.1387.upload.video_card.click&vd_source=2a672ca4e8794dca68cbe6d047b42ca5

下方为实物展示图片

三、硬件功能介绍

2.1 硬件清单:

  • STM32F103C8T6
  • OLED液晶显示
  • 温湿度传感器
  • MQ-2烟雾传感器
  • 矩阵键盘
  • 声光报警电路
  • DS1302时钟模块
  • 舵机
  • RFID门禁模块
  • 指纹模块

2.2 功能介绍:

(1)人机交互:在OLED显示时间信息,环境温湿度,烟雾浓度值,这两个传感器作用于发现室内环境异常自动打开门锁
(2)解锁功能:密码介绍,指纹介绍,IC卡解锁,APP解锁四种解锁方式
(3)具备物联网功能:连接WiFi实现远程控制查看实现远程解锁
(4)阈值报警:设定对应的报警参数,环境参数超出设定判定为室内异常,自动开启门锁
(5)密码管理:可实现对指纹密码IC卡的信息录入

四、软件设计流程图

五、硬件PCB展示

六、软件主函序展示

复制代码
//头文件
#include "main.h"//所有头文件都放在里面方便调用管理


//函数声明
void Key_Init(void);//按键函数声明
void display(void);
void DJ(unsigned int p_a );
u8 b_1s,eer_f,smart_config,openflag;
u16 sys_time,sys_time2;//系统计数
u8 mod=0;//显示模式
short menu1,set_f; //一级目录编号 设置数据位标记
u8 run_b;//运行标志,短信发送标志

u16 open_time;//开门时间
u16 input_f;//输入计数
u16 pass[4];
u32 begin_code[EEPROM_volume] = {66,30,90,1000,10, //初始化数据
										 0,0,0,0,0,
										0,0,0,0,0,
										0,0,0,0,0,0};
u32 set_code[EEPROM_volume];//设置参数		
char str[32];//显示缓存										
u16 station;							
u16 key_num;//按键值,
u16 smoke;		


////////////////////////关于rc522的使用寄存器定义  ////////////////////////////
u16 User_ID,integral;//用户编号,用户当前积分 
u8 CT[2];                                           //卡类型
u8 SN[4];                                           //卡号
u32 RFID,RFID_Past;
u8 status;                                          
u8 t;


void DJ(unsigned int p_a )
	{               //舵机函数(需配合0.1ms延迟函数)
	  dj_out = 1;  
}		

void open(void)
{
	DJ(24);
	DJ(24);
	DJ(24);
	open_time = set_code[4];
}

////////////////////////////////查卡////////////////////////////
//查内部有没有这个数据
u16 check_dat(u32 C_ID)
{
	u16 i;
	for(i=0;i<10;i++)
	{
		if(C_ID==set_code[i+20])
		{
			break; 
		}
	}
	return i;
}


//查内部有没有空余
u16 check_ID(void)
{
	u16 i;
	for(i=0;i<10;i++)
	{
		if(0==set_code[20+i])
		{
			break; 
		}
	}
	return i;
}

//////////////////////////////////////////查密码///////////////////////

//查内部有没有这个数据
u16 PASS_dat(u32 C_ID)
{
	u16 i;
	for(i=0;i<10;i++)
	{
		if(C_ID==set_code[i+10])
		{
			break; 
		}
	}
	return i;
}

//查内部有没有空余
u16 PASS_ID(void)
{
	u16 i;
	for(i=0;i<10;i++)
	{
		if(0==set_code[10+i])
		{
			break; 
		}
	}
	return i;
}	
///////////////////////////////////////////////////////////////////////////////////显示函数/////////////////////////										
void display(void)
{
	char i;
	switch(mod)
	{
		case 0://待机界面

						OLED_ShowCC(0,0,"==智能门禁系统==");
						sprintf(str," %02d-%02d %02d:%02d:%02d ",mon,day,hour,min,sec);//显示当前时间
						OLED_ShowCC(0,2,(unsigned char *)str);
						sprintf(str,"RH:%02d%% 温度:%02d℃",DHT11_RH,DHT11_temp);//显示当前时间
						OLED_ShowCC(0,4,(unsigned char *)str);		
						sprintf(str,"烟雾浓度:%03dppm ",smoke);//显示当前时间
						OLED_ShowCC(0,6,(unsigned char *)str);				
			break;
		case 1://密码输入界面

						OLED_ShowCC(0,0,"===请输入密码===");

						OLED_ShowCC(0,2,"================");
						sprintf(str,"   %d  %d  %d  %d   ",pass[0],pass[1],pass[2],pass[3]);//显示当前时间
						if(input_f==0){ str[3] = str[6] = str[9] = str[12] = '_';}
						else if(input_f==1){ str[6] = str[9] = str[12] = '_';}
						else if(input_f==2){ str[3] = '*';str[9] = str[12] = '_';}
						else if(input_f==3){ str[3] = str[6] = '*';str[12] = '_';}
						OLED_ShowCC_S(0,4,(unsigned char *)str,4+(input_f-1)*3,1);		
						OLED_ShowCC(0,6,"================");


			break;


		//管理员设置界面
			case 2:
							OLED_ShowCC(0,6,"4. 用户密码管理 ");//显示标题
							OLED_ShowCC(0,0,"1. 系统参数设置 ");//显示标题
							OLED_ShowCC(0,2,"2. 用户指纹管理 ");//显示标题
							OLED_ShowCC(0,4,"3. 用户IC卡管理 ");//显示标题							
			break;

		//系统参数设置
			case 3:																
							sprintf(str,"温度阈值:%02d℃   ",set_code[1]);
							if(set_f==1) i = 4;	else i = 0;
							str[16] = 0;
							OLED_ShowCC_S(0,0,(unsigned char *)str,10,i);
							sprintf(str,"湿度阈值:%02d%%    ",set_code[2]);
							if(set_f==2) i = 3;		else i = 0;
							str[16] = 0;
							OLED_ShowCC_S(0,2,(unsigned char *)str,10,i);
							sprintf(str,"烟雾阈值:%03dppm ",set_code[3]);
							if(set_f==3) i = 6;		else i = 0;
							str[16] = 0;
							OLED_ShowCC_S(0,4,(unsigned char *)str,10,i);

							sprintf(str,"开门时间:%03d秒  ",set_code[4]);
							if(set_f==4) i = 5;		else i = 0;
							str[16] = 0;
							OLED_ShowCC_S(0,6,(unsigned char *)str,10,i);
			break;
		//管理员设置界面
			case 4:
							OLED_ShowCC(0,0,"==用户指纹管理==");//显示标题
							OLED_ShowCC(0,2,"1. 增加指纹     ");//显示标题
							OLED_ShowCC(0,4,"2. 删除指纹库   ");//显示标题
							OLED_ShowCC(0,6,"3. 退出         ");//显示标题	

			break;		

		//用户管理设置界面
			case 5:
							OLED_ShowCC(0,0,"==用户IC卡管理==");//显示标题
							OLED_ShowCC(0,2,"1. 增加IC卡     ");//显示标题
							OLED_ShowCC(0,4,"2. 删除IC卡库   ");//显示标题
							OLED_ShowCC(0,6,"3. 退出         ");//显示标题	

			break;
			case 6:
							OLED_ShowCC(0,0,"==用户密码管理==");//显示标题
							OLED_ShowCC(0,2,"1. 增加密码     ");//显示标题
							OLED_ShowCC(0,4,"2. 删除密码库   ");//显示标题
							OLED_ShowCC(0,6,"3. 退出         ");//显示标题	

			break;

			case 7://系统时间设置界面
						OLED_ShowCC(0,0,"==系统时间设置==");
						sprintf(str,"   20%02d-%02d-%02d   ",year,mon,day);//显示设置年月日
						if(set_f==1) i=4;  else {
						if((set_f>=2)&(set_f<=3)) i=2;  else i = 0;}
						OLED_ShowStr_S(0,2,(unsigned char *)str,8-i+(set_f-1)*3,i,2);//显示时分秒
						sprintf(str,"    %02d:%02d:%02d    ",hour,min,sec);
						if((set_f>=4)&(set_f<=6)) i=2;  else i = 0;
						OLED_ShowStr_S(0,4,(unsigned char *)str,5+(set_f-4)*3,i,2);
						OLED_ShowStr(0,6,"OK  +  -  Return",2);	
			break;
			case 11:
						OLED_ShowCC(0,0,"==请输入新密码==");
						OLED_ShowCC(0,2,"================");
						sprintf(str,"   %d  %d  %d  %d   ",pass[0],pass[1],pass[2],pass[3]);//显示当前时间
						if(input_f==0){ str[3] = str[6] = str[9] = str[12] = '_';}
						else if(input_f==1){ str[6] = str[9] = str[12] = '_';}
						else if(input_f==2){ str[12]= str[9] = '_';}
						else if(input_f==3){ str[12] = '_';}
						if(input_f==0) i= 4;
						else i= 4+(input_f-1)*3;
						OLED_ShowCC_S(0,4,(unsigned char *)str,i,1);		
						OLED_ShowCC(0,6,"================");

			break;

	}

	if(openflag==1)
	{
		openflag = 0;
		OLED_CLS(); 
		OLED_ShowCC(0,2,"==远程解锁成功==");
		OLED_ShowCC(0,4,"====欢迎回家====");
		DelayMs(3000);
	}

}


void run(void)//逻辑程序
{
	if((DHT11_RH>set_code[2])||(DHT11_temp>set_code[1])||(smoke>set_code[3]))//判断阈值是不是超标
	{
			eer_f = 4;//蜂鸣器叫2声
	}

	if(smoke>set_code[3])//烟雾超过报警
	{
		DJ(24);
		DJ(24);//开门
		DJ(24);
		open_time = 60;//60秒内没有重复触发就吧门关上

	}
}




//=============================================================================
//文件名称:main
//功能概要:主函数
//参数说明:无
//函数返回:int
//=============================================================================
//	RCC_ClocksTypeDef get_rcc_clock;//定义一个结构体检查系统时钟



int main(void)
{	
	int i;
	  DelayInit();//系统延时函数初始化
		DelayMs(1000);
		USART3_Init(9600);//串口以初始化 波特率设置为9600
		as608_init();
	  Key_Init();//按键引脚初始化
		ADC1_DMA_Config();
		TIM2_Int_Init(10000,3600);//输出话定时器  这边用到定时器2作为0.5秒钟中断发生源
		TIM_Cmd(TIM2, ENABLE);//开启定时器2	
		DS1302_init(0x23,0x02,0x18,0x14,0x30,0x30);//时钟模块初始化
		OLED_Init();//OLED屏幕初始化
	  OLED_CLS();//清屏
		DHT11_Init();
		mod = 0;//开机显示开机界面
		InitRc522();//初始化RC522
			DJ(14);//初始状态
			DJ(14);//初始状态
			DJ(14);//初始状态
		Readflash(set_code,0,EEPROM_volume);  //读取内部保存数据
	  DelayMs(10);

		if(set_code[EEPROM_volume-1] != 66)//对比内部数据是不是以及被重新覆盖  是的话载入初始化数据
		{
			OLED_ShowStr(0,0,"===NO  FLIASH===",2);
			begin_code[EEPROM_volume-1] = 66;
			Writeflash(0,begin_code,0,EEPROM_volume);//写入初始化数据
			DelayMs(500);
			Readflash(set_code,0,EEPROM_volume);//读取写写入后的数据
			sprintf(str,"Init System [%2d]",set_code[EEPROM_volume-1]);//显示验证数据
			OLED_ShowStr(0,4,(unsigned char *)str,2);
			DelayMs(100);
			OLED_CLS();//清屏
		}
		KEY34_O_1 = 0;	//全开
		KEY34_O_2 = 0;
		KEY34_O_3 = 0;
		KEY34_O_4 = 0;
		smart_config = 1;
		OLED_ShowStr(0,0,"===Device Starting===",1);
		OLED_ShowStr(0,1,"Wait for link Interne",1);//等待网络连接
		OLED_ShowStr(0,2,"=====================",1);		
		OLED_ShowStr(0,3,"KE2   Skip networking",1);//跳过配网
		OLED_ShowStr(0,4,"KE3  WIFI_SOFTAP_MODE",1);//热点配网模式
		OLED_ShowStr(0,5,"KE4 WIFI_AIRLINK_MODE",1);//一键配网模式		

		while(smart_config)//配网标志
		{
			if(KEY2 == 0) smart_config = 0;
			if(KEY3 == 0) 
			{
				OLED_CLS();//清屏
				OLED_ShowStr(0,0,"===Device Starting===",1);
				OLED_ShowStr(0,1,"==WIFI smart_config==",1);
				OLED_ShowStr(0,2,"WIFI_SOFTAP_MODE",1);
				OLED_ShowStr(0,3,"SSID:XPG-GAgne-   ",1);//热点名称
				OLED_ShowStr(0,4,"password:123456789",1);//连接的热点WiFi密码
				OLED_ShowStr(0,5,"Operation on app",1);
			}
			if(KEY4 == 0) 
			{
				OLED_CLS();//清屏
				OLED_ShowStr(0,0,"===Device Starting===",1);
				OLED_ShowStr(0,1,"==WIFI smart_config==",1);
				OLED_ShowStr(0,2,"WIFI_AIRLINK_MODE",1);
				OLED_ShowStr(0,3,"Distribution network",1);
				OLED_ShowStr(0,4," by broadcasting",1);
				OLED_ShowStr(0,5,"Operation on app",1);
			}

			OLED_ShowStr(i*8,6,">",1);
			i++;	
			if(i>=15){OLED_ShowStr(0,6,"                     ",1);i = 0;}
			DelayMs(500);
		}
		OLED_CLS();//清屏	
    while (1)
		{		    

			if(mod == 0)//待机模式下
			{
				DS1302_Readtime(); //获取当前日期/时间
				DHT11_Read_Data();
				smoke = ADCConvertedValue[0]/10;
				press_FR();

			}
			display();//显示程序
			if(mod!=3)run();
		}
}



//=============================================================================
//文件名称:Key_Init
//功能概要:GPIO初始化
//参数说明:无
//函数返回:无
//=============================================================================
void Key_Init(void)  //按键引脚定义
{
//将按键接口设置为上拉电阻输入因为我们使用低电平信号触发
	GPIO_InitTypeDef gpio_initstruct;

//	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);	
	//按键引脚定义

	RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO | RCC_APB2Periph_GPIOA , ENABLE);
  GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE);	
	gpio_initstruct.GPIO_Mode = GPIO_Mode_Out_PP;							
	gpio_initstruct.GPIO_Pin = GPIO_Pin_6;			
	gpio_initstruct.GPIO_Speed = GPIO_Speed_50MHz;							
	GPIO_Init(GPIOA, &gpio_initstruct);		

	RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO | RCC_APB2Periph_GPIOB , ENABLE);
  GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE);	
	gpio_initstruct.GPIO_Mode = GPIO_Mode_Out_PP;							
	gpio_initstruct.GPIO_Pin = GPIO_Pin_12;			
	gpio_initstruct.GPIO_Speed = GPIO_Speed_50MHz;							
	GPIO_Init(GPIOB, &gpio_initstruct);		
	beep = 1;
}

七、单片机实物资料

资料获取 查看主页介绍:兆龙电子单片机设计

相关推荐
ApacheSeaTunnel2 小时前
结项报告完整版 | Apache SeaTunnel支持metalake开发
大数据·开源·数据集成·seatunnel·数据同步
白鲸开源2 小时前
结项报告完整版:Apache SeaTunnel 支持 Flink 引擎 Schema Evolution 功能
大数据·flink·开源
云雾J视界3 小时前
C语言位运算深度应用:嵌入式硬件寄存器控制与低功耗优化实践
c语言·stm32·嵌入式硬件·低功耗·数据压缩·寄存器
塔能物联运维3 小时前
物联网运维中的自适应DNS解析优化与动态负载均衡技术
运维·物联网·负载均衡
芋头莎莎3 小时前
MCU单片机驱动WS2812,点亮RGB灯带各种效果
单片机·嵌入式硬件
软件供应链安全指南4 小时前
“基于‘多模态SCA+全周期协同’的中间件开源风险治理实践”荣获OSCAR开源+安全及风险治理案例
安全·中间件·开源
CoderJia程序员甲4 小时前
GitHub 热榜项目 - 日榜(2025-11-11)
ai·开源·大模型·github·ai教程
芋头莎莎5 小时前
STM32利用AES加密数据、解密数据
数据结构·stm32·算法
无垠的广袤5 小时前
【CPKCOR-RA8D1】Home Assistant 物联网 ADC 电压温度计
嵌入式硬件·物联网·智能家居·瑞萨