硬汉嵌入式论坛

 找回密码
 立即注册
查看: 2857|回复: 2
收起左侧

[有问必答] FIFO按键移植问题

[复制链接]

3

主题

3

回帖

12

积分

新手上路

积分
12
发表于 2021-2-26 22:48:53 | 显示全部楼层 |阅读模式
请教硬汉哥,我把H7 BSP的KEY_FIFO程序移植到了MM32当中去,改变了一些底层代码后,测试发现5个独立按键中只有后3个可以使用,前2个不可以。 测试IsKeyDownFunc函数其可以正常的响应每一个按键。修改s_gpio_list中按键的顺序,同样是前2个不可以使用,后3个正常使用。我debug后发现调用bsp_DetectKey时,s_gpio_list列表前两个按键不论进入次数,其计数器值均会被归为0值。而其他3个则不会。卡在这里不知道怎么修改了,想请问一下这类地方debug的思路。按键扫描函数正常10ms扫描了。
回复

使用道具 举报

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106913
QQ
发表于 2021-2-27 09:23:28 | 显示全部楼层
方便的话,贴代码看下。
回复

使用道具 举报

3

主题

3

回帖

12

积分

新手上路

积分
12
 楼主| 发表于 2021-2-27 16:12:31 | 显示全部楼层
  1. /*
  2. *********************************************************************************************************
  3. *
  4. *        模块名称 : 独立按键驱动模块 (外部输入IO)
  5. *        文件名称 : bsp_key.c
  6. *        版    本 : V1.3
  7. *        说    明 : 扫描独立按键,具有软件滤波机制,具有按键FIFO。可以检测如下事件:
  8. *                                (1) 按键按下
  9. *                                (2) 按键弹起
  10. *                                (3) 长按键
  11. *                                (4) 长按时自动连发
  12. *
  13. *        修改记录 :
  14. *                版本号  日期        作者     说明
  15. *                V1.0    2013-02-01 armfly  正式发布
  16. *                V1.1    2013-06-29 armfly  增加1个读指针,用于bsp_Idle() 函数读取系统控制组合键(截屏)
  17. *                                                                   增加 K1 K2 组合键 和 K2 K3 组合键,用于系统控制
  18. *                V1.2        2016-01-25 armfly  针对P02工控板更改. 调整gpio定义方式,更加简洁
  19. *                V1.3        2018-11-26 armfly  s_tBtn结构赋初值0
  20. *
  21. *        Copyright (C), 2016-2020, 安富莱电子 www.armfly.com
  22. *
  23. *********************************************************************************************************
  24. */

  25. #include "headfile.h"
  26. #include "zb_key.h"

  27. #define HARD_KEY_NUM            5                                                  /* 实体按键个数 */
  28. #define KEY_COUNT                            HARD_KEY_NUM+0                /* 8个独立建 + 2个组合按键 */

  29. /* 使能GPIO时钟 */
  30. #define ALL_KEY_GPIO_CLK_ENABLE() {        \
  31.                 RCC_AHBPeriphClockCmd(RCC_AHBENR_GPIOA,ENABLE);    \
  32.         };

  33. /* 依次定义GPIO */
  34. typedef struct
  35. {
  36.         GPIO_TypeDef* gpio;
  37.         uint16_t pin;
  38.         uint8_t ActiveLevel;        /* 激活电平 */
  39. }X_GPIO_T;

  40. /* GPIO和PIN定义 */
  41. static const X_GPIO_T s_gpio_list[HARD_KEY_NUM] = {
  42.         {GPIOA, GPIO_Pin_8, 0},                /* K1 */
  43.         {GPIOA, GPIO_Pin_9, 0},        /* K2 */
  44.         {GPIOA, GPIO_Pin_10, 0},                /* K3 */
  45.         {GPIOA, GPIO_Pin_11, 0},                /* JOY_U */       
  46.         {GPIOA, GPIO_Pin_12, 0},                /* JOY_D */
  47. };       

  48. /* 定义一个宏函数简化后续代码
  49.         判断GPIO引脚是否有效按下
  50. */
  51. static KEY_T s_tBtn[KEY_COUNT] = {0};
  52. static KEY_FIFO_T s_tKey;                /* 按键FIFO变量,结构体 */

  53. static void bsp_InitKeyVar(void);
  54. static void bsp_InitKeyHard(void);
  55. static void bsp_DetectKey(uint8_t i);

  56. #define KEY_PIN_ACTIVE(id)       

  57. /*
  58. *********************************************************************************************************
  59. *        函 数 名: KeyPinActive
  60. *        功能说明: 判断按键是否按下
  61. *        形    参: 无
  62. *        返 回 值: 返回值1 表示按下(导通),0表示未按下(释放)
  63. *********************************************************************************************************
  64. */
  65. static uint8_t KeyPinActive(uint8_t _id)
  66. {
  67.         uint8_t level;
  68.        
  69.         if ((s_gpio_list[_id].gpio->IDR & s_gpio_list[_id].pin) == 0)
  70.         {
  71.                 level = 0;
  72.         }
  73.         else
  74.         {
  75.                 level = 1;
  76.         }

  77.         if (level == s_gpio_list[_id].ActiveLevel)
  78.         {
  79.                 return 1;
  80.         }
  81.         else
  82.         {
  83.                 return 0;
  84.         }
  85. }

  86. /*
  87. *********************************************************************************************************
  88. *        函 数 名: IsKeyDownFunc
  89. *        功能说明: 判断按键是否按下。单键和组合键区分。单键事件不允许有其他键按下。
  90. *        形    参: 无
  91. *        返 回 值: 返回值1 表示按下(导通),0表示未按下(释放)
  92. *********************************************************************************************************
  93. */
  94. static uint8_t IsKeyDownFunc(uint8_t _id)
  95. {
  96.         /* 实体单键 */
  97.         if (_id < HARD_KEY_NUM)
  98.         {
  99.                 uint8_t i;
  100.                 uint8_t count = 0;
  101.                 uint8_t save = 255;
  102.                
  103.                 /* 判断有几个键按下 */
  104.                 for (i = 0; i < HARD_KEY_NUM; i++)
  105.                 {
  106.                         if (KeyPinActive(i))
  107.                         {
  108.                                 count++;
  109.                                 save = i;
  110.                         }
  111.                 }
  112.                                 uart_putchar        (UART_1, _id);               
  113.                 if (count == 1 && save == _id)
  114.                 {
  115.                         return 1;        /* 只有1个键按下时才有效 */
  116.                 }               

  117.                 return 0;
  118.         }
  119.        
  120. //        /* 组合键 K1K2 */
  121. //        if (_id == HARD_KEY_NUM + 0)
  122. //        {
  123. //                if (KeyPinActive(KID_K1) && KeyPinActive(KID_K2))
  124. //                {
  125. //                        return 1;
  126. //                }
  127. //                else
  128. //                {
  129. //                        return 0;
  130. //                }
  131. //        }

  132. //        /* 组合键 K2K3 */
  133. //        if (_id == HARD_KEY_NUM + 1)
  134. //        {
  135. //                if (KeyPinActive(KID_K2) && KeyPinActive(KID_K3))
  136. //                {
  137. //                        return 1;
  138. //                }
  139. //                else
  140. //                {
  141. //                        return 0;
  142. //                }
  143. //        }

  144.         return 0;
  145. }

  146. /*
  147. *********************************************************************************************************
  148. *        函 数 名: bsp_InitKey
  149. *        功能说明: 初始化按键. 该函数被 bsp_Init() 调用。
  150. *        形    参:  无
  151. *        返 回 值: 无
  152. *********************************************************************************************************
  153. */
  154. void bsp_InitKey(void)
  155. {
  156.         bsp_InitKeyVar();                /* 初始化按键变量 */
  157.         bsp_InitKeyHard();        /* 初始化按键硬件 */
  158. }

  159. /*
  160. *********************************************************************************************************
  161. *        函 数 名: bsp_InitKeyHard
  162. *        功能说明: 配置按键对应的GPIO
  163. *        形    参:  无
  164. *        返 回 值: 无
  165. *********************************************************************************************************
  166. */
  167. static void bsp_InitKeyHard(void)
  168. {       
  169.         GPIO_InitTypeDef gpio_init;
  170.         uint8_t i;

  171.         /* 第1步:打开GPIO时钟 */
  172.         ALL_KEY_GPIO_CLK_ENABLE();
  173.        
  174.         /* 第2步:配置所有的按键GPIO为浮动输入模式(实际上CPU复位后就是输入状态) */

  175.         gpio_init.GPIO_Mode = GPIO_Mode_IPU;
  176.         gpio_init.GPIO_Speed = GPIO_Speed_50MHz;
  177.        
  178.         for (i = 0; i < HARD_KEY_NUM; i++)
  179.         {
  180.                 gpio_init.GPIO_Pin = s_gpio_list[i].pin;
  181.                 GPIO_Init(s_gpio_list[i].gpio, &gpio_init);
  182.         }
  183. }

  184. /*
  185. *********************************************************************************************************
  186. *        函 数 名: bsp_InitKeyVar
  187. *        功能说明: 初始化按键变量
  188. *        形    参:  无
  189. *        返 回 值: 无
  190. *********************************************************************************************************
  191. */
  192. static void bsp_InitKeyVar(void)
  193. {
  194.         uint8_t i;

  195.         /* 对按键FIFO读写指针清零 */
  196.         s_tKey.Read = 0;
  197.         s_tKey.Write = 0;
  198.         s_tKey.Read2 = 0;

  199.         /* 给每个按键结构体成员变量赋一组缺省值 */
  200.         for (i = 0; i < KEY_COUNT; i++)
  201.         {
  202.                 s_tBtn[i].LongTime = KEY_LONG_TIME;                        /* 长按时间 0 表示不检测长按键事件 */
  203.                 s_tBtn[i].Count = KEY_FILTER_TIME/2;                /* 计数器设置为滤波时间的一半 */
  204.                 s_tBtn[i].State = 0;                                                        /* 按键缺省状态,0为未按下 */
  205.                 s_tBtn[i].RepeatSpeed = 0;                                                /* 按键连发的速度,0表示不支持连发 */
  206.                 s_tBtn[i].RepeatCount = 0;                                                /* 连发计数器 */
  207.         }

  208.         /* 如果需要单独更改某个按键的参数,可以在此单独重新赋值 */
  209.        
  210. //        /* 摇杆上下左右,支持长按1秒后,自动连发 */
  211. //        bsp_SetKeyParam(KID_JOY_U, 100, 6);
  212. //        bsp_SetKeyParam(KID_JOY_D, 100, 6);
  213. //        bsp_SetKeyParam(KID_JOY_L, 100, 6);
  214. //        bsp_SetKeyParam(KID_JOY_R, 100, 6);
  215. }

  216. /*
  217. *********************************************************************************************************
  218. *        函 数 名: bsp_PutKey
  219. *        功能说明: 将1个键值压入按键FIFO缓冲区。可用于模拟一个按键。
  220. *        形    参:  _KeyCode : 按键代码
  221. *        返 回 值: 无
  222. *********************************************************************************************************
  223. */
  224. void bsp_PutKey(uint8_t _KeyCode)
  225. {
  226.         s_tKey.Buf[s_tKey.Write] = _KeyCode;
  227. //        uart_putstr(UART_1, "入队列:");
  228. //        uart_putchar        (UART_1, _KeyCode);
  229.         if (++s_tKey.Write  >= KEY_FIFO_SIZE)
  230.         {
  231.                 s_tKey.Write = 0;
  232.         }
  233. }

  234. /*
  235. *********************************************************************************************************
  236. *        函 数 名: bsp_GetKey
  237. *        功能说明: 从按键FIFO缓冲区读取一个键值。
  238. *        形    参: 无
  239. *        返 回 值: 按键代码
  240. *********************************************************************************************************
  241. */
  242. uint8_t bsp_GetKey(void)
  243. {
  244.         uint8_t ret;

  245.         if (s_tKey.Read == s_tKey.Write)
  246.         {
  247.                 return KEY_NONE;
  248.         }
  249.         else
  250.         {
  251.                 ret = s_tKey.Buf[s_tKey.Read];

  252.                 if (++s_tKey.Read >= KEY_FIFO_SIZE)
  253.                 {
  254.                         s_tKey.Read = 0;
  255.                 }
  256.                 return ret;
  257.         }
  258. }

  259. /*
  260. *********************************************************************************************************
  261. *        函 数 名: bsp_GetKey2
  262. *        功能说明: 从按键FIFO缓冲区读取一个键值。独立的读指针。
  263. *        形    参:  无
  264. *        返 回 值: 按键代码
  265. *********************************************************************************************************
  266. */
  267. uint8_t bsp_GetKey2(void)
  268. {
  269.         uint8_t ret;

  270.         if (s_tKey.Read2 == s_tKey.Write)
  271.         {
  272.                 return KEY_NONE;
  273.         }
  274.         else
  275.         {
  276.                 ret = s_tKey.Buf[s_tKey.Read2];

  277.                 if (++s_tKey.Read2 >= KEY_FIFO_SIZE)
  278.                 {
  279.                         s_tKey.Read2 = 0;
  280.                 }
  281.                 return ret;
  282.         }
  283. }

  284. /*
  285. *********************************************************************************************************
  286. *        函 数 名: bsp_GetKeyState
  287. *        功能说明: 读取按键的状态
  288. *        形    参:  _ucKeyID : 按键ID,从0开始
  289. *        返 回 值: 1 表示按下, 0 表示未按下
  290. *********************************************************************************************************
  291. */
  292. uint8_t bsp_GetKeyState(KEY_ID_E _ucKeyID)
  293. {
  294.         return s_tBtn[_ucKeyID].State;
  295. }

  296. /*
  297. *********************************************************************************************************
  298. *        函 数 名: bsp_SetKeyParam
  299. *        功能说明: 设置按键参数
  300. *        形    参:_ucKeyID : 按键ID,从0开始
  301. *                        _LongTime : 长按事件时间
  302. *                         _RepeatSpeed : 连发速度
  303. *        返 回 值: 无
  304. *********************************************************************************************************
  305. */
  306. void bsp_SetKeyParam(uint8_t _ucKeyID, uint16_t _LongTime, uint8_t  _RepeatSpeed)
  307. {
  308.         s_tBtn[_ucKeyID].LongTime = _LongTime;                        /* 长按时间 0 表示不检测长按键事件 */
  309.         s_tBtn[_ucKeyID].RepeatSpeed = _RepeatSpeed;                        /* 按键连发的速度,0表示不支持连发 */
  310.         s_tBtn[_ucKeyID].RepeatCount = 0;                                                /* 连发计数器 */
  311. }

  312. /*
  313. *********************************************************************************************************
  314. *        函 数 名: bsp_ClearKey
  315. *        功能说明: 清空按键FIFO缓冲区
  316. *        形    参:无
  317. *        返 回 值: 按键代码
  318. *********************************************************************************************************
  319. */
  320. void bsp_ClearKey(void)
  321. {
  322.         s_tKey.Read = s_tKey.Write;
  323. }

  324. /*
  325. *********************************************************************************************************
  326. *        函 数 名: bsp_DetectKey
  327. *        功能说明: 检测一个按键。非阻塞状态,必须被周期性的调用。
  328. *        形    参: IO的id, 从0开始编码
  329. *        返 回 值: 无
  330. *********************************************************************************************************
  331. */
  332. static void bsp_DetectKey(uint8_t i)
  333. {
  334.         KEY_T *pBtn;

  335.         pBtn = &s_tBtn[i];
  336.         if (IsKeyDownFunc(i))
  337.         {
  338.                 if (pBtn->Count < KEY_FILTER_TIME)
  339.                 {
  340.                         uart_putchar(UART_1, 0xaa);               
  341.                         pBtn->Count = KEY_FILTER_TIME;       
  342.                 }
  343.                 else if(pBtn->Count < 2 * KEY_FILTER_TIME)
  344.                 {
  345.                         pBtn->Count++;
  346.                 }
  347.                 else
  348.                 {
  349.                         if (pBtn->State == 0)
  350.                         {
  351.                                 pBtn->State = 1;
  352. //                                uart_putchar        (UART_1, (uint8_t)(3 * i + 1));                               
  353.                                 /* 发送按钮按下的消息 */
  354.                                 bsp_PutKey((uint8_t)(3 * i + 1));
  355.                         }

  356.                         if (pBtn->LongTime > 0)
  357.                         {
  358.                                 if (pBtn->LongCount < pBtn->LongTime)
  359.                                 {
  360.                                         /* 发送按钮持续按下的消息 */
  361.                                         if (++pBtn->LongCount == pBtn->LongTime)
  362.                                         {
  363.                                                 /* 键值放入按键FIFO */
  364.                                                 bsp_PutKey((uint8_t)(3 * i + 3));
  365.                                         }
  366.                                 }
  367.                                 else
  368.                                 {
  369.                                         if (pBtn->RepeatSpeed > 0)
  370.                                         {
  371.                                                 if (++pBtn->RepeatCount >= pBtn->RepeatSpeed)
  372.                                                 {
  373.                                                         pBtn->RepeatCount = 0;
  374.                                                         /* 常按键后,每隔10ms发送1个按键 */
  375.                                                         bsp_PutKey((uint8_t)(3 * i + 1));
  376.                                                 }
  377.                                         }
  378.                                 }
  379.                         }
  380.                 }
  381.         }
  382.         else
  383.         {
  384.                 if(pBtn->Count > KEY_FILTER_TIME)
  385.                 {
  386.                         pBtn->Count = KEY_FILTER_TIME;
  387.                 }
  388.                 else if(pBtn->Count != 0)
  389.                 {
  390.                         pBtn->Count--;
  391.                 }
  392.                 else
  393.                 {
  394.                         if (pBtn->State == 1)
  395.                         {
  396.                                 pBtn->State = 0;

  397.                                 /* 发送按钮弹起的消息 */
  398.                                 bsp_PutKey((uint8_t)(3 * i + 2));
  399.                         }
  400.                 }

  401.                 pBtn->LongCount = 0;
  402.                 pBtn->RepeatCount = 0;
  403.         }
  404. }

  405. /*
  406. *********************************************************************************************************
  407. *        函 数 名: bsp_DetectFastIO
  408. *        功能说明: 检测高速的输入IO. 1ms刷新一次
  409. *        形    参: IO的id, 从0开始编码
  410. *        返 回 值: 无
  411. *********************************************************************************************************
  412. */
  413. static void bsp_DetectFastIO(uint8_t i)
  414. {
  415.         KEY_T *pBtn;

  416.         pBtn = &s_tBtn[i];
  417.         if (IsKeyDownFunc(i))
  418.         {
  419.                 if (pBtn->State == 0)
  420.                 {
  421.                         pBtn->State = 1;

  422.                         /* 发送按钮按下的消息 */
  423.                         bsp_PutKey((uint8_t)(3 * i + 1));
  424.                 }

  425.                 if (pBtn->LongTime > 0)
  426.                 {
  427.                         if (pBtn->LongCount < pBtn->LongTime)
  428.                         {
  429.                                 /* 发送按钮持续按下的消息 */
  430.                                 if (++pBtn->LongCount == pBtn->LongTime)
  431.                                 {
  432.                                         /* 键值放入按键FIFO */
  433.                                         bsp_PutKey((uint8_t)(3 * i + 3));
  434.                                 }
  435.                         }
  436.                         else
  437.                         {
  438.                                 if (pBtn->RepeatSpeed > 0)
  439.                                 {
  440.                                         if (++pBtn->RepeatCount >= pBtn->RepeatSpeed)
  441.                                         {
  442.                                                 pBtn->RepeatCount = 0;
  443.                                                 /* 常按键后,每隔10ms发送1个按键 */
  444.                                                 bsp_PutKey((uint8_t)(3 * i + 1));
  445.                                         }
  446.                                 }
  447.                         }
  448.                 }
  449.         }
  450.         else
  451.         {
  452.                 if (pBtn->State == 1)
  453.                 {
  454.                         pBtn->State = 0;

  455.                         /* 发送按钮弹起的消息 */
  456.                         bsp_PutKey((uint8_t)(3 * i + 2));
  457.                 }

  458.                 pBtn->LongCount = 0;
  459.                 pBtn->RepeatCount = 0;
  460.         }
  461. }

  462. /*
  463. *********************************************************************************************************
  464. *        函 数 名: bsp_KeyScan10ms
  465. *        功能说明: 扫描所有按键。非阻塞,被systick中断周期性的调用,10ms一次
  466. *        形    参: 无
  467. *        返 回 值: 无
  468. *********************************************************************************************************
  469. */
  470. void bsp_KeyScan10ms(void)
  471. {
  472.         uint8_t i;

  473.         for (i = 0; i < KEY_COUNT; i++)
  474.         {
  475.                 bsp_DetectKey(i);
  476.         }
  477. }

  478. /*
  479. *********************************************************************************************************
  480. *        函 数 名: bsp_KeyScan1ms
  481. *        功能说明: 扫描所有按键。非阻塞,被systick中断周期性的调用,1ms一次.
  482. *        形    参: 无
  483. *        返 回 值: 无
  484. *********************************************************************************************************
  485. */
  486. void bsp_KeyScan1ms(void)
  487. {
  488.         uint8_t i;

  489.         for (i = 0; i < KEY_COUNT; i++)
  490.         {
  491.                 bsp_DetectFastIO(i);
  492.         }
  493. }

  494. /***************************** 安富莱电子 www.armfly.com (END OF FILE) *********************************/
  495. [code]/*
  496. *********************************************************************************************************
  497. *
  498. *        模块名称 : 按键驱动模块
  499. *        文件名称 : bsp_key.h
  500. *        版    本 : V1.0
  501. *        说    明 : 头文件
  502. *
  503. *        Copyright (C), 2013-2014, 安富莱电子 www.armfly.com
  504. *
  505. *********************************************************************************************************
  506. */

  507. #ifndef __BSP_KEY_H
  508. #define __BSP_KEY_H

  509. #include "common.h"


  510. /* 根据应用程序的功能重命名按键宏 */
  511. #define KEY_DOWN_K1                KEY_1_DOWN
  512. #define KEY_UP_K1                KEY_1_UP
  513. #define KEY_LONG_K1                KEY_1_LONG

  514. #define KEY_DOWN_K2                KEY_2_DOWN
  515. #define KEY_UP_K2                KEY_2_UP
  516. #define KEY_LONG_K2                KEY_2_LONG

  517. #define KEY_DOWN_K3                KEY_3_DOWN
  518. #define KEY_UP_K3                KEY_3_UP
  519. #define KEY_LONG_K3                KEY_3_LONG

  520. #define JOY_DOWN_U                KEY_4_DOWN                /* 上 */
  521. #define JOY_UP_U                KEY_4_UP
  522. #define JOY_LONG_U                KEY_4_LONG

  523. #define JOY_DOWN_D                KEY_5_DOWN                /* 下 */
  524. #define JOY_UP_D                KEY_5_UP
  525. #define JOY_LONG_D                KEY_5_LONG

  526. //#define JOY_DOWN_L                KEY_6_DOWN                /* 左 */
  527. //#define JOY_UP_L                KEY_6_UP
  528. //#define JOY_LONG_L                KEY_6_LONG

  529. //#define JOY_DOWN_R                KEY_7_DOWN                /* 右 */
  530. //#define JOY_UP_R                KEY_7_UP
  531. //#define JOY_LONG_R                KEY_7_LONG

  532. //#define JOY_DOWN_OK                KEY_8_DOWN                /* ok */
  533. //#define JOY_UP_OK                KEY_8_UP
  534. //#define JOY_LONG_OK                KEY_8_LONG

  535. //#define SYS_DOWN_K1K2        KEY_9_DOWN                /* K1 K2 组合键 */
  536. //#define SYS_UP_K1K2            KEY_9_UP
  537. //#define SYS_LONG_K1K2        KEY_9_LONG

  538. //#define SYS_DOWN_K2K3        KEY_10_DOWN                /* K2 K3 组合键 */
  539. //#define SYS_UP_K2K3          KEY_10_UP
  540. //#define SYS_LONG_K2K3        KEY_10_LONG

  541. /* 按键ID, 主要用于bsp_KeyState()函数的入口参数 */
  542. typedef enum
  543. {
  544.         KID_K1 = 0,
  545.         KID_K2,
  546.         KID_K3,
  547.         KID_K4,
  548.         KID_K5,
  549.         KID_JOY_L,
  550.         KID_JOY_R,
  551.         KID_JOY_OK
  552. }KEY_ID_E;

  553. /*
  554.         按键滤波时间50ms, 单位10ms。
  555.         只有连续检测到50ms状态不变才认为有效,包括弹起和按下两种事件
  556.         即使按键电路不做硬件滤波,该滤波机制也可以保证可靠地检测到按键事件
  557. */
  558. #define KEY_FILTER_TIME   5
  559. #define KEY_LONG_TIME     100                        /* 单位10ms, 持续1秒,认为长按事件 */

  560. /*
  561.         每个按键对应1个全局的结构体变量。
  562. */
  563. typedef struct
  564. {
  565.         /* 下面是一个函数指针,指向判断按键手否按下的函数 */
  566.         uint8_t (*IsKeyDownFunc)(void); /* 按键按下的判断函数,1表示按下 */

  567.         uint8_t  Count;                        /* 滤波器计数器 */
  568.         uint16_t LongCount;                /* 长按计数器 */
  569.         uint16_t LongTime;                /* 按键按下持续时间, 0表示不检测长按 */
  570.         uint8_t  State;                        /* 按键当前状态(按下还是弹起) */
  571.         uint8_t  RepeatSpeed;        /* 连续按键周期 */
  572.         uint8_t  RepeatCount;        /* 连续按键计数器 */
  573. }KEY_T;

  574. /*
  575.         定义键值代码, 必须按如下次序定时每个键的按下、弹起和长按事件

  576.         推荐使用enum, 不用#define,原因:
  577.         (1) 便于新增键值,方便调整顺序,使代码看起来舒服点
  578.         (2) 编译器可帮我们避免键值重复。
  579. */
  580. typedef enum
  581. {
  582.         KEY_NONE = 0,                        /* 0 表示按键事件 */

  583.         KEY_1_DOWN,                                /* 1键按下 */
  584.         KEY_1_UP,                                /* 1键弹起 */
  585.         KEY_1_LONG,                                /* 1键长按 */

  586.         KEY_2_DOWN,                                /* 2键按下 */
  587.         KEY_2_UP,                                /* 2键弹起 */
  588.         KEY_2_LONG,                                /* 2键长按 */

  589.         KEY_3_DOWN,                                /* 3键按下 */
  590.         KEY_3_UP,                                /* 3键弹起 */
  591.         KEY_3_LONG,                                /* 3键长按 */

  592.         KEY_4_DOWN,                                /* 4键按下 */
  593.         KEY_4_UP,                                /* 4键弹起 */
  594.         KEY_4_LONG,                                /* 4键长按 */

  595.         KEY_5_DOWN,                                /* 5键按下 */
  596.         KEY_5_UP,                                /* 5键弹起 */
  597.         KEY_5_LONG,                                /* 5键长按 */

  598. //        KEY_6_DOWN,                                /* 6键按下 */
  599. //        KEY_6_UP,                                /* 6键弹起 */
  600. //        KEY_6_LONG,                                /* 6键长按 */

  601. //        KEY_7_DOWN,                                /* 7键按下 */
  602. //        KEY_7_UP,                                /* 7键弹起 */
  603. //        KEY_7_LONG,                                /* 7键长按 */

  604. //        KEY_8_DOWN,                                /* 8键按下 */
  605. //        KEY_8_UP,                                /* 8键弹起 */
  606. //        KEY_8_LONG,                                /* 8键长按 */

  607. //        /* 组合键 */
  608. //        KEY_9_DOWN,                                /* 9键按下 */
  609. //        KEY_9_UP,                                /* 9键弹起 */
  610. //        KEY_9_LONG,                                /* 9键长按 */

  611. //        KEY_10_DOWN,                        /* 10键按下 */
  612. //        KEY_10_UP,                                /* 10键弹起 */
  613. //        KEY_10_LONG,                        /* 10键长按 */
  614. }KEY_ENUM;

  615. /* 按键FIFO用到变量 */
  616. #define KEY_FIFO_SIZE        10
  617. typedef struct
  618. {
  619.         uint8_t Buf[KEY_FIFO_SIZE];                /* 键值缓冲区 */
  620.         uint8_t Read;                                        /* 缓冲区读指针1 */
  621.         uint8_t Write;                                        /* 缓冲区写指针 */
  622.         uint8_t Read2;                                        /* 缓冲区读指针2 */
  623. }KEY_FIFO_T;

  624. /* 供外部调用的函数声明 */
  625. void bsp_InitKey(void);
  626. void bsp_KeyScan10ms(void);
  627. void bsp_PutKey(uint8_t _KeyCode);
  628. uint8_t bsp_GetKey(void);
  629. uint8_t bsp_GetKey2(void);
  630. uint8_t bsp_GetKeyState(KEY_ID_E _ucKeyID);
  631. void bsp_SetKeyParam(uint8_t _ucKeyID, uint16_t _LongTime, uint8_t  _RepeatSpeed);
  632. void bsp_ClearKey(void);

  633. #endif
复制代码
[/code]
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2024-5-9 16:47 , Processed in 0.238101 second(s), 25 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

快速回复 返回顶部 返回列表