|
仿真原理图如下(proteus仿真工程文件可到本帖附件中下载)
/*************
功能:用LCD1602显示输出8位可连续进行简单的加减乘除运算
说明:无论与0相乘还是相除输出结果是随机的,错误的;
除法输出是带小数点的8位数字显示输出,还没有继续小数点转换
*************/
#include <reg52.h>
#define uchar unsigned char
#define uint unsigned int
sbit rs=P2^2;
sbit rw=P2^1;
sbit e=P2^0;
void write_dat(uchar dat);
void write_com(uchar com);
void process(void);
void keyscan();
/*按键功能*/
uchar code table1[]=
{
1,2,3,0x2b-0x30, // 1, 2, 3, +
4,5,6,0x2d-0x30, // 4, 5, 6, -
7,8,9,0x2a-0x30, // 7, 8, 9, x
0,0x3d-0x30,0x01-0x30,0x2f-0x30 // 0, =, 清零, /
};
uchar k=0,flag=0,num,fuhao[6],i,temp1=0,flag1=0;
long a,b,c,d;
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
/********按键处理***********/
void keyscan()
{
uchar temp;
P3=0xfe;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
temp=P3;
switch(temp)
{
case 0xee:num=0;
break;
case 0xde:num=1;
break;
case 0xbe:num=2;
break;
case 0x7e:num=3;
break;
}
while(temp!=0xf0) // 松手检测
{ temp=P3;
temp=temp&0xf0;
}
}
if(num==0||num==1||num==2)
{
if(flag==0)
a=a*10+table1[num]; //如果没有按符号键,符号前的数值为a
else if(flag==1)
b=b*10+table1[num]; //如果按了符号键,符号后的数值为b
else if(temp1>=2&&flag1==1)
{
flag=1;
flag1=0;
process();
a=c;
b=table1[num];
}
if(k==1)
{
k=0;
write_com(0x01);
}
}
else if(num==3)
{
flag++;
flag1=1;
temp1++;
fuhao[temp1-1]=1;
}
i=table1[num]; //显示按下的键
write_dat(0x30+i);
}
P3=0xfd;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
temp=P3;
switch(temp)
{
case 0xed:num=4;
break;
case 0xdd:num=5;
break;
case 0xbd:num=6;
break;
case 0x7d:num=7;
break;
}
while(temp!=0xf0)
{ temp=P3;
temp=temp&0xf0;
}
}
if(num==4||num==5||num==6)
{
if(k==1)
{
k=0;
write_com(0x01);
}
if(flag==0)
a=a*10+table1[num];
else if(flag==1)
b=b*10+table1[num];
else if(temp1>=2&&flag1==1)
{
flag=1;
flag1=0;
process();
a=c;
b=table1[num];
}
}
else if(num==7)
{
flag++;
temp1++;
flag1=1;
fuhao[temp1-1]=2;
}
i=table1[num];
write_dat(0x30+i);
}
P3=0xfb;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
temp=P3;
switch(temp)
{
case 0xeb:num=8;
break;
case 0xdb:num=9;
break;
case 0xbb:num=10;
break;
case 0x7b:num=11;
break;
}
while(temp!=0xf0)
{ temp=P3;
temp=temp&0xf0;
}
}
if(num==8||num==9||num==10)
{
if(k==1)
{
k=0;
write_com(0x01);
}
if(flag==0)
a=a*10+table1[num];
else if(flag==1)
b=b*10+table1[num];
else if(temp1>=2&&flag1==1)
{
flag=1;
flag1=0;
process();
a=c;
b=table1[num];
}
}
else if(num==11)
{
flag++;
temp1++;
flag1=1;
fuhao[temp1-1]=3;
}
i=table1[num];
write_dat(0x30+i);
}
P3=0xf7;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
temp=P3;
switch(temp)
{
case 0xe7:num=12; // 0键
break;
case 0xd7:num=13; // '='
break;
case 0xb7:num=14; //清零键
break;
case 0x77:num=15; //除号键
break;
}
while(temp!=0xf0)
{ temp=P3;
temp=temp&0xf0;
}
}
switch(num)
{
case 12:
{
if(k==1)
{
k=0;
write_com(0x01);
}
if(flag==0)
a=a*10;
else if(flag==1)
b=b*10;
else if(temp1>=2&&flag1==1)
{
flag=1;
flag1=0;
process();
a=c;
b=table1[num];
}
write_dat(0x30);
}
break;
case 13:
{
k=1;
if(temp1>=2)
fuhao[0]=fuhao[temp1-1];
if(fuhao[0]==1)
{
write_com(0x80+0x4f);
write_com(0x04);
c=a+b;
d=c;
while(c!=0)
{
write_dat(0x30+c%10);
c=c/10;
}
write_dat(0x3d);
fuhao[0]=0;fuhao[1]=0;fuhao[2]=0;
fuhao[3]=0;fuhao[4]=0;fuhao[5]=0;
a=0;b=0;flag=0;flag1=0;temp1=0;
}
if(fuhao[0]==2)
{
write_com(0x80+0x4f);
write_com(0x04);
if(a>=b)
{
c=a-b;
d=c;
while(c!=0)
{
write_dat(0x30+c%10);
c=c/10;
}
}
else if(a<b)
{
c=b-a;
d=c;
while(c!=0)
{
write_dat(0x30+c%10);
c=c/10;
}
write_dat(0x2d);
}
write_dat(0x3d);
fuhao[0]=0;fuhao[1]=0;fuhao[2]=0;
fuhao[3]=0;fuhao[4]=0;fuhao[5]=0;
a=0;b=0;flag=0;flag1=0;temp1=0;
}
if(fuhao[0]==3)
{
write_com(0x80+0x4f);
write_com(0x04);
c=a*b;
d=c;
while(c!=0)
{
write_dat(0x30+c%10);
c=c/10;
}
write_dat(0x3d);
fuhao[0]=0;fuhao[1]=0;fuhao[2]=0;
fuhao[3]=0;fuhao[4]=0;fuhao[5]=0;
a=0;b=0;flag=0;flag1=0;temp1=0;
}
if(fuhao[0]==4)
{
i=0;
write_com(0x80+0x4f);
write_com(0x04);
c=(long)(((float)a/b)*1000000);
d=c;
while(c!=0)
{
write_dat(0x30+c%10);
c=c/10;
i++;
if(i==6)
write_dat(0x2e);
}
if(a/b<=0)
write_dat(0x30);
write_dat(0x3d);
fuhao[0]=0;fuhao[1]=0;fuhao[2]=0;
fuhao[3]=0;fuhao[4]=0;fuhao[5]=0;
a=0;b=0;flag=0;flag1=0;temp1=0;
}
}
break;
case 14:
{ write_com(0x01);
a=0;b=0;flag=0;temp1=0;flag1=0;
fuhao[0]=0;fuhao[1]=0;fuhao[2]=0;
fuhao[3]=0;fuhao[4]=0;fuhao[5]=0;
}
break;
case 15:
{
flag++;
temp1++;
flag1=1;
fuhao[temp1-1]=4;
write_dat(0x30+table1[num]);
}
break;
}
}
}
/*******led1602显示*******/
void write_com(uchar com)
{
rs=0;
rw=0;
P0=com;
e=1;
delay(5);
e=0;
}
void write_dat(uchar dat)
{
rs=1;
rw=0;
P0=dat;
e=1;
delay(5);
e=0;
}
void process(void)
{
if(fuhao[temp1-2]==1) //如果符号键是+,执行加法运算
{
c=a+b;
b=0;
} // 如果符号键是-,执行减法运算
if(fuhao[temp1-2]==2)
{
c=a-b;
b=0;
}
if(fuhao[temp1-2]==3) //如果符号键是*执行乘法运算
{
c=a*b;
b=0;
}
if(fuhao[temp1-2]==4) //如果符号键是/ 执行除法运算
{
c=(long)((float)a/b);
b=0;
}
}
/*液晶的初始化*/
void init() //初始化
{
delay(15);
write_com(0x38);
delay(6);
write_com(0x38);
delay(6);
write_com(0x38);
write_com(0x38);
write_com(0x0c); //开显示,关光标
write_com(0x06); //光标移动
write_com(0x01); //清屏
}
void main()
{
init();
while(1)
{
keyscan();
}
}
|
-
-
计算器.zip
86.09 KB, 下载次数: 33, 下载积分: 黑币 -5
源码
评分
-
查看全部评分
|