51 单片机 ds1302 时钟芯片.docx
《51 单片机 ds1302 时钟芯片.docx》由会员分享,可在线阅读,更多相关《51 单片机 ds1302 时钟芯片.docx(13页珍藏版)》请在冰豆网上搜索。
![51 单片机 ds1302 时钟芯片.docx](https://file1.bdocx.com/fileroot1/2022-11/20/8fa56ad3-8c4f-4609-bb88-c2970e85fafb/8fa56ad3-8c4f-4609-bb88-c2970e85fafb1.gif)
51单片机ds1302时钟芯片
51单片机ds1302时钟芯片
#defineuintunsignedint
#defineucharunsignedchar
sbitlcdrs=P1^0;
sbitlcdrw=P1^1;
sbitlcden=P1^2;
sbitkey0=P2^0;//功能键,选择时分秒
sbitkey1=P2^1;//加1键
sbitkey2=P2^2;//减1键
sbitkey4=P2^4;
sbitclk_1302=P1^5;//1302芯片位定义
sbitio_1302=P1^6;
sbitrst_1302=P1^7;
ucharbdatadat;
sbitdat0=dat^0;
sbitdat7=dat^7;
ucharkey0_count;//按键0被按的次数(0~3
ucharflag;
charhour,minute,second;
uchartable_date[]="2009-4-12Mon";
uchartable_time[]="00:
00:
00";
/******函数申明********/
voidwrite_cmd_1602(ucharcmd;
voidwrite_data_1602(uchardat;
voidwrite_add(ucharadd,uchardat;
voidinit1602(;
voiddelay(uintz;
ucharreverse(ucharc;
voidkeyscan(;
voidinit(;
voidRTC_initial(;
voidwr_1302(ucharwr_data;
ucharrd_1302(void;
ucharuc_R1302(ucharucAddr;
voidv_W1302(ucharucAddr,ucharucDa;
主程序
#include
#include
#include"header.h"
/******主函数********/
voidmain(
{
RTC_initial(;
init(;
//init1602(;
//while(1;
while(1
{
if(flag
{
second=uc_R1302(0x81;
minute=uc_R1302(0x83;
hour=uc_R1302(0x85;
write_add(0x40+10,second;
write_add(0x40+7,minute;
write_add(0x40+4,hour;
}
keyscan(;
delay(1;
}
}
voidRTC_initial(
{
v_W1302(0x8e,0x00;//使能
v_W1302(0x80,0x80;//停止晶振
v_W1302(0x90,0x00;//关闭充电
v_W1302(0x8c,0x07;//设置年
v_W1302(0x8a,0x06;//设置周
v_W1302(0x88,0x01;//设置月
v_W1302(0x86,0x13;//设置日
v_W1302(0x84,0x18;//设置小时
v_W1302(0x82,0x05;//设置分
v_W1302(0x80,0x00;//启动晶振,设置秒
v_W1302(0x8e,0x80;//使能
}
/*****************************
*功能:
往DS1302写入1Byte数据
*输入:
wr_data写入的数据
*返回值:
无
*******************************/
voidwr_1302(ucharwr_data
{
uchari=0;
dat=wr_data;
rst_1302=1;
clk_1302=0;
delay(5;
for(i=0;i<8;i++
{
io_1302=dat0;
clk_1302=0;
_nop_(;
clk_1302=1;
_nop_(;
dat>>=1;
}
//rst_1302=0;
}
/*****************************
*功能:
从DS1302读出1Byte数据
*返回值:
dat
*******************************/
ucharrd_1302(void
{
uchari;
rst_1302=1;
clk_1302=1;
delay(5;
for(i=0;i<8;i++
{
dat>>=1;
dat7=io_1302;
clk_1302=1;
_nop_(;
_nop_(;
clk_1302=0;
_nop_(;
}
rst_1302=0;
returndat;
}
/********************************************************************
*名称:
uc_R1302
*说明:
先写地址,后读命令/数据
*功能:
读取DS1302某地址的数据
*调用:
v_RTInputByte(,uc_RTOutputByte(
*输入:
ucAddr:
DS1302地址
*返回值:
ucDa:
读取的数据
***********************************************************************/
ucharuc_R1302(ucharadd
{
uchartemp=0xff;
wr_1302(add;
temp=rd_1302(;
returntemp;
}
/********************************************************************
*名称:
v_W1302
*说明:
先写地址,后写命令/数据
*功能:
往DS1302写入数据
*调用:
v_RTInputByte(
*输入:
ucAddr:
DS1302地址,ucDa:
要写的数据
*返回值:
无
**********************************************************************/
voidv_W1302(ucharucAddr,ucharucDa
{
wr_1302(ucAddr;
wr_1302(ucDa;
rst_1302=0;
clk_1302=0;
}
//1602液晶初始化
voidinit1602(
{
lcdrw=0;//本程序只读不写,故将其置低
lcden=0;//关闭1602
delay(5;
write_cmd_1602(0x01;//清屏
write_cmd_1602(0x38;//显示模式
write_cmd_1602(0x0c;//开显示,不显示光标,不闪烁
write_cmd_1602(0x06;//地址指针自动加1
write_cmd_1602(0x80+1;//将光标指向第一行第二个位置
delay(5;
}
voiddelay(uintz
{
uintx,y;
for(x=z;x>0;x--
for(y=110;y>0;y--;
}
/**将发送的数据进行翻转,高位到低位,低位转到高位**/
ucharreverse(ucharc
{
ucharchbuff=0;
if(c&0x01chbuff=chbuff|0x80;
if(c&0x02chbuff=chbuff|0x40;
if(c&0x04chbuff=chbuff|0x20;
if(c&0x08chbuff=chbuff|0x10;
if(c&0x10chbuff=chbuff|0x08;
if(c&0x20chbuff=chbuff|0x04;
if(c&0x40chbuff=chbuff|0x02;
if(c&0x80chbuff=chbuff|0x01;
returnchbuff;
}
//向液晶写命令
voidwrite_cmd_1602(ucharcmd
{
lcdrs=0;//低表示写命令,高表示写数据
delay(5;
P0=reverse(cmd;
delay(5;
lcden=1;//给一个高脉冲
delay(5;
lcden=0;
delay(5;
}
//向液晶写数据
voidwrite_data_1602(uchardat
{
lcdrs=1;//低表示写命令,高表示写数据
delay(5;
P0=reverse(dat;
delay(5;
lcden=1;//给一个高脉冲
delay(5;
lcden=0;
delay(5;
}
//根据地址向液晶写数据
voidwrite_add(ucharadd,uchardat
{
ucharshi,ge;
shi=dat/10;
ge=dat%10;
delay(5;
write_cmd_1602(0x80+add;
write_data_1602(shi+0x30;
delay(5;
write_data_1602(ge+0x30;
}
//键盘扫描函数
voidkeyscan(
{
key4=0;
if(0==key0//第一个键被按下
{
delay(5;//消抖
if(0==key0
{
key0_count++;
if(4==key0_count
{
key0_count=0;
flag=1;
}
while(!
key0;//松手检测
flag=0;
if(0==key0_count
{
flag=0;
write_cmd_1602(0x0c;//禁止显示光标并不让其闪烁
}
if(1==key0_count
{
flag=0;
write_cmd_1602(0x80+0x40+11;//将地址指针指向秒的位置
write_cmd_1602(0x0f;//显示光标并闪烁
delay(5;
}
if(2==key0_count
{
flag=0;
write_cmd_1602(0x80+0x40+8;//将地址指针指向分的位置
write_cmd_1602(0x0f;//显示光标并闪烁
delay(5;
}
if(3==key0_count
{
flag=0;
write_cmd_1602(0x80+0x40+5;//将地址指针指向小时的位置
write_cmd_1602(0x0f;//显示光标并闪烁
delay(5;
}
}
}
if(0==key1//第二个键被按下
{
delay(5;//消抖
if(0==key1
{
while(!
key1;//松手检测
flag=0;
if(key0_count==1
{
second++;
if(60==second