stm32f103c8t6之4x4矩阵按键

基于普中精灵开发板
1、矩阵按键原理

当我们需要使用较多的按键时,单片机的IO口可能不够用,这是就需要使用矩阵按键。

对应IO口如下:

 步骤解析:

1、全部按键都没有按下时,全行IO为低电平(全列对应的IO设置为下拉低电平)。
2、第一行IO口全为高电平,检测对应列的IO口电平,2、3、4行对应IO为电平。
3、第二行IO口全为高电平,检测对应列的IO口电平,1、3、4行对应IO为电平。
4、第三行IO口全为高电平,检测对应列的IO口电平,1、2、4行对应IO为电平。
5、第四行IO口全为高电平,检测对应列的IO口电平,1、2、3行对应IO为电平。

 ---------------------------------------------------------******----------------------------------------------------------------

一、第一行IO口全为高电平,检测对应列的IO口电平,2、3、4行对应的IO为低电平,那么只需要读取列对应的4个IO口电平,就可以判断是第一行第几个按键按下。因为按下时按键连通,则对应的按键的列引脚电平就为高电平(列对应的io为电平)。

注意:行对应的引脚为推挽输出,列对应的引脚为下拉(默认低电平0)

 例如,当第一行第一个按键按下时,KEY_L1对应的IO电平将从0变为1,如下图所示。

 二、第二行IO口全为高电平,检测对应列的IO口电平,1、3、4行对应IO为电平。同样的思路进行编程

三、 按键扫描函数:
u8 KEY_Matrix_Scan(void)
{u8 col1,col2,col3,col4;//保存电平状态u8 key_value;//保存键值//1、没有检测到按键按下GPIO_SetBits(KEY_MATRIX_H1_PORT,KEY_MATRIX_H1_PIN);GPIO_SetBits(KEY_MATRIX_H2_PORT,KEY_MATRIX_H2_PIN);GPIO_SetBits(KEY_MATRIX_H3_PORT,KEY_MATRIX_H3_PIN);GPIO_SetBits(KEY_MATRIX_H4_PORT,KEY_MATRIX_H4_PIN);	//全部都没有按下,返回0if((GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))==0){return 0;}//有按下,但没有检测到,同样返回0else{delay_ms(5);//按键消抖if((GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))==0){return 0;}}//2、第一行检测GPIO_SetBits(KEY_MATRIX_H1_PORT,KEY_MATRIX_H1_PIN);GPIO_ResetBits(KEY_MATRIX_H2_PORT,KEY_MATRIX_H2_PIN);GPIO_ResetBits(KEY_MATRIX_H3_PORT,KEY_MATRIX_H3_PIN);GPIO_ResetBits(KEY_MATRIX_H4_PORT,KEY_MATRIX_H4_PIN);//记录电平col1=GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN);col2=GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN);col3=GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN);col4=GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN);if(col1==1&&col2==0&&col3==0&&col4==0)key_value=1;//第一行第一个按键按下了if(col1==0&&col2==1&&col3==0&&col4==0)key_value=2;//第一行第二个按键按下了if(col1==0&&col2==0&&col3==1&&col4==0)key_value=3;//第一行第三个按键按下了if(col1==0&&col2==0&&col3==0&&col4==1)key_value=4;//第一行第四个按键按下了//需判断按键是否松开,当某按键按下时值为1大于0为真,继续等待;当按键松开都没有按下时值为0>0为假,退出等待while((GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))>0);//3、第二行检测GPIO_ResetBits(KEY_MATRIX_H1_PORT,KEY_MATRIX_H1_PIN);GPIO_SetBits(KEY_MATRIX_H2_PORT,KEY_MATRIX_H2_PIN);GPIO_ResetBits(KEY_MATRIX_H3_PORT,KEY_MATRIX_H3_PIN);GPIO_ResetBits(KEY_MATRIX_H4_PORT,KEY_MATRIX_H4_PIN);//记录电平col1=GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN);col2=GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN);col3=GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN);col4=GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN);if(col1==1&&col2==0&&col3==0&&col4==0)key_value=5;//第二行第一个按键按下了if(col1==0&&col2==1&&col3==0&&col4==0)key_value=6;//第二行第二个按键按下了if(col1==0&&col2==0&&col3==1&&col4==0)key_value=7;//第二行第三个按键按下了if(col1==0&&col2==0&&col3==0&&col4==1)key_value=8;//第二行第四个按键按下了//需判断按键是否松开,当某按键按下时值为1大于0为真,继续等待;当按键松开都没有按下时值为0>0为假,退出等待while((GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))>0);//4、第三行检测GPIO_ResetBits(KEY_MATRIX_H1_PORT,KEY_MATRIX_H1_PIN);GPIO_ResetBits(KEY_MATRIX_H2_PORT,KEY_MATRIX_H2_PIN);GPIO_SetBits(KEY_MATRIX_H3_PORT,KEY_MATRIX_H3_PIN);GPIO_ResetBits(KEY_MATRIX_H4_PORT,KEY_MATRIX_H4_PIN);//记录电平col1=GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN);col2=GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN);col3=GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN);col4=GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN);if(col1==1&&col2==0&&col3==0&&col4==0)key_value=9;//第三行第一个按键按下了if(col1==0&&col2==1&&col3==0&&col4==0)key_value=10;//第三行第二个按键按下了if(col1==0&&col2==0&&col3==1&&col4==0)key_value=11;//第三行第三个按键按下了if(col1==0&&col2==0&&col3==0&&col4==1)key_value=12;//第三行第四个按键按下了//需判断按键是否松开,当某按键按下时值为1大于0为真,继续等待;当按键松开都没有按下时值为0>0为假,退出等待while((GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))>0);//5、第四行检测GPIO_ResetBits(KEY_MATRIX_H1_PORT,KEY_MATRIX_H1_PIN);GPIO_ResetBits(KEY_MATRIX_H2_PORT,KEY_MATRIX_H2_PIN);GPIO_ResetBits(KEY_MATRIX_H3_PORT,KEY_MATRIX_H3_PIN);GPIO_SetBits(KEY_MATRIX_H4_PORT,KEY_MATRIX_H4_PIN);//记录电平col1=GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN);col2=GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN);col3=GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN);col4=GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN);if(col1==1&&col2==0&&col3==0&&col4==0)key_value=13;//第四行第一个按键按下了if(col1==0&&col2==1&&col3==0&&col4==0)key_value=14;//第四行第二个按键按下了if(col1==0&&col2==0&&col3==1&&col4==0)key_value=15;//第四行第三个按键按下了if(col1==0&&col2==0&&col3==0&&col4==1)key_value=16;//第四行第四个按键按下了//需判断按键是否松开,当某按键按下时值为1大于0为真,继续等待;当按键松开都没有按下时值为0>0为假,退出等待while( (GPIO_ReadInputDataBit(KEY_MATRIX_L1_PORT,KEY_MATRIX_L1_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L2_PORT,KEY_MATRIX_L2_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L3_PORT,KEY_MATRIX_L3_PIN)|GPIO_ReadInputDataBit(KEY_MATRIX_L4_PORT,KEY_MATRIX_L4_PIN))>0);return key_value;
}

实验结果:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/688734.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

免费SSL证书有效期现状

自2024年4月25日起,腾讯云上申请的免费SSL证书有效期将从原先的12个月调整为3个月。而在其他平台,比如Gworg,已经有策略表明将停止签发1年期的免费SSL证书,转而仅提供有效期为3个月的证书。 目前,免费SSL证书的有效期…

docker(三):常用命令

0、启动命令 1、启动docker systemctl start docker2、停止docker systemctl stop docker3、重启docker: systemctl restart docker4、查看docker状态 systemctl status docker5、开机启动: systemctl enable docker6、查看docker概要信息 docker…

综合能力 | 误差 | 学习笔记

误差指真值与观测值的差值。 误差分为系统误差(消除方法:观测方法、仪器校正、修正等)、偶然误差(符合正态分布规律,进行计算纠正)、粗差(一般舍弃)。 中误差(均方差或标…

代码随想录算法训练营第二十天:二叉树成长

代码随想录算法训练营第二十天:二叉树成长 110.平衡二叉树 力扣题目链接(opens new window) 给定一个二叉树,判断它是否是高度平衡的二叉树。 本题中,一棵高度平衡二叉树定义为:一个二叉树每个节点 的左右两个子树的高度差的绝…

内容安全(AV)

防病毒网关(AV)简介 基于网络侧 识别 病毒文件,工作范围2~7层。这里的网关指的是内网和外网之间的一个关口,在此进行病毒的查杀。在深信服中就有一个EDR设备,该设备就是有两种部署,一个部署在网关&#xf…

mybatisPlus一个事务中切换数据源概述

概述 在多数据源的配置下,业务中经常遇到在一个被本地事务包裹的save/edi方法中需要查询另一个数据源的数据; 直接查询会提示table不存在,这是因为一个事务和一个mysql连接是绑定的,mysql的连接背后包含了数据库信息,…

[AutoSar]lauterbach_001_ORTI_CPUload_Trace

目录 关键词平台说明一、ORTI概述二、ORTI文件的生成三、ORTI文件的导入四、Trace 功能4.1 Trace 功能菜单介绍4.2 Trace功能的配置4.3 Trace MCDS 设置4.4 Task Switches断点的设置4.5 Trace 数据的录取4.6 CPU 负载和Task调度的查看 关键词 嵌入式、C语言、autosar、OS、BSW…

如何禁止打开PDF文件?推荐2种方法!

在工作中,我们经常会使用到PDF文件,对于重要的文件,不想被随意打开怎么办呢?下面小编分享2个方法,第二个很实用,记得收藏起来! 方法1:设置密码保护 我们可以通过PDF编辑器&#xff…

人脸识别之bbox【det_10g】-ncnn(c++)

模型描述 det_10g是insightface 人脸框图和人脸关键点的分类,最终能够得到人脸框图bbox,分值还有人脸五官(眼x2、鼻子x1、嘴巴x2) 由于我这里没有采用最终结果,通过onnx转换为ncnn,所以后面的步骤结果丢弃…

测斜仪的具体应用:从地下工程到斜坡监测

测斜仪作为一种精密的测量工具,在多个领域都有广泛的应用。从最初的地下工程,到现今的斜坡监测,测斜仪的技术进步和应用范围的扩大,为工程安全提供了有力的保障。 一、地下工程中的测斜仪应用 在地下工程中,测斜仪主要…

Node.js安装与配置环境 v20.13.1(LTS)

1 下载 Node.js — Run JavaScript Everywhere LTS -- long-term support,长期维护版本 如果要下载其他版本在download里选择下载 2 安装 一路点击next,默认安装路径C:\Program Files\nodejs 3 环境变量配置 1)Path环境变量增加nodejs安装…

uniapp下拉选择组件

uniapp下拉选择组件 背景实现思路代码实现配置项使用尾巴 背景 最近遇到一个这样的需求,在输入框中输入关键字,通过接口查询到结果之后,以下拉框列表形式展现供用户选择。查询了下uni-app官网和项目中使用的uv-ui库,没找到符合条…