标题:
STM32 GPIO按键检测技术(按键复用源码)
[打印本页]
作者:
MrHuan991
时间:
2019-2-16 03:04
标题:
STM32 GPIO按键检测技术(按键复用源码)
自己刚刚学STM32一个礼拜,学完了GPIO,尝试自己写了按键的检测,最简单的单击,
能准确的识别每一次,再到双击(其实多击逻辑一样),长按等复用模式。
这里提一下按键复用的思想:其实在做产品的时候,有复用思想可以节约按键,降低后期产品的PCB体积大小
具体的STM32实现的功能我简述下,刚刚入门的萌新可以看下,写的一般。
(1)环境复用:这个简单,就是不同环境设置不同标志量即可
(2)组合复用:这里就是通过按两次实现一个组合的效果,当然你写复杂了有许多组合的效果,我这个小程序主要是在220ms内连续
按下两次,PC13口连接的LED会闪烁2.5s,间隔是50ms。
(3)时间复用:就是长按,通过按键时间的长短实现不同功能。(长按复位,其中STM32的复位必须先关闭中断,再调用NVIC中的复位函数
因为复位前有个延时,会影响复位的效果)
注:如果能用TIM(定时器)检测按键,实现按键效果,更加perfect
萌新们一定要学会自己建立STM32工程哟
0.png
(35.07 KB, 下载次数: 49)
下载附件
2019-2-16 03:32 上传
这是我的通过按键来实现不同功能的灯亮的实验。
1.主要用到GPIO输入与输出的技术。
2.按键的复用功能
(1).环境复用:这个简单,不同标志下实现不同功能,这里就不做功能实现了。
(2).组合复用:连续两次按键(220ms连续按两次),实现Led亮灭2.5s,亮灭间隔为50ms。
(3).时间切换:单次按键实现的Led的亮灭,长按实现STM32MicroController系统的复位。
单片机源程序如下:
#include <STM32F10X.H>
#include <misc.h>
#define PC14 GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_14) //独C14按键的值
#define PC15_On GPIO_SetBits(GPIOC,GPIO_Pin_15) //Set是置1
#define PC15_Off GPIO_ResetBits(GPIOC,GPIO_Pin_15) //Reset置0
#define PC13_Off GPIO_SetBits(GPIOC,GPIO_Pin_13) //Set是置1
#define PC13_On GPIO_ResetBits(GPIOC,GPIO_Pin_13) //Reset置0
u16 Led_Count=0,Button_Flag=0,time=0;
void RCC_Configuration(void); //复位与时钟寄存器初始化函数
void Delay_ms(u16 n); //延时函数ms
void GPIO_Configuration(void); //通用IO口初始化函数
void System_Reset(void); //系统复位函数
void Led_Show(void); //Led亮灭显示函数
u16 Key_Mode(u16 time); //时间复用模式
void Group_Button(void); //组合复用模式(双击,多击鼠标的检测函数)
int main(void)
{
RCC_Configuration();
GPIO_Configuration();
while(1)
{
switch(Key_Mode(100))
{
case 0:break;
case 1:Led_Show();break;
case 2:System_Reset();break;
default:break;
}
Group_Button();
}
}
void RCC_Configuration(void)
{
SystemInit();
}
void Delay_ms(u16 n)
{
u16 i;
while(n--)
{
i=12000;
while(i--);
}
}
void GPIO_Configuration(void)
{
//配置按键输出的工作模式,同组的同类型一次配置,同组不同类型分次配置
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC,ENABLE);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_13|GPIO_Pin_15;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_Init(GPIOC,&GPIO_InitStructure);
//配置按键输入的工作模式
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_14;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IPU;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_Init(GPIOC,&GPIO_InitStructure);
PC15_Off;PC13_Off;
}
void System_Reset(void) //系统软件复位函数
{
PC13_On;
Delay_ms(500);
__set_FAULTMASK(1); //首先先要关闭中断
NVIC_SystemReset(); //在进行软复位
}
u16 Key_Mode(u16 time) //独立按键函数
{
u16 i=0;
if(PC14 == 0)
{
Delay_ms(10);
if(PC14 == 0)
{
while(!PC14)
{
Delay_ms(10);i++;
}
Button_Flag++;
}
}
if(i == 0)
return 0;
else
{
if(i < time)
return 1;
else
return 2;
}
}
void Led_Show(void)
{
Led_Count++;
if(Led_Count == 1)
PC15_On;
else
{
PC15_Off;Led_Count=0;
}
}
void Group_Button(void) //双击鼠标和多击鼠标的模块写出来了,后期用定时器系统能干其他的事情
{ //其实单片机是单线程,所谓的中断无非是效率更高,其实主程序仍不能干其他事情
u16 i=0;
if(Button_Flag == 1)
{
PC13_On;Delay_ms(1);time++;
}
else
{
Button_Flag = 0;PC13_Off;
if(time < 220 && time > 5)
{
time = 0;
for(i=0;i<50;i++)
{
if(i%2 == 0)
{PC13_On;Delay_ms(50);}
else
{PC13_Off;Delay_ms(50);}
}
}
else time = 0;
}
}
复制代码
所有资料51hei提供下载:
DetectKey.7z
(191.26 KB, 下载次数: 26)
2019-2-16 03:33 上传
点击文件名下载附件
下载积分: 黑币 -5
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1