所有资料51hei提供下载:
1602 DS1302按键调时 闹钟.zip
(53.36 KB, 下载次数: 43)
单片机源程序如下:
- #include <reg52.h>
- #include <intrins.h>
- #define uchar unsigned char
- #define uint unsigned int
- sbit clock=P2^1; // 闹钟
- sbit ds=P2^0; // 18b20
- bit flag1;
- uint temp;
- sbit SCK=P1^7;
- sbit SDA=P1^6;
- sbit RST=P1^5;// DS1302复位
- sbit set=P3^4;//定义按键端口
- sbit s1=P3^5;
- sbit s2=P3^6;
- sbit s3=P3^7;
- sbit RS=P1^0;//RS为数据/指令选择1/0
- sbit RW=P1^1;//读写
- sbit E=P1^2;//E为使能信号
- bit flag;//是否读取时间的标志位
- uchar setn=0;//复位键、增加键、减少键按下次数
- uchar code time0[]="20 - - ";
- uchar code time1[]=" : : ";
- uchar code time2[]=" Noise : : ";
- uchar code time3[]=" Noise Power: ";
- uchar l_tmpdate[7];//秒分时日月周年// 可随时更改
- uchar code write_add[7]={0x80,0x82,0x84,0x86,0x88,0x8a,0x8c}; //秒分时日月周年 写的寄存器地址
- uchar code read_add[7]={0x81,0x83,0x85,0x87,0x89,0x8b,0x8d}; //秒分时日月周年 读的寄存器地址
- uchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x40}; //共阴数码管 0-9加'-'熄灭表
- void delay(uint z)
- {
- while(--z);
- }
- void write_com(uchar com)//液晶写命令函数
- {
- RS=0;//写命令使能
- RW=0;//写
- delay(100);
- E=0;
- P0=com;
- E=1;
- delay(10);
- E=0;
- }
- void write_data(uchar dat)//液晶写数据函数
- {
- RS=1;//写数据使能
- RW=0;
- delay(10);
- E=0;
- P0=dat;
- E=1;
- delay(10);
- E=0;
- }
- void init()//液晶初始化
- {
- uchar num;
- E=0;
- write_com(0x38);//显示模式设置
- write_com(0x38);
- write_com(0x38);
- write_com(0x08);//显示关闭
- write_com(0x01);//显示清屏
- write_com(0x06);//光标移动设置整屏不移动
- write_com(0x0c);//屏幕开、光标不闪(0)不显示(0)
- write_com(0x80);
- for(num=0;num<16;num++)
- {
- write_data(time0[num]);
- delay(5);
- }
- write_com(0x80+0x40);
- for(num=0;num<9;num++)
- {
- write_data(time1[num]);
- delay(5);
- }
- }
- void delay1(uint t)
- {
- while(t--);
- }
- void ds_reset()
- {
- ds=1;
- delay1(5);
- ds=0;
- delay1(80);
- ds=1;
- delay1(14);
- if(ds==0)
- flag1=1;
- else
- flag1=0;
- delay1(20);
- }
- bit ds_read_bit()
- {
- bit dat;
- ds=0;
- _nop_();
- _nop_();
- ds=1;
- _nop_();
- dat=ds;
- delay1(10);
- return dat;
- }
- uchar ds_read_byte()
- {
- uchar i,j,k;
- for(i=0;i<8;i++)
- {
- j=ds_read_bit();
- k=(j<<7)|(k>>1);
- }
- return k;
- }
- void ds_write_byte(uchar dat)
- {
- uchar i;
- for(i=0;i<8;i++)
- {
- ds=0;
- _nop_();
- ds=dat&0x01;
- delay1(6);
- ds=1;
- dat=dat>>1;
- }
- delay(6);
- }
- uint read_temperature()
- {
- uchar a,b;
- ds_reset();
- ds_write_byte(0xcc);
- ds_write_byte(0xbe);
- a=ds_read_byte();
- b=ds_read_byte();
- temp=b;
- temp=temp<<8;
- temp=temp|a;
- temp=temp*0.0625*10+0.5;
- return temp;
- }
- void display_18b20()
- {
- write_com(0x80+0x40+11);
- write_data(temp/100+0x30);
- write_com(0x80+0x40+12);
- write_data((temp%100)/10+0x30);
- write_com(0x80+0x40+13);
- write_data('.');
- write_com(0x80+0x40+14);
- write_data((temp%100)%10+0x30);
- write_com(0x80+0x40+15);
- write_data('C');
- }
- void Write_Ds1302_Byte(uchar temp) //写一个字节
- {
- uchar i;
- for (i=0;i<8;i++) //循环8次写入数据
- {
- SCK=0;
- SDA=temp&0x01; //每次传输低字节
- temp>>=1; //右移一位
- SCK=1;
- }
- }
- void Write_Ds1302(uchar add,uchar dat )//向寄存器写数据
- {
- RST=0;
- _nop_();
- SCK=0;
- _nop_();
- RST=1;//启动
- _nop_();
- Write_Ds1302_Byte(add); //发送地址
- Write_Ds1302_Byte(dat); //发送数据
- RST=0; //恢复
- }
- uchar Read_Ds1302_Byte()//读一个字节
- {
- uchar i,temp=0x00;
- for (i=0;i<8;i++) //循环8次 读取数据
- {
- if(SDA)
- temp|=0x80; //每次传输低字节
- SCK=0;
- temp>>=1; //右移一位
- SCK=1;
- }
- return(temp);
- }
- uchar Read_Ds1302(uchar address )//从寄存器读数据
- {
- uchar date;
- RST=0;
- _nop_();
- SCK=0;
- _nop_();
- RST=1;
- _nop_();
- Write_Ds1302_Byte(address);
- date=Read_Ds1302_Byte();
- RST=0;
- _nop_(); //以下为DS1302复位的稳定时间
- RST=0;
- SCK=0;
- _nop_();
- SCK=1;
- _nop_();
- SDA=0;
- _nop_();
- SDA=1;
- _nop_();
- return (date);
- }
- void Read_RTC(void) //读取日历
- {
- uchar i,*p;
- p=read_add; //读的地址传递
- for(i=0;i<7;i++) //分7次读取 秒分时日月周年
- {
- l_tmpdate[i]=Read_Ds1302(*p);
- p++;
- }
- }
- void Set_RTC(void) //设定日历
- {
- uchar i,*p,tmp;
- for(i=0;i<7;i++)
- { //BCD处理,将十六进制转换成十进制
- tmp=l_tmpdate[i]/10;
- l_tmpdate[i]=l_tmpdate[i]%10;
- l_tmpdate[i]=l_tmpdate[i]+tmp*16;
- }
- Write_Ds1302(0x8E,0X00);//关闭写保护
- p=write_add;//传要写的寄存器地址
- for(i=0;i<7;i++) //7次写入秒分时日月周年
- {
- Write_Ds1302(*p,l_tmpdate[i]);
- p++;
- }
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- void write_lcd()
- {
- static uchar i,temp[2];
- switch(i)
- {
- case 0: write_com(0x80+0x40+0x07);break;//秒
- case 1: write_com(0x80+0x40+4);break;//分
- case 2: write_com(0x80+0x40+1);break;//时
- case 3: write_com(0x80+0x08);break;//日
- case 4: write_com(0x80+5);break;//月
- case 5: write_com(0x80+0x0e);break;//星期
- case 6: write_com(0x80+2);break;//年
- }
- temp[0]=l_tmpdate[i]/16;//数据的转换
- temp[1]=l_tmpdate[i]&0x0f;
- write_data(0x30+temp[0]);
- write_data(0x30+temp[1]);
- i++;
- if(i==7)
- i=0;
- }
- uchar change(uchar x)//十进制转换成十六进制
- {
- uchar tep,y;
- y=x;
- tep=y/16;
- y=y%16;
- y=y+tep*10;
- return y;
- }
- void keyscan()
- {
-
- uchar tem[2],tp,Flag;//存储要更改的时间数据
- if(set==0)
- {
- flag=1;//时间停止
- delay(500);//去键盘按下抖动
- if(set==0)
- {
- delay(500);
- while(!set);
- delay(500);//去键盘抬起时抖动
- while(!set);
- delay(500);
- setn++;
- if(setn==1)
- {
- write_com(0x80+0x40+8);//将光标移动到秒个位
- write_com(0x0f);//显示光标并且闪烁
-
- }
- if(setn==2)
- {
- write_com(0x80+0x40+5);//将光标移动到分个位
- write_com(0x0f);//显示光标并且闪烁
- }
- if(setn==3)
- {
-
- write_com(0x80+0x40+2);//将光标移动到时个位
- write_com(0x0f);//显示光标并且闪烁
- }
- if(setn==4)
- {
- write_com(0x80+15); // 将光标移动到星期
- write_com(0x0f);
- }
- if(setn==5)
- {
- write_com(0x80+9); // 将光标移动到日
- write_com(0x0f);
- }
- if(setn==6)
- {
- write_com(0x80+6); // 将光标移动到月
- write_com(0x0f);
- }
- if(setn==7)
- {
- write_com(0x80+3); // 将光标移动到年
- write_com(0x0f);
- }
- if(setn==8)
- {
- setn=0;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[0],l_tmpdate[0]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- flag=0;//时钟正常运行
- write_com(0x0c);//光标停止闪烁
- }
- }
-
- }
- if(setn!=0)//更改时间
- {
- if(s1==0)//增加时间
- {
- delay(5000);
- if(s1==0)
- {
-
- while(!s1);
- delay(5000);//去键盘抬起时抖动
- while(!s1);
- if(setn==1)
- {
- l_tmpdate[0]=change(l_tmpdate[0]);
- l_tmpdate[0]++;
- if(l_tmpdate[0]>=60)
- l_tmpdate[0]=0;
- {
- tp=l_tmpdate[0]/10;
- l_tmpdate[0]=l_tmpdate[0]%10;
- l_tmpdate[0]=l_tmpdate[0]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[0],l_tmpdate[0]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+7); //秒
- tem[0]=l_tmpdate[0]/16;//数据的转换
- tem[1]=l_tmpdate[0]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+8);
- Flag=1;
- }
- if(setn==2)
- { l_tmpdate[1]=change(l_tmpdate[1]);
- l_tmpdate[1]++;
- if(l_tmpdate[1]==60)
- l_tmpdate[1]=0;
- {
- tp=l_tmpdate[1]/10;
- l_tmpdate[1]=l_tmpdate[1]%10;
- l_tmpdate[1]=l_tmpdate[1]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[1],l_tmpdate[1]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+4); //分
- tem[0]=l_tmpdate[1]/16;//数据的转换
- tem[1]=l_tmpdate[1]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+5);
- }
- if(setn==3)
- { l_tmpdate[2]=change(l_tmpdate[2]);
- l_tmpdate[2]++;
- if(l_tmpdate[2]>=24)
- l_tmpdate[2]=0;
- {
- tp=l_tmpdate[2]/10;
- l_tmpdate[2]=l_tmpdate[2]%10;
- l_tmpdate[2]=l_tmpdate[2]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[2],l_tmpdate[2]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+1); //时
- tem[0]=l_tmpdate[2]/16;//数据的转换
- tem[1]=l_tmpdate[2]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+2);
- }
- if(setn==4)
- {
- l_tmpdate[5]=change(l_tmpdate[5]);
- l_tmpdate[5]++;
- if(l_tmpdate[5]==8)
- l_tmpdate[5]=1;
- {
- tp=l_tmpdate[5]/10;
- l_tmpdate[5]=l_tmpdate[5]%10;
- l_tmpdate[5]=l_tmpdate[5]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[5],l_tmpdate[5]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+14); //星期
- tem[0]=l_tmpdate[5]/16;//数据的转换
- tem[1]=l_tmpdate[5]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+15);
- }
-
- if(setn==5)
- {
- l_tmpdate[3]=change(l_tmpdate[3]);
- l_tmpdate[3]++;
- if(l_tmpdate[3]==32)
- l_tmpdate[3]=0;
- {
- tp=l_tmpdate[3]/10;
- l_tmpdate[3]=l_tmpdate[3]%10;
- l_tmpdate[3]=l_tmpdate[3]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[3],l_tmpdate[3]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+8); //日
- tem[0]=l_tmpdate[3]/16;//数据的转换
- tem[1]=l_tmpdate[3]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+9);
- }
- if(setn==6)
- {
- l_tmpdate[4]=change(l_tmpdate[4]);
- l_tmpdate[4]++;
- if(l_tmpdate[4]==13)
- l_tmpdate[4]=0;
- write_com(0x80+5); //月
- {
- tp=l_tmpdate[4]/10;
- l_tmpdate[4]=l_tmpdate[4]%10;
- l_tmpdate[4]=l_tmpdate[4]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[4],l_tmpdate[4]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- tem[0]=l_tmpdate[4]/16;//数据的转换
- tem[1]=l_tmpdate[4]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+6);
- }
- if(setn==7)
- {
- l_tmpdate[6]=change(l_tmpdate[6]);
- l_tmpdate[6]++;
- if(l_tmpdate[6]==100)
- l_tmpdate[6]=0;
- write_com(0x80+2); //年
- {
- tp=l_tmpdate[6]/10;
- l_tmpdate[6]=l_tmpdate[6]%10;
- l_tmpdate[6]=l_tmpdate[6]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[6],l_tmpdate[6]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- tem[0]=l_tmpdate[6]/16;//数据的转换
- tem[1]=l_tmpdate[6]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+3);
- }
- }
- }
- if(s2==0)//减少时间
- {
- delay(5000);
- if(s2==0)
- {
- while(!s2);
- delay(5000);//去键盘抬起时抖动
- while(!s2);
- if(setn==1)
- {
- l_tmpdate[0]=change(l_tmpdate[0]);
- if(l_tmpdate[0]!=0)
- l_tmpdate[0]--;
- if(l_tmpdate[0]==0)
- l_tmpdate[0]=59;
- {
- tp=l_tmpdate[0]/10;
- l_tmpdate[0]=l_tmpdate[0]%10;
- l_tmpdate[0]=l_tmpdate[0]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[0],l_tmpdate[0]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+7); //日
- tem[0]=l_tmpdate[0]/16;//数据的转换
- tem[1]=l_tmpdate[0]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+8);
- }
- if(setn==2)
- {
- l_tmpdate[1]=change(l_tmpdate[1]);
- if(l_tmpdate[1]!=0)
- l_tmpdate[1]--;
- if(l_tmpdate[1]==0)
- l_tmpdate[1]=59;
- {
- tp=l_tmpdate[1]/10;
- l_tmpdate[1]=l_tmpdate[1]%10;
- l_tmpdate[1]=l_tmpdate[1]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[1],l_tmpdate[1]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+4); //月
- tem[0]=l_tmpdate[1]/16;//数据的转换
- tem[1]=l_tmpdate[1]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+5);
- }
- if(setn==3)
- { l_tmpdate[2]=change(l_tmpdate[2]);
- if(l_tmpdate[2]!=0)
- l_tmpdate[2]--;
- if(l_tmpdate[2]==0)
- l_tmpdate[2]=23;
- {
- tp=l_tmpdate[2]/10;
- l_tmpdate[2]=l_tmpdate[2]%10;
- l_tmpdate[2]=l_tmpdate[2]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[2],l_tmpdate[2]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+0x40+1); //年
- tem[0]=l_tmpdate[2]/16;//数据的转换
- tem[1]=l_tmpdate[2]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+0x40+2);
- }
- if(setn==4)
- {
- l_tmpdate[5]=change(l_tmpdate[5]);
- if(l_tmpdate[5]!=0)
- l_tmpdate[5]--;
- if(l_tmpdate[5]==0)
- l_tmpdate[5]=7;
- {
- tp=l_tmpdate[5]/10;
- l_tmpdate[5]=l_tmpdate[5]%10;
- l_tmpdate[5]=l_tmpdate[5]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[5],l_tmpdate[5]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+14); //星期
- tem[0]=l_tmpdate[5]/16;//数据的转换
- tem[1]=l_tmpdate[5]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+15);
- }
- if(setn==5)
- {
- l_tmpdate[3]=change(l_tmpdate[3]);
- if(l_tmpdate[3]!=0)
- l_tmpdate[3]--;
- if(l_tmpdate[3]==0)
- l_tmpdate[3]=31;
- {
- tp=l_tmpdate[3]/10;
- l_tmpdate[3]=l_tmpdate[3]%10;
- l_tmpdate[3]=l_tmpdate[3]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[3],l_tmpdate[3]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- write_com(0x80+8); //日
- tem[0]=l_tmpdate[3]/16;//数据的转换
- tem[1]=l_tmpdate[3]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+9);
- }
- if(setn==6)
- {
- l_tmpdate[4]=change(l_tmpdate[4]);
- if(l_tmpdate[4]!=0)
- l_tmpdate[4]--;
- if(l_tmpdate[4]==0)
- l_tmpdate[4]=12;
- write_com(0x80+5); //月
- {
- tp=l_tmpdate[4]/10;
- l_tmpdate[4]=l_tmpdate[4]%10;
- l_tmpdate[4]=l_tmpdate[4]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[4],l_tmpdate[4]);
- Write_Ds1302(0x8E,0x80);//打开写保护
- }
- tem[0]=l_tmpdate[4]/16;//数据的转换
- tem[1]=l_tmpdate[4]&0x0f;
- write_data(0x30+tem[0]);
- write_data(0x30+tem[1]);
- write_com(0x80+6);
- }
- if(setn==7)
- {
- l_tmpdate[6]=change(l_tmpdate[6]);
- if(l_tmpdate[6]!=0)
- l_tmpdate[6]--;
- if(l_tmpdate[6]==0)
- l_tmpdate[6]=99;
- write_com(0x80+2); //年
- {
- tp=l_tmpdate[6]/10;
- l_tmpdate[6]=l_tmpdate[6]%10;
- l_tmpdate[6]=l_tmpdate[6]+tp*16;
- Write_Ds1302(0x8E,0X00);//关闭写保护
- Write_Ds1302(write_add[6],l_tmpdate[6]);
- ……………………
- …………限于本文篇幅 余下代码请从51黑下载附件…………
复制代码
|