小白最近想用51+lcd1602+ds3231做一个时钟,由于编程实在菜,只好先用
proteus来
仿真提高成功率,无奈proteus里面没有ds3231只有ds3232,看了一下资料两个
芯片编程可以直接移植,于是就用了24c02的程序结合ds3231来修改。结果发现了问题,时钟的时、分、秒都能读出来,但是显示的位置不对,如下图:
把几段相关程序贴出来,大神们帮看看是哪出错了
/********************************************************************
* 名称 : flash()
* 功能 : 延时,时间为2个NOP,大概为2US
* 输入 : 无
* 输出 : 无
***********************************************************************/
void flash(void)
{
_nop_();
_nop_();
}
/********************************************************************
* 名称 : IIC_init()
* 功能 : IIC初始化子程序
* 输入 : 无
* 输出 : 无
***********************************************************************/
void IIC_init(void)
{
scl = 1;
flash();
sda = 1;
flash();
}
/********************************************************************
* 名称 : start(void)
* 功能 : 启动IIC总线
* 输入 : 无
* 输出 : 无
***********************************************************************/
void start(void)
{
scl = 1;
flash();
sda = 1;
flash();
sda = 0;
flash();
scl = 0;
flash();
}
/********************************************************************
* 名称 : stop()
* 功能 : 停止I2C总线
* 输入 : 无
* 输出 : 无
***********************************************************************/
void stop()
{
scl = 0;
flash();
sda = 0;
flash();
scl = 1;
flash();
sda = 1;
flash();
}
/********************************************************************
* 名称 : writex()
* 功能 : 写一个字节
* 输入 : j(需要写入的值)
* 输出 : 无
***********************************************************************/
void writex(uchar j)
{
uchar i,temp;
temp = j;
for(i=0; i<8; i++)
{
scl = 0;
flash();
sda = (bit)(temp & 0x80);
flash();
scl = 1;
flash();
temp = temp << 1;
}
scl = 0;
flash();
}
/********************************************************************
* 名称 : readx()
* 功能 : 读一个字节
* 输入 : 无
* 输出 : 读出的值
***********************************************************************/
uchar readx(void)
{
uchar i, j, k = 0;
for(i=0; i<8; i++)
{
scl = 1;
flash();
if(sda == 1)
{
j = 1;
}
else j = 0;
k = (k << 1) | j;
scl = 0;
flash();
}
return(k);
}
/********************************************************************
* 名称 : ack()
* 功能 : I2C总线时钟
* 输入 : 无
* 输出 : 无
***********************************************************************/
void ack(void)
{
uchar i = 0;
scl = 1;
flash();
while((sda == 1) && (i < 255))
{
i++;
}
scl = 0;
flash();
}
/********************************************************************
* 名称 : IIC_read()
* 功能 : 从IIC中读出值
* 输入 : address(要在这个地址读取值)
* 输出 : 从IIC中读出的值
***********************************************************************/
uchar IIC_read(uchar address)
{
uchar i;
start();
writex(0xd0);
ack();
writex(address);
ack();
stop();
start();
writex(0xd1);
ack();
i = readx();
stop();
return(i);
}
/********************************************************************
* 名称 : IIC_write()
* 功能 : 想IIC中写入数据
* 输入 : address(地址) , info(值)
* 输出 : 无
***********************************************************************/
void IIC_write(uchar address, uchar info)
{
start();
writex(0xd0);
ack();
writex(address);
ack();
writex(info);
ack();
stop();
}
/********************************************************************
* 名称 : B2H()
* 功能 : BCD转Hex
* 输入 : val(值)
* 输出 : 无
***********************************************************************/
uchar B2H(uchar val)
{
uchar temp;
temp=val&0x0f;
val>>=4;
val&=0x0f;
val*=10;
temp+=val;
return (temp);
}
/********************************************************************
* 名称 : H2B()
* 功能 : Hex转BCD
* 输入 : val(值)
* 输出 : 无
***********************************************************************/
uchar H2B(uchar val)
{
uchar i,j,k;
i=val/10;
j=val%10;
k=j+(i<<4);
return k;
}
/********************************************************************
* 名称 : read_
time()
* 功能 : 读取时间并显示
* 输入 :
* 输出 : 无
***********************************************************************/
void read_time() //当hou、min、sec三段程序位置互换时,显示的位置也会变化
{
hou0=IIC_read(0x02);
hou0&=0x3f;
hou1=B2H(hou0);
LCD_write_command(0x80);
LCD_write_data(hou1/10+0x30);
LCD_write_command(0x81);
LCD_write_data(hou1%10+0x30);
min0=IIC_read(0x01);
min1=B2H(min0);
LCD_write_command(0x83);
LCD_write_data(min0/10+0x30);
LCD_write_command(0x84);
LCD_write_data(min0%10+0x30);
sec0=IIC_read(0x00);
sec1=B2H(sec0);
LCD_write_command(0x86);
LCD_write_data(sec1/10+0x30);
LCD_write_command(0x87);
LCD_write_data(sec1%10+0x30);
}
/********************************************************************
* 名称 : write_time()
* 功能 : 写入初始时间
* 输入 : hou(时),min(分),sec(秒)
* 输出 : 无
***********************************************************************/
void write_time(uchar hou,uchar min,uchar sec)
{
uchar temp;
temp=H2B(hou);
IIC_write(0x02,temp); //修改时
temp=H2B(min);
IIC_write(0x01,temp); //修改分
temp=H2B(sec);
IIC_write(0x00,temp); //修改秒
}
void main()
{
LCD_init();
IIC_init();
for(i=0;i<13;i++)
LCD_disp_char(i,1,date0
); //显示两个“:”
write_time(4,30,22);
while(1)
{
read_time();
delay(10);
}
}
一周热门 更多>