173 2438 5004
KEROS加密芯片——品牌直销 | 免费样品 | 技术支持
当前位置:网站首页 > 资讯中心 正文 资讯中心

单片机显示冒号

htxw 2023-03-05 资讯中心 28 ℃

有关单片机的几个问题!跪求高手回答

1.是个循环,而且是个死循环。他在单片机中是常要用到的,功能就是只要单片机上电它使程序不停里执行死循环里的内容!

2.这个看你的单片机的硬件电路了,你最好也先看懂硬件电路才编程。通常LED的公共端是用三极管选通的!看来你的LED是共阳极接法的,就是8个LED正极共同接到三极管的发射极,集电极接VCC,基极连到P1口的接法,如果你会三极管,应该就能看懂为什么了!P1=0,三极管正向导通,VCC加到LED上,如果LED的另一端接的是低电平,使LED正偏,则LED亮。想想吧~~

3。CPU不停地执行while(1)里面的语句,但是当有中断发生时,CPU得先去执行中断,然后才能返回到while处继续执行,也就相当等待中断了!也就是说:有中断发生CPU就立该执行中断,没有的话就一直执行while(1)里面的~~

单片机程序中;----------是什么意思了,为什么有的在RET后,有的却不是,不是冒号后是解释吗?

;----------

这就是注释,注释不一定非要写文字吗,只要是分号,后面就是注释,这样的注释也是很常见的,可以把程序分成几部分,或分成几段,这样看起来,比较清楚。这还不好理解吗?

用汇编语言做单片机时钟显示

基于c8051f020单片机最小系统的实时时钟显示程序

c8051f020 FYD12864-0402B LCD显示,按键电子时钟//

#include c8051f020.h

#includelcd.h

#include intrins.h

#define uchar unsigned char

void lcd_ini();

void DISPInitial();

void ascii_change(void);

void delay();

void wri_add(uchar com);

void wri_dat(uchar com1);

void shan(void);

void disp();

void tkey(void);

void PORT_Init (void);

sbit cs=P1^7;

sbit sid=P1^6;

sbit sclk=P1^5;

bit flag=1;

uchar dat,count,f=1;//f测试哪个单元为当前闪烁状态

uchar data clock[3]={24,00,00};

uchar code clockname[10]={"北京时间:"};

uchar data num[6];

/*******主程序*************/

void main()

{

lcd_ini();

count=10;//机器周期为1us,每次定时50ms,此变量用来控制循环次数,在下面赋值为20,共定时1秒

TMOD=0x01;

TL0=0XB0;

TH0=0X3C;

EA=1;

ET0=1;

IT0=1;

EX0=1;

TR0=1;

while(1)

{

back:ascii_change();

disp();

delay();

if(flag==1)

goto back;

tkey();

shan();

delay();

}

}

/****lcd初始化*******/

/*void lcd_ini()

{

wri_add(0x30);

delay();

wri_add(0x0c);

delay();

wri_add(0x01);

delay();

wri_add(0x06);

delay();

}*/

void PORT_Init (void)

{

XBR0 = 0x00; //不让他连上IO口

XBR1 = 0x14; //允许外部中断连在端口上

XBR2 = 0x40; // Enable crossbar and weak pull-ups

P0MDOUT |= 0x00; // enable TX0 as a push-pull output

// P1MDOUT |= 0x07; // enable P1.6 (LED) as push-pull output

P2MDOUT=0xfe; //为了驱动步进电机的控制线

//P3MDOUT = 0xFF;

P74OUT=0x00; //配置成漏极方式可以让LCD显示成功 ,我试了配置成推挽方式不能正常显示

}

/********定时程序*************/

void timer1() interrupt 1 using 2

{

TL0=0XB0;

TH0=0X3C;

count--;

if(count==0)

{

count=10;

clock[2]++;//秒//

}

else

goto out;

if(clock[2]==60)

{

clock[2]=0;

clock[1]++;//分//

}

if(clock[1]==60)

{

clock[1]=0;

clock[0]++;

}

if(clock[0]==24)//时//

clock[0]=0;

out:_nop_();

}

/*******十位个位转换成ASCII码************/

void ascii_change(void)

{

num[5]=clock[2]-(clock[2]/10)*10+0x30;

num[4]=clock[2]/10+0x30;

num[3]=clock[1]-(clock[1]/10)*10+0x30;

num[2]=clock[1]/10+0x30;

num[1]=clock[0]-(clock[0]/10)*10+0x30;

num[0]=clock[0]/10+0x30;

}

/********廷时程序*************/

void delay()

{

uchar i,j;

for (i=250;i0;i--)

for (j=250;j0;j--);

}

/*****Write address*********/

void wri_add(uchar com)

{

uchar i,j,k;

cs=0;

cs=1;

dat=0xf8;

for(i=1;i=8;i++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

dat=com;

dat=dat0xf0;

for(j=1;j=8;j++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

dat=com;

dat=_cror_(dat,4);// 此为高低四位交换

dat=dat0xf0;

for(k=1;k=8;k++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

}

/*********Write data*************/

void wri_dat(uchar com1)

{

uchar i,j,k;

cs=0;

cs=1;

dat=0xfa;

for(i=1;i=8;i++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

dat=com1;

dat=dat0xf0;

for(j=1;j=8;j++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

dat=com1;

dat=_cror_(dat,4);// 此为高低四位交换

dat=dat0xf0;

for(k=1;k=8;k++)

{

sid=(bit)(dat0x80);

sclk=0;

sclk=1;

sclk=0;

dat=dat1;

}

}

/******display program***********/ //显示时间

void disp()

{

uchar i,k=0;

wri_add(0x80);

for (i=1;i=9;i++)

wri_dat(clockname[i-1]);

wri_add(0x90);

for (i=1;i=6;i++)

{

k++;

if(k==3||k==5)

wri_dat(clockname[8]);//时间之间的冒号。

wri_dat(num[i-1]);

}

}

/*******闪烁程序*************************/

void shan(void)

{

uchar i,k=0;

wri_add(0x90);

if(f==1)

{

num[0]=' ';

num[1]=' ';

}

else

goto next;

for (i=1;i=6;i++)

{

k++;

if(k==3||k==5)

wri_dat(clockname[8]);//时间之间的冒号。

wri_dat(num[i-1]);

}

goto return1;

next: if(f==2)

{

num[2]=' ';

num[3]=' ';

}

else

goto next1;

for (i=1;i=6;i++)

{

k++;

if(k==3||k==5)

wri_dat(clockname[8]);//时间之间的冒号。

wri_dat(num[i-1]);

}

goto return1;

next1: if(f==3)

{

num[4]=' ';

num[5]=' ';

}

else

goto return1;

for (i=1;i=6;i++)

{

k++;

if(k==3||k==5)

wri_dat(clockname[8]);//时间之间的冒号。

wri_dat(num[i-1]);

}

return1:_nop_();

}

/*******外部中断***********/

void intr0() interrupt 0 using 2

{

flag=~flag;//判断是否闪烁位//

TR0=~TR0; //闪关定时否则开定时

f=1;

}

/**********按键程序************/

void tkey(void)

{

uchar judcekey;

judcekey=P10x0f;

if(judcekey==0x0f)

goto return2;

/*******移位键*********/

if (judcekey==0x0e)

f++;

if (f==4)

f=1;

/**********加一键*********/

if(judcekey==0x0d)

{clock[f-1]++;}

if (f==1)

{ if (clock[f-1]==24){

clock[f-1]=0;}

}

else{ if (clock[f-1]==60)

clock[f-1]=0;

}

/******减一键***********/

if(judcekey==0x0b)

{clock[f-1]--;}

if (f==1)

{ if (clock[f-1]==0xff){

clock[f-1]=23;}

}

else

{ if (clock[f-1]==0xff)

clock[f-1]=59;

}

return2:_nop_();

}

//本程序已经调试成功并能够正确执行

关于51单片机若干的问题,急。。。。。

//实际晶振为11.0592MHz

//为方便计算,假设为12MHz

#includereg52.h //包含52单片机头文件

#define uchar unsigned char //宏定义

#define uint unsigned int //红定义

//#include24c02.h

sbit dula=P2^6; //定义锁存器锁存端

sbit wela=P2^7;

sbit rs=P3^5; //定义1602液晶RS端

sbit lcden=P3^4; //定义1602液晶LCDEN端

sbit s1=P3^0; //定义按键——功能键

sbit s2=P3^1; //定义按键——增大键

sbit s3=P3^2; //定义按键——减小键

//sbit s4=P3^6; //闹钟查看器

sbit rd=P3^7;

sbit beep=P2^3; //蜂鸣器

sbit dscs=P1^4;

sbit dsas=P1^5;

sbit dsrw=P1^6;

sbit dsds=P1^7;

sbit dsirq=P3^3;

bit flag1,flag_ri; //定义两个位变量

uchar count,s1num,flag,t0_num; //其他变量定义

char miao,fen,shi,day,month,year,week,amiao,afen,ashi;

uchar code table[]=" 20 - - "; //定义初始上电时液晶默认显示状态

//uchar code table1[]=" : : ";

void write_ds(uchar,uchar); //函数声明

uchar read_ds(uchar);

void set_time();

void delay(uint z) //延时函数

{

uint x,y;

for(x=z;x0;x--)

for(y=110;y0;y--);

}

void di() //蜂鸣器报警声音

{

beep=0;

delay(100);

beep=1;

}

void write_com(uchar com) //写液晶命令函数

{

rs=0;

lcden=0;

P0=com;

delay(5);

lcden=1;

delay(5);

lcden=0;

}

void write_date(uchar date) //写液晶数据函数

{

rs=1;

lcden=0;

P0=date;

delay(5);

lcden=1;

delay(5);

lcden=0;

}

void write_sfm(uchar add,uchar date) //写时分秒函数

{

uchar shi,ge;

shi=date/10; //分解一个2位数的十位和个位

ge=date%10;

write_com(0x80+0x40+add); //设置显示位置

write_date(0x30+shi); //送去液晶显示十位

write_date(0x30+ge); //送去液晶显示个位

}

void write_nyr(uchar add,uchar date) //写年月日函数

{

uchar shi,ge;

shi=date/10; //分解一个2位数的十位和个位

ge=date%10;

write_com(0x80+add); //设置显示位置

write_date(0x30+shi); //送去液晶显示十位

write_date(0x30+ge); //送去液晶显示个位

}

void write_week(char we)

{ //写液晶星期显示函数

write_com(0x80+12);

switch(we)

{

case 1: write_date('M');

delay(5);

write_date('O');

delay(5);

write_date('N');

break;

case 2: write_date('T');

delay(5);

write_date('U');

delay(5);

write_date('E');

break;

case 3: write_date('W');

delay(5);

write_date('E');

delay(5);

write_date('D');

break;

case 4: write_date('T');

delay(5);

write_date('H');

delay(5);

write_date('U');

break;

case 5: write_date('F');

delay(5);

write_date('R');

delay(5);

write_date('I');

break;

case 6: write_date('S');

delay(5);

write_date('A');

delay(5);

write_date('T');

break;

case 7: write_date('S');

delay(5);

write_date('U');

delay(5);

write_date('N');

break;

}

}

void init() //初始化函数

{

uchar num;

rd=0; //软件将矩阵按键第四列一端置低用以分解出独立按键

dula=0; //关闭两锁存器锁存端,防止操作液晶时数码管出现乱码

wela=0;

lcden=0;

fen=0; //初始化分钟变量值

miao=0;

shi=0;

day=1;

month=1;

year=12;

week=1;

count=0;

s1num=0;

// init_24c02();

//一下几行在首次设置DS12C887时使用,以后不必在写入

// write_ds(0x0A,0x20); //打开振荡器

// write_ds(0x0B,0x26); //设置24小时模式,数据二进制格式 ,开启闹铃中断

set_time(); //设置上电默认时间

write_com(0x38); //初始化1602液晶

write_com(0x0c);

write_com(0x06);

write_com(0x01);

write_com(0x80); //设置显示初始坐标

for(num=0;num15;num++) //显示年月日星期

{

write_date(table[num]);

delay(5);

}

/* for(num=0;num12;num++)

{

write_date(table1[num]);

delay(5);

}

*/

write_com(0x80+0x40+6); //写出时间显示部分的两个冒号

write_date(':');

delay(5);

write_com(0x80+0x40+9);

write_date(':');

delay(5);

// miao=read_add(1);

// fen=read_add(2);

// shi=read_add(3);

write_sfm(10,miao);

write_sfm(7,fen);

write_sfm(4,shi);

write_nyr(9,day);

write_nyr(6,month);

write_nyr(3,year);

write_week(week);

TMOD=0x01; //设置定时器0工作模式1

TH0=(65536-50000)/256; //定时器装初值

TL0=(65536-50000)%256;

EA=1; //开总中断

ET0=1; //开定时器0中断

TR0=1; //启动定时器0

}

void keyscan() //按键扫描函数

{

// rd=0; //前面已定义

if(s1==0)

{

delay(5);

if(s1==0) //确认功能键被按下

{ s1num++; //功能键按下次数记录

while(!s1); //释放确认

di(); //每当有按键释放蜂鸣器发出滴声

if(s1num==1) //第一次被按下时

{

TR0=0; //关闭定时器

write_com(0x80+0x40+10); //光标定位到秒位置

write_com(0x0f); //光标开始闪烁

}

if(s1num==2) //第二次按下光标闪烁定位到分钟位置

{

write_com(0x80+0x40+7);

}

if(s1num==3) //第三次按下光标闪烁定位到小时位置

{

write_com(0x80+0x40+4);

}

if(s1num==4) //第四次按下光标闪烁定位到日期位置

{

write_com(0x80+9);

}

if(s1num==5) //第五次按下光标闪烁定位到月份位置

{

write_com(0x80+6);

}

if(s1num==6) //第六次按下光标闪烁定位到年份位置

{

write_com(0x80+3);

}

if(s1num==7) //第七次按下光标闪烁定位到年份位置

{

write_com(0x80+12);

}

if(s1num==8) //第八次按下

{

s1num=0; //记录按键数清0

write_com(0x0c); //取消光标闪烁

TR0=1; //启动定时器使时钟走

}

flag=0;

write_ds(0,miao);

write_ds(2,fen);

write_ds(4,shi);

write_ds(6,week);

write_ds(7,day);

write_ds(8,month);

write_ds(9,year);

// break;

}

}

if(s1num!=0) //只有功能键被按下后,增大和减小键才有效

{

if(s2==0)

{

delay(5);

if(s2==0) //增大键确认被按下

{

while(!s2); //按键释放

di(); //每当有按键释放蜂鸣器发出滴声

if(s1num==1) //若功能键第一次按下

{

miao++; //则调整秒加1

if(miao==60) //若满60后将清0

miao=0;

write_sfm(10,miao); //每调节一次送液晶显示一下

write_com(0x80+0x40+10); //显示位置重新回到调节处

// write_add(1,miao); //数据改变立即存入24C02

}

if(s1num==2) //若功能键第二次按下

{

fen++; //则调整分钟加1

if(fen==60) //若满60后将清0

fen=0;

write_sfm(7,fen); //每调节一次送液晶显示一下

write_com(0x80+0x40+7); //显示位置重新回到调节处

// write_add(2,fen);

}

if(s1num==3) //若功能键第三次按下

{

shi++; //则调整小时加1

if(shi==24) //若满24后将清0

shi=0;

write_sfm(4,shi);//每调节一次送液晶显示一下

write_com(0x80+0x40+4); //显示位置重新回到调节处

// write_add(3,shi); //数据改变立即存入24C02

}

if(s1num==4) //若功能键第四次按下

{

day++; //则调整日期加1

if(day==32) //若满31后将清0

day=1;

write_nyr(9,day);//每调节一次送液晶显示一下

write_com(0x80+9); //显示位置重新回到调节处

// write_add(9,day); //数据改变立即存入24C02

}

if(s1num==5) //若功能键第五次按下

{

month++; //则调整月份加1

if(month==13) //若满12后将清0

month=1;

write_nyr(6,month);//每调节一次送液晶显示一下

write_com(0x80+6); //显示位置重新回到调节处

// write_add(6,month); //数据改变立即存入24C02

}

if(s1num==6) //若功能键第六次按下

{

year++; //则调整年份加1

if(year==33) //若满32后将返回初始年份

year=12;

write_nyr(3,year);//每调节一次送液晶显示一下

write_com(0x80+3); //显示位置重新回到调节处

// write_add(3,year); //数据改变立即存入24C02

}

if(s1num==7) //若功能键第七次按下

{

week++; //则调整年份加1

if(week==8) //若满32后将返回初始年份

week=1;

write_week(week);//每调节一次送液晶显示一下

write_com(0x80+12); //显示位置重新回到调节处

// write_add(week); //数据改变立即存入24C02

}

}

}

if(s3==0)

{

delay(5);

if(s3==0) //确认减小按键按下

{

while(!s3); //按键释放

di(); //每当有按键释放蜂鸣器发出滴声

if(s1num==1) //若功能键第一次按下

{

miao--; //则调整秒减1

if(miao==-1) //若减到负数则将其重新设置为59

miao=59;

write_sfm(10,miao); //每调节一次送液晶显示一下

write_com(0x80+0x40+10); //显示位置重新回到调节处

// write_add(1,miao); //数据改变立即存入24C02

}

if(s1num==2) //若功能键第二次按下

{

fen--; //则调整分钟减1

if(fen==-1) //若减到负数则将其重新设置为59

fen=59;

write_sfm(7,fen); //每调节一次送液晶显示一下

write_com(0x80+0x40+7); //显示位置重新回到调节处

// write_add(2,fen); //数据改变立即存入24C02

}

if(s1num==3) //若功能键第三次按下

{

shi--; //则调整小时减1

if(shi==-1) //若减到负数则将其重新设置为23

shi=23;

write_sfm(4,shi); //每调节一次送液晶显示一下

write_com(0x80+0x40+4); //显示位置重新回到调节处

// write_add(3,shi); //数据改变立即存入24C02

}

if(s1num==4) //若功能键第四次按下

{

day--; //则调整日期减1

if(day==0) //若减到0则将其重新设置为31

day=31;

write_nyr(9,day); //每调节一次送液晶显示一下

write_com(0x80+9); //显示位置重新回到调节处

// write_add(9,day); //数据改变立即存入24C02

}

if(s1num==5) //若功能键第五次按下

{

month--; //则调整月份减1

if(month==0) //若减到0则将其重新设置为12

month=12;

write_nyr(6,month); //每调节一次送液晶显示一下

write_com(0x80+6); //显示位置重新回到调节处

// write_add(6,month); //数据改变立即存入24C02

}

if(s1num==6) //若功能键第六次按下

{

year--; //则调整月份减1

if(year==11) //若减到初始值则将其重新设置为32

year=32;

write_nyr(3,year); //每调节一次送液晶显示一下

write_com(0x80+3); //显示位置重新回到调节处

// write_add(3,year); //数据改变立即存入24C02

}

if(s1num==7) //若功能键第七次按下

{

week--; //则调整月份减1

if(week==0) //若减到初始值则将其重新设置为32

week=7;

write_week(week); //每调节一次送液晶显示一下

write_com(0x80+12); //显示位置重新回到调节处

// write_add(week); //数据改变立即存入24C02

}

}

}

}

}

void write_ds(uchar add,uchar date)

{ //写12C887函数

dscs=0;

dsas=1;

dsds=1;

dsrw=1;

P0=add; //先写地址

dsas=0;

dsrw=0;

P0=date; //再写数据

dsrw=1;

dsas=1;

dscs=1;

}

uchar read_ds(uchar add)

{ //读12C887函数

uchar ds_date;

dsas=1;

dsds=1;

dsrw=1;

dscs=0;

P0=add; //先写地址

dsas=0;

dsds=0;

P0=0xff;

ds_date=P0; //再读数据

dsds=1;

dsas=1;

dscs=1;

return ds_date;

}

void set_time()

{ //首次上电初始化时间函数

write_ds(0,0);

write_ds(1,0);

write_ds(2,0);

write_ds(3,0);

write_ds(4,0);

write_ds(5,0);

write_ds(6,0);

write_ds(7,0);

write_ds(8,0);

write_ds(9,0);

}

void main() //主函数

{

init(); //首先初始化各函数

while(1) //进入主程序大循环

{

keyscan(); //不停地检测按键是否被按下

if(flag==0flag1==0) //正常工作时进入这里

{

keyscan(); //按键扫描

year=read_ds(9); //读取12C887数据

month=read_ds(8);

day=read_ds(7);

week=read_ds(6);

shi=read_ds(4);

fen=read_ds(2);

miao=read_ds(0);

write_sfm(10,miao); //送液晶显示

write_sfm(7,fen);

write_sfm(4,shi);

write_week(week);

write_nyr(3,year);

write_nyr(6,month);

write_nyr(9,day);

}

}

// while(1);

}

void timer0() interrupt 1 //定时器0中断服务程序

{

TH0=(65536-50000)/256; //再次装定时器初值

TL0=(65536-50000)%256;

count++; //中断次数累加

if(count==20) //20次50毫秒为1秒

{

count=0;

miao++;

if(miao==60) //秒加到60则进位分钟

{

miao=0; //同时秒数清0

fen++;

if(fen==60) //分钟加到60则进位小时

{

fen=0; //同时分钟数清0

shi++;

if(shi==24) //小时加到24则进位日期

{

shi=0; //同时小时数清0

day++;

if(day==31) //日期加到31则进位月份

{

day=0; //同时日期数清0

month++;

if(month==12) //月份加到12则进位年份

{

month=0; //同时月份数清0

year++;

if(year==99) //年份加到32则将年份返回初始值

{

year=0;

}

write_nyr(3,year);

// write_add(3,year); //数据改变立即存入24C02

}

write_nyr(6,month);

// write_add(6,month); //数据改变立即存入24C02

}

write_nyr(9,day);

// write_add(9,day); //数据改变立即存入24C02

}

write_sfm(4,shi); //小时若变化则重新写入

// write_add(3,shi); //数据改变立即存入24C02

}

write_sfm(7,fen); //分钟若变化则重新写入

// write_add(2,fen); //数据改变立即存入24C02

}

write_sfm(10,miao); //秒若变化则重新写入

// write_add(1,miao); //数据改变立即存入24C02

}

}

这都是我调试好用过的程序,不知道硬件连接的是不是一样,希望对你有帮助。

求教一个51单片机程序。。(LCD电子时钟)

#includereg52.h

#define uint unsigned int

#define uchar unsigned char

uchar a,miao,shi,fen,ri,yue,nian,week,flag,key1n,temp;

#define yh 0x80

#define er 0x80+0x40//液晶屏的与 C51 之间的引脚连接定义

sbit rs=P2^5;

sbit en=P2^7;

sbit rw=P2^6;//如果硬件上 rw 接地,就不用写这句和后面的 rw=0

//DS1302 时钟芯片与 C51 之间的引脚连接定义

sbit IO=P3^6;

sbit SCLK=P3^5;

sbit RST=P3^7;

sbit ACC0=ACC^0;

sbit ACC7=ACC^7;//校时按键与 C51 的引脚连接定义

sbit key1=P3^2;//设置键

sbit key2=P3^3;//加键

sbit key3=P3^4;//减键

uchar code tab1[]={"20//////////"};//年显示的固定字符

uchar code tab2[]={"LOVE ::::::"};//时间显示的固定字符

//延时函数,后面经常调用

void delay(uint xms)//延时函数,有参函数

{

uint x,y;

for(x=xms;x0;x--)

for(y=110;y0;y--);

}

/********液晶写入指令函数与写入数据函数,以后可调用**************/

write_1602com(uchar com) //****液晶写入指令函数****

{

rs=0; //数据/指令选择置为指令

rw=0; //读写选择 置为写

P0=com; //送入数据

delay(1);

en=1; //拉高使能端,为制造有效的下降沿做准备

delay(1);

en=0;

//en 由高变低,产生下降沿,液晶执行命令

}

write_1602dat(uchar dat) //***液晶写入数据函数****

{

rs=1; //数据/指令选择置为数据

rw=0; //读写选择置为写

P0=dat; //送入数据

delay(1);

en=1; //en 置高电平,为制造下降沿做准备

delay(1);

en=0; //en 由高变低,产生下降沿,液晶执行命令

}

lcd_init() //***液晶初始化函数****//

{

write_1602com(0x38); //设置液晶工作模式,意思:16*2 行显示,5*7 点阵,8 位数据

write_1602com(0x0c); //开显示不显示光标

write_1602com(0x06); //整屏不移动,光标自动右移

write_1602com(0x01); //清显示

write_1602com(yh+1); //日历显示固定符号从第一行第 1 个位置之后开始显示

for(a=0;a14;a++)

{

write_1602dat(tab1[a]); //向液晶屏写日历显示的固定符号部分

}

write_1602com(er+1);//时间显示固定符号写入位置,从第 2 个位置后开始显示

for(a=0;a12;a++)

{

write_1602dat(tab2[a]);//写显示时间固定符号,两个冒号

}

}

/***************DS1302 有关子函数********************/

void write_byte(uchar dat)//写一个字节

{

ACC=dat;

RST=1;

for(a=8;a0;a--)

{

IO=ACC0;//相当于汇编中的 RRC

SCLK=0;

SCLK=1;

ACC=ACC1;

}

}

uchar read_byte() //读一个字节

{

RST=1;

for(a=8;a0;a--)

{

ACC7=IO;

SCLK=1;

SCLK=0;

ACC=ACC1;

}

return (ACC);

}

//----------------------------------------//

void write_1302(uchar add,uchar dat) //向 1302 芯片写函数,指定写入地址,数据

{

RST=0;

SCLK=0;

RST=1;

write_byte(add);

write_byte(dat);

SCLK=1;

RST=0;

}

uchar read_1302(uchar add) //从 1302 读数据函数,指定读取数据来源地址

{

uchar temp;

RST=0;

SCLK=0;

RST=1;

write_byte(add);

temp=read_byte();

SCLK=1;

RST=0;

return(temp);

}

uchar BCD_Decimal(uchar bcd)//BCD 码转十进制函数,输入 BCD,返回十进制

{

uchar Decimal;

Decimal=bcd4;

return(Decimal=Decimal*10+(bcd=0x0F));

}

//--------------------------------------//

void ds1302_init()//1302 芯片初始化子函数(2010-01-07,12:00:00,week4)

{

RST=0;

SCLK=0;

write_1302(0x8e,0x00);//允许写,禁止写保护

write_1302(0x8e,0x80);//打开写保护

}

//时分秒显示子函数

void write_sfm(uchar add,uchar dat)//向 LCD 写时分秒,有显示位置加、现示数据,两个参数

{

uchar gw,sw;

gw=dat%10;//取得个位数字

sw=dat/10;//取得十位数字

write_1602com(er+add);//er 是头文件规定的值 0x80+0x40

write_1602dat(0x30+sw);//数字+30 得到该数字的 LCD1602 显示码

write_1602dat(0x30+gw);//数字+30 得到该数字的 LCD1602 显示码

}

//年月日显示子函数

void write_nyr(uchar add,uchar dat)//向 LCD 写年月日,有显示位置加数、显示数据,两个参数

{

uchar gw,sw;

gw=dat%10;//取得个位数字

sw=dat/10;//取得十位数字

write_1602com(yh+add);//设定显示位置为第一个位置+add

write_1602dat(0x30+sw);//数字+30 得到该数字的 LCD1602 显示码

write_1602dat(0x30+gw);//数字+30 得到该数字的 LCD1602 显示码

}

void write_week(uchar week)//写星期函数

{

write_1602com(yh+0x0c);//星期字符的显示位置

switch(week)

{

case 1:write_1602dat('M');//星期数为一时,显示

write_1602dat('o');

write_1602dat('n');break;

case 2:write_1602dat('T');//星期数据为二时显示

write_1602dat('u');

write_1602dat('e');break;

case 3:write_1602dat('W');//星期数据为三时显示

write_1602dat('e');

write_1602dat('d');break;

case 4:write_1602dat('T');//星期数据为四是显示

write_1602dat('h');

write_1602dat('u');break;

case 5:write_1602dat('F');//星期数据为五时显示

write_1602dat('r');

write_1602dat('i');break;

case 6:write_1602dat('S');//星期数据为六时显示

write_1602dat('t');

write_1602dat('a');break;

case 7:write_1602dat('S');//星期数据为日时显示

write_1602dat('u');

write_1602dat('n');break;

}

}

//****************键盘扫描有关函数**********************

void keyscan()

{

if(key1==0)//key1 为功能键(设置键)

{

delay(9);//延时,用于消抖动

if(key1==0)//延时后再次确认按键按下

{

delay(20);

while(!key1);

key1n++;

if(key1n==9)

key1n=1;//设置按键共有秒、分、时、星期、日、月、年、返回,8 个功能循环

switch(key1n)

{

case 1:TR0=0;//关闭定时器

write_1602com(er+0x0E);//设置按键按动一次,秒位置显示光标

write_1602com(0x0f);//设置光标为闪烁

temp=(miao)/10*16+(miao)%10;//秒数据写入 DS1302

write_1302(0x8e,0x00);

write_1302(0x80,0x80|temp);//miao

write_1302(0x8e,0x80);break;

case 2:write_1602com(er+11);//按 2 次 fen 位置显示光标

break;

case 3:write_1602com(er+8);//按动 3 次,shi

break;

case 4:write_1602com(yh+0x0e);//按动 4 次,week

break;

case 5:write_1602com(yh+0x0a);//按动 5 次,ri

break;

case 6:write_1602com(yh+0x07);//按动 6 次,yue

break;

case 7:write_1602com(yh+0x04);//按动 7 次,nian

break;

case 8:write_1602com(0x0c);//按动到第 8 次,设置光标不闪烁

TR0=1;//打开定时器

TR0=1;

temp=(miao)/10*16+(miao)%10;

write_1302(0x8e,0x00);

write_1302(0x80,0x00|temp);//miao 数据写入 DS1302

write_1302(0x8e,0x80);break;

}

}

}

//------------------------------加键 key2----------------------------//

if(key1n!=0)//当 key1 按下以下。再按以下键才有效(按键次数不等于零)

{

if(key2==0)//上调键

{

delay(10);

if(key2==0)

{

delay(20);

while(!key2);

switch(key1n)

{

case 1:miao++;//设置键按动 1 次,调秒

if(miao==60)

miao=0;

write_sfm(0x0D,miao);

temp=(miao)/10*16+(miao)%10;

write_1302(0x8e,0x00);

write_1302(0x80,temp);

write_1302(0x8e,0x80);

write_1602com(er+0x0E);

break;

case 2:fen++;

if(fen==60)

fen=0;

write_sfm(0x0A,fen);

temp=(fen)/10*16+(fen)%10;

write_1302(0x8e,0x00);

write_1302(0x82,temp);

write_1302(0x8e,0x80);

write_1602com(er+11);

break;

case 3:shi++;

if(shi==24)

shi=0;

write_sfm(7,shi);

temp=(shi)/10*16+(shi)%10;

write_1302(0x8e,0x00);

write_1302(0x84,temp);

write_1302(0x8e,0x80);

write_1602com(er+8);

break;

case 4:week++;

if(week==8)

week=1;

write_1602com(yh+0x0C) ;

write_week(week);

temp=(week)/10*16+(week)%10;

write_1302(0x8e,0x00);

write_1302(0x8a,temp);

write_1302(0x8e,0x80);

write_1602com(yh+0x0e);

break;

case 5:ri++;

if(ri==32)

ri=1;

write_nyr(9,ri);

temp=(ri)/10*16+(ri)%10;

write_1302(0x8e,0x00);

write_1302(0x86,temp);

write_1302(0x8e,0x80);

write_1602com(yh+10);

break;

case 6:yue++;

if(yue==13)

yue=1;

write_nyr(6,yue);

temp=(yue)/10*16+(yue)%10;

write_1302(0x8e,0x00);

write_1302(0x88,temp);

write_1302(0x8e,0x80);

write_1602com(yh+7);

break;

case 7:nian++;

if(nian==100)

nian=0;

write_nyr(3,nian);

temp=(nian)/10*16+(nian)%10;

write_1302(0x8e,0x00);

write_1302(0x8c,temp);

write_1302(0x8e,0x80);

write_1602com(yh+4);

break;

}

}

}

//------------------减键 key3,各句功能参照'加键'注释---------------

if(key3==0)

{

delay(10);

//调延时,消抖动

if(key3==0)

{

delay(20);

while(!key3);

switch(key1n)

{

case 1:miao--;

if(miao==-1)

miao=59;

write_sfm(0x0D,miao);

temp=(miao)/10*16+(miao)%10;

write_1302(0x8e,0x00);

write_1302(0x80,temp);

write_1302(0x8e,0x80);

write_1602com(er+0x0E);

break;

case 2:fen--;

if(fen==-1)

fen=59;

write_sfm(10,fen);

temp=(fen)/10*16+(fen)%10;

write_1302(0x8e,0x00);

write_1302(0x82,temp);

write_1302(0x8e,0x80);

write_1602com(er+11);

break;

case 3:shi--;

if(shi==-1)

shi=23;

write_sfm(7,shi);

temp=(shi)/10*16+(shi)%10;

write_1302(0x8e,0x00);

write_1302(0x84,temp);

write_1302(0x8e,0x80);

write_1602com(er+8);

break;

case 4:week--;

if(week==0)

week=7;

write_1602com(yh+0x0C);

write_week(week);

temp=(week)/10*16+(week)%10;

write_1302(0x8e,0x00);

write_1302(0x8a,temp);

write_1302(0x8e,0x80);

write_1602com(yh+0x0e);

break;

case 5:ri--;

if(ri==0)

ri=31;

write_nyr(9,ri);

temp=(ri)/10*16+(ri)%10;//十进制转换成 DS1302 要求的 DCB 码

write_1302(0x8e,0x00);//允许写,禁止写保护

write_1302(0x86,temp);//向 DS1302 内写日期寄存器 86H 写入调整后的日期数据 BCD 码

write_1302(0x8e,0x80);//打开写保护

write_1602com(yh+10);//因为设置液晶的模式是写入数据后,指针自动加一,所以需要光标回位

break;

case 6:yue--;

if(yue==0)

yue=12;

write_nyr(6,yue);

temp=(yue)/10*16+(yue)%10; //十进制转换成 DS1302 要求的 DCB 码

write_1302(0x8e,0x00); //允许写,禁止写保护

write_1302(0x88,temp); //向 DS1302 内写月份寄存器 88H 写入调整后的月份数据 BCD 码

write_1302(0x8e,0x80); //打开写保护

write_1602com(yh+7); //因为设置液晶的模式是写入数据后,指针自动加一,所以需要光标回位

break;

case 7:nian--;

if(nian==-1)

nian=99;

write_nyr(3,nian);

temp=(nian)/10*16+(nian)%10; //十进制转换成 DS1302 要求的 DCB 码

write_1302(0x8e,0x00); //允许写,禁止写保护

write_1302(0x8c,temp); //向 DS1302 内写年份寄存器 8cH 写入调整后的年份数据 BCD 码

write_1302(0x8e,0x80); //打开写保护

write_1602com(yh+4); //因为设置液晶的模式是写入数据后,指针自动加一,所以需要光标回位

break;

}

}

}

}

}

void init()

//定时器、计数器设置函数

{

TMOD=0x11;

//指定定时/计数器的工作方式为 3

TH0=0;

//定时器 T0 的高四位=0

TL0=0;

//定时器 T0 的低四位=0

EA=1;

//系统允许有开放的中断

ET0=1;

//允许 T0 中断

TR0=1;

//开启中断,启动定时器

}

//*******************主函数**************************

void main()

{

lcd_init(); //调用液晶屏初始化子函数

ds1302_init(); //调用 DS1302 时钟的初始化子函数

init(); //调用定时计数器的设置子函数

delay(80);

while(1)

//无限循环下面的语句:

{

keyscan();

//调用键盘扫描子函数

}

}

void timer0() interrupt 1 //取得并显示日历和时间

{ //读取秒时分周日月年七个数据(DS1302 的读寄存器与写寄存器不一样)

miao = BCD_Decimal(read_1302(0x81));

fen = BCD_Decimal(read_1302(0x83));

shi = BCD_Decimal(read_1302(0x85));

ri = BCD_Decimal(read_1302(0x87));

yue = BCD_Decimal(read_1302(0x89));

nian=BCD_Decimal(read_1302(0x8d));

week=BCD_Decimal(read_1302(0x8b));

//显示秒、时、分数据:

write_sfm(13,miao); //秒,从第二行第 8 个字后开始显示(调用时分秒显示子函数)

write_sfm(10,fen); //分,从第二行第 5 个字符后开始显示

write_sfm(7,shi); //小时,从第二行第 2 个字符后开始显示

//显示日、月、年数据:

write_nyr(9,ri); //日期,从第二行第 9 个字符后开始显示

write_nyr(6,yue); //月份,从第二行第 6 个字符后开始显示

write_nyr(3,nian); //年,从第二行第 3 个字符后开始显示

write_week(week);

}

单片机显示冒号的介绍就聊到这里吧,感谢您花时间阅读,谢谢。

本文标签:单片机显示冒号

<