基于stm32f103的矩阵键盘

2019-08-16来源: eefocus关键字:stm32f103  矩阵键盘  下拉输入

我现在的任务是做一个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板回来再测量。

关键字:stm32f103  矩阵键盘  下拉输入

编辑:什么鱼 引用地址:http://news.eeworld.com.cn/mcu/ic471360.html
本网站转载的所有的文章、图片、音频视频文件等资料的版权归版权所有人所有,本站采用的非本站原创文章及图片等内容无法一一联系确认版权者。如果本网所选内容的文章作者及编辑认为其作品不宜公开自由传播,或不应无偿使用,请及时通过电子邮件或电话通知我们,以迅速采取适当措施,避免给双方造成不必要的经济损失。

上一篇:基于 STM32F407 使用 4*4 矩阵键盘
下一篇:ARM开发(10)基于STM32的通用定时器中断控制蜂鸣器响

关注eeworld公众号 快捷获取更多信息
关注eeworld公众号
快捷获取更多信息
关注eeworld服务号 享受更多官方福利
关注eeworld服务号
享受更多官方福利

推荐阅读

【STM32F103】中断综述

一、中断内核: STM32的中断很强大,每个外设都可以产生中断,F103在内核水平上搭载了异常响应系统,系统异常有8个(算上RESET和HardFault也就10个),外部中断有60个,但是根据NVIC(嵌套向量中断控制器,控制整个芯片中断相关的功能),IP(中断优先级寄存器)数组中预留了240个位置(NVIC结构如上图),可见眼光之远,用于扩展,这是STM32F103用不到这么多。如果以后要找跟内核相关的函数,都存在core_cm3.c和misc.c中,包括NVIC的函数的声明,但是其具体的库函数内容并不是和固件库头文件core_cm3.h一致(不在core_cm3.c),而是放在库函数的misc.c中,这点需要
发表于 2019-08-23
【STM32F103】中断综述

关于由CubeMx生成stm32f4+freertos,不正常分析之堆栈大小设置

freertos官方手册上有说,移植中出现的问题大多数是由堆栈设置不合理造成的,今天结合自身遇到问题分析一下1.任务堆栈设置过小,很容易造成硬件溢出,跳转到void HardFault_Handler(void);调试方法,可以通过调用函数,UBaseType_t uxTaskGetStackHighWaterMark( TaskHandle_t xTask );来跟踪剩余堆栈,不过在CubeMx中的Configuration->FreeRtos->Include parameters中使能uxTaskGetStackHighWaterMark函数;2.整体设置过小,TOTAL_HEAP_SIZE
发表于 2019-08-23

CubeMX Stm32F407生成一定周期的占空比不同的方波DMA+定时器

先上图如图 是我生成的一个波形  这个波形的占空比在连续的四个周期内分别是10%,20%,30%,40%, 并且按照这个顺序循环这里大致介绍一下实现的方式。使用的软件是Cubemx(库函肯定也可以实现)第一步是器件选型  这一部分不做介绍  用的是Stm32F407第二是时钟配置接下来是定时器配置 第三步就是生成代码了这里 需要在生成的代码里面加上一行开始的代码。
发表于 2019-08-23
CubeMX Stm32F407生成一定周期的占空比不同的方波DMA+定时器

STM32F103控制舵机

//TIM4 PWM部分初始化 //PWM输出初始化//arr:自动重装值//psc:时钟预分频数void TIM4_PWM_Init(u16 arr,u16 psc){   GPIO_InitTypeDef GPIO_InitStructure; TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure; TIM_OCInitTypeDef  TIM_OCInitStructure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE); //使能定时器3时钟 
发表于 2019-08-23

基于STM32F103ZET6主控平台实现定时器TIM3的驱动

_Clock_Init(9);   //系统时钟设置 delay_init(72);     //延时初始化 uart_init(72,115200); //串口初始化为115200 LED_Init(); BEEP_Init(); TIM3_Init(4999,7199); while(1) { if(Wl_stat==0)//代表进入WHILE循环 { printf("Input While(1)-->rn"); Wl_stat=1; } LED1=!LED1; delay_ms(200); }} 第四步:编译通过后,烧录进STM32F103ZET6开发板,实现
发表于 2019-08-22

STM32f103ZET6定时器TIM3使用通道1输出PWM程序

总结:TIM3_CH1输出口为PA6(重映射为PB4),PB5位DS0接口。1.使用重映射之后,原始IO口不再有输出;本例子中,若使用部分重映射,则 PA6映射到PB4中,所以仅仅PB4有波形输出;飞线连接PB4与PB5即可观察PWM呼吸灯效果。2.使用IO口前务必初始化,本例子中开始仅仅初始化了PB5口,而没有初始化PA6导致一直验证失败;正点原子给出程序中是由通道2直接映射到PB5因此只需要初始化PB5口即可,不存在上述问题。3.除了正常输出输入信号之外,输出PWM以及其他功能均属于IO口的复用功能。#include "stm32f10x.h"#include "led.h"
发表于 2019-08-22

小广播

何立民专栏

单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

电子工程世界版权所有 京ICP证060456号 京ICP备10001474号 电信业务审批[2006]字第258号函 京公海网安备110108001534 Copyright © 2005-2019 EEWORLD.com.cn, Inc. All rights reserved