Arduino与Proteus仿真实例-密码门禁控制仿真
密码门禁控制仿真
1、应用介绍
本文将演示如何实现密码门禁控制逻辑仿真。
此次仿真主要涉及如下内容:
此次仿真将使用继电器和直流电机作为电子门禁元件仿真器件。
在前面的文章中,对密码输入、更新、验证、储存,做了详细的仿真,请参考:
在前面的文章中,对继电器控制仿真,请参考:
2、仿真电路原理图
此次仿真电路原理图如下:

仿真电路分如下模块:
- LCD驱动电路:按四线SPI驱动连接
- 键盘驱动电路:由PCF8574驱动4x4矩阵键盘
- 继电+直流电机驱动电路
3、仿真代码实现
在本次实例中,主要使用到如下开源库:
1)导入依赖头文件
1 2 3 4 5 6
| #include <LiquidCrystal.h> #include <Keypad\_I2C.h> #include <Keypad.h> #include <Wire.h> #include <EEPROM.h>
|
2)创建LCD1602对象和定义继电器引脚
1 2 3 4
| // LCD1602 LiquidCrystal lcd(12, 11,5, 4, 3, 2);// RS、RW,D0~D7 #define LOCK\_RELAY\_PIN 7
|
3)定义矩阵键盘对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| #define KEYPAD\_I2CADDR 0x20 // I2C键盘 const byte ROWS = 4; // 4行 const byte COLS = 4; // 4列 char keys[ROWS][COLS] = { {'1','2','3','A'}, {'4','5','6','B'}, {'7','8','9','C'}, {'\*','0','#','D'} }; // PCF8574IO映射 byte rowPins[ROWS] = {0, 1, 2, 3}; // 连接矩阵键盘行引脚 byte colPins[COLS] = {4, 5, 6, 7}; // 连接矩阵键盘列引脚
TwoWire \*jwire = &Wire; // I2C总线 Keypad_I2C kpd( makeKeymap(keys), rowPins, colPins, ROWS, COLS, KEYPAD_I2CADDR, PCF8574, jwire );
|
4)定义密码储存变量
1 2 3 4 5 6 7 8 9 10 11 12
| #define PASSWORD\_ADDR 0x10 // 密码储存地址 #define PASSWORD\_INIT\_ADDR 0x01 // 密码状态地址 #define PASSWORD\_LEN 0x06 // 密码长度 #define PASSWORD\_UPDATE "\*#01#\*" // 密码更新 #define PASSWORD\_CMD\_COMPARE 0x01 // 密码验证 #define PASSWORD\_CMD\_UPDATE 0x02 // 密码更新
const char inited_password[PASSWORD_LEN] = {'1','2','3','4','5','6'}; // 默认密码 char saved_password[PASSWORD_LEN] = {0}; // EEPROM储存的密码 char current_password[PASSWORD_LEN] = {0}; // 当前输入密码 char password_cmd = PASSWORD_CMD_COMPARE; // 密码操作命令
|
5)密码初始化
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| // 初始化密码 void init\_password(){ int isInited = 0; isInited = EEPROM.read(PASSWORD_INIT_ADDR); if(isInited != 1){ // 密码未初始化 int addr = PASSWORD_ADDR; for(unsigned char i = 0;i < PASSWORD_LEN;i++){ EEPROM.write(addr,inited_password[i]); // 写入默认密码 addr++; } EEPROM.write(PASSWORD_INIT_ADDR,1); // 更新密码标志 Serial.println("initialized password"); } }
|
6)密码读取
1 2 3 4 5 6 7 8 9
| // 读取密码 void read\_password(){ int addr = PASSWORD_ADDR; for(unsigned char i = 0;i < PASSWORD_LEN;i++){ saved_password[i] = (char)EEPROM.read(addr); addr++; } }
|
7)密码比较
1 2 3 4 5 6 7 8 9
| // 读取密码 void read\_password(){ int addr = PASSWORD_ADDR; for(unsigned char i = 0;i < PASSWORD_LEN;i++){ saved_password[i] = (char)EEPROM.read(addr); addr++; } }
|
8)密码更新
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| // 更新密码 void update\_password(char\* pass){ int addr = PASSWORD_ADDR; for(unsigned char i = 0;i < PASSWORD_LEN;i++){ EEPROM.write(addr,inited_password[i]); addr++; } Serial.println("password updated"); }
bool is\_update\_password(char\* pass){ return(pass[0] == '\*' && pass[1] == '#' && pass[2] == '0' && pass[3] == '1' && pass[4] == '#' && pass[5] == '\*'); }
|
9)门禁控制
1 2 3 4 5 6 7 8 9 10 11 12
| // 开锁 void unlock\_door(){ digitalWrite(LOCK_RELAY_PIN,LOW); delay(3000); digitalWrite(LOCK_RELAY_PIN,HIGH); } // 关锁 void lock\_door(){ digitalWrite(LOCK_RELAY_PIN,HIGH); }
|
10)设备初始化
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| void setup() { Serial.begin(9600); init\_password(); read\_password(); pinMode(LOCK_RELAY_PIN,OUTPUT); digitalWrite(LOCK_RELAY_PIN,HIGH); Serial.print("inited password:"); for(unsigned char i = 0;i < PASSWORD_LEN;i++){ Serial.print((char)saved_password[i]); } Serial.println(); lcd.begin(16, 2); // 设置LCD的行和列 // 键盘初始化 jwire->begin(); kpd.begin(); }
|
11)门锁控制逻辑实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61
| unsigned char index = 0; // 当前密码输入索引 bool is_updating_password = false; // 当前页面是否正在更新密码 void loop() { char key = kpd.getKey(); if(key){ if(password_cmd == PASSWORD_CMD_COMPARE){ current_password[index] = key; if(index == 0){ lcd.clear(); } lcd.setCursor(index, 0); lcd.print('\*'); }else{ if(index == 0){ is_updating_password = true; } saved_password[index] = key; current_password[index] = key; lcd.setCursor(index, 2); lcd.print((char)key); } Serial.print("index:"); Serial.print(index); Serial.print(",key="); Serial.println(key); index++; } if(index == 6){ lcd.clear(); lcd.setCursor(0,0); if(is\_update\_password(current_password)){ password_cmd = PASSWORD_CMD_UPDATE; } if(password_cmd == PASSWORD_CMD_UPDATE){ if(!is_updating_password){ lcd.clear(); lcd.setCursor(0,0); lcd.print("Update Password:"); }else{ is\_update\_password(current_password); lcd.clear(); lcd.setCursor(0,0); lcd.print("Password Updated"); password_cmd = PASSWORD_CMD_COMPARE; is_updating_password = false; } }else{ password_cmd = PASSWORD_CMD_COMPARE; if(compare\_password(current_password)){ lcd.print("Lock opened"); unlock\_door(); }else{ lcd.print("Password Failed"); lock\_door(); } } index = 0; } }
|
仿真结果:

文章来源: https://iotsmart.blog.csdn.net/article/details/127918456
如果觉得我的文章对您有用,请随意打赏。您的支持将鼓励我继续创作!