简介:
1. 电子密码锁采用51单片机作为主控芯片,4x4矩阵键盘作为输入设备,通过LCD1602显示,使用24C02芯片用于存储用户密码。
2.系统密码长度设置为7位,具有输入密码,更改密码,恢复初始密码功能,密码具有掉电存储功能。密码输入错误达到三次,则锁住键盘,并报警。
3.电子密码锁使用继电器进行模拟开锁过程。开锁声光提示。

 

密码锁的ppt教程:

原理图:

密码锁单片机程序源码:
#include<reg52.h>
#include<intrinS.h>
#include<absacc.h>
#include "keyc1.h" //见3.12
#include "LCD1602.h"
#include "24C02.h" //见2.2
 //见4.1
#define unchar unsigned char
#define uint unsigned int
 
#define C02_write 0xa0
#define C02_read 0xa1
//----------------------------------------------------------------------------------------------
#define enter 0x0c //确定
#define backspace 0x0f //退格
#define A 0x0a //输入密码
#define B 0x0b //修改密码
//-----------------------------------------------------------------------------------------------
unchar idata temp5_password[6]=
{0,0,0,0,0,0}; //设置初始密码为"123456"
unchar num;//错误次数
uint M1,M2=0,M3,M4,M5,M6; 
//-----------------------------------------------------------------------------------------------
sbit SET=P3^2; //恢复出厂密码设置键
sbit Lock_BIT=P2^0; //锁控制信号,输出低电平
sbit SPK=P2^2; //报警信号输出端
//-----------------------------------------------------------------------------------------------
unchar int_count_1;
unsigned int int_count_2;
void SPKdelay(uint z) //蜂鸣器延时
{ uint i;
 for(i=z;i>0;i--);
} 
 
//===============================================================================================
void Longdelay(unsigned int i) //长时间延时函数
{
 unsigned int j;
 for (;i>0;i--)
 for(j=10000;j>0;j--);
}
 
//================================================================================================
bit compare_string(unchar *string1,unchar *string2)//密码对比函数
{
 unchar count;//设置循环对比计数器
 for(count=0;count<6;count++)//设置要对比的密码为六位
 {
 if(string1[count]!=string2[count])
 return(0);//输入密码与原密码不相同时返回出错函数0
}
 return(1);//输入密码正确返回正确参数1
}
//---------------------------------------------------------------------------------------------------
unchar step_choose(void)//选择输入密码或修改密码处理函数
{
 unsigned int i;
 unchar key;
 do{
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);//设置显示“input password”的地址
 Show_Char("Input Password");//显示"输入密码"
 GotoXY(0,1);//设置显示plaese press A的首地址
 Show_Char("Please Press A");//显示请输入A
 for(i=0;i<30000;i++)//循环读键盘
 {
 key=key1();//读键盘
 if((key==A)||(key==B)) break;//如果是A或B就退出
 }
 if((key!=A)&&(key!=B))//如果不是A也不是B,就执行下列程序
 {
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);// AC递增,画面不动
 GotoXY(0,0);//设置显示“input password”的地址
 Show_Char("Change Password");//显示修改密码
 GotoXY(0,1);//设置显示“please press B”的首地址
 Show_Char("Please Press B");//显示请输入B
 for(i=0;i<30000;i++)//循环读键盘
 { 
 key=key1();//读键盘
 if((key==A)||(key==B)) break;//如果是A或B就退出
 }
 }
 }
 while((key!=A)&&(key!=B));//如果不是A也不是B,就循环读键盘
 return (key);//是A或B就带参数返回
}
//=================================================================================================
bit input_password(unchar *password)//输入密码函数
{
 unchar count,count1;//设置输入密码位数计数器
 unchar key;//设置键值变量
 GotoXY(0,1);
 for(count=0;count<7;count++)
 {
 Longdelay(3);//延时
 if(count<6);//输入密码小于六位吗?
 { 
 do{key=key1();}//是的,读键盘
 while(key==0xff);//如果键盘值为0xff,继续读键盘
 if(key==0x0d) break; //退出键,回到初始界面
 if((key!=backspace)&&(key!=enter)&&(key>=0)&&(key<=9))//不是退格或确认键吗?
 { 
 Show_1_Char('*');//不是,是数字键就显示'*'号
 password[count]=key;//键值送入输入密码数组对应位
 }
 if(key==backspace)//是退格键吗?
 {
 if(count>0)//输入位数大于0吗?
 {
 GotoXY(--count,1);//是的,送删除位的显示地址
 Show_1_Char(' '); //删除位显示空白
 password[count]=' '; //输入密码数组对应位置空白
 GotoXY(count,1); //送闪烁位
 count--;//密码位计数器减1
 
 }
}
 if(key==enter)//是确认键吗
 {
 GotoXY(0,0);//是的,改变显示首地址
 return(0);//返回出错参数0
}
 }
 if(count==6)//密码位计数器等于6吗
 {
 do{key=key1();}//等于6,读键盘
 while((key!=backspace)&&(key!=enter));//不是退格键或确认键,继续读键盘
 if(key==backspace)//是退格键吗
 {
 GotoXY(--count,1);//是的,送删除位的显示地址
 Show_1_Char(' ');//删除位显示空白
 GotoXY(count,1);//送闪烁位
 count--;//密码位计数器减1
 }
 if(key==enter)//是确认键吗
 {return(1);}//是的,输入密码完成,返回正确参数1
 }
 }
}
//===================================================================================================
void password()//密码处理函数
{
 uchar key,key2;
 uint kscount=0;
 unchar idata temp1_password[6]={' ',' ',' ',' ',' ',' '};//设置4组6位密码变量
 unchar idata temp3_password[6]={' ',' ',' ',' ',' ',' '}; //初始化为空白
 unchar idata temp2_password[6]={' ',' ',' ',' ',' ',' '};
 unchar idata temp4_password[6]={' ',' ',' ',' ',' ',' '};
 key=step_choose( );//读选择状态
 if(key==A)//是选择输入密码吗?
 {
 Read_Flash(temp1_password,0x00,6);//是的从24c02中读取密码送入第一组密码变量中
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);//设置显示“input password”的首地址
 Show_Char("Input Password");//显示“输入密码”
 if(input_password(temp2_password))//完成输入密码了吗?
 {
 if(compare_string(temp1_password,temp2_password))//完成,比较密码正确吗
 { num=0;
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);//正确,设置显示“password correct”的首地址
 Show_Char("Password Correct");//显示"密码正确"
 GotoXY(0,1);//正确,设置显示“password correct”的首地址
 Show_Char("Open Lock");//显示"密码正确" Lock_BIT=0;//密码正确,开锁
 Lock_BIT=0;//关开锁信号
 while(1)
 {
 kscount++;
 if(kscount==1000)
 break;
 SPK=0;
 SPKdelay(10);//发开锁提示声
 SPK=1;
 SPKdelay(40);
 } 
 
 while(1)
 { key2=key1();
 if(key2==0x0e)
 {
 Lock_BIT=1;//关开锁信号
 break;
 }
 }
 SPK=0;
 //关开锁提示音
 TR0=0;//关定时器0
 return;//返回
 }
 else
 {
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);//错误,设置显示“wrong password”的首地址
 Show_Char("Wrong Password");//显示“密码错误”
 Longdelay(25);
 num++;
 if(num==3)
 {
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);
 Show_Char("Please Wait For");
 GotoXY(0,1);
 Show_Char(" 3 Minute");
 while(1)
 {
 SPK=0;
 SPKdelay(100);
 SPK=1;
 SPKdelay(100);
 M1++;
 if(M1==24000)
 {
 break;
 }
 }
 Longdelay(1400);
 }
 Longdelay(10);//延时
 return;//返回
 }
 }
 else
 {
 GotoXY(0,1);//没有完成密码输入,设置显示“error!”的首地址
 Show_Char("Error!");//显示“出错”
 Longdelay(15);//延时
 } 
 }
 else//是,修改密码
 {
 Read_Flash(temp1_password,0x00,6);//从24c02中读取密码送入第一组密码变量中
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);//设置显示“input old password”的首地址
 Show_Char("Input Old Password");//显示输入旧密码
 if(input_password(temp2_password))//完成输入密码了吗(输入的旧密码放在数组2中)
 {
 if(compare_string(temp1_password,temp2_password))//完成,比较密码正确吗?
 {
 GotoXY(0,1);//正确,设置显示“password correct!”的首地址
 Show_Char("Password Correct!");//显示“密码正确”
 Longdelay(6);//延时
 WR_CMD(0x01);
 WR_CMD(0x06);
 GotoXY(0,0);
 Show_Char("Input New Password!");
 if(input_password(temp3_password))//完成第一次新密码输入吗?(输入密码放在数组三中)
 {
 WR_CMD(0x01);
 WR_CMD(0x06);
 GotoXY(0,0);
 Show_Char("Input Again");//显示再次输入密码
 if(input_password(temp4_password))//完成第二次新密码输入吗?(输入的密码放在密码组4中)
 {
 if(compare_string(temp3_password,temp4_password))//比较两次输入密码属否相同
 {
 Write_Flash(temp3_password,0x00,6);//相同,将新密码存入24c02中
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);
 Show_Char("Password has");
 GotoXY(0,1);
 Show_Char("been changed");
 Longdelay(10);
 return;
 }
 else
 {
 WR_CMD(0x01);//两次输入不同清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);
 Show_Char("Twice input"); //显示”两次输入“
 GotoXY(0,1);
 Show_Char("is different"); //显示是“不同的”
 Longdelay(10);
 return; 
 }
 }
 else
 {
 GotoXY(0,1);//没有正确完成第二次新密码的输入,设置显示“error”的首地址
 Show_Char("Error!");//显示错误
 Longdelay(15);
 return;
 }
 }
 else
 {
 GotoXY(0,1);//没有正确完成第一次新密码输入,设置显示“error”的首地址
 Show_Char("Error!");
 Longdelay(15);
 return;
 }
 }
 else
 {
 WR_CMD(0x01);//两次输入不同清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(3,0);//旧密码输入错误,设置显示“wrong password”的首地址
 Show_Char("Sorry"); 
 GotoXY(0,1); 
 Show_Char("Wrong password");
num++;
 if(num==3)
 {
 WR_CMD(0x01);//清屏
 WR_CMD(0x06);//AC递增,画面不动
 GotoXY(0,0);
 Show_Char("Please Wait For");
 GotoXY(0,1);
 Show_Char(" 3 Minute");
 while(1)
 {
 SPK=0;
 SPKdelay(100);
 SPK=1;
 SPKdelay(100);
 M1++;
 if(M1==24000)
 {
 break;
 }
 }
 Longdelay(1400);
 }
 Longdelay(25);
 return;
 }
 }
 else
 {
 GotoXY(0,1);//没有正确完成旧密码的输入,设置显示“error!”的首地址
 Show_Char("Error!");
 Longdelay(15);
 return;
 }
 }
}
//============================================================================================================
void int_service(void) interrupt 0 //外部中断0处理函数
{
 EA=1;//关CPU中断
 EX0=1;//关外部中断0
 for(int_count_1=4;int_count_1>0;int_count_1--)//设置延时时间,10秒
 {
 for(int_count_2=0xffff;int_count_2>0;int_count_2--)
 {
 if(SET==1)//恢复出厂密码设置键松开否?
 {
 return;
 }
 }
 } 
 WR_CMD(0x01);
 WR_CMD(0x06);
 Show_Char("Reset Cuccess!");//显示“恢复出厂密码”
 Longdelay(50);
 Write_Flash(temp5_password,0x00,6); //初始密码0000000密码送入24c02中保存
 
/* EA=1;//关CPU中断
 EX0=1; */
}
//==========================================================================================
void t0(void) interrupt 1 using 0//定时、计数器0中断处理函数
{
 TH0=(65536-1000)/256;//重新将定时1000微秒初值的高八位送入TH0
 TL0=(65536-1000)%256;// 重新将定时1000微秒初值的低八位送入TL0
 SPK=~SPK;//信号输出位取反,即1000微秒反转一次,产生周期为2ms的方波
}
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 main()
 { unchar key;
 Initialize(); //1602初始化
 IT0=1;//设INT0为跳变沿沿触发方式
 EX0=1;//开外部中断0
 TMOD=0x01;
 TH0=(65536-1000)/256;//重新将定时1000微秒初值的高八位送入TH0
 TL0=(65536-1000)%256;// 重新将定时1000微秒初值的低八位送入TL0
 TR0=0;
 ET0=1;
 EA=1;
 while(1)
 { 
 password();//运行密码处理函数
 }
}
//=================================终于完成了==================================================