本篇为DS1302搭配数码管动态显示
段码表:
u8 code t_display[]={ //标准字库
// 0 1 2 3 4 5 6 7 8 9 A B C D E F
0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71,
//black - H J K L N o P U t G Q r M y
0x00,0x40,0x76,0x1E,0x70,0x38,0x37,0x5C,0x73,0x3E,0x78,0x3d,0x67,0x50,0x37,0x6e,
0xBF,0x86,0xDB,0xCF,0xE6,0xED,0xFD,0x87,0xFF,0xEF,0x46}; //0. 1. 2. 3. 4. 5. 6. 7. 8. 9. -1
u8 code T_COM[]={0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80}; //位码
可在stc-isp中找到,不用记
具体步骤可以再数码管那篇公众号看,这里发个截图。
DS1302文件处理:
STEP1:将ds1302复制到当前目录下并加入文件到工程
STEP2:修改ds1302.h文件,把ds1302.c中所有函数复制黏贴进去
DS1302处理时间步骤:
1、在程序的开始写读取数据的地址数组、写数据的地址数组、存储时间变量的数组
读取数据的地址数组:
unsigned char code Read_addr[]={0x81,0x83,0x85,0x87,0x89,0x8b,0x8d,0x8f};
写数据的地址数组:
unsigned char code Write_addr[]={0x80,0x82,0x84,0x86,0x88,0x8a,0x8c,0x8e};
存储时间变量的数组:(顺序为秒分时日月)
unsigned char Time[]={0x57,0x59,0x23,0x31,0x12};//自行定义初始值,顺序为秒分时日月
2、写时间(在初始化部分完成,即在void main中的while(1)外部)
3、读取时间
DS1302写时间步骤:
1、往0x8e中写0x00
2、写时间(使用循环),更新存储时间变量的数组中
3、往0x8e中写0x80
void ds1302_config()
{
unsigned char i;
Write_Ds1302_Byte(0x8e,0x00);
for(i=0;i<5;i++)
{
Write_Ds1302_Byte(Write_addr[i],Time[i]);
}
Write_Ds1302_Byte(0x8e,0x80);
}
DS1302读取时间步骤:
1、读取时间(使用循环),更新存储时间变量的数组中
void ds1302()
{
unsigned char i;
for(i=0;i<5;i++)
{
Time[i]=Read_Ds1302_Byte(Read_addr[i]);
}
}
总体代码展示:(main.c)
#include "reg52.h"
#include "intrins.h"
#include "ds1302.h"
unsigned char code Read_addr[]={0x81,0x83,0x85,0x87,0x89,0x8b,0x8d,0x8f};
unsigned char code Write_addr[]={0x80,0x82,0x84,0x86,0x88,0x8a,0x8c,0x8e};
unsigned char Time[]={0x57,0x59,0x23,0x31,0x12};
/************* 本地常量声明 **************/
unsigned char code t_display[]={ //标准字库
// 0 1 2 3 4 5 6 7 8 9 A B C D E F
0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71,
//black - H J K L N o P U t G Q r M y
0x00,0x40,0x76,0x1E,0x70,0x38,0x37,0x5C,0x73,0x3E,0x78,0x3d,0x67,0x50,0x37,0x6e,
0xBF,0x86,0xDB,0xCF,0xE6,0xED,0xFD,0x87,0xFF,0xEF,0x46}; //0. 1. 2. 3. 4. 5. 6. 7. 8. 9. -1
void InitSys();
void SelectHC138(unsigned char channel,unsigned char dat);
void Delay1ms();
void SMG_bit(unsigned char pos,unsigned char dat);
void SMG_1();
void ds1302();
void ds1302_config();
void main()
{
InitSys();
ds1302_config();
while(1)
{
ds1302();
SMG_1();
}
}
void SelectHC138(unsigned char channel,unsigned char dat)
{
P0=dat;
switch(channel)
{
case 0:
P2=(P2&0x1f)|0x00;
break;
case 4:
P2=(P2&0x1f)|0x80;
break;
case 5:
P2=(P2&0x1f)|0xa0;
break;
case 6:
P2=(P2&0x1f)|0xc0;
break;
case 7:
P2=(P2&0x1f)|0xe0;
break;
}
P2=(P2&0x1f)|0x00;
}
void InitSys()
{
SelectHC138(4,0xff);
SelectHC138(5,0x00);
SelectHC138(6,0xff);
SelectHC138(7,0xff);
SelectHC138(0,0x00);
}
void SMG_bit(unsigned char pos,unsigned char dat)
{
SelectHC138(6,0x01<<pos);
SelectHC138(7,dat);
Delay1ms();
SelectHC138(7,0xff);
}
void Delay1ms() //@11.0592MHz
{
unsigned char i, j;
_nop_();
_nop_();
_nop_();
i = 11;
j = 190;
do
{
while (--j);
} while (--i);
}
void SMG_1()
{
SMG_bit(7,~t_display[Time[0]%16]);
SMG_bit(6,~t_display[Time[0]/16]);
SMG_bit(5,~(0x40));
SMG_bit(4,~t_display[Time[1]%16]);
SMG_bit(3,~t_display[Time[1]/16]);
SMG_bit(2,~(0x40));
SMG_bit(1,~t_display[Time[2]%16]);
SMG_bit(0,~t_display[Time[2]/16]);
}
void ds1302_config()
{
unsigned char i;
Write_Ds1302_Byte(0x8e,0x00);
for(i=0;i<5;i++)
{
Write_Ds1302_Byte(Write_addr[i],Time[i]);
}
Write_Ds1302_Byte(0x8e,0x80);
}
void ds1302()
{
unsigned char i;
for(i=0;i<5;i++)
{
Time[i]=Read_Ds1302_Byte(Read_addr[i]);
}
}
易错点:
1、只有往ds1302中写数据的时候才需要对WP位进行操作
2 、WP置0才是写允许,WP置1是保护状态
3、读取出来的数据用数码管显示的时候用的是%16和/16
作者的话:
本系列不是教学篇,为速通版。因此涉及打破砂锅问到底的逻辑部分较少。
C语言教程可移步曾经发过的C语言速通教程。
有建议欢迎指出,也欢迎友好交流!
另也欢迎关注其他平台上本人的账号 如下:
知乎:youzuos
微信公众号:知识薪火站
感谢支持!