单片机矩阵按键长短按
2015-08-05 14:42
169 查看
实习的时候,同事给了我一个矩阵键盘程序,竟然长达1千多行代码,当时我就吓尿了。仔细分析代码,也未见其独到之处,仅仅是普通的按键扫描以及判断长短按。但其中使用的结构很复杂,中间产生的临时变量特别多,而且指针很多,也不容易移植。稍微搜索一下网上的程序,也并不是很详尽。这里贴出我的程序给大家参考一下,是基于NUC100RE3AN单片机的。这里不使用太多枚举以及宏定义,大家根据自己的需求去修改吧。
1首先定义矩阵的行列,已经相对应的引脚列表
#define LINE 4
#define COLUMN 4
uint8_t key_line[LINE][2]={
{GPC,7},
{GPC,7},
{GPC,7},
{GPC,7},
};
uint8_t key_column[COLUMN][2]={
{GPC,8},
{GPC,9},
{GPC,10},
{GPC,11},
};
2定义一个存放按键状态的数组,0无按键,1短按,2长按
uint8_t key[LINE][COLUMN];
3初始化矩阵键盘,将引脚列表里面的行列进行输入输出设置,该拉高的拉高,该拉低的拉低
void key_matrix_init()
{
uint8_t i;
for(i=0;i<LINE;i++)
{
DrvGPIO_Open((DRVGPIO_PORT)key_line[i][0],key_line[i][1],IO_OUTPUT);
DrvGPIO_ClrBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
}
for(i=0;i<COLUMN;i++)
{
DrvGPIO_Open((DRVGPIO_PORT)key_column[i][0],key_column[i][1],IO_INPUT);
}
}
4宏定义一个时间值,当按键按下超过这个值时判断为长按
#define LONG_TIME 20
5嵌套的for循环对按键进行扫描。扫描完成后,按键状态便存放在数组key中了。
void key_matrix_scan()
{
int long_flag_cnt=0;
uint8_t i,j;
for(i=0;i<LINE;i++)
{
DrvGPIO_ClrBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
for(j=0,long_flag_cnt=0;j<COLUMN;j++)
{
if(DrvGPIO_GetBit((DRVGPIO_PORT)key_column[j][0],key_column[j][1])==0)
{
delay_ms(10);
while(DrvGPIO_GetBit((DRVGPIO_PORT)key_column[j][0],key_column[j][1])==0)
{
long_flag_cnt++;
if(long_flag_cnt>=LONG_TIME)
{
break;
}
delay_ms(1);
}
if(long_flag_cnt>=LONG_TIME)
{
key[i][j]=2;
//long_flag_cnt=0;
}
else
{
key[i][j]=1;
delay_ms(10);
}
}
}
DrvGPIO_SetBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
}
}
说明:
当要对矩阵键盘进行修改的时候,只需要修改步骤1中的行列大小以及相应的引脚列表即可。
本人QQ1607114262,有什么不懂的地方可以找我。
1首先定义矩阵的行列,已经相对应的引脚列表
#define LINE 4
#define COLUMN 4
uint8_t key_line[LINE][2]={
{GPC,7},
{GPC,7},
{GPC,7},
{GPC,7},
};
uint8_t key_column[COLUMN][2]={
{GPC,8},
{GPC,9},
{GPC,10},
{GPC,11},
};
2定义一个存放按键状态的数组,0无按键,1短按,2长按
uint8_t key[LINE][COLUMN];
3初始化矩阵键盘,将引脚列表里面的行列进行输入输出设置,该拉高的拉高,该拉低的拉低
void key_matrix_init()
{
uint8_t i;
for(i=0;i<LINE;i++)
{
DrvGPIO_Open((DRVGPIO_PORT)key_line[i][0],key_line[i][1],IO_OUTPUT);
DrvGPIO_ClrBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
}
for(i=0;i<COLUMN;i++)
{
DrvGPIO_Open((DRVGPIO_PORT)key_column[i][0],key_column[i][1],IO_INPUT);
}
}
4宏定义一个时间值,当按键按下超过这个值时判断为长按
#define LONG_TIME 20
5嵌套的for循环对按键进行扫描。扫描完成后,按键状态便存放在数组key中了。
void key_matrix_scan()
{
int long_flag_cnt=0;
uint8_t i,j;
for(i=0;i<LINE;i++)
{
DrvGPIO_ClrBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
for(j=0,long_flag_cnt=0;j<COLUMN;j++)
{
if(DrvGPIO_GetBit((DRVGPIO_PORT)key_column[j][0],key_column[j][1])==0)
{
delay_ms(10);
while(DrvGPIO_GetBit((DRVGPIO_PORT)key_column[j][0],key_column[j][1])==0)
{
long_flag_cnt++;
if(long_flag_cnt>=LONG_TIME)
{
break;
}
delay_ms(1);
}
if(long_flag_cnt>=LONG_TIME)
{
key[i][j]=2;
//long_flag_cnt=0;
}
else
{
key[i][j]=1;
delay_ms(10);
}
}
}
DrvGPIO_SetBit((DRVGPIO_PORT)key_line[i][0],key_line[i][1]);
}
}
说明:
当要对矩阵键盘进行修改的时候,只需要修改步骤1中的行列大小以及相应的引脚列表即可。
本人QQ1607114262,有什么不懂的地方可以找我。
相关文章推荐
- 51单片机的中断整理
- 时钟+温度+遥控设置,综合时钟例子
- 温度传感器+I2C+串口+PC上位机(pyserial)例子
- 51单片机中data,idata,xdata,pdata的区别
- 什么叫51单片机最小系统
- 用串口连接GSM手机发送和接收短消息,在应用程序中如何编程实现?
- MCU之心路分享
- 按键led
- 单片机学会释放CPU
- 单片机无线串行接口电路设计
- 单片机无线串行接口电路设计
- 单片机系统中的红外通信接口
- 单片机系统中的红外通信接口
- 单片机实现接收从电脑发送过来的字符串的方法
- 单片机IO口模拟串口程序(发送+接收
- DSP、ARM和单片机的区别
- 转:接地:数字地、模拟地、信号地、交流地、直流地、屏蔽地、浮地
- 单片机存储器之flash,eeprom,sram,dram简介
- 程序状态字(PSW)的动画说明,
- 51单片机