实训2

您所在的位置:网站首页 电脑怎么指纹开锁 实训2

实训2

2023-12-13 07:10| 来源: 网络整理| 查看: 265

实训二:指纹开锁实验 一、实验目的

利用ESP32和FPM10A光学指纹模块,完成指纹匹配后启动舵机。指纹匹配功能需要先按一些键盘才能唤醒指纹模块,在10s内进行指纹匹配。 指纹匹配成功,启动舵机。

二、实验内容

1.按键唤醒指纹模块,然后匹配已录入的指纹 2.匹配指纹成功后启动舵机

三、实验设备

1.ESP32-WROOM-32D开发板 2.FPM10A光学指纹模块(红色:5V TX:绿色 RX:黄色 黑色:GND) 在这里插入图片描述 3.杜邦线 4.SG90舵机

四、实验步骤 1) 安装Adafruit指纹传感器库

1.Adafruit指纹传感器库下载:https://github.com/adafruit/Adafruit-Fingerprint-Sensor-Library/archive/master.zip 2.解压下载的.zip文件,你会看到一个Adafruit-Fingerprint-Sensor-Library-master文件夹 3.将Adafruit-Fingerprint-Sensor-Library-master文件夹重命名为Adafruit_Fingerprint_Sensor_Library文件夹 4.将文件夹移动到您的Arduino IDE安装库文件夹中的libraries文件夹 5.重新打开Arduino IDE

2) 连接设备

1.连接设备 将FPM10A指纹模块与ESP32连接,如下图所示: FPM10A的RX连接ESP32引脚17 FPM10A的TX连接ESP32引脚16

在这里插入图片描述

3) 测试代码 /*Author :王滨伟 * Time :2020.6.11 */ #include #include #include #include #include #include #include #include #include /* * ESP32 引脚17(TX)和16(RX)上的Serial2 * 指纹模块 连 接 ESP32 RX黄 --- 17 TX绿 --- 16 */ #define mySerial Serial2 #define SS_PIN 21 //定义RC522的SDA引脚的接线位置 #define RST_PIN 22 //定义RC522的RST引脚的接线位置 #define SERVO_PIN 15 //舵机的脚位 #define NormolClose 13 #define SERVICE_UUID "6E400001-B5A3-F393-E0A9-E50E24DCCA9E" #define CHARACTERISTIC_UUID_RX "6E400002-B5A3-F393-E0A9-E50E24DCCA9E" #define CHARACTERISTIC_UUID_TX "6E400003-B5A3-F393-E0A9-E50E24DCCA9E" #define openInterval 5000 #define fpInterval 10000 BLECharacteristic *pCharacteristic; bool deviceConnected = false; /* * 按键 */ const byte ROWS = 4; //four rows const byte COLS = 3; //three columns char keys[ROWS][COLS] = { {'1','2','3'}, {'4','5','6'}, {'7','8','9'}, {'*','0','#'} }; byte rowPins[ROWS] = {33, 27, 14, 12}; //connect to the row pinouts of the keypad byte colPins[COLS] = {4, 0, 2}; //connect to the column pinouts of the keypad /* * RFID标签结构体 */ struct RFIDTag { //Tag标签结构体 uint8_t uid[4]; char *name; }; MFRC522 rfid(SS_PIN, RST_PIN); //实例化类 struct RFIDTag tags[20] = { // 初始化结构资料,请自行修改RFID识别码 {{233, 232, 210, 126}, "Mini_Tag"}, {{0, 0, 0, 0}, "Mini_Tag1"}, {{1, 1, 1, 1}, "Mini_Tag2"}, }; byte totalTags = sizeof(tags) / sizeof(RFIDTag); //计算结构资料的数量 bool door_open_flag; //开门动作标志位 bool alarm_flag;//报警标志位 static bool lock_back_flag=false; //回锁标志位 Keypad keypad = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS ); byte ble_rx_buffer[20]; //接收蓝牙指令 byte verfi_code[6] = {0x31,0x32,0x33,0x34,0x35,0x36};//初始密码 byte init_pw[6] = {1,2,3,4,5,6};//初始按键密码 Servo myservo; Adafruit_Fingerprint finger = Adafruit_Fingerprint(&mySerial); short active_fp = -1; //激活指纹模块, -1休眠,1激活,2指纹模块正在激活时间 int pos=0; bool toggle; //开锁判断位 void locker(bool toggle) { //开锁 myservo.attach(SERVO_PIN); if (toggle) { myservo.write(90); // 开锁 } else { myservo.write(0); // 关锁 } delay(500); // 等马达转到定位 myservo.detach(); } class MyServerCallbacks: public BLEServerCallbacks { void onConnect(BLEServer* pServer) { deviceConnected = true; }; void onDisconnect(BLEServer* pServer) { deviceConnected = false; } }; /* 55aa1000313233343536 蓝牙发送开门指令,hex 16进制发送 * 55aa2000363534333231 蓝牙修改密码指令 * 55aa3000000000000000 蓝牙查询指令 * 55aa3100310000000000 蓝牙注册指纹 注册id号为01 * 55aa3200330000000000 蓝牙删除指纹 删除id号为03 */ class MyCallbacks: public BLECharacteristicCallbacks { void onWrite(BLECharacteristic *pCharacteristic) { std::string rxValue = pCharacteristic->getValue(); byte op; for (int i = 0; i op=ble_rx_buffer[2]; switch(op){ case 0x10:{ //蓝牙开门 if(memcmp(ble_rx_buffer+4,verfi_code,6) == 0){ //匹配成功 toggle = true; Serial.println("开门成功"); } else{ Serial.println("密码错误"); } break; } case 0x20:{ //设置密码 static byte temp_pw[6]; //临时密码 for(byte i=0;i //保证密码在0-9之间 temp_pw[i]=ble_rx_buffer[i+4]-0x30; } else{ //无效字符 break; } if(i==5){ //密码修改完成 Serial.println("密码修改完成"); memcpy(init_pw,temp_pw,6); } } break; } case 0x30:{ //查看指纹 break; } case 0x31:{//添加指纹 break; } case 0x32:{ //删除指纹 break; } } } } }; /*配置蓝牙 * 参数:BLEName 蓝牙名字 * 返回值: 无 */ void setupBLE(String BLEName){ const char *ble_name = BLEName.c_str(); BLEDevice::init(ble_name); BLEServer *pServer = BLEDevice::createServer(); //创建服务 pServer->setCallbacks(new MyServerCallbacks()); BLEService *pService = pServer->createService(SERVICE_UUID); pCharacteristic = pService->createCharacteristic(CHARACTERISTIC_UUID_TX,BLECharacteristic::PROPERTY_NOTIFY); pCharacteristic->addDescriptor(new BLE2902()); //添加描述 BLECharacteristic *pCharacteristic = pService->createCharacteristic(CHARACTERISTIC_UUID_RX,BLECharacteristic::PROPERTY_WRITE); pCharacteristic->setCallbacks(new MyCallbacks()); //receive message callback pService->start();// Start the service pServer->getAdvertising()->start();// Start advertising Serial.println("Waiting a client connection to notify..."); } /*按键输入的匹配函数 * 参数:key为一次按键输入的值 */ bool compare_pw(char key){ static byte pw[20]; static byte keys_len = 0; bool pw_flag = false; //匹配密码的标志位 if(key){ //FP_busy = false;//唤醒指纹模块,可以开始匹配 Serial.println(key); active_fp = 1; //Serial.println(active_fp); switch(key){ case '#':{ //确认键 if(keys_len == 6 && memcmp(pw,init_pw,6)==0){ //匹配成功,开锁 Serial.println("开门成功"); pw_flag = true; } else{ Serial.println("密码错误"); } keys_len=0; //清零 break; } case '*':{ //回退键 if(keys_len >0) keys_len--; break; } default:{ //默认数字键0-9 pw[keys_len++]=key-'0'; if(keys_len>19){ Serial.println("OverSize"); keys_len=0; } break; } } } return pw_flag; } void printDec(byte *buffer, byte bufferSize) { for (byte i = 0; i bool foundTag = false; //是否找到记录中的标签,初始是false if (rfid.PICC_IsNewCardPresent() && rfid.PICC_ReadCardSerial()) { //寻找新卡 byte *id = rfid.uid.uidByte; // 取得卡片的UID byte idSize = rfid.uid.size; // 取得UID的长度 Serial.print("十进制UID:"); printDec(rfid.uid.uidByte, rfid.uid.size); Serial.println(); for (byte i = 0; i // 比对阵列资料值 Serial.println(tags[i].name); //显示标签名字 foundTag = true; break; } if(i==card_num-1){ Serial.println("验证失败"); } } // 使放置在读卡区的IC卡进入休眠状态,不再重复读卡 rfid.PICC_HaltA(); // 停止读卡模块编码 rfid.PCD_StopCrypto1(); } return foundTag; } /*门磁中断函数 * 参数 open_flag:正常开门的标志位 */ void handleInterrupt() { delay(100); if (digitalRead(NormolClose)){// 电平高,门开 detachInterrupt(digitalPinToInterrupt(NormolClose)); //屏蔽中断脚位 door_open_flag = 1; if(!lock_back_flag){//门没在开锁时间,门磁变化,算撬门报警 alarm_flag = 1; } Serial.println("door open"); } } /*指纹模块配置函数 * configure_FP() */ void configure_FP(){ finger.begin(57600); if (finger.verifyPassword()) { Serial.println("Found fingerprint sensor!"); finger.getTemplateCount(); Serial.print("Sensor contains "); Serial.print(finger.templateCount); Serial.println(" templates"); Serial.println("Waiting for valid finger..."); } else { delay(1000); Serial.println("Did not find fingerprint sensor :"); } } /* 匹配指纹函数 * 传入:searchFinger,表示匹配指纹与否 * returns -1 if failed, otherwise returns ID */ int getFingerprintIDez() { uint8_t p = finger.getImage(); if (p != FINGERPRINT_OK) return -1; p = finger.image2Tz(); if (p != FINGERPRINT_OK) return -1; p = finger.fingerFastSearch(); if (p != FINGERPRINT_OK) return -1; // Found a match! //searchFinger = 1; //idSearch = finger.fingerID; Serial.print("Found ID #"); Serial.print(finger.fingerID); Serial.print(" with confidence of "); Serial.println(finger.confidence); //active_fp = -1; //休眠 return finger.fingerID; } void setup() { Serial.begin(115200); setupBLE("ESP32 Device");//设置蓝牙名称 myservo.attach(SERVO_PIN); //引脚12为PWM脚 SPI.begin(); // 初始化SPI总线 rfid.PCD_Init(); // 初始化 MFRC522 configure_FP();//配置指纹模块 pinMode(NormolClose, INPUT_PULLUP); attachInterrupt(digitalPinToInterrupt(NormolClose), handleInterrupt, RISING); } void loop() { static unsigned long toggle_time = millis(); static unsigned long fp_time = millis(); //Serial.print("Active_fp="); //Serial.println(active_fp); short idSearch = -1; //匹配的指纹id if (!digitalRead(NormolClose)){ //电平低,门关 attachInterrupt(digitalPinToInterrupt(NormolClose), handleInterrupt, RISING); // 设置中断脚位,检测下降沿电压 door_open_flag = 0; } if(active_fp==2) //指纹模块空闲时进行指纹匹配 && 指纹模块正在激活期间 idSearch=getFingerprintIDez(); //指纹匹配 if(compare_pw(keypad.getKey()) || Match_Card(totalTags) || idSearch!=-1){ //密码正确 or 刷卡成功 or 指纹开门 //Serial.println("开门"); //Serial.println(idSearch); toggle = true; alarm_flag = false; //解除报警 } if(toggle){ //开门 locker(toggle); //开锁 toggle = false; lock_back_flag = true; toggle_time = millis(); } if(millis() - toggle_time > openInterval && lock_back_flag){ //回锁时间5s lock_back_flag = false; locker(toggle);//回锁 } if(active_fp == 1){ //激活指纹模块 fp_time = millis(); active_fp=2; } if(active_fp==2 && millis() - fp_time > fpInterval){ //指纹激活时间5s active_fp = -1; //休眠 } //报警信息:1、门未关好 2、有人撬门 if(!lock_back_flag && door_open_flag){//关锁 and 门的状态是开 if(alarm_flag){ //非法撬门 Serial.println("非法撬门"); } else{ //门未关好 Serial.println("门未关好"); } } } 4) 测试结果 指纹匹配

首先按一下键盘中的任意一键,唤醒指纹模块。在10s内,将手指放置到指纹模块上。若为注册过的指纹,则驱动舵机开门。

指纹匹配



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3