自己做的指纹识别小模块,自己画的板子,经测试已经可以正常运行,在这里记录一下,并且给大家开源共享一下~~~
也参考了很多资料以及程序,谢谢。另外如果大家发现什么问题还请多多讨论~~~
源代码链接可以参考文章:
https://blog.csdn.net/Fighting_Boom/article/details/87969477
单片机型号:IAP15W4K58S4,STC15系列的也可以替换。
指纹识别模块:ATK-AS608。
显示器:LCD12864。
模块部分资料如下:
AD资料如下:
PCB在截图的时候没调整好,凑合着看~~~
成品图片如下:
主程序代码如下:
#include "FPM10A.h"
#include "key.h"
#include "uart.h"
#include "lcd12864_c.h"
#include "delay.h"
#include "led.h"
void main()
{
Lcd12864_Init(); // 12864液晶初始化
CGRAM(); // 自定义字符
Uart_Init(); // 串口初始化
Key_Init(); // 按键初始化
Led_Init(); // LED初始化
Device_Check(); // 指纹检测
Delay_Ms(3000); // 等待显示更新
DisplayUpdata(); // 显示更新
Delay_Ms(500); // 延时500MS,等待指纹模块复位
while(1)
{
if(local_date!=base_date) //光标位置变化,则更新显示
{
DisplayUpdata();
base_date=local_date;
}
if(KEY_OK == 0)
{
while(KEY_OK == 0);//等待松开按键
switch(local_date)
{
case 0: //添加指纹
Led_Green_On();
FPM10A_Add_Fingerprint();
Led_Green_Off();
local_date = 0;
DisplayUpdata();
break;
case 1://搜索指纹
Led_red_On();
FPM10A_Find_Fingerprint();
Led_red_Off();
local_date = 1;
DisplayUpdata();
break;
case 2: //清空指纹
FPM10A_Delete_All_Fingerprint();
local_date = 2;
DisplayUpdata();
break;
}
}
//下
if(KEY_DOWN == 0)
{
while(KEY_DOWN == 0); //等待松开按键
if(local_date<=2)
{
local_date++;
if(local_date==3)
local_date=0;
}
}
//上
if(KEY_UP == 0)
{
while(KEY_UP == 0); //等待松开按键
if(local_date>=0)
{
local_date--;
if(local_date==-1)
local_date=2;
}
}
Delay_Ms(100); //延时判断100MS检测一次
}
}
AS608 .h文件代码如下:
#ifndef __FPMXX_H__
#define __FPMXX_H__
#include
extern unsigned char FPM10A_RECEICE_BUFFER[32];
void FPM10A_Cmd_Get_Img(void);
void FPM10A_Cmd_Check(void);
void Device_Check(void);
void FPM10A_Receive_Data(unsigned char ucLength);
void FPM10A_Delete_All_Fingerprint();
void FPM10A_Find_Fingerprint();
void FPM10A_Cmd_Search_Finger(void);
void FPM10A_Add_Fingerprint();
void FPM10A_Cmd_Reg_Model();
void FPM10A_Cmd_Save_Finger( unsigned int storeID );
void FINGERPRINT_Cmd_Delete_All_Finger(void);
#endif
AS608 .C文件代码如下:
#include "FPM10A.h"
#include "key.h"
#include "uart.h"
#include "lcd12864_c.h"
#include "delay.h"
#include "led.h"
volatile unsigned char FPM10A_RECEICE_BUFFER[32];
unsigned int finger_id = 0;
//FINGERPRINT通信协议定义
code unsigned char FPM10A_Get_Device[10] = {0x01,0x00,0x07,0x13,0x00,0x00,0x00,0x00,0x00,0x1b}; //口令验证
code unsigned char FPM10A_Pack_Head[6] = {0xEF,0x01,0xFF,0xFF,0xFF,0xFF}; //协议包头
code unsigned char FPM10A_Get_Img[6] = {0x01,0x00,0x03,0x01,0x00,0x05}; //获得指纹图像
code unsigned char FPM10A_Get_Templete_Count[6] = {0x01,0x00,0x03,0x1D,0x00,0x21 }; //获得模版总数
code unsigned char FPM10A_Search[11]= {0x01,0x00,0x08,0x04,0x01,0x00,0x00,0x03,0xE7,0x00,0xF8}; //搜索指纹搜索范围0 - 999,使用BUFFER1中的特征码搜索
code unsigned char FPM10A_Search_0_9[11]= {0x01,0x00,0x08,0x04,0x01,0x00,0x00,0x00,0x13,0x00,0x21}; //搜索0-9号指纹
code unsigned char FPM10A_Img_To_Buffer1[7]= {0x01,0x00,0x04,0x02,0x01,0x00,0x08}; //将图像放入到BUFFER1
code unsigned char FPM10A_Img_To_Buffer2[7]= {0x01,0x00,0x04,0x02,0x02,0x00,0x09}; //将图像放入到BUFFER2
code unsigned char FPM10A_Reg_Model[6]= {0x01,0x00,0x03,0x05,0x00,0x09}; //将BUFFER1跟BUFFER2合成特征模版
code unsigned char FPM10A_Delete_All_Model[6]= {0x01,0x00,0x03,0x0d,0x00,0x11}; //删除指纹模块里所有的模版
volatile unsigned char FPM10A_Save_Finger[9]= {0x01,0x00,0x06,0x06,0x01,0x00,0x0B,0x00,0x19}; //将BUFFER1中的特征码存放到指定的位置
//volatile:系统总是重新从它所在的内存读取数据,即使它前面的指令刚刚从该处读取过数据
/*------------------ FINGERPRINT命令字 --------------------------*/
//发送包头
void FPM10A_Cmd_Send_Pack_Head(void)
{
int i;
for(i=0; i<6; i++) //包头
{
Uart_Send_Byte(FPM10A_Pack_Head[i]);
}
}
//发送指令
void FPM10A_Cmd_Check(void)
{
int i=0;
FPM10A_Cmd_Send_Pack_Head(); //发送通信协议包头
for(i=0; i<10; i++)
{
Uart_Send_Byte(FPM10A_Get_Device[i]);
}
}
//接收反馈数据缓冲
void FPM10A_Receive_Data(unsigned char ucLength)
{
unsigned char i;
for (i=0; i>8;
FPM10A_Save_Finger[6] = (storeID&0x00FF);
for(i=0; i<7; i++) //计算校验和
temp = temp + FPM10A_Save_Finger[i];
FPM10A_Save_Finger[7]=(temp & 0x00FF00) >> 8; //存放校验数据
FPM10A_Save_Finger[8]= temp & 0x0000FF;
FPM10A_Cmd_Send_Pack_Head(); //发送通信协议包头
for(i=0; i<9; i++)
Uart_Send_Byte(FPM10A_Save_Finger[i]); //发送命令 将图像转换成 特征码 存放在 CHAR_buffer1
}
//添加指纹
void FPM10A_Add_Fingerprint()
{
unsigned char id_show[]= {0,0,0};
ClrScreen(); //清空显示屏
while(1)
{
english(0,0,13,"请输入指纹ID:");
english(1,0,12,"上:+ 下:-");
//按返回键直接回到主菜单
if(KEY_CANCEL == 0)
{
while(KEY_CANCEL==0);
break;
}
//按上键finger值加一
if(KEY_UP==0)
{
while(KEY_UP==0);
if(finger_id == 299)
{
finger_id = 0;
}
else
{
finger_id = finger_id + 1;
};
}
//按下键finger值减一
if(KEY_DOWN == 0)
{
while(KEY_DOWN==0);
if(finger_id == 0)
{
finger_id = 299;
}
else
finger_id = finger_id - 1;
}
//finger值显示处理
id_show[0]=finger_id/100;
id_show[1]=finger_id%100/10;
id_show[2]=finger_id%100%10;
english(2,1,3,"ID:");
Lcd12864_R_W(0,0x88+4);
Lcd12864_R_W(1,0x30+id_show[0]);
Lcd12864_R_W(0,0x88+5);
Lcd12864_R_W(1,0x30+id_show[1]);
Lcd12864_R_W(0,0x88+6);
Lcd12864_R_W(1,0x30+id_show[2]);
//按确认键开始录入指纹信息
if(KEY_OK == 0)
{
while(KEY_OK==0);
ClrScreen(); //清空显示屏
english(0,0,11,"请输入指纹:");
do
{
//按下返回键退出录入返回fingerID调整状态
if(KEY_CANCEL == 0)
{
while(KEY_CANCEL==0);
break;
}
FPM10A_Cmd_Get_Img(); //获得指纹图像
FPM10A_Receive_Data(12);
//判断接收到的确认码,等于0指纹获取成功
if(FPM10A_RECEICE_BUFFER[9]==0)
{
Delay_Ms(100);
FINGERPRINT_Cmd_Img_To_Buffer1();
FPM10A_Receive_Data(12);
english(1,1,8,"输入成功");
// Buzz_Times(1);
// Delay_Ms(500);
english(2,0,16,"请确认,输入指纹");
do
{
FPM10A_Cmd_Get_Img(); //获得指纹图像
FPM10A_Receive_Data(12);
//判断接收到的确认码,等于0指纹获取成功
if(FPM10A_RECEICE_BUFFER[9]==0)
{
Delay_Ms(100);
FINGERPRINT_Cmd_Img_To_Buffer2();
FPM10A_Receive_Data(12);
FPM10A_Cmd_Reg_Model();//转换成特征码
FPM10A_Receive_Data(12);
FPM10A_Cmd_Save_Finger(finger_id++);
FPM10A_Receive_Data(12);
english(3,0,12,"指纹录入成功");
// Buzz_Times(1);
// Delay_Ms(1000);
break;
}
} while(KEY_CANCEL == 1);
break;
}
} while(KEY_CANCEL == 1);
ClrScreen(); //清空显示屏
}
// Delay_Ms(500);
}
}
//搜索指纹
void FPM10A_Find_Fingerprint()
{
unsigned int find_fingerid = 0;
unsigned char id_show[]= {0,0,0};
ClrScreen(); //清空显示屏
english(0,0,11,"请输入指纹:");
do
{
FPM10A_Cmd_Get_Img(); //获得指纹图像
FPM10A_Receive_Data(12);
//判断接收到的确认码,等于0指纹获取成功
if(FPM10A_RECEICE_BUFFER[9]==0)
{
Delay_Ms(100);
FINGERPRINT_Cmd_Img_To_Buffer1();
FPM10A_Receive_Data(12);
FPM10A_Cmd_Search_Finger();
FPM10A_Receive_Data(16);
if(FPM10A_RECEICE_BUFFER[9] == 0) //搜索到
{
ClrScreen(); //清空显示屏
english(0,0,11,"请输入指纹:");
english(1,0,8,"搜索成功");
// Buzz_Times(1);
// 拼接指纹ID数
find_fingerid = FPM10A_RECEICE_BUFFER[10]*256 + FPM10A_RECEICE_BUFFER[11];
id_show[0]=find_fingerid/100;
id_show[1]=find_fingerid%100/10;
id_show[2]=find_fingerid%100%10;
english(2,3,3,"ID:");
Lcd12864_R_W(0,0x88+4);
Lcd12864_R_W(1,0x30+id_show[0]);
Lcd12864_R_W(0,0x88+5);
Lcd12864_R_W(1,0x30+id_show[1]);
Lcd12864_R_W(0,0x88+6);
Lcd12864_R_W(1,0x30+id_show[2]);
Delay_Ms(2000);
}
else //没有找到
{
ClrScreen(); //清空显示屏
english(0,1,12,"请输入指纹:");
english(1,0,14,"未找到指纹信息");
// Buzz_Times(3);
}
}
} while(KEY_CANCEL == 1);
}
//删除所有存贮的指纹库
void FPM10A_Delete_All_Fingerprint()
{
unsigned char i=0;
ClrScreen(); //清空显示屏
english(0,0,12,"清空指纹库?");
do
{
if(KEY_OK==0)
{
while(KEY_OK==0);
english(1,1,6,"清空中");
Delay_Ms(300);
for(i=0; i<8; i++)
{
english(2,i,20,"*");
Delay_Ms(1500);
}
FINGERPRINT_Cmd_Delete_All_Model();
FPM10A_Receive_Data(12);
english(3,4,8,"清空成功");
// Buzz_Times(3);
break;
}
} while(KEY_CANCEL==1);
}
void Device_Check(void)
{
unsigned char i=0;
FPM10A_RECEICE_BUFFER[9]=1;
ClrScreen(); //清空显示屏
english(0,1,10,"设备加载中");
Delay_Ms(500);
for(i=0; i<8; i++)
{
english(1,i,2,"*");
Delay_Ms(800);
}
english(2,1,12,"设备加载失败");
FPM10A_Cmd_Check();
Delay_Ms(2000);
// ClrScreen(); //清空显示屏
// Delay_Ms(4000);
// FPM10A_Receive_Data(12); // 另起一行 if(FPM10A_RECEICE_BUFFER[9] == 0)
// if(1)
// {
english(2,1,12,"设备加载成功");
// Buzz_Times(1);
Delay_Ms(5000);
ClrScreen(); //清空显示屏
english(0,2,8,"欢迎使用");
Delay_Ms(1000);
english(1,1,12,"指纹识别系统");
Delay_Ms(1000);
english(2,1,12,"系统初始化中");
Delay_Ms(1000);
for(i=0; i<8; i++)
{
english(3,i,2,"*");
Delay_Ms(1000);
}
// Buzz_Times(3);
// Delay_Ms(1000);
// }
}
适用于本项目的程序源码完整文件如下,比较多,就不一一粘贴了,参考文章开头的网址,去百度网盘请自行保存~~~
1. 板子设计不是太好,元器件排布不太方便。
2. 按键总是有抖动,软件消抖不能解决问题,于是在每个按键两端并联了一个10nf电容,效果显著提升。
3. 程序不太熟练,写的时候遇到很多问题,最后还是借鉴了源码,才得以成功实现!
4. 有什么问题欢迎评论,大家共同进步~~~