|
自己设计了一个电子密码锁,可掉电保存密码!涉及了24C02、IIC 、E2PROM等,采用LCD12864中文显示
1、在这一版中,将24C02的两引脚SCL和SDA接在了P3.2和P3.3,原来接的是P2.0和P2.1
全部资料下载:
password终极版.zip
(180.19 KB, 下载次数: 113)
矩阵键盘信息:
1 0x7e 2 0xbe 3 0xde
4 0x7d 5 0xbd 6 0xdd
7 0x7b 8 0xbb 9 0xdb
0 0x77 * 0xb7 # 0xd7
0xee 改密码
0xed 启动
0xeb 消除
0xe7 确定
键盘扫描程序
uchar keyscan() //键盘扫描函数,使用行列反转扫描法
{
uchar cord_h,cord_l; //行列值中间变量
P1=0x0f; //行线输出全为1 列线输出全为0
cord_h=P1 & 0x0f; //读入行线值
if(cord_h != 0x0f) //先检测有无按键按下
{
Delay(10); //去抖
if(cord_h!=0x0f)
{
cord_h=P1 & 0x0f; //读入行线值
P1=cord_h | 0xf0; //注意:执行这一步的时候后,按键还没有松开
cord_l=P1 & 0xf0; //读入列线值
return(cord_h + cord_l); //键盘最后组合码值
}
}
return(0xff); //返回该值
}
源码如下:
- #include<reg52.h>
- #include<intrins.h>
- #include"delay.h"
- #include"lcd12864.h"
- #include"keyboard.h"
- #include"24C02.h"
- #include"uart.h"
- #include"T0.h"
- #include"character.h"
- #define uchar unsigned char
- #define uint unsigned int
- uchar dumima,oldmima_flag,newmima_flag,newpass_flag,again_flag,flag,again_and_again_flag;
- uchar code chushimima_tab[]={1,2,3,4,5,6}; //设定系统第一次初始密码为123456
- uchar data dumima_tab1[6]=" "; //从24C02中读取写入的初始或修改的密码保存
- uchar data dumima_tab2[6]=" "; // 储存键入的密码,用于与24C02中的对比
- uchar data dumima_tab3[6]=" "; // 储存键入的新密码
- uchar data dumima_tab4[6]=" "; // 储存再次键入的新密码
- uchar code key_table[]={0,1,2,3,4,5,6,7,8,9}; //显示密码数字字符
- uchar code tiaoshi_ok[]="01"; //调试用
- void main()
- {
- uchar j;
- Init_lcd12864();
- Display_interface();
- UART_init(); //读出0x00处的数据,发送到串口查看
- InitI2C(); //初始化
- Timer0_init(); //定时器0初始化
- mm=3; //可以有5次输入密码的机会
- /* for(i=0;i<6;i++) //先将密码写入24C02
- {
- write_eeprom(i+2,chushimima_tab[i]);
- Delayms(10);
- } */
- // c = read_eeprom(0x07); //串口发送程序段,可以用来测试
- // UART_send_byte(c);
- // dumima = read_eeprom(0x01); //读取01地址的数据判断是否写入初始或修改的密码
- // if(dumima != 1)
- // {
- // write_eeprom(0x01,0x01); //在0X01出写入1
- // for(j=0;j<6;j++) //从02地址开始写初始密码数据
- // {
- // write_eeprom(j+2,chushimima_tab[j]);
- // Delayms(10);
- // }
- // }
- /*****************如果忘记密码,可以利用这段程序重新设置初始密码*************
- for(j=0;j<6;j++) //从02地址开始写初始密码数据
- {
- write_eeprom(j+2,chushimima_tab[j]); //初始密码123456
- Delayms(10);
- }
- *********************************************************************************/
- for(j=0;j<6;j++) //将24C02中的密码读取出来保存在dumima_tab1[]数组中
- {
- dumima_tab1[j] = read_eeprom(j+2);
- Delayms(10);
- }
- while(1) //程序大循环
- {
- keyscan(); //调用键盘扫描 查询按键是否有按下(只对启动和修改密码按键有效)
- if(start == 1) //启动
- {
- prevent_wucaozuo(); //防止误操作
- Input_password();
- char_num=0;loop=1;
- while(loop==1)
- {
- keyscan(); //仅数字键和取消键有效
- if(key_flag==1) //有数字键被按下
- {
- prevent_wucaozuo(); //防止误操作
- Display_num(i,char_num); //显示键入的数字
- dumima_tab2[char_num] = key_table[i]; //储存键入的数字
- UART_send_byte(key_table[i]); //调试用
- decide_songkai(); //判断按键是否松开
- char_num++;
- if(char_num==6)
- {
- loop=0; char_num=0; wait_ok=1;
- for(j=0;j<6;j++) //将24C02中的密码读取出来保存在dumima_tab1[]数组中
- {
- dumima_tab1[j] = read_eeprom(j+2);
- Delayms(10);
- }
- while(wait_ok==1)
- {
- keyscan(); //等待确认键按下
- if(ok==1)
- {
- prevent_wucaozuo(); wait_ok=0;
- if(dumima_tab2[0]==dumima_tab1[0]&&dumima_tab2[1]==dumima_tab1[1]
- &&dumima_tab2[2]==dumima_tab1[2]&&dumima_tab2[3]==dumima_tab1[3]
- &&dumima_tab2[4]==dumima_tab1[4]&&dumima_tab2[5]==dumima_tab1[5])
- {
- // UART_send_byte(tiaoshi_ok[1]);
- input_password_ok(); //显示输入的密码正确
- Delayms(2000); //延时显示
- Display_interface(); //返回界面
- }
- else //执行密码输入错误操作
- {
- // UART_send_byte(dumima_tab2[5]);
- input_password_no(); //显示"密码错误"
- Delayms(2000); //延时显示
- mm--; //输入机会减少一次
- if(mm>0)
- {
- Display_tishi_information(mm); //提示信息
- Delayms(2000);
- start = 1;
- }
- else
- {
- // UART_send_byte(mm);
- Display_suoping_information(); //锁屏信息
- TR0=1; //启动定时器0,在Timer0_service();中关闭
- suoping_flag=10; //锁屏秒数
- while(suoping_flag)
- {
- Timer0_service(); //锁屏倒计时服务函数
- }
- suoping_flag=10; //重新恢复锁屏次数
- Delayms(1000); //延时
- start = 0; //重新进入while(1)大循环
- mm=3; //重新恢复可输入密码的次数
- Display_interface(); //显示开始界面
- }
-
- }
- }
- }
-
- }
- }
- if(remove==1) //在输入密码的过程中可以按“取消”键取消输入密码,直接返回到开始界面
- {
- prevent_wucaozuo(); //防止误操作
- start = 0; //重新进入while(1)大循环
- loop = 0;
- mm=3; //重新恢复可输入密码的次数
- Display_interface(); //显示开始界面
- }
- }
- }
- /*******************按下"重置密码"键**************************/
- if(alter_password ==1)
- {
- prevent_wucaozuo(); //防止误操作
- Input_old_password(); //输入旧密码
- char_num=0;oldmima_flag = 1; //char_num为输入密码的位数
- while(oldmima_flag==1) //
- {
- keyscan(); //仅数字键和取消键有效
- if(key_flag==1) //有数字键被按下
- {
- prevent_wucaozuo(); //防止误操作
- Display_num(i,char_num); //显示键入的数字
- dumima_tab2[char_num] = key_table[i]; //储存键入的数字
- // UART_send_byte(key_table[i]); //调试用
- decide_songkai(); //判断按键是否松开
- char_num++;
- if(char_num==6)
- {
- oldmima_flag=0; char_num=0; wait_ok=1; //在按下确认键之前将其置为0,其实也可以在两分支(1.输入密码成功 2.输入密码错误)内将其置为0
- while(wait_ok==1) //记得在这个循环里将wait_ok置0
- {
- keyscan(); //等待确认键按下
- if(ok==1)
- {
- prevent_wucaozuo();
- if(dumima_tab2[0]==dumima_tab1[0]&&dumima_tab2[1]==dumima_tab1[1]
- &&dumima_tab2[2]==dumima_tab1[2]&&dumima_tab2[3]==dumima_tab1[3]
- &&dumima_tab2[4]==dumima_tab1[4]&&dumima_tab2[5]==dumima_tab1[5])
- {
- input_password_ok(); //显示输入的密码正确
- Delayms(2000); //延时显示
- Input_new_password(); //显示“输入新密码”界面
- newmima_flag=1;
- while(newmima_flag==1) //记得在这个循环里将newmima_flag置0
- {
- keyscan(); //只有数字键和取消键有效
- if(key_flag==1)
- {
- prevent_wucaozuo(); //防止误操作
- Display_num(i,char_num); //显示键入的数字
- dumima_tab3[char_num] = key_table[i]; //储存键入的新密码
- // UART_send_byte(key_table[i]);
- decide_songkai(); //判断按键是否松开
- char_num++;
- if(char_num==6)
- {
- char_num=0; newpass_flag=1;
- for(j=0;j<6;j++) //从02地址开始写初始密码数据
- {
- write_eeprom(j+2,dumima_tab3[j]);
- Delayms(10);
- }
- //将新密码保存在24C02中
- while(newpass_flag == 1)
- {
-
- keyscan();
- if(ok==1) //只有确认键有效
- {
- prevent_wucaozuo(); //防止误操作
- Input_new_password_again();
- again_flag=1;
- while(again_flag==1) //再次输入新密码
- {
- keyscan(); //只有数字键有效
- if(key_flag==1)
- {
- prevent_wucaozuo(); //防止误操作
- Display_num(i,char_num); //显示键入的数字
- dumima_tab4[char_num] = key_table[i]; //储存键入的新密码
- // UART_send_byte(key_table[i]);
- decide_songkai(); //判断按键是否松开
- char_num++;
- if(char_num==6)
- {
- char_num = 0; again_flag=0; flag=1;
- while(flag==1)
- {
- keyscan();
- if(1==ok)
- {
- prevent_wucaozuo(); //防止误操作
- if(dumima_tab3[0]==dumima_tab4[0]&&dumima_tab3[1]==dumima_tab4[1]
- &&dumima_tab3[2]==dumima_tab4[2]&&dumima_tab3[3]==dumima_tab4[3]
- &&dumima_tab3[4]==dumima_tab4[4]&&dumima_tab3[5]==dumima_tab4[5])
- {
- flag=0; newpass_flag=0;again_flag=0;newmima_flag=0;wait_ok=0;
- Alter_password_success();
- Delayms(2000);
- Display_interface(); //显示开始界面
- }
- else //两次输入的新密码不一致执行的操作
- {
- Display_again_cuowu_information(); //显示第二次输入的密码错误
- Delayms(3000);
- Input_new_password_again();
- again_and_again_flag = 1;
- while(again_and_again_flag==1)
- {
- keyscan(); //只有数字键有效
- if(key_flag==1)
- {
- prevent_wucaozuo(); //防止误操作
- Display_num(i,char_num); //显示键入的数字
- dumima_tab4[char_num] = key_table[i]; //储存键入的新密码
- // UART_send_byte(key_table[i]);
- decide_songkai(); //判断按键是否松开
- char_num++;
- if(char_num==6)
- {
- char_num = 0;again_and_again_flag=0; flag=1;
- while(flag==1)
- {
- keyscan();
- if(1==ok)
- {
- prevent_wucaozuo(); //防止误操作
- if(dumima_tab3[0]==dumima_tab4[0]&&dumima_tab3[1]==dumima_tab4[1]
- &&dumima_tab3[2]==dumima_tab4[2]&&dumima_tab3[3]==dumima_tab4[3]
- &&dumima_tab3[4]==dumima_tab4[4]&&dumima_tab3[5]==dumima_tab4[5])
- {
- flag=0; again_and_again_flag=0;newpass_flag=0;again_flag=0;newmima_flag=0;wait_ok=0;
- Alter_password_success();
- Delayms(2000);
- Display_interface(); //显示开始界面
- }
- else //又一次第二次输错新密码(有点绕^_^)
- {
- flag=0; again_and_again_flag=0;newpass_flag=0;again_flag=0;newmima_flag=0;wait_ok=0;
- Alter_no_success(); //修改密码失败
- Delayms(2000);
- Display_interface(); //显示开始界面
- }
- }
- }
-
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- if(remove==1) //第一次输入新密码过程中按下“取消”按键执行的操作
- {
- prevent_wucaozuo(); //防止误操作
- newmima_flag = 0; wait_ok = 0; alter_password = 0;
- Display_interface(); //显示开始界面
- }
- }
- }
- else //输入的密码错误执行操作
- {
- input_password_no(); //显示"密码错误"
- Delayms(2000); //延时显示
- mm--; //输入机会减少一次
- if(mm>0)
- {
- Display_tishi_information(mm); //提示信息
- Delayms(2000);
- alter_password = 1; //还是将alter_password置0比较合适
- wait_ok = 0;
- }
- else
- {
- // UART_send_byte(mm);
- Display_suoping_information(); //锁屏信息
- TR0=1; //启动定时器0,在Timer0_service();中关闭
- suoping_flag=10; //锁屏秒数
- while(suoping_flag)
- {
- Timer0_service(); //锁屏倒计时服务函数
- }
- suoping_flag=10; //重新恢复锁屏次数
- Delayms(1000); //延时
- alter_password = 0; //重新进入while(1)大循环
- mm=3; wait_ok = 0; //重新恢复可输入密码的次数
- Display_interface(); //显示开始界面
- }
- }
- }
- }
- }
- }
- if(remove==1) //在输入密码的过程中可以按“取消”键取消输入密码,直接返回到开始界面
- {
- prevent_wucaozuo(); //防止误操作
- oldmima_flag=0;
- alter_password=0; //我觉得这里应该吧alter_password置为0
- Display_interface(); //显示开始界面
- }
- }
- }
- }
- }
复制代码
|
评分
-
查看全部评分
|