找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 299|回复: 0
打印 上一主题 下一主题
收起左侧

MCU 6x6的矩阵键盘,按键按下串口接收数据感觉多运行了一次,会显示多一个加6之后的数据

[复制链接]
跳转到指定楼层
楼主


单片机源程序如下:
  1. #include "XMCE003.h"
  2. #include "Function_define.h"
  3. //*****************  The Following is in define in Fucntion_define.h  ***************************
  4. //****** Always include Function_define.h call the define you want, detail see main(void) *******
  5. //***********************************************************************************************
  6. /*------------------------------------------------
  7. The main C function.  Program execution starts
  8. here after stack initialization.
  9. ------------------------------------------------*/
  10. //P06 P07 串口 P02 P16 烧码 P20 复位 P30 晶振
  11. //下面端口定义根据实际情况修改
  12. #define P_IN_0        P00        //输入0号
  13. #define P_IN_1        P10
  14. #define P_IN_2        P11
  15. #define P_IN_3        P12
  16. #define P_IN_4        P13
  17. #define P_IN_5        P14
  18. #define P_OUT_0        P05 //输出0号
  19. #define P_OUT_1        P20
  20. #define P_OUT_2        P30
  21. #define P_OUT_3        P17
  22. #define P_OUT_4        P03
  23. #define P_OUT_5        P01
  24. #define BR_16M_115200  (0x8a)
  25. #define SCAN_TIMES        (10)        //1个判决周期内扫描次数
  26. #define PUSH_TIMES        (5)                //1个判决周期内多少次按下算真正按下
  27. static uint8_t gUartBuf[5]; //串口数据缓冲
  28. static uint8_t gScanCnt;        //扫描计数
  29. static uint8_t gKeyPressCnt[36]; //按键数
  30. static uint8_t gKeyState[36];         //按键状态
  31. void delay()                           //延时函数
  32. {
  33.         uint16_t temp_u16 = 4000;
  34.         while(temp_u16--){nop;}
  35. }

  36. void IO_Init()                         //IO初始化
  37. {
  38.         uint8_t i;
  39.         P00_PullUp_Mode;
  40.         P06_PullUp_Mode;         //上拉
  41.         P10_PullUp_Mode;
  42.         P11_PullUp_Mode;
  43.         P12_PullUp_Mode;
  44.         P13_PullUp_Mode;
  45.         P14_PullUp_Mode;

  46.         P05_OpenDrain_Mode;         //开漏
  47.         P20_OpenDrain_Mode;
  48.         P30_OpenDrain_Mode;
  49.         P17_OpenDrain_Mode;
  50.         P03_OpenDrain_Mode;
  51.         P01_OpenDrain_Mode;

  52.         P_OUT_0 = 1;
  53.         P_OUT_1 = 1;
  54.         P_OUT_2 = 1;
  55.         P_OUT_3 = 1;
  56.         P_OUT_4 = 1;
  57.         P_OUT_5 = 1;

  58.         for(i = 0; i < 36; i++)
  59.         {
  60.                 gKeyPressCnt[i] = 0; //按键计数清零
  61.                 gKeyState[i] = 0;         //按键状态清零
  62.         }
  63.         gScanCnt = 0;                         //扫描计数清零
  64. }


  65. void Send_Data_To_UART(unsigned char r_data)
  66. {
  67.         TI = 0;
  68.         SBUF = r_data;
  69.         while(TI==0);
  70. }

  71. void Send_Key_State(uint8_t Key, uint8_t UpDown)
  72. {      
  73.         uint8_t i;
  74.         uint8_t Check =0;            //00000000                                                                                               
  75.         gUartBuf[0] = 0xaa;     //10101010                   10101010                       
  76.         gUartBuf[1] = 0x55;          //01010101                          11111111
  77.         gUartBuf[2] = Key;                 //00000000
  78.         gUartBuf[3] = UpDown;        //00000000/00000001               
  79.     for (i = 0; i < 4; i++)
  80.         {
  81.                 Check ^= gUartBuf[i];
  82.         }
  83.         gUartBuf[4] = Check;                                                                                                               
  84.         for (i = 0; i < 5; i++)                                                                                                      
  85.         {
  86.                 Send_Data_To_UART(gUartBuf[i]);
  87.       
  88.         }
  89. }
  90. void KeyBoard_ReadInput(uint8_t Line)  
  91. {      
  92.         Line *= 6;                                                //Line=Line*6         
  93.         if (P_IN_0 == 0)                              
  94.         {
  95.                 gKeyPressCnt[Line]++;                        
  96.         }
  97.         if (P_IN_1 == 0)                              
  98.         {
  99.                 gKeyPressCnt[Line + 1]++;
  100.         }
  101.         if (P_IN_2 == 0)                                 
  102.         {
  103.                 gKeyPressCnt[Line + 2]++;
  104.         }
  105.         if (P_IN_3 == 0)
  106.         {
  107.                 gKeyPressCnt[Line + 3]++;
  108.         }
  109.         if (P_IN_4 == 0)
  110.         {
  111.                 gKeyPressCnt[Line + 4]++;
  112.         }
  113.         if (P_IN_5 == 0)
  114.         {
  115.                 gKeyPressCnt[Line + 5]++;
  116.         }
  117. }
  118. void UART_Init()                //串口初始化
  119. {
  120.         P06 = 1;
  121.         P07 = 1;

  122.         TI = 0;                                //标志位清零
  123.         RI = 0;                                
  124.       
  125.         B8EN = 0;                         //关闭串口第九位
  126.                                                                                                          
  127.         SOVRH = 0x00;                        //波特率高两位
  128.         SOVRL =        BR_16M_115200;                //波特率低八位         

  129.         REN = 1;                        //串口使能位
  130. }  

  131. void KeyBoard_ScanOnce(void)
  132. {
  133.         uint8_t i;                                         
  134.         P_OUT_0 = 0;                                 
  135.         KeyBoard_ReadInput(0);                 
  136.         P_OUT_0 = 1;                                 

  137.         P_OUT_1 = 0;
  138.         KeyBoard_ReadInput(1);
  139.         P_OUT_1 = 1;

  140.         P_OUT_2 = 0;
  141.         KeyBoard_ReadInput(2);
  142.         P_OUT_2 = 1;

  143.         P_OUT_3 = 0;
  144.         KeyBoard_ReadInput(3);         
  145.         P_OUT_3 = 1;

  146.         P_OUT_4 = 0;
  147.         KeyBoard_ReadInput(4);
  148.         P_OUT_4 = 1;

  149.         P_OUT_5 = 0;
  150.         KeyBoard_ReadInput(5);
  151.         P_OUT_5 = 1;

  152.         gScanCnt++;
  153.         if (gScanCnt >= SCAN_TIMES)                   //扫描次数大于上线
  154.         {
  155.                 gScanCnt = 0;                                   //扫描次数清零
  156.                 for(i = 0; i < 36; i++)                  
  157.                 {  
  158.                         if (gKeyPressCnt[i] >= PUSH_TIMES)//判断按键按下
  159.                         {
  160.                                 if (!gKeyState[i])           // 如果按键按下
  161.                                 {
  162.                                         gKeyState[i] = 1;  //串口发送按键按下
  163.                                          Send_Key_State(i,1);//发送按键状态1
  164.                                 }
  165.                         }
  166.                         else
  167.                         {
  168.                                 if (gKeyState[i])           //按键松开
  169.                                 {
  170.                                         gKeyState[i] = 0;  //串口发送按键抬起
  171.                                         Send_Key_State(i,0);//发送按键状态0
  172.                                 }
  173.                         }
  174.                 }
  175.                 for(i = 0; i < 36; i++)                     
  176.                 {                                                         
  177.                         gKeyPressCnt[i] = 0;                //按键计数清零
  178.                 }
  179.         }
  180.         else
  181.         {
  182.                 delay();
  183.         }
  184. }

  185. void main (void)
  186. {
  187.         Set_All_GPIO_PushPull_Mode;                                  // Define in Function_define.h
  188.         UART_Init();                                                          //初始化
  189.         IO_Init();                                                                  //初始化
  190.         WDTEN;
  191.           while(1)
  192.         {
  193.                 WDTCLR;
  194.                 KeyBoard_ScanOnce();
  195.         }


  196. }
复制代码


分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享淘帖 顶 踩
回复

使用道具 举报

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

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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