PORTB的电平变化中断进行键盘输入
//该程序通过PORTB的"电平变化中断"进行键盘的输入,使按下K1键时第一个数码管显示1,按下K2
//键时第一个数码管上显示2,按下K3键时第一个数码管上显示3,按下K4键时第一个数码管上显示4
//对键盘的扫描采用中断方式
#include"p18f458.h"
unsigned chardata;
unsigned inti;
unsigned charj;
const char table[20]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0XD8,0x80,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e,0x7f,0xbf,0x89,0xff};
voidInterruptHandlerHigh(void);
/*初始化子程序*/
/* http://www.51hei.com 提供此程序*/
void initial()
{
INTCON=0x08;/*关闭所有中断,B口变位中断允许*/
INTCON2=0x01;/*使能B口弱上拉,B口变位中断高优先级*/
RCONbits.IPEN=1;/*使能中断优先级*/
TRISA=0x00;/*A口设置为输出*/
TRISB=0XF0;/*RB1输出,RB4输入*/
TRISC=0x00;/*SDO引脚为输出,SCK引脚为输出*/
TRISE=0x00;/*E口设置为输出*/
SSPCON1=0x30;/*SSPEN=1;CKP=1,FOSC/4*/
SSPSTAT=0xC0;/*时钟下降沿发送数据*/
PIR1=0;/*清除SSPIF标志*/
data=0X00;/*待显示的寄存器赋初值*/
PORTBbits.RB1=0;
PORTAbits.RA3=0;
PORTE=0;/*将K1,K2,K3,K4四条列线置0*/
PORTB=PORTB;/*读B口的值,为变位中断创造条件*/
}
/*键服务子程序*/
voidKEYSERVE()
{
PORTBbits.RB1=0;/*K1,K2置低电平,K3,K4置高电平*/
PORTAbits.RA3=0;/*RB4为0,表示按键为K1,K2中的一个*/
PORTE=3;/*RB4为1,表示按键为K3,K4中的一个*/
if(PORTBbits.RB4==0)
{
PORTBbits.RB1=0;/*K1置低电平,K2置高电平*/
PORTAbits.RA3=1;/*RB4为0,表示按键为K1;RB4为1,表示按键为K2*/
if(PORTBbits.RB4==0)j=0X01;
else{j=0X02;PORTAbits.RA3=0;}
}
else
{
PORTEbits.RE0=0;/*K3置低电平,K4置高电平*/
PORTEbits.RE1=1;/*RB4为0,表示按键为K3;RB4为1,表示按键为K4*/
if(PORTBbits.RB4==0)j=0X03;
else{j=0X04;PORTEbits.RE1=0;}
}
}
/*软件延时子程序*/
void DELAY()
{
for(i = 6553; --i ;)
continue;
}
/*显示子程序*/
voidSPILED(char data)
{
PORTAbits.RA5=0;/*LACK送低电平,为锁存做准备*/
SSPBUF=data;/*启动发送*/
do
{
;
}while(PIR1bits.SSPIF==0);/*等待发送完毕*/
PIR1bits.SSPIF=0;/*清除SSPIF标志*/
PORTAbits.RA5=1;/*最后给锁存信号,代表显示任务完成*/
}
/*高优先级中断向量*/
#pragma code InterruptVectorHigh=0x08
voidInterruptVectorHigh (void)
{
_asm
goto InterruptHandlerHigh /*跳到中断程序*/
_endasm
}
/*高优先级中断程序*/
#pragma code
#pragma interrupt InterruptHandlerHigh
voidInterruptHandlerHigh ()
{
INTCONbits.RBIF=0;/*中断标志清0*/
DELAY();/*软件延时*/
PORTB=PORTB;/*读PORTB的值,并改变中断发生的条件,可屏蔽*/
/*一次按键松开时产生的无效的中断,又可以防止按键*/
/*时间过长发生连续中断*/
if(PORTBbits.RB4==0)
{
KEYSERVE();/*进行键盘的识别*/
PORTBbits.RB1=0;
PORTAbits.RA3=0;
PORTE=0;/*将K1,K2,K3,K4四条列线置0,以防止键扫描时改变*/
/*K1,K2,K3,K4的电平,从而改变中断条件*/
INTCONbits.RBIF=0;/*键扫描时可能会产生"电平变化"而使置1,再清除一次*/
/*RBIF以求避免额外中断*/
data=table[j];/*获得需要送出显示的段码*/
SPILED(data);
}
}
/*主程序*/
main()
{
initial();/*系统初始化*/
INTCONbits.GIE=1;/*总中断允许*/
while(1)
{
}/*等待中断*/
}
- PIC单片机中断程序设计技巧(12-18)
- pic16f877a的电平变化中断(interrupt on change)使用误区(12-03)
- 单片机键盘输入及串口发送(11-26)
- 第83节:矩阵键盘输入任意数字或小数点的液晶屏显示程序(11-22)
- Windows CE 进程、线程和内存管理(11-09)
- RedHatLinux新手入门教程(5)(11-12)