完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
STM32F103按键控制
按键双击,长按有效,单击取消 在学习过程中需要完成稍微复杂一点的功能,按键又不想设计太多(主要节省成本) 在工程中主要有以下几个步骤 一、按键初始化 1、初始化按键IO引脚,这里配置的是上拉输入 2、编写单个按键检测程序(加延时消抖) 3、宏定义每个按键的状态值Key_State 4、编写判断是否有按键按下函数,并确定此按键的状态值 5、编写按键功能函数 二、定时器初始化 1、选择通用定时器 2、配置定时器时间,并开启中断 3、编写中断服务函数 //宏定义每个按键的状态值Key_State #define KEY1_STATE_VALUE (0x0001) #define KEY2_STATE_VALUE (0x0002) #define KEY3_STATE_VALUE (0x0004) #define KEY4_STATE_VALUE (0x0008) #define KEY5_STATE_VALUE (0x0010) #define KEY6_STATE_VALUE (0x0020) #define KEY7_STATE_VALUE (0x0040) #define KEY8_STATE_VALUE (0x0080) #define KEY9_STATE_VALUE (0x0100) #define KEY10_STATE_VALUE (0x0200) #define KEY11_STATE_VALUE (0x0400) #define KEY12_STATE_VALUE (0x0800) //按键延时超时值 #define Key_Two_Click_Time 200 //200以内双击有效输出 #define Key_Long_Click_Time 300 //长按300及以上有效输出 uint16_t Key_State = 0; //按键状态值 uint8_t Key_Value = 0; //按键按下去的值 uint8_t Old_Key_Value = 0; //上一次按键按下去的值 uint8_t Key_Ture_Value = 0; //最终输出的值 uint8_t Old_Key_Ture_Value = 0; //上一次最终输出的值 uint8_t Key_Down_Count_Flag = 0;//按键按下次数的值,用于判断是单击还是双击 uint8_t Key_Down_Flag = 0; //按键按下标志位,防止一直按着导致按键次数一直增加 uint16_t Key_Click_Time = 0; //按键次数为1时开始计时,其他状态为0 void Key_Init(void) //初始化12个按键引脚 { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC,ENABLE); GPIO_InitStructure.GPIO_Pin = KYE10_GPIO_PIN| KYE8_GPIO_PIN| KYE7_GPIO_PIN| KYE6_GPIO_PIN| KYE5_GPIO_PIN| KYE4_GPIO_PIN| KYE3_GPIO_PIN| KYE1_GPIO_PIN; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOA,&GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = KYE2_GPIO_PIN; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOB,&GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = KYE9_GPIO_PIN| KYE11_GPIO_PIN| KYE12_GPIO_PIN; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; GPIO_Init(GPIOC,&GPIO_InitStructure); } /* * 描述: 返回key1控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key1_State(void) { if(GPIO_ReadInputDataBit(KEY1_GPIO,KYE1_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY1_GPIO,KYE1_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key2控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key2_State(void) { if(GPIO_ReadInputDataBit(KEY2_GPIO,KYE2_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY2_GPIO,KYE2_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key3控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key3_State(void) { if(GPIO_ReadInputDataBit(KEY3_GPIO,KYE3_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY3_GPIO,KYE3_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key4控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key4_State(void) { if(GPIO_ReadInputDataBit(KEY4_GPIO,KYE4_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY4_GPIO,KYE4_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key5控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key5_State(void) { if(GPIO_ReadInputDataBit(KEY5_GPIO,KYE5_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY5_GPIO,KYE5_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key6控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key6_State(void) { if(GPIO_ReadInputDataBit(KEY6_GPIO,KYE6_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY6_GPIO,KYE6_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key7控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key7_State(void) { if(GPIO_ReadInputDataBit(KEY7_GPIO,KYE7_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY7_GPIO,KYE7_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key8控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key8_State(void) { if(GPIO_ReadInputDataBit(KEY8_GPIO,KYE8_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY8_GPIO,KYE8_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key9控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key9_State(void) { if(GPIO_ReadInputDataBit(KEY9_GPIO,KYE9_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY9_GPIO,KYE9_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key10控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key10_State(void) { if(GPIO_ReadInputDataBit(KEY10_GPIO,KYE10_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY10_GPIO,KYE10_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key11控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key11_State(void) { if(GPIO_ReadInputDataBit(KEY11_GPIO,KYE11_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY11_GPIO,KYE11_GPIO_PIN) == RESET) { return 0; } } return 1; } /* * 描述: 返回key12控制键的状态 * 参数: 无 * 返回值:0按下 1没按下 */ uint8_t Get_Key12_State(void) { if(GPIO_ReadInputDataBit(KEY12_GPIO,KYE12_GPIO_PIN) == RESET) { Delay_Ms(10); if(GPIO_ReadInputDataBit(KEY12_GPIO,KYE12_GPIO_PIN) == RESET) { return 0; } } return 1; } /* *描述: 判断只有一个按键按下 *参数: 无 *返回值: 1:有按键按下,0:无按键按下 */ uint8_t Key_Down_Num(void) { if(0 == Get_Key1_State()) { Delay_Ms(10); if(0 == Get_Key1_State()) { Key_State |= KEY1_STATE_VALUE; } } else { Key_State &= ~KEY1_STATE_VALUE; } /// if(0 == Get_Key2_State()) { Delay_Ms(10); if(0 == Get_Key2_State()) { Key_State |= KEY2_STATE_VALUE; } } else { Key_State &= ~KEY2_STATE_VALUE; } /// if(0 == Get_Key3_State()) { Delay_Ms(10); if(0 == Get_Key3_State()) { Key_State |= KEY3_STATE_VALUE; } } else { Key_State &= ~KEY3_STATE_VALUE; } /// if(0 == Get_Key4_State()) { Delay_Ms(10); if(0 == Get_Key4_State()) { Key_State |= KEY4_STATE_VALUE; } } else { Key_State &= ~KEY4_STATE_VALUE; } /// if(0 == Get_Key5_State()) { Delay_Ms(10); if(0 == Get_Key5_State()) { Key_State |= KEY5_STATE_VALUE; } } else { Key_State &= ~KEY5_STATE_VALUE; } /// if(0 == Get_Key6_State()) { Delay_Ms(10); if(0 == Get_Key6_State()) { Key_State |= KEY6_STATE_VALUE; } } else { Key_State &= ~KEY6_STATE_VALUE; } /// if(0 == Get_Key7_State()) { Delay_Ms(10); if(0 == Get_Key7_State()) { Key_State |= KEY7_STATE_VALUE; } } else { Key_State &= ~KEY7_STATE_VALUE; } /// if(0 == Get_Key8_State()) { Delay_Ms(10); if(0 == Get_Key8_State()) { Key_State |= KEY8_STATE_VALUE; } } else { Key_State &= ~KEY8_STATE_VALUE; } /// if(0 == Get_Key9_State()) { Delay_Ms(10); if(0 == Get_Key9_State()) { Key_State |= KEY9_STATE_VALUE; } } else { Key_State &= ~KEY9_STATE_VALUE; } /// if(0 == Get_Key10_State()) { Delay_Ms(10); if(0 == Get_Key10_State()) { Key_State |= KEY10_STATE_VALUE; } } else { Key_State &= ~KEY10_STATE_VALUE; } /// if(0 == Get_Key11_State()) { Delay_Ms(10); if(0 == Get_Key11_State()) { Key_State |= KEY11_STATE_VALUE; } } else { Key_State &= ~KEY11_STATE_VALUE; } /// if(0 == Get_Key12_State()) { Delay_Ms(10); if(0 == Get_Key12_State()) { Key_State |= KEY12_STATE_VALUE; } } else { Key_State &= ~KEY12_STATE_VALUE; } /// Key_State &= 0x0fff; if(Key_State != 0) { return 1; } return 0; } /* *描述: 按键检测 *参数: 无 *返回值: 无 */ void Key_Scanf(void) { if(1 == Key_Down_Num())//判断是否有按键按下 { Old_Key_Value = Key_Value; //每一次按下记录上一次按键的值 switch(Key_State) //判断按键状态值 { case KEY1_STATE_VALUE:Key_Value = 1;break; case KEY2_STATE_VALUE:Key_Value = 2;break; case KEY3_STATE_VALUE:Key_Value = 3;break; case KEY4_STATE_VALUE:Key_Value = 4;break; case KEY5_STATE_VALUE:Key_Value = 5;break; case KEY6_STATE_VALUE:Key_Value = 6;break; case KEY7_STATE_VALUE:Key_Value = 7;break; case KEY8_STATE_VALUE:Key_Value = 8;break; case KEY9_STATE_VALUE:Key_Value = 9;break; case KEY10_STATE_VALUE:Key_Value = 10;break; case KEY11_STATE_VALUE:Key_Value = 11;break; case KEY12_STATE_VALUE:Key_Value = 12;break; default:Key_Value = 0;break; } if(Key_Down_Flag == 1) { Key_Down_Count_Flag++; //记录按键按下去的次数 } Key_Down_Flag = 0; } else { Key_Down_Flag = 1; } } /* *描述:判断是否是有效键值 *参数:无 *返回值:无 */ void GetKey_True_Touch(void) { if(Key_Down_Count_Flag == 1) //按下1次 { if(Key_Down_Flag == 0) //按键按下 { //定时器超过长按规定时间 if(Key_Click_Time >= Key_Long_Click_Time) { Key_Ture_Value = Key_Value; } else { Key_Ture_Value = 0; } } else ///按键松开 { //判断定时器时间是否超过规定时间 //如果超过规定时间,清零变量 if(Key_Click_Time > Key_Two_Click_Time) { Key_Ture_Value = 0; //输出值清零 Key_Click_Time = 0; //定时器时间清零 Key_Down_Count_Flag = 0; //按键次数清零 } } } else if(Key_Down_Count_Flag == 2)//按下2次 { //如果两次按键值相等,说明双击的是同一个按键 //如果两次按键值不相等,输出0; if(Old_Key_Value == Key_Value) { Key_Ture_Value = Key_Value; } else { Key_Ture_Value = 0; //输出值清零 } Key_Click_Time = 0; //定时器时间清零 Key_Down_Count_Flag = 0; //按键次数清零 while(Key_Down_Num()); //等待按键松开 } } //定时器配置// void TIM2_Init(void) { TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure; NVIC_InitTypeDef NVIC_InitStructure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2,ENABLE); //配置周期为5ms TIM_TimeBaseInitStructure.TIM_Period = 4999; TIM_TimeBaseInitStructure.TIM_Prescaler = 71; TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up; //向上计数 TIM_TimeBaseInitStructure.TIM_ClockDivision = 0; TIM_TimeBaseInit(TIM2,&TIM_TimeBaseInitStructure); TIM_ARRPreloadConfig(TIM2,ENABLE);//在ARR上启用或禁用TIMx外设预加载寄存器。 TIM_ITConfig(TIM2,TIM_IT_Update,ENABLE); TIM_Cmd(TIM2,ENABLE); NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02; NVIC_Init(&NVIC_InitStructure); } //中断服务函数 void TIM2_IRQHandler(void) { while(TIM_GetFlagStatus(TIM2,TIM_FLAG_Update)) { //按键单击,双击,长按监测 if(Key_Down_Count_Flag == 1) { Key_Click_Time++; if(Key_Click_Time > Key_Long_Click_Time) { Key_Click_Time = Key_Long_Click_Time; } } else { Key_Click_Time = 0; } TIM_ClearITPendingBit(TIM2,TIM_FLAG_Update); } } |
|
|
|
只有小组成员才能发言,加入小组>>
调试STM32H750的FMC总线读写PSRAM遇到的问题求解?
1780 浏览 1 评论
X-NUCLEO-IHM08M1板文档中输出电流为15Arms,15Arms是怎么得出来的呢?
1621 浏览 1 评论
1081 浏览 2 评论
STM32F030F4 HSI时钟温度测试过不去是怎么回事?
728 浏览 2 评论
ST25R3916能否对ISO15693的标签芯片进行分区域写密码?
1679 浏览 2 评论
1938浏览 9评论
STM32仿真器是选择ST-LINK还是选择J-LINK?各有什么优势啊?
731浏览 4评论
STM32F0_TIM2输出pwm2后OLED变暗或者系统重启是怎么回事?
570浏览 3评论
596浏览 3评论
stm32cubemx生成mdk-arm v4项目文件无法打开是什么原因导致的?
556浏览 3评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-24 03:25 , Processed in 1.495089 second(s), Total 77, Slave 61 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号