| 
 
| 例程资料链接如下: BD网盘链接:
 https://pan.baidu.com/s/1JUMZH-sJAH-dPB0AtEvE7w
 提取码:oe9t
 相关视频:基于CW32的薄膜式键盘的应用
 
 一、简介
 薄膜式键盘是一种常见的输入设备,它由一层薄膜电路板和一层触摸膜组成。薄膜电路板上印有导电图案,而触摸膜则具有与之对应的按键区域。这种键盘的应用场景非常广泛,以下是几个典型的应用场景:
 
 (1)电子产品:薄膜式键盘被广泛应用于各种电子产品中,如手机、平板电脑、数码相机等。由于其结构简单、体积小巧,可以很好地满足电子产品的设计需求。
 
 (2)工业控制:在工业自动化领域,薄膜式键盘常用于控制面板和操作界面。它们具有防尘、防水、抗腐蚀等特性,能够适应恶劣的工作环境。
 
 (3)医疗设备:医疗设备通常需要高度卫生和易清洁的特点,薄膜式键盘因其表面光滑、易擦拭的特性而被广泛应用于医疗设备中,如手术台、心电图仪等。
 
 二、所需物料
 
 本实验使用到了CW32-48F大学计划开发板、5*4薄膜式键盘模块、0.96寸OLED显示屏及Keil5开发环境。开发板上留有矩阵键盘接口,可以直接将模块插上使用。
 
 
   
 
   
 
 三、核心代码
 main.c:
 #include "main.h"
 #include "OLED.h"
 #include "Key.h"
 #include "Delay.h"
 #include "BTIM.h"
 
 #define NUM_LENGTH 6
 
 uint8_t choose_flag=0;    //选中标识
 uint8_t choose_index=0;   //数组下标
 uint8_t exert_flag=0;     //执行标识
 
 uint8_t number[NUM_LENGTH]={0};    //存储6位数字
 uint8_t num_index=0;      //数组下标
 char temp='.';            //默认值'.'
 
 int main()
 {
 uint8_t i;
 uint8_t position=0;     //选中的数字在数组中的位置
 OLED_Init();            //OLED显示
 Key_GPIO_Init();        //5*4薄膜键盘GPIO初始化
 BTIM_Init();            //定时器初始化,控制按键扫描周期
 while(1)
 {
 if(exert_flag==1)     //若执行标识已打开
 {
 switch(temp)
 {
 case '<':           //选中左移
 if(choose_flag==0) position=choose_index+1; //向左选中数字
 if(position!=0)                                                                                                                  //若已有数字输入
 {
 choose_flag=1;                                                                                  //打开选中标识
 OLED_Clear_Row(2);                                                                                                 //先清除已有标识符号‘^’
 if(--position==0) position=choose_index;  //选中左移
 OLED_ShowChar(2,position,'^');                        //显示选中标识符号'^'
 }
 break;
 case '>':
 if(choose_flag==0) position=choose_index;   //向右选中数字
 if(position!=0)                                                                                                                        //若已有数字输入
 {
 choose_flag=1;                            //打开选中标识
 OLED_Clear_Row(2);                                                                                                //先清除已有标识符号'^'
 if(++position==choose_index+1) position=1;//选中右移
 OLED_ShowChar(2,position,'^');                                                //显示选中标识符号'^'
 }
 break;
 case 'E':
 choose_flag=0;                              //关闭选中标识
 OLED_Clear_Row(2);                                                                                                        //清除选中标识符号'^'
 break;
 default:
 if(choose_flag==0)                                 //若未打开选中标识
 {
 choose_index=num_index+1;
 if(num_index==0)
 {
 OLED_Clear_Row(1);
 for(i=0;i<NUM_LENGTH;i++)                                                                                                //溢出清零
 number=0;
 }
 number[num_index]=temp;
 OLED_ShowNum(1,num_index+1,number[num_index],1);
 num_index++;                                                                                                                        //输入右移
 choose_index=num_index;
 if(num_index==NUM_LENGTH) num_index=0;
 }
 else
 {
 number[position-1]=temp;                      //若已打开选中标识,将获取的键值保存至数组中对应的位置
 OLED_ShowNum(1,position,number[position-1],1);//显示屏上覆盖原有数字
 }
 break;
 }
 exert_flag=0;        //执行后关闭标识
 }
 }
 }
 
 void BTIM1_IRQHandler(void)     //基本定时器1中断服务函数
 {
 static uint8_t cnt = 0;
 if(BTIM_GetITStatus(CW_BTIM1,BTIM_IT_OV))
 {
 if(++cnt>=18)
 {
 cnt=0;
 temp=Key_Scan(); //每180ms执行一次按键扫描,返回值赋值给temp
 if(temp!='.')  exert_flag=1;    //打开执行标识
 }
 BTIM_ClearITPendingBit(CW_BTIM1,BTIM_IT_OV); //清除标志位
 }
 }
 Key.c:
 #include "Key.h"
 #include "main.h"
 #include "Delay.h"
 #include "OLED.h"
 
 #define  ROW_PORT CW_GPIOA      //键盘行引脚端口
 #define  COL_PORT CW_GPIOB      //键盘列引脚端口
 
 #define  ROW_NUM  4     //4行
 #define  COL_NUM  4     //4列
 
 uint16_t row_pins[ROW_NUM]={GPIO_PIN_1,GPIO_PIN_4,GPIO_PIN_5,GPIO_PIN_6};     //每一行所对应的引脚
 
 uint16_t col_pins[COL_NUM]={GPIO_PIN_15,GPIO_PIN_14,GPIO_PIN_13,GPIO_PIN_12}; //每一列所对应的引脚
 
 char key_value[ROW_NUM][COL_NUM]={    //键值
 1,   2,  3,   '(',
 4,   5,  6,   ')',
 7,   8,  9,   'E',
 '<', 0,  '>', 'Y'
 };
 
 void Key_GPIO_Init(void)
 {
 __RCC_GPIOA_CLK_ENABLE();
 __RCC_GPIOB_CLK_ENABLE();
 
 //rows-->置行
 GPIO_InitTypeDef GPIO_InitStruct;
 GPIO_InitStruct.IT=GPIO_IT_NONE;
 GPIO_InitStruct.Mode=GPIO_MODE_OUTPUT_PP;      //推挽输出
 GPIO_InitStruct.Pins=row_pins[0]|row_pins[1]|row_pins[2]|row_pins[3];
 GPIO_InitStruct.Speed=GPIO_SPEED_HIGH;
 GPIO_Init(ROW_PORT, &GPIO_InitStruct);
 
 //cols-->检列
 GPIO_InitStruct.Mode=GPIO_MODE_INPUT_PULLUP;   //上拉输入
 GPIO_InitStruct.Pins=col_pins[0]|col_pins[1]|col_pins[2]|col_pins[3];
 GPIO_Init(COL_PORT, &GPIO_InitStruct);
 }
 
 char Key_Scan(void)
 {
 uint8_t i,j;
 char key = '.';  //默认值'.'
 
 for ( i = 0; i < ROW_NUM; i ++ )   //1-4行依次置低
 {
 GPIO_WritePin(ROW_PORT,row_pins,GPIO_Pin_RESET);
 for( j = 0; j < COL_NUM; j ++ )  //依次检测1~4列电平
 {
 if( GPIO_ReadPin(COL_PORT,col_pins[j])==RESET )  //如果检测到低电平,则代表有按键按下
 {
 key = key_value[j];    //获取键值
 break;            //跳出检列循环
 }
 }
 GPIO_WritePin(ROW_PORT,row_pins,GPIO_Pin_SET);  //本行恢复高电平,准备置低下一行
 if(key != '.') break; //若key不是默认值,则代表已检测到按键按下,退出置行循环,结束本次按键扫描
 }
 
 return key;  //返回键值
 }
 
 
 
 四、效果演示
 
 
   
 ————————————————
 
 版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
 
 原文链接:https://blog.csdn.net/2302_81038468/article/details/136449440
 
 
 | 
 |