stm32 工业按键检测_「正点原子STM32Mini板资料连载」第七章 按键输入实验
1)实验平台:正点原子STM32mini开发板
2)摘自《正点原子STM32 不完全手册(HAL 库版)》关注官方微信号公众号,获取更多资料:正点原子
第七章 按键输入实验
上一章,我们介绍了 STM32 的 IO 口作为输出的使用,这一章,我们将向大家介绍如何使
用 STM32 的 IO 口作为输入用。在本章中,我们将利用板载的 3 个按键,来控制板载的两个 LED
的亮灭。通过本章的学习,你将了解到 STM32 的 IO 口作为输入口的使用方法。本章分为如下
几个小节:
7.1 STM32 IO 口简介
7.2 硬件设计
7.3 软件设计
7.4 下载验证
7.1 STM32 IO 口简介
STM32 的 IO 口在上一章已经有了详细的介绍,这里我们不再多说。STM32 的 IO 口做输
入使用的时候,是通过读取 IDR 的内容来读取 IO 口的状态的。了解了这点,就可以开始我们
的代码编写了。
这一节,我们将通过 MiniSTM32 开发板上载有的 3 个按钮(KEY0/KEY1/WK_UP),来控
制板上的 2 个 LED,其中 KEY0 控制 DS0,按一次亮,再按一次,就灭。KEY1 控制 DS1,效
果同 KEY0。WK_UP 按键则同时控制 DS0 和 DS1,按一次,他们的状态就翻转一次。
。
7.2 硬件设计
本实验用到的硬件资源有:
1) 指示灯 DS0、DS1
2) 3 个按键:KEY0、KEY1 和 KEY_UP。
DS0、DS1 和 STM32 的连接在上一章已经介绍了,在 MiniSTM32 开发板上的按键 KEY0
连接在 PC5 上、KEY1 连接在 PA15 上、WK_UP 连接在 PA0 上。如图 7.2.1 所示:
图 7.2.1 按键与 STM32 连接原理图
这里需要注意的是:KEY0 和 KEY1 是低电平有效的,而 WK_UP 是高电平有效的,除了
KEY1 有上拉电阻(与 JTDI 共用),其他两个都没有上下拉电阻,所以,需要在 STM32 内部设
置上下拉。
7.3 软件设计
这里的代码设计,我们还是在之前的基础上继续编写,打开上一章的 TEST 工程,然后在
HARDWARE 文件夹下新建一个 KEY 文件夹,用来存放与按键相关的代码。如图 7.3.1 所示:
图 7.3.1 在 HARDWARE 下新增 KEY 文件夹
然后我们打开 USER 文件夹下的 test.uvprojx 工程,按
按钮新建一个文件,然后保存在
HARDWARE→KEY 文件夹下面,保存为 key.c。在该文件中输入如下代码:
#include "key.h"
#include "delay.h"
//按键初始化函数
void KEY_Init(void)
{
GPIO_InitTypeDef GPIO_Initure;
__HAL_RCC_GPIOA_CLK_ENABLE(); //开启 GPIOA 时钟
__HAL_RCC_GPIOC_CLK_ENABLE(); //开启 GPIOC 时钟
GPIO_Initure.Pin=GPIO_PIN_0;
//PA0
GPIO_Initure.Mode=GPIO_MODE_INPUT; //输入
GPIO_Initure.Pull=GPIO_PULLDOWN; //下拉
GPIO_Initure.Speed=GPIO_SPEED_FREQ_HIGH; //高速
HAL_GPIO_Init(GPIOA,&GPIO_Initure);
GPIO_Initure.Pin=GPIO_PIN_15;
//PA15
GPIO_Initure.Pull=GPIO_PULLUP; //上拉
HAL_GPIO_Init(GPIOA,&GPIO_Initure);
GPIO_Initure.Pin=GPIO_PIN_5;
//PC5
GPIO_Initure.Pull=GPIO_PULLUP; //上拉
HAL_GPIO_Init(GPIOC,&GPIO_Initure);
}
//按键处理函数
//返回按键值
//mode:0,不支持连续按;1,支持连续按;
//0,没有任何按键按下
//1,WKUP 按下 WK_UP
//注意此函数有响应优先级,KEY0>KEY1>KEY2>WK_UP!!
u8 KEY_Scan(u8 mode)
{
static u8 key_up=1; //按键松开标志
if(mode==1)key_up=1; //支持连按
if(key_up&&(KEY0==0||KEY1==0||WK_UP==1))
{
delay_ms(10);
key_up=0;
if(KEY0==0) return KEY0_PRES;
else if(KEY1==0) return KEY1_PRES;
else if(WK_UP==1) return WKUP_PRES;
}else if(KEY0==1&&KEY1==1&&WK_UP==0)key_up=1;
return 0; //无按键按下
}
这段代码包含 2 个函数,void KEY_Init(void)和 u8 KEY_Scan(u8 mode),KEY_Init 是用来
初始化按键输入的 IO 口的。实现 PA0、PA15 和 PC5 的输入设置,注意这调用了:JTAG_Set
这个函数,用于禁止 JTAG,开启 SWD,因为 PA15 占用了 JTAG 的一个 IO,所以要禁止 JTAG,
从而让 PA15 用作普通 IO 输入。
KEY_Scan 函数,则是用来扫描这 3 个 IO 口是否有按键按下。KEY_Scan 函数,支持两种
扫描方式,通过 mode 参数来设置。
当 mode 为 0 的时候,KEY_Scan 函数将不支持连续按,扫描某个按键,该按键按下之后必
须要松开,才能第二次触发,否则不会再响应这个按键,这样的好处就是可以防止按一次多次
触发,而坏处就是在需要长按的时候就不合适了。
当 mode 为 1 的时候,KEY_Scan 函数将支持连续按,如果某个按键一直按下,则会一直返
回这个按键的键值,这样可以方便的实现长按检测。
有了 mode 这个参数,大家就可以根据自己的需要,选择不同的方式。这里要提醒大家,
因为该函数里面有 static 变量,所以该函数不是一个可重入函数,在有 OS 的情况下,这个大家
要留意下。同时还有一点要注意的就是,该函数的按键扫描是有优先级的,最优先的是 KEY0,
第二优先的是 KEY1,最后是 WK_UP 按键。该函数有返回值,如果有按键按下,则返回非 0
值,如果没有或者按键不正确,则返回 0。
保存 key.c 代码,然后我们按同样的方法,新建一个 key.h 文件,也保存在 KEY 文件夹下
面。在 key.h 中输入如下代码:
#ifndef __KEY_H
#define __KEY_H
#include "sys.h"
#define KEY0 HAL_GPIO_ReadPin(GPIOC,GPIO_PIN_5) //KEY0 按键 PC5
#define KEY1 HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_15) //KEY1 按键 PA15
#define WK_UP HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_0) //WKUP 按键 PA0
#define KEY0_PRES 1
#define KEY1_PRES 2
#define WKUP_PRES 3
void KEY_Init(void);
u8 KEY_Scan(u8 mode);
#endif
这段代码里面最关键就是 3 个宏定义:
#define KEY0 HAL_GPIO_ReadPin(GPIOC,GPIO_PIN_5) //KEY0 按键 PC5
#define KEY1 HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_15) //KEY1 按键 PA15
#define WK_UP HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_0) //WKUP 按键 PA0
这里使用的是位带操作来实现读取某个 IO 口的 1 个位的。同输出一样,上面的功能也同
样可以通过位带操作来简单的实现:
#define KEY0 PCin(5) //KEY0 按键 PC5
#define KEY1 PAin(15) //KEY1 按键 PA15
#define WK_UP PAin(0) //WKUP 按键 PA0
用库函数实现的好处是在各个 STM32 芯片上面的移植性非常好,不需要修改任何代码。
用位带操作的好处是简洁,至于使用哪种方法,看各位的爱好了。
在 key.h 中,我们还定义了 KEY0_PRES / KEY1_PRES / KEYUP_PRES 等 3 个宏定义,分
别对应开发板的 KEY0、KEY1 和 WK_UP 按键按下时 KEY_Scan 的返回值。通过这些宏定义,
可以方便大家记忆和使用。
将 key.h 也保存一下。接着,我们把 key.c 加入到 HARDWARE 这个组里面,这一次我们通
过双击的方式来增加新的.c 文件,双击 HARDWARE,找到 key.c,加入到 HARDWARE 里面,
如图 7.3.2 所示:
图 7. 3.2 将 key.c 加入 HARDWARE 组下
可以看到 HARDWARE 文件夹里面多了一个 key.c 的文件, 然后还是用老办法把 key.h 头
文件所在的路径加入到工程里面。回到主界面,在 test.c 里面编写如下代码:
#include "sys.h"
#include "usart.h"
#include "delay.h"
#include "led.h"
#include "key.h"
int main(void)
{
u8 key=0;
HAL_Init();
//初始化 HAL 库
Stm32_Clock_Init(RCC_PLL_MUL9); //设置时钟,72M
delay_init(72);
//初始化延时函数
LED_Init();
//初始化 LED
KEY_Init();
//初始化按键
LED0=0;
//点亮 LED
while(1)
{
key=KEY_Scan(0);
//得到键值
switch(key)
{
case KEY0_PRES:
LED0=!LED0;
break;
case KEY1_PRES:
LED1=!LED1;
break;
case WKUP_PRES:
LED0=!LED0;
LED1=!LED1;
break;
default:
delay_ms(10);
}
}
}
注意要将 KEY 文件夹加入头文件包含路径,不能少,否则编译的时候会报错。这段代码
就实现前面 7.1 节所阐述的功能,相对比较简单。
然后按
,编译工程,得到结果如图 7.3.3 所示
图 7.3.3 编译结果
可以看到没有错误,也没有警告。接下来,大家就可以下载验证了。
7.4 下载验证
同样,我们还是通过 flymcu 下载代码,在下载完之后,我们可以按 KEY0、KEY1 和 KEY_UP
来看看 DS0 和 DS1 以及蜂鸣器的变化,是否和我们预期的结果一致?
特别注意:因为 PA0 用作按键输入,而且是高电平有效的,所以不要把 PA0 和 1820 的跳
线帽短接在一起了,否则会按键“失灵”。
至此,我们的本章的学习就结束了。本章,作为 STM32F1 的入门第三个例子,介绍了
STM32F1 的 IO 作为输入的使用方法,同时巩固了前面的学习。希望大家在开发板上实际验证
一下,从而加深印象。
stm32 工业按键检测_「正点原子STM32Mini板资料连载」第七章 按键输入实验相关推荐
- stm32 读取sd卡图片显示_「正点原子STM32Mini板资料连载」第三十五章 汉字显示实验...
1)实验平台:正点原子STM32mini开发板 2)摘自<正点原子STM32 不完全手册(HAL 库版)>关注官方微信号公众号,获取更多资料:正点原子 第三十五章 汉字显示实验 汉字显示在 ...
- stm32l0的停止模式怎么唤醒_「正点原子STM32Mini板资料连载」第十九章 待机唤醒实验...
1)实验平台:正点原子STM32mini开发板 2)摘自<正点原子STM32 不完全手册(HAL 库版)>关注官方微信号公众号,获取更多资料:正点原子 第十九章 待机唤醒实验 本章我们将向 ...
- 1709 ltsb 内存占用_「正点原子STM32Mini板资料连载」第三十二章 内存管理实验
1)实验平台:正点原子STM32mini开发板 2)摘自<正点原子STM32 不完全手册(HAL 库版)>关注官方微信号公众号,获取更多资料:正点原子 第三十二章 内存管理实验 上一章,我 ...
- 看门狗寄存器c语言代码_「正点原子NANO STM32F103开发板资料连载」第十一章 看门狗实验...
1)实验平台:[正点原子] NANO STM32F103 开发板 2)摘自<正点原子STM32 F1 开发指南(NANO 板-HAL 库版)>关注官方微信号公众号,获取更多资料:正点原子 ...
- 判断按键值_「正点原子NANO STM32开发板资料连载」第十六章电容触摸按键实验...
1)实验平台:ALIENTEK NANO STM32F411 V1开发板2)摘自<正点原子STM32F4 开发指南(HAL 库版>关注官方微信号公众号,获取更多资料:正点原子 第十六章电容 ...
- stm32 文件系统dma大小_「正点原子NANO STM32F103开发板资料连载」第二十二章 DMA 实验...
1)实验平台:[正点原子] NANO STM32F103 开发板 2)摘自<正点原子STM32 F1 开发指南(NANO 板-HAL 库版)>关注官方微信号公众号,获取更多资料:正点原子 ...
- stm32看门狗_「正点原子NANO STM32开发板资料连载」第十一章 独立看门狗实验
1)实验平台:ALIENTEK NANO STM32F411 V1开发板2)摘自<正点原子STM32F4 开发指南(HAL 库版>关注官方微信号公众号,获取更多资料:正点原子 第十一章 独 ...
- 韦东山 IMX6ULL和正点原子_「正点原子NANO STM32开发板资料连载」第三章 MDK5 软件入门1...
1)实验平台:ALIENTEK NANO STM32F411 V1开发板 2)摘自<正点原子STM32F4 开发指南(HAL 库版>关注官方微信号公众号,获取更多资料:正点原子 第三章 M ...
- 嵌入式实时操作系统ucos-ii_「正点原子NANO STM32开发板资料连载」第三十八章 UCOSII 实验 3...
1)实验平台:alientek NANO STM32F411 V1开发板2)摘自<正点原子STM32F4 开发指南(HAL 库版>关注官方微信号公众号,获取更多资料:正点原子 第三十八章 ...
最新文章
- Ubuntu12.04 安装 mongodb
- 【错误记录】Flutter 构建报错 ( Because xxx requires SDK version >=2.12.0-0 <3.0.0, versio | Dart SDK 版本低 )
- 二分法(递归非递归)
- flink写入 mysql_flink写数据到mysql(java)
- WebService的学习
- git - 基础 - 01 - git reset --hard 回滚以后,看不到之前的分支版本怎么解决:
- go interface类型转换_Go语言的九大核心特性主要有哪些?
- beetle 2.7海量消息广播测试
- 面板x轴模式包括哪些_虎扑轻跃 | 体验一汽大众探岳X
- Git学习笔记 - 钢钢更新
- 数据结构之--series,DataFrame.use python and pandas for data mining
- java 面试 概率论_仿概率论系列(一) 开篇引导
- 高等数学——常用不定积分公式
- 谷歌Chrome浏览器就能远程控制安卓手机,电脑远程控制手机的快捷方法get!
- linux磁盘配额测试,Linux磁盘配额测试过程完全攻略
- Unity 灯光系统(一)
- 学习强国十年磨剑最新分数及排名
- 【CTR预估】The Wide and Deep Learning Model(译文+Tensorlfow源码解析)
- 桑基图绘制的简易操作
- 计算机网络的基本知识和技术
热门文章
- html5 文字定义线宽,html 5画布线宽
- python计算身体质量指数_利用Python计算身体质量指数BMI来判断体型
- 胡想——对机器人控制体系的一些想法
- key php 转小写_PHP代码层防护与绕过
- tensorflow创建张量
- python 下载大文件
- 目标定位--Deep Self-Taught Learning for Weakly Supervised Object Localization
- python协程异步原理_简单介绍Python的Tornado框架中的协程异步实现原理
- c语言bool怎么用_C语言中的一维数组和二维数组什么?怎么用?
- C++_类和结构体所占内存大小,静态成员问题