×
单片机 > 单片机程序设计 > 详情

基于stm32f103的矩阵键盘

发布时间:2020-05-30 发布时间:
|

我现在的任务是做一个8*8的矩阵键盘,制PCB版之前,我用电路板搭了一个3*3的矩阵键盘来模拟一下,设置PA0、PA1、PA2为PP输出,设置P3、P4、P5下拉输入。大多数的芯片内部上拉或下拉电阻都是弱上拉或弱下拉,stm32f103的内部也一样,内部上拉或下拉的电阻阻值约为40K,这样可以方便外部调整,但是,在作为一些通讯引脚时,可能会出现上电时数据不稳定的问题,如I2C通讯,解决的办法是在外部在加上一个较强的上拉或下拉即可。具体程序如下:



#include

#include "usart.h"



void KeyBoard_Init(void)//按键初始化

{

GPIO_InitTypeDef GPIO_InitStruct;

GPIO_InitStruct.GPIO_Pin=GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_2;

GPIO_InitStruct.GPIO_Speed=GPIO_Speed_10MHz;

GPIO_InitStruct.GPIO_Mode=GPIO_Mode_Out_PP;

GPIO_Init(GPIOA,&GPIO_InitStruct);

GPIO_InitStruct.GPIO_Pin=GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7;

GPIO_InitStruct.GPIO_Speed=GPIO_Speed_10MHz;

GPIO_InitStruct.GPIO_Mode=GPIO_Mode_IPD;

GPIO_Init(GPIOA,&GPIO_InitStruct);

GPIO_SetBits(GPIOA,GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_2);

GPIO_ResetBits(GPIOA,GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7);

}

void Delay(u32 nCount)//延时函数

{

for(; nCount != 0; nCount--);

}



u8 KeyDown(void)

{

if((GPIO_ReadInputData(GPIOA)&0xff)!=0x07)//判断是否有键按下

return 1;//keydown

}

else return 0; 

}



u8 Read_KeyValue(void)   

{

unsigned int  KeyValue=0;


GPIO_SetBits(GPIOA,GPIO_Pin_0);

GPIO_ResetBits(GPIOA,GPIO_Pin_1|GPIO_Pin_2);//此时PA0读取的数据是0x01

switch(GPIO_ReadInputData(GPIOA)&0xff)

{

case 0x11:KeyValue='A';break;//此时PA口去的数据是0x11,其余读数与此原理相同

case 0x21:KeyValue='B';break;

case 0x41:KeyValue='C';break;

default: break;

}

GPIO_SetBits(GPIOA,GPIO_Pin_1);

GPIO_ResetBits(GPIOA,GPIO_Pin_0|GPIO_Pin_2);

switch(GPIO_ReadInputData(GPIOA)&0xff)

{

case 0x12:KeyValue='D';break;

case 0x22:KeyValue='E';break;

case 0x42:KeyValue='F';break;

default: break;

}

GPIO_SetBits(GPIOA,GPIO_Pin_2);

GPIO_ResetBits(GPIOA,GPIO_Pin_0|GPIO_Pin_1);

switch(GPIO_ReadInputData(GPIOA)&0xff)

{

case 0x14:KeyValue='G';break;

case 0x24:KeyValue='H';break;

case 0x44:KeyValue='I';break;

default: break;

}

GPIO_SetBits(GPIOA,GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_2);

GPIO_ResetBits(GPIOA,GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7);

while((GPIO_ReadInputData(GPIOA)&0xff)!=0x07);

printf("%c",KeyValue);

return KeyValue;

}




int ScanKeyBoard(void)

{

if(KeyDown()

{

Delay(0xffff);//软件去抖。按键抖动时间一般为5-10ms,延时以20ms为宜


if(KeyDown())

{


return Read_KeyValue();//按键扫描

}

else 

{

printf("nothing");


}

return 0;

}



int main(void)

{

u32 i=100;

SystemInit();

usart_Configuration(); 

KeyBoard_Init();

Delay(i);

  while(1)

{

ScanKeyBoard();

    Delay(500);

}

}


用串口观察实验结果还可以,但个别时候会同时打印出按键字母和“nothing”,我感觉可能是焊接的问题,元器件接触不良很有可能造成这种结果,具体等PCB板回来再测量。



『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
浅谈msp430f5529入门(2)----时钟配置.例程分析