首页 区块链

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)

分类:区块链
字数: (1897)
阅读: (8769)
内容摘要:51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技),

相信很多初学 51 单片机的同学都会遇到矩阵键盘这个拦路虎。刚开始的时候,我也是各种头大,扫描不准、按键抖动等等问题层出不穷。本文就以江协科技的教程为基础,结合我多年的嵌入式开发经验,带你彻底搞懂 51 单片机的矩阵键盘,并分享一些实战中的避坑经验。

矩阵键盘的原理深度剖析

矩阵键盘相比独立按键,最大的优势在于节省 IO 口资源。比如,要实现 16 个按键,如果使用独立按键,需要 16 个 IO 口,而使用 4x4 的矩阵键盘,只需要 8 个 IO 口。矩阵键盘的原理就是行线和列线交叉,通过扫描行线或列线,来判断哪个按键被按下。

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)

行列扫描的实现方式

通常有两种扫描方式:行扫描和列扫描。

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)
  • 行扫描: 将行线设置为输出,列线设置为输入。依次将行线输出低电平,然后读取列线的电平。如果某列线为低电平,则表示该行与该列交叉的按键被按下。
  • 列扫描: 将列线设置为输出,行线设置为输入。依次将列线输出低电平,然后读取行线的电平。如果某行线为低电平,则表示该列与该行交叉的按键被按下。

这两种方式本质上是一样的,选择哪一种取决于你的硬件连接方式和个人习惯。

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)

消抖处理的重要性

按键按下或释放时,会产生抖动,如果不进行消抖处理,可能会导致误判。常用的消抖方法有两种:硬件消抖和软件消抖。

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)
  • 硬件消抖: 使用电容等元件,滤除抖动信号。这种方法简单有效,但会增加硬件成本。
  • 软件消抖: 通过延时一段时间,等待抖动稳定后再读取按键状态。这种方法不需要额外的硬件,但会占用 CPU 资源。

在实际应用中,根据具体情况选择合适的消抖方法。

基于江协科技的代码示例及解析

下面是一个基于江协科技教程的简单的 4x4 矩阵键盘扫描代码:

#include <reg52.h>

#define KEY_PORT P1 // 定义键盘端口

sbit L1 = P2^0;
sbit L2 = P2^1;
sbit L3 = P2^2;
sbit L4 = P2^3;

void delay_ms(unsigned int ms) {
    unsigned int i, j;
    for (i = ms; i > 0; i--)
        for (j = 110; j > 0; j--);
}

unsigned char KeypadScan() {
    unsigned char keyValue = 0;

    // 行扫描
    KEY_PORT = 0xF0; // 行输出低电平,列输入高电平
    if ((KEY_PORT & 0xF0) != 0xF0) { // 有按键按下
        delay_ms(10); // 软件消抖
        if ((KEY_PORT & 0xF0) != 0xF0) { // 再次确认
            // 判断是哪一行
            KEY_PORT = 0xFE; // 第一行置低
            if ((KEY_PORT & 0xF0) != 0xF0) {keyValue = 1; while((KEY_PORT & 0xF0) != 0xF0);}
            KEY_PORT = 0xFD; // 第二行置低
            if ((KEY_PORT & 0xF0) != 0xF0) {keyValue = 2; while((KEY_PORT & 0xF0) != 0xF0);}
            KEY_PORT = 0xFB; // 第三行置低
            if ((KEY_PORT & 0xF0) != 0xF0) {keyValue = 3; while((KEY_PORT & 0xF0) != 0xF0);}
            KEY_PORT = 0xF7; // 第四行置低
            if ((KEY_PORT & 0xF0) != 0xF0) {keyValue = 4; while((KEY_PORT & 0xF0) != 0xF0);}

            // 判断是哪一列
            KEY_PORT = 0xF0;
            if ((KEY_PORT & 0xEF) == 0xEE) keyValue = keyValue * 4 - 3; // 第一列
            if ((KEY_PORT & 0xDF) == 0xDE) keyValue = keyValue * 4 - 2; // 第二列
            if ((KEY_PORT & 0xBF) == 0xBE) keyValue = keyValue * 4 - 1; // 第三列
            if ((KEY_PORT & 0x7F) == 0x7E) keyValue = keyValue * 4;     // 第四列

        }
    }
    return keyValue;
}

void main() {
    unsigned char key;
    while (1) {
        key = KeypadScan();
        if (key != 0) {
           switch(key){
                case 1: L1=~L1;break;
                case 2: L2=~L2;break;
                case 3: L3=~L3;break;
                case 4: L4=~L4;break;
                case 5: L1=~L1;L2=~L2;break;
                case 6: L1=~L1;L3=~L3;break;
                case 7: L1=~L1;L4=~L4;break;
                case 8: L2=~L2;L3=~L3;break;
                case 9: L2=~L2;L4=~L4;break;
                case 10: L3=~L3;L4=~L4;break;
                case 11: L1=~L1;L2=~L2;L3=~L3;break;
                case 12: L1=~L1;L2=~L2;L4=~L4;break;
                case 13: L1=~L1;L3=~L3;L4=~L4;break;
                case 14: L2=~L2;L3=~L3;L4=~L4;break;
                case 15: L1=~L1;L2=~L2;L3=~L3;L4=~L4;break;
                case 16: L1=0;L2=0;L3=0;L4=0;break;
           }
        }
    }
}

代码解析:

  1. KEY_PORT 定义了键盘端口,这里使用了 P1 口。
  2. delay_ms 函数是一个简单的延时函数,用于软件消抖。
  3. KeypadScan 函数是键盘扫描函数,通过行列扫描的方式,获取按键值。
  4. 在主函数中,不断调用 KeypadScan 函数,获取按键值,并根据按键值执行相应的操作。
  5. 这里为了方便观察结果,使用四个LED灯的亮灭作为结果展示

实战避坑经验总结

  • IO 口驱动能力不足: 51 单片机的 IO 口驱动能力有限,如果键盘连接的电阻过小,可能会导致 IO 口输出高电平时电压不足,从而导致扫描不准确。解决方法是适当增大电阻。
  • 干扰问题: 在复杂的电磁环境下,键盘扫描可能会受到干扰,导致误判。解决方法是使用屏蔽线,或者增加滤波电路。
  • 消抖时间不合理: 消抖时间过短,可能无法消除抖动;消抖时间过长,会影响按键响应速度。需要根据实际情况调整消抖时间。
  • 行列线接反: 矩阵键盘的行列线如果接反了,会导致扫描结果错误。解决方法是仔细检查硬件连接。
  • 上拉电阻: 如果列线没有上拉电阻,可能会导致列线电平不稳定,从而导致扫描不准确。解决方法是在列线上加上拉电阻。

掌握了以上技巧,相信你就能轻松驾驭 51 单片机的矩阵键盘了。希望本文能够帮助到正在学习 51 单片机的你!记住,实践是检验真理的唯一标准,多动手实践才能真正掌握知识。

51单片机矩阵键盘入门:原理、代码与避坑指南(基于江协科技)

转载请注明出处: 代码小能豆

本文的链接地址: http://m.acea4.store/blog/545200.SHTML

本文最后 发布于2026-04-05 15:21:52,已经过了22天没有更新,若内容或图片 失效,请留言反馈

()
您可能对以下文章感兴趣
评论
  • 单身狗 5 天前
    请问大佬,有没有关于数码管显示的教程,最好也像这篇文章一样详细!
  • 折耳根yyds 2 天前
    IO 口驱动能力确实是个坑,之前就被这个问题困扰了很久。
  • 柚子很甜 2 天前
    请问大佬,有没有关于数码管显示的教程,最好也像这篇文章一样详细!
  • 烤冷面 6 天前
    代码很实用,直接拿来就能用,省了不少时间。