新闻中心

EEPW首页 > 嵌入式系统 > 设计应用 > DS1302时钟芯片显示时间C51程序

DS1302时钟芯片显示时间C51程序

作者:时间:2012-11-10来源:网络

/*
程序效果:通过芯片,本程序主要是要理解
    芯片的协议,这样便于编写程序。
    当然时间显示也可以用单片机的定时器来控制,比起延时
    子函数来说较精准。
*/
#includereg52.h> //头文件
#includeintrins.h>
#define uchar unsigned char //宏定义
sbit scl2=P1^3; //位声明
sbit sda2=P1^4;
sbit rst2=P1^5;
uchar tmpdata[8]={0x00,0x3b, //显示的时间值
0x17,0x1f,0x0c,0x08,0x09,0x00};
uchar tmpdisplay[8];
code uchar write_rtc_address[7]={ //写入时间的地址
0x80,0x82,0x84,0x86,0x88,0x8a,0x8c};
code uchar read_rtc_address[7]={ //读取时间的地址
0x81,0x83,0x85,0x87,0x89,0x8b,0x8d};
code unsigned char table[]={
0x3f,0x06,0x5b,0x4f,0x66,
0x6d,0x7d,0x07,0x7f,0x6f, //共阴数码管 0-9
0x40,0x00}; // '-' '熄灭‘表
void delay();
void display(uchar *lp,uchar lc); //显示子函数
void write_ds1302(uchar address,uchar dat); //写子函数
uchar read_ds1302(uchar address);//读子函数
void read_rtc();
void set_rtc();
void main()
{
  rst2=0;
  set_rtc();
  while(1)
  {
    read_rtc();
    switch(tmpdata[0]/5) // 设计每隔5秒交替显示年月日 时分秒
    {  
      case 0: //显示时分秒
      case 2:
      case 4:
      case 6:
      case 8:
      case 10:
          tmpdisplay[0]=tmpdata[2]/16;
          tmpdisplay[1]=tmpdata[2]0x0f;
          tmpdisplay[2]=10; //在时与分之间加一个“-”
          tmpdisplay[3]=tmpdata[1]/16;
          tmpdisplay[4]=tmpdata[1]0x0f;
          tmpdisplay[5]=10;
          tmpdisplay[6]=tmpdata[0]/16;
          tmpdisplay[7]=tmpdata[0]0x0f;
          break;
      case 1: //显示年月日
      case 3:
      case 5:
      case 7:
      case 9:
      case 11:
          tmpdisplay[0]=tmpdata[6]/16;
          tmpdisplay[1]=tmpdata[6]0x0f;
          tmpdisplay[2]=10;
          tmpdisplay[3]=tmpdata[4]/16;
          tmpdisplay[4]=tmpdata[4]0x0f;
           tmpdisplay[5]=10;
          tmpdisplay[6]=tmpdata[3]/16;
          tmpdisplay[7]=tmpdata[3]0x0f;
          break;
      default :
        break;
      }
    display(tmpdisplay,8);
  }
}
void display(uchar *lp,uchar lc) //lp为数组的首地址,lc为显示的个数
{
  uchar i; //定义局部变量
  P2=0; //清零端口,准备显示
  P1=P10xf8; //不影响P1口的高5位,低三位用于控制哪个数码管亮
  for(i=0;ilc;i++) //循环显示
  {
    P2=table[lp[i]];//查表获得相应的数值
    delay(); //延时,使数码管更加亮
    P2=0; //清零端口,准备显示下一位
    P1++; //点亮下一个数码管
  }
}
void delay() //延时子函数
{
  uchar i; //i的值的大小可以决定数码管的亮暗的程度
  for(i=20;i>0;i--); //但i的值要适中,并不是越大越好
}
void write_ds1302_byte(uchar temp) //写子函数
{
  uchar i;
  for(i=0;i8;i++) //循环8次,写入数据
  {
    scl2=0;
    sda2=temp0x01; //每次传输低字节
    temp>>=1; //右移一位
    scl2=1;
  }
}
void write_ds1302(uchar address,uchar dat) //根据ds1302协议编写的程序
{
  rst2=0;
  _nop_();
  scl2=0;
  _nop_();
  rst2=1;
  _nop_(); //从此后开始发送数据
  write_ds1302_byte(address);//发送地址
  write_ds1302_byte(dat); //发送数据
  rst2=0; //停止发送数据
}
uchar read_ds1302(uchar address) //根据ds1302编写的程序
{
  uchar i,temp=0;
  rst2=0;
  _nop_();
  scl2=0;
  _nop_();
  rst2=1;
  _nop_();
  write_ds1302_byte(address);
  for(i=0;i8;i++) //循环8次,读取数据
  {
    scl2=1;
    _nop_();
    if(sda2)
    temp|=0x80;//每次传输低字节
    scl2=0;
    temp>>=1; // 右移一位
  }
  rst2=0;
  _nop_();
  scl2=1;
  sda2=0;
  return temp; //返回 temp值
}
void read_rtc() //读取日历
{
  uchar i,*p;
  p=read_rtc_address; //传递地址
  for(i=0;i7;i++) //分七次读取年月日 时分秒 星期
  {
    tmpdata[i]=read_ds1302(*p);
    p++;
  }
}
void set_rtc() //设定日历
{
  uchar i,*p,tmp;
  for(i=0;i7;i++)
{
  tmp=tmpdata[i]/10;
  tmpdata[i]=tmpdata[i]%10;
  tmpdata[i]=tmpdata[i]+tmp*16;
}
  write_ds1302(0x8e,0x00);

  p=write_rtc_address; //传递地址
   for(i=0;i7;i++) //分七次写入年月日 时分秒星期
  {
    write_ds1302(*p,tmpdata[i]);
    p++;
  }
  write_ds1302(0x8e,0x80);
}

万能遥控器相关文章:万能遥控器代码




评论

技术专区

关闭