51单片机学习笔记 STC89C52RC (05)矩阵键盘和独立键盘(轻触开关)

发布时间 2023-04-22 21:53:56作者: 沉默的王さん

按键抖动,需要消抖

 原理图来自清翔电子

一、独立键盘模块

1.可以直接获取  P3^0对应S2  P3^1对应S3  P3^2对应S4  P3^3对应S5  的电压

当轻触开关按下时,电流会流向GND,此时这一路的电压为0V,松开轻触开关,又变为5V

 

//第一种方法:单个I/O口检测控制

#include <reg51.h>

sbit S2 = P3^0;
sbit S3 = P3^1;
sbit S4 = P3^2;
sbit S5 = P3^3;

void main() {
    if(S2 == 0) {//判断按键是否被按下,按下就是电压为0
        Delay10ms();//按键消抖
        if(S2 == 0) {//判断按键是真的被按下
            //要执行的代码
        }//此时按键一直处于按下状态,也就是电压一直为0
        while(!S2);//按键不松手,就不重复执行,此时S2为0,!取反后为1,就会一直在循环里不出来
    }
    if(S3 == 0) {
        Delay10ms();
        while(!S3);
        if(S3 == 0) {//松手响应,与S2不同,S2为按下相应,和键盘一样
            //要执行的代码
        }
    }
    if(S4 == 0) {
        Delay10ms();
        if(S4 == 0) {
            //要执行的代码
        }
        while(!S4);
    }
    if(S5 == 0) {
        Delay10ms();
        if(S5 == 0) {
            //要执行的代码
        }
        while(!S5);
    }
}

//第二种方法:用switch对I/O口检测控制

#include <reg51.h>

void main() {
    P3 = 0xFF;//默认所有P3口为高电平,二进制1111 1111
    if(P3 != 0xFF){//按键按下,电压发生变化
        Delay10ms();//消除按键抖动
        if(P3 != 0xFF) {//判断按键是真的被按下
            switch(P3) {
                 /*
                     0xFE 1111 1110  P0^0口电压为0
                     0xFD 1111 1101  P0^1口电压为0
                     0xFB 1111 1011  P0^2口电压为0
                     0xF7 1111 0111  P0^3口电压为0
                 */
                case 0xFE:  //S2按键要执行的逻辑代码;	
                    break;
                case 0xFD: //S3按键要执行的逻辑代码;	
                    break;
                case 0xFB: //S4按键要执行的逻辑代码;	
                    break;
                case 0xF7: //S5按键要执行的逻辑代码;	
                    break;
            }
        }
    }
}

二、独立键盘模块

1.行扫描 + 列扫描 可以准确获取那一个按钮被按下

#include <reg51.h>

unsigned char keyValue;

void main() {
//4*4矩阵键盘
    P3 = 0xF0;//行选择器 二进制1111 0000
	if(P3 != 0xF0) {//判断按键是否被按下
		Delay10ms();//软件消抖
		if(P3 != 0xF0) {//判断按键是真的被按下
			switch(P3) {
				case 0xE0: keyValue = 0;
                    break;
				case 0xD0: keyValue = 1;	
                    break;
				case 0xB0: keyValue = 2;	
                    break;
				case 0x70: keyValue = 3;	
                    break;
			}
			P3 = 0x0F;//行选择器 二进制0000 1111
			switch(P3) {
				case 0xE: keyValue = keyValue;	//第一行第一个为 S6 记为第0个,后面根据原理图往后依次S7 S8 S9
                    break;
				case 0xD: keyValue = keyValue + 4;	//第二行第一个为 S10 记为第0个,后面根据原理图往后依次S11 S12 S13
                    break;
				case 0xB: keyValue = keyValue + 8;	//第三行第一个为 S14 记为第0个,后面根据原理图往后依次S15 S16 S17
                    break;
				case 0x7: keyValue = keyValue + 12;	//第四行第一个为 S18 记为第0个,后面根据原理图往后依次S19 S20 S21
                    break;
			}
		}
	}
}

图解,编程一下就很好理解了