本帖最后由 a369518650 于 2010-5-12 17:14 编辑
我用的是AT89S52单片机 让控制芯片为ST7920的12864液晶显示万年历。
问题是在没节日的时候时间走时都正常的,但是到了有显示节日的时候,时间走时就走几秒卡几秒钟然后继续走几下卡一会儿.....小弟刚接触C语言,想不明白。请高手指导
还有一个问题是让按键K1选中的部分反白显示。看了一些网上的帖子有说结合绘图功能可以实现任意位置的反白,但是都没详写希望大侠帮忙修改下。非常感谢
下面就是我整理出的程序:
#include<reg51.h>
#include <string.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
/**********定义变量*******/
uchar a,b,c,h,m,s,yue,ri,xingqi;
int mun,nian,n;
double j;
/*************定义LCD控制字********/
sbit lcd_rs=P2^2;
sbit lcd_rw=P2^3;
sbit lcd_en=P2^4;
sbit lcd_ret=P2^1;
sbit lcd_psb=P2^0;
/*************定义按键************/
sbit k1=P3^0;
sbit k2=P3^1;
sbit k3=P3^2;
/***************************************************/
/*延时函数*/
void delayms(uint z)
{
int x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
void delay(int mun)
{
while(mun--);
}
/***************************************************/
/*定时器初始化*/
void timer_init()
{
TMOD=0x01; //选择定时器方式
TH0=(65536-50000)/256; //设置定时时间为50ms
TL0=(65536-50000)%256;
EA=1; //开总中断
ET0=1; //开定时器中断
TR0=1; //启动定时器
}
/**************************************************/
void write_com_data(bit ,unsigned char); //(0,指令) (1,数据)
//写指令或数据 (0,指令) (1,数据)
void write_com_data(bit dat_comm,uchar content)
{
uchar u,i,t;
delay(50);
u=content;
lcd_rs=1;
lcd_en=0;
lcd_rw=1;
for(i=0;i<5;i++)
{
lcd_en=1;
lcd_en=0;
}
lcd_rw=0;
lcd_en=1;
lcd_en=0;
if(dat_comm)
lcd_rw=1; //data
else
lcd_rw=0; //command
lcd_en=1;
lcd_en=0;
lcd_rw=0;
lcd_en=1;
lcd_en=0;
for(t=0;t<2;t++)
{
for(i=0;i<4;i++)
{
u=u<<1;
lcd_rw=CY;
lcd_en=1;
lcd_en=0;
}
lcd_rw=0;
for(i=0;i<4;i++)
{
lcd_en=1;
lcd_en=0;
}
}
}
void write_string(unsigned char *str);
void write_string(unsigned char *str)
{
while(*str != '\0')
{
write_com_data(1,*str++);
}
*str = 0;
}
/**************************************************/
void write_tupian();
void write_tupian(void)
{
lcd_rs=0;
lcd_rw=0;
P0=0x04;
}
/**************************************************/
void lcd_clr(void); //清屏
void lcd_clr(void)
{
write_com_data (0,0x30);
write_com_data (0,0x01);
delay (180);
}
//lcd 初始化
/**************************************************/
void lcd_init(void)
{
lcd_ret=1;
lcd_psb=0;
write_com_data (0,0x30); /*30---基本指令动作*/
write_com_data (0,0x01); /*清屏,地址指针指向00H*/
delay (100);
write_com_data (0,0x06); /*光标的移动方向*/
write_com_data (0,0x0c); /*开显示,关游标*/
}
/*年、月、日、星期、时间初始化*/
void data_init()
{
nian=2010; //“年”
yue=4; //“月”
ri=29; //“日”
h=23; //“小时”
m=59; //“分钟”
s=0; //“秒”
xingqi=5; //“星期”
}
/*显示初始化*/
/**************************************************/
void write_init()
{
write_com_data(0,0x80); //第一行第一个
write_com_data(1,(nian/1000)+0x30);
write_com_data(1,(nian%1000/100)+0x30);
write_com_data(1,(nian%1000%100/10)+0x30);
write_com_data(1,(nian%1000%100%10)+0x30);
write_string("年");
write_com_data(1,(yue/10)+0x30);
write_com_data(1,(yue%10)+0x30);
write_string("月");
write_com_data(1,(ri/10)+0x30);
write_com_data(1,(ri%10)+0x30);
write_string("日 ");
write_com_data(0,0x90); //第二行第二个
write_string(" 今");
write_string("天");
write_string("是");
write_string("星");
write_string("期");
if(xingqi==0){write_string("日 ");}
if(xingqi==1){write_string("一 ");}
if(xingqi==1){write_string("二 ");}
if(xingqi==1){write_string("三 ");}
if(xingqi==1){write_string("四 ");}
if(xingqi==1){write_string("五 ");}
if(xingqi==1){write_string("六 ");}
write_string(" ");
write_com_data(0,0x88); //第三行第三个
write_string(" ");
write_com_data(1,(h/10)+0x30);
write_com_data(1,(h%10)+0x30);
write_string(":");
write_com_data(1,(m/10)+0x30);
write_com_data(1,(m%10)+0x30);
write_string(":");
write_com_data(1,(s/10)+0x30);
write_com_data(1,(s%10)+0x30);
write_string(" ");
write_com_data(0,0x98);
if ( yue == 1 && ri == 1 ){ write_string(" 元旦快乐 "); }//1月
if ( yue == 1 && ri == 28 ){ write_string(" 世界麻风日 "); }
if ( yue == 2 && ri == 2 ){ write_string(" 世界湿地日 "); }//2月
if ( yue == 2 && ri == 13 ){ write_string(" 明天情人节 "); }
if ( yue == 2 && ri == 14 ){ write_string(" 情人节 "); }
if ( yue == 3 && ri == 1 ){ write_string(" 国际海豹日 "); }//3月
if ( yue == 3 && ri == 3 ){ write_string(" 全国爱耳日 "); }
if ( yue == 3 && ri == 8 ){ write_string(" 3.8妇女节 "); }
if ( yue == 3 && ri == 13 ){ write_string(" 植树节 "); }
if ( yue == 3 && ri == 14 ){ write_string(" 国际警察日 "); }
if ( yue == 3 && ri == 15 ){ write_string(" 消费者权益日 "); }
if ( yue == 3 && ri == 17 ){ write_string(" 国际航海日 "); }
if ( yue == 3 && ri == 21 ){ write_string(" 世界森林日 "); }
if ( yue == 3 && ri == 22 ){ write_string(" 世界水日 "); }
if ( yue == 3 && ri == 23 ){ write_string(" 世界气象日 "); }
if ( yue == 3 && ri == 24 ){ write_string("世界防治结核病日"); }
if ( yue == 4 && ri == 1 ){ write_string(" 愚人节 "); }//4
if ( yue == 4 && ri == 5 ){ write_string(" 清明节 "); }
if ( yue == 4 && ri == 7 ){ write_string(" 世界卫生日 "); }
if ( yue == 4 && ri == 22 ){ write_string(" 世界地球日 "); }
if ( yue == 5 && ri == 1 ){ write_string(" 5.1劳动节 "); }//5
if ( yue == 5 && ri == 4 ){ write_string(" 青年节 "); }
if ( yue == 5 && ri == 8 ){ write_string(" 世界红十字日 "); }
if ( yue == 5 && ri == 12 ){ write_string(" 国际护士节 "); }
if ( yue == 5 && ri == 15 ){ write_string(" 国际家庭日 "); }
if ( yue == 5 && ri == 31 ){ write_string(" 世界无烟日 "); }
if ( yue == 6 && ri == 1 ){ write_string(" 国际儿童节 "); }//6
if ( yue == 6 && ri == 5 ){ write_string(" 世界环境日 "); }
if ( yue == 6 && ri == 6 ){ write_string(" 全国爱眼日 "); }
if ( yue == 6 && ri == 25 ){ write_string(" 全国土地日 "); }
if ( yue == 6 && ri == 26 ){ write_string(" 国际禁毒日 "); }
if ( yue == 7 && ri == 1 ){ write_string("香港回归记念日 "); }//7
if ( yue == 7 && ri == 7 ){ write_string("抗日战争记念日 "); }
if ( yue == 7 && ri == 11 ){ write_string(" 世界人口日 "); }
if ( yue == 8 && ri == 1 ){ write_string(" 八一建军节 "); }//8
if ( yue == 9 && ri == 10 ){ write_string(" 中国教师节 "); }//9
if ( yue == 9 && ri == 18 ){ write_string("九·一八事变记念"); }
if ( yue == 9 && ri == 20 ){ write_string(" 国际爱牙日 "); }
if ( yue == 9 && ri == 27 ){ write_string(" 世界旅游日 "); }
if ( yue == 10 && ri == 1 ){ write_string(" 中国国庆节 "); }//10
if ( yue == 10 && ri == 4 ){ write_string(" 世界动物日 "); }
if ( yue == 10 && ri == 12 ){ write_string("明天国际教师节 "); }
if ( yue == 10 && ri == 13 ){ write_string(" 国际教师节 "); }
if ( yue == 10 && ri == 24 ){ write_string(" 联合国日 "); }
if ( yue == 11 && ri == 10 ){ write_string(" 世界青年节 "); }//11
if ( yue == 11 && ri == 17 ){ write_string(" 世界学生节 "); }
if ( yue == 12 && ri == 1 ){ write_string(" 世界艾滋病日 "); }//12
if ( yue == 12 && ri == 23 ){ write_string(" 明晚平安夜 "); }
if ( yue == 12 && ri == 24 ){ write_string(" 今晚平安夜 "); }
if ( yue == 12 && ri == 25 ){ write_string(" 圣诞快乐 "); }
if ( yue == 12 && ri == 31 ){ write_string(" 明日元旦 "); }
else write_string("应工学院应电0816");
}
void write_information() //显示产品信息
{
write_com_data(0,0x80);
write_string("万年历 ");
write_com_data(0,0x90);
write_string("版本信息: V1.0 ");
write_com_data(0,0x88);
write_string(" ");
write_com_data(0,0x98);
write_string(" ");
}
//作为反白显示
/**************************************************/
void select_write_com_data(bit ,unsigned char);
void select_write_com_data(bit dat_comm,uchar content)
{
uchar u,i,t;
delay(50);
u=content;
lcd_rs=1;
lcd_en=0;
lcd_rw=1;
for(i=0;i<5;i++)
{
lcd_en=1;
lcd_en=0;
}
lcd_rw=0;
lcd_en=1;
lcd_en=0;
if(dat_comm)
lcd_rw=1; //data
else
lcd_rw=0; //command
lcd_en=1;
lcd_en=0;
lcd_rw=0;
lcd_en=1;
lcd_en=0;
for(t=0;t<2;t++)
{
for(i=0;i<4;i++)
{
u=u<<1;
lcd_rw=CY;
lcd_en=1;
lcd_en=0;
}
lcd_rw=0;
for(i=0;i<4;i++)
{
lcd_en=1;
lcd_en=0;
}
}
}
/**************************************************/
/*功能键:增加*/
void button_k2()
{
if(!k2)
{
for(n=0;n<1000;n++); //去抖延时;
while(!k2);
for(n=0;n<1000;n++); //去抖延时;
if(b==1) //修改秒数值;
{
s++;
if(s==60)
{
s=0;
}
}
if(b==2) //修改分数值;
{
m++;
if(m==60)
{
m=0;
}
}
if(b==3) //修改小时数值;
{
h++;
if(h==24)
{
h=0;
}
}
if(b==4) //修改星期数值;
{
xingqi++;
if(xingqi==7)
{
xingqi=0;
}
}
if(b==5) //修改日数值;
{
ri++;
if((yue==1||yue==3||yue==5||yue==7||yue==8||yue==10||yue==12)&&ri==32)
{
ri=1;
}
else if((yue==4||yue==6||yue==9||yue==11)&&ri==31)
{
ri=1;
}
else if(yue==2&&ri==29)
{
ri=1;
}
}
if(b==6) //修改月份数值;
{
yue++;
if(yue==13)
{
yue=1;
}
}
if(b==7) //修改年份数值;
{
nian++;
if(nian==10000)
{
nian=2000;
}
}
}
}
/**************************************************/
/*功能键:减少*/
void button_k3()
{
if(!k3)
{
for(n=0;n<1000;n++); //去抖延时;
while(!k3);
for(n=0;n<1000;n++); //去抖延时;
if(b==1) //修改秒数值;
{
if(s>-1)
{
s--;
if(s==-1)
{
s=59;
}
}
}
if(b==2) //修改分数值;
{
if(m>-1)
{
m--;
if(m==-1)
{
m=59;
}
}
}
if(b==3) //修改小时数值;
{
if(h>-1)
{
h--;
if(h==-1)
{
h=23;
}
}
}
if(b==4) //修改星期数值;
{
if(xingqi>-1)
{
xingqi--;
if(xingqi==-1)
{
xingqi=7;
}
}
}
if(b==5) //修改日数值;
{
if(ri>0)
{
ri--;
if((yue==1||yue==3||yue==5||yue==7||yue==8||yue==10||yue==12)&&ri==0)
{
ri=31;
}
else if((yue==4||yue==6||yue==9||yue==11)&&ri==0)
{
ri=30;
}
else if(yue==2&&ri==0)
{
ri=28;
}
}
}
if(b==6) //修改月份数值;
{
if(yue>0)
{
yue--;
if(yue==0)
{
yue=12;
}
}
}
if(b==7) //修改年份数值;
{
if(nian>1999)
{
nian--;
if(nian==1999)
{
nian=9999;
}
}
}
}
}
/**************************************************/
/*功能键:选择 选中时反白显示 */
void button_k1()
{
if(!k1)
{
for(n=0;n<1000;n++); //去抖延时;
while(!k1);
for(n=0;n<1000;n++);
TR0=0;
b++;
//for(n=0;n<1000;n++);
while(1)
{
if(!k1)
{
for(n=0;n<1000;n++);
while(!k1);
for(n=0;n<1000;n++);
b++;
write_init();
}
//write_init();
switch(b)
{
case 1: //选中秒;
write_com_data(0,0x8d);
select_write_com_data(1,~(s/10)+0x30);
select_write_com_data(1,~(s%10)+0x30);
button_k2();
button_k3();
break;
case 2:
//选中分;
write_com_data(0,0x8b);
write_string(":");
select_write_com_data(1,~(m/10)+0x30);
select_write_com_data(1,~(m%10)+0x30);
button_k2();
button_k3();
break;
case 3:
//选中小时;
write_com_data(0,0x8a);
select_write_com_data(1,~(h/10)+0x30);
select_write_com_data(1,~(h%10)+0x30);
button_k2();
button_k3();
break;
case 4:
//选中星期;
write_com_data(0,0x96);
select_write_com_data(1,~(xingqi)+0x30);
button_k2();
button_k3();
break;
case 5:
//选中日;
write_com_data(0,0x85);
select_write_com_data(1,~(ri/10)+0x30);
select_write_com_data(1,~(ri%10)+0x30);
button_k2();
button_k3();
break;
case 6:
//选中月份
write_com_data(0,0x83);
select_write_com_data(1,~(yue/10)+0x30);
select_write_com_data(1,~(yue%10)+0x30);
button_k2();
button_k3();
break;
case 7:
//选中年份
write_com_data(0,0x80);
select_write_com_data(1,~(nian/1000)+0x30);
select_write_com_data(1,~(nian%1000/100)+0x30);
select_write_com_data(1,~(nian%1000%100/10)+0x30);
select_write_com_data(1,~(nian%1000%100%10)+0x30);
button_k2();
button_k3();
break;
case 8: //没有选中项,启动定时器
TR0=1;
b=0;
break;
}
if(b==0)
{
break; //退出循环
}
a=0;
}
}
}
/**************************************************/
/*时间日期显示*/
void timer_display()
{
if(a==20)
{
//秒加加,加到60,清0;
a=0;
//lcd_display_shuzi(2,1,4,10);
s++;
if(s==60)
{
s=0; //定时器清0;
//分加加,加到60,分清0;
m++;
if(m==60)
{
m=0;
//小时加加,加到24。小时清0;
h++;
if(h==24)
{
h=0;
//星期加加,加到星期日时,返回星期一;
xingqi++;
if(xingqi==7)
{
xingqi=0;
}
ri++; //日加加;
//7个31天的月份;
if((yue==1||yue==3||yue==5||yue==7||yue==8||yue==10||yue==12)&&ri==32)
{
yue++;
ri=1;
}
//4个30天的月份;
else if((yue==4||yue==6||yue==9||yue==11)&&ri==31)
{
yue++;
ri=1;
}
//1个28天的月份;
else if(yue==2)
{
if((int)j==j&&ri==30)
{
yue++;
ri=1;
}
else if((j-(int)j)&&ri==29)
{
yue++;
ri=1;
}
}
//增加到13月份时,返回到1月;
if(yue==13)
{
yue=1;
nian++; //年加加,到9999时,返回2000;
if(nian==10000)
{
nian=2000;
}
}
}
}
}
}
}
/**************************************************/
/*主函数*/
void main()
{
j=(nian/4.0);
data_init(); //时间、日期初始化;
lcd_init(); //LCD初始化
timer_init(); //定时器初始化
while(1)
{ if(k2==0 && k3==0)
{
write_information(); //显示产品信息
}
else write_init(); //LCD显示初始化
button_k1();
timer_display();
}
}
/************************************************/
/* 重置定时器定时时间*/
void timer() interrupt 1
{
TH0=(65536-50000)/256; //设置定时时间为50ms
TL0=(65536-50000)%256;
a++;
c++;
} |
|