|
单片机小制作时写的一些小程序,在最小系统上运行成功,采用的是中断键盘扫描. //****键值表如下: // 1 2 3 4 // 5 6 7 8 // 9 + - * // / = CLR //*************// #include<reg51.h> #define unint unsigned int #define unchar unsigned char sbit P3_4=P3^4; sbit P3_5=P3^5; unchar code table[]={0xc0,0xf9,0xa4,0xb0,0x99, 0x92,0x82,0xf8,0x80,0x90,0x88,0x83, 0xc6,0xa1,0x86,0x8e,0x00 }; #define ADD 10 #define SUB 11 #define MUL 12 #define DIV 13 void delay(unint c){ unint i,j; for(j=0;j<c;j++){ for(i=0;i<200;i++) {;} } } //**************键盘扫描程序************** unint keyscan(void) { unint n; delay(1); if((P1&0xF0)!=0xF0) { P1=0xFE; if((P1&0xFE)!=0xFE) { if((P1&0xFE)==0xEE) n=1; else if((P1&0xFE)==0xDE) n=2; else if((P1&0xFE)==0xBE) n=3; else n=4; } P1=0xFD; if((P1&0xFD)!=0xFD) { if((P1&0xFD)==0xED) n=5; else if((P1&0xFD)==0xDD) n=6; else if((P1&0xFD)==0xBD) n=7; else n=8; } P1=0xFB; if((P1&0xFB)!=0xFB) { if((P1&0xFB)==0xEB) n=9; else if((P1&0xFB)==0xDB) n=10; else if((P1&0xFB)==0xBB) n=11; else n=12; } P1=0xF7; if((P1&0xF7)!=0xF7) { if((P1&0xF7)==0xE7) n=13; else if((P1&0xF7)==0xD7) n=14; else if((P1&0xF7)==0xB7) n=15; else n=16; } } else n=0; P1=0xF0; return(n); } //LED数值显示程序 void led_display(unint m){ switch(m) { case 1:P2=~0xf1;P0=0xf9;break;//LED以二进制形式显示1 case 2:P2=~0xf2;P0=0xa4;break;//LED以二进制形式显示2 case 3:P2=~0xf3;P0=0xb0;break;//LED以二进制形式显示3 case 4:P2=~0xf4;P0=0x99;break;//LED以二进制形式显示4 case 5:P2=~0xf5;P0=0x92;break;//LED以二进制形式显示5 case 6:P2=~0xf6;P0=0x82;break;//LED以二进制形式显示6 case 7:P2=~0xf7;P0=0xf8;break;//LED以二进制形式显示7 case 8:P2=~0xf8;P0=0x80;break;//LED以二进制形式显示8 case 9:P2=~0xf9;P0=0x90;break;//LED以二进制形式显示9 case 10:P2=~0xfa;P0=0x88;break;//LED以二进制形式显示10 case 11:P2=~0xfb;P0=0x83;break;//LED以二进制形式显示11 case 12:P2=~0xfc;P0=0xc6;break;//LED以二进制形式显示12 case 13:P2=~0xfd;P0=0xa1;break;//LED以二进制形式显示13 case 14:P2=~0xfe;P0=0x86;break;//LED以二进制形式显示14 case 15:P2=~0xff;P0=0x8e;break;//LED以二进制形式显示15 case 16:P2=~0x00;P0=0xc0;break;//CLR } } void service_int0()interrupt 0 using 2//采用中断0触发中断的程序 { unint last;//第一次键入的数值 unint second;//第二次键入的数值 unint result;//最终运算结果 unint op;//用来存储+、-、*、/操作符键值 last=0; second=0; result=0; op=0; keyscan(); if(keyscan()>0&&keyscan()<10){//得到的键盘数值是数字的1-9之间的。 if (last==0){ last=keyscan(); led_display(last);//显示第一次按键键值 delay(200);} else{ second=keyscan(); led_display(second);//显示下一次按键键值 delay(200); } } else if(keyscan()>9&&keyscan()<14){//返回的键值为10代表+,11代表-,12代表*,13代表/。 op=keyscan();//将+、-、*、/的键值赋给操作符OP } else if((keyscan()==14) (keyscan()==15)){//返回的键值为15则代表=。 led_display(result); delay(200);//显示最终的计算结果。 last=0;//清零回复初始状态,当然我们也可以设置一个CLR键来达到此目的。 second=0; result=0; op=0; } else if(keyscan()==16){//返回的键值为16代表CLR。 led_display(16); last=0;//清零回复初始状态,当然我们也可以设置一个CLR键来达到此目的。 second=0; result=0; op=0; } //***** 四则运算程序***** if(op!=0&&last!=0&&second!=0) { // 判断是否操作符键以及先后两次的数值键都已经按下。 switch(op){ case 10:result=last+second;if(result>=16){result=result%10;} break; case 11:result=last-second;if(result>=16){result=result%10;}break; case 12:result=last*second;if(result>=16){result=result%10;}break; case 13:result=last/second;if(result>=16){result=result%10;}break; } } } void main(void){ P0=0xc0; P2=0xff;//四个LED全灭 P1=0xF0;//处于初始状态,当然随便你设置一个合适的值即可。 P3_4=0; P3_5=1; IT0=1; EX0=1; EA=1; while(1); }
|