矩阵键盘扫描代码

  1 typedef struct         //定义任意IO初始化结构体 
  2         {
  3             GPIO_TypeDef* GPIOX;
  4             uint16_t GPIO_Pin;
  5         }KHGPT[4]; //4*4
  6         
  7 KHGPT KHPIN={ 
  8                             //只需要在下面填写横竖行的IO口和管脚   IO口和管脚都可以随意定义 无需在一个IO口 管脚也无需按顺序
  9              {GPIOB,GPIO_Pin_15} ,{GPIOB,GPIO_Pin_14}, {GPIOB,GPIO_Pin_13},{GPIOB,GPIO_Pin_12}//row 横行
 10                         };                //这个数组中顺序即为按键行io的顺序
 11 
 12 typedef struct 
 13         {
 14             GPIO_TypeDef* GPIOX;
 15             uint16_t GPIO_Pin;
 16         }KLGPT[3]; //4*3
 17         
 18 KLGPT KLPIN={ 
 19                           //只需要在下面填写横竖行的IO口和管脚   IO口和管脚都可以随意定义 无需在一个IO口 管脚也无需按顺序
 20              {GPIOD,GPIO_Pin_8},     {GPIOD,GPIO_Pin_9},  {GPIOD,GPIO_Pin_10}  //col 竖行
 21                         };                //这个数组中顺序即为按键列io的顺序
 22 
 23 #define RCC_APB2_GPIOX  RCC_APB2Periph_GPIOB|RCC_APB2Periph_GPIOD//IO时钟                                        
 24 #define MAX_time   36000000 // 松手检测最大延时  
 25 
 26 void KEY_Init1(void)                    //按键io初始化函数
 27 {
 28   u8 i;
 29   GPIO_InitTypeDef GPIO_InitStructure;
 30   RCC_APB2PeriphClockCmd(RCC_APB2_GPIOX,ENABLE);//使能PORTC时钟
 31   for(i=0;i<4;i++)
 32         
 33             {
 34              GPIO_InitStructure.GPIO_Pin = KHPIN[i].GPIO_Pin;        //从行的数组取io
 35              GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;   //设置成推挽输出
 36              GPIO_Init(KHPIN[i].GPIOX, &GPIO_InitStructure);    //初始化行的io
 37              GPIO_ResetBits(KHPIN[i].GPIOX,KHPIN[i].GPIO_Pin);
 38             }
 39     
 40     for(i=0;i<3;i++)
 41             {
 42              GPIO_InitStructure.GPIO_Pin  = KLPIN[i].GPIO_Pin;    //从列的数组取io
 43              GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;      //设置成上拉输入
 44              GPIO_Init(KLPIN[i].GPIOX, &GPIO_InitStructure);    //初始化列io
 45             }
 46 } 
 47 
 48 u8 ReScan(GPIO_TypeDef* GPIOX,uint16_t colPin,u8 colIndex)
 49     {
 50     u8 i;
 51     delay_ms(10);                    //消抖延时
 52     for(i = 0;i<4;i++)
 53         {
 54         GPIO_SetBits(KHPIN[i].GPIOX,KHPIN[i].GPIO_Pin);    //每个行置1
 55         if((GPIO_ReadInputDataBit(GPIOX, colPin) == 1)) //如果列也变了 行的值就知道了 为 i
 56                 {
 57                     GPIO_ResetBits(KHPIN[i].GPIOX,KHPIN[i].GPIO_Pin); //行恢复 置0 
 58                     return colIndex+i*3+1;//返回的数据 为1-12 对应3x4键盘的12个键
 59                 }                                                //colIndex+i*4+1返回的数据 为1-16 对应4x4键盘的16个键
 60                 GPIO_ResetBits(KHPIN[i].GPIOX,KHPIN[i].GPIO_Pin);     //行恢复 置0
 61         }
 62     return 0;
 63     }
 64 u8 KEY_Scan1(void)
 65     {         
 66     u8 i,keyvalue;
 67                 u32 j=0;
 68                 for(i = 0;i<3;i++)
 69                 {
 70                  if(GPIO_ReadInputDataBit(KLPIN[i].GPIOX,KLPIN[i].GPIO_Pin) == 0)//检测列 列值为 i
 71                          {
 72                          keyvalue = ReScan(KLPIN[i].GPIOX,KLPIN[i].GPIO_Pin,i);//检测行 取键值
 73                          while(GPIO_ReadInputDataBit(KLPIN[i].GPIOX,KLPIN[i].GPIO_Pin) == 0)
 74                          while((GPIO_ReadInputDataBit(KLPIN[i].GPIOX,KLPIN[i].GPIO_Pin) == 0)&&(j<MAX_time))j++;//松手检测
 75                          return keyvalue;//返回键值
 76                             }
 77                 }
 78                 return 0;
 79     }
 80 
 81 void KEY_Value(void)//设置键值
 82 {
 83         u8 KEY=0;
 84         KEY=KEY_Scan1();    //得到键值
 85         if(KEY !=0 )
 86         {        
 87                 delay_ms(5);
 88                 BEEP_RUN();                                        //控制蜂鸣器
 89                 switch(KEY)                                        //得到键值,分配功能
 90                 {                 
 91                         case S1:
 92                             OLED_ShowNum(0,0,1,4,12);//显示数字码值 1
 93                             OLED_Refresh_Gram();        //更新显示到OLED     
 94                             break;
 95                         case S2:
 96                             OLED_ShowNum(0,0,2,4,12);//显示数字码值 2
 97                             OLED_Refresh_Gram();        //更新显示到OLED     
 98                             break;
 99                         case S3:    
100                             OLED_ShowNum(0,0,3,4,12);//显示数字码值 3
101                             OLED_Refresh_Gram();        //更新显示到OLED     
102                             break;
103                         case S4:    
104                             OLED_ShowNum(0,0,4,4,12);//显示数字码值 4
105                             OLED_Refresh_Gram();        //更新显示到OLED     
106                             break;
107                         case S5:
108                             OLED_ShowNum(0,0,5,4,12);
109                             OLED_Refresh_Gram();        //更新显示到OLED     
110                             break;
111                         case S6:    
112                             OLED_ShowNum(0,0,6,4,12);
113                             OLED_Refresh_Gram();        //更新显示到OLED     
114                             break;
115                         case S7:
116                             OLED_ShowNum(0,0,7,4,12);
117                             OLED_Refresh_Gram();        //更新显示到OLED     
118                             break;
119                         case S8:     
120                             OLED_ShowNum(0,0,8,4,12);
121                             OLED_Refresh_Gram();        //更新显示到OLED     
122                             break;
123                         case S9:    
124                             OLED_ShowNum(0,0,9,4,12);//
125                             OLED_Refresh_Gram();        //更新显示到OLED     
126                             break;
127                         case S10:
128                             LED1=1;
129                             OLED_ShowString(18,0,"*",12);  
130                             OLED_Refresh_Gram();        //更新显示到OLED     
131                             break;
132                         case S11:     
133                             OLED_ShowNum(0,0,0,4,12);
134                             OLED_Refresh_Gram();        //更新显示到OLED     
135                             break;
136                         case S12:    
137                             OLED_ShowString(18,0,"#",12);  //显示字符串码值 #
138                             OLED_Refresh_Gram();        //更新显示到OLED     
139                             break;
140                     }        
141          }
142 }

猜你喜欢

转载自www.cnblogs.com/llmx002/p/11073060.html
今日推荐