注:本学习笔记基于stm32f4系列
使用的开发板为正点原子stmf407ZGT6探索者开发板
GPIO引脚使用时,可输入或输出数字信号
例如:
检测按键输入信号(Read_Pin)输出信号(Write_Pin)
输出信号点亮或熄灭LED
HAL_GPIO_WritePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin, GPIO_PinState PinState);
HAL_GPIO_ReadPin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)
HAL_GPIO_TogglePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)
实现功能:
按下KEY0时,使LED1的输出翻转
按下KEY1时,使LED2的输出翻转
按下KEY2时,使LED1与LED2的状态都翻转
连接按键的引脚选择GPIO_Input
连接LED的引脚选择GPIO_Output
并设置相应的用户标签
keyled.c
#include "keyled.h"
//编写函数扫描被按下的按键
KEYS ScanPressedKey(uint32_t timeout)
{
uint32_t tickstart = HAL_GetTick();
const uint32_t btnDelay = 20;//延时时间
while (1)
{
#ifdef KeyRight_Pin
if (HAL_GPIO_ReadPin(Key0_GPIO_Port, Key0_Pin) == GPIO_PIN_RESET)
{
HAL_Delay(btnDelay);//延时消除前抖动
if (HAL_GPIO_ReadPin(Key0_GPIO_Port, Key0_Pin) == GPIO_PIN_RESET)
return KEY_0;
}
#endif
#ifdef KeyDown_Pin
if (HAL_GPIO_ReadPin(Key1_GPIO_Port, Key1_Pin) == GPIO_PIN_RESET)
{
HAL_Delay(btnDelay);
if (HAL_GPIO_ReadPin(Key1_GPIO_Port, Key1_Pin) == GPIO_PIN_RESET)
return KEY_1;
}
#endif
#ifdef KeyLeft_Pin
if (HAL_GPIO_ReadPin(Key2_GPIO_Port, Key2_Pin) == GPIO_PIN_RESET)
{
HAL_Delay(btnDelay);
if (HAL_GPIO_ReadPin(Key2_GPIO_Port, Key2_Pin) == GPIO_PIN_RESET)
return KEY_2;
}
#endif
#ifdef KeyUp_Pin
if (HAL_GPIO_ReadPin(KeyUp_GPIO_Port, KeyUp_Pin) == GPIO_PIN_SET)
{
HAL_Delay(btnDelay);
if (HAL_GPIO_ReadPin(KeyUp_GPIO_Port, KeyUp_Pin) == GPIO_PIN_SET)
return KEY_UP;
}
#endif
if (timeout != KEY_WAIT_ALWAYS) {
if ((HAL_GetTick() - tickstart) > timeout)
break;
}
}
return KEY_NONE;
}//若没有按键被按下,超时后跳出循环
keyled.h
#include "main.h"
//创建枚举类型
typedef enum {
KEY_NONE = 0,
KEY_1,
KEY_2,
KEY_UP,
KEY_NONE
} KEYS;
//定义参数-表示一直等待按键按下
#define KEY_WAIT_ALWAYS 0
KEYS ScanPressedKey(uint32_t timeout);
//LED1的宏定义函数
#ifdef LED1_Pin
#define LED1_Toggle() HAL_GPIO_TogglePin(LED1_GPIO_Port, LED1_Pin)//实现翻转
#define LED1_OFF() HAL_GPIO_WritePin(LED1_GPIO_Port, LED1_Pin, GPIO_PIN_SET)//实现打开
#define LED1_ON() HAL_GPIO_WritePin(LED1_GPIO_Port, LED1_Pin, GPIO_PIN_RESET)//实现关闭
#endif
//LED2的宏定义函数
#ifdef LED2_Pin
#define LED2_Toggle() HAL_GPIO_TogglePin(LED2_GPIO_Port, LED2_Pin)
#define LED2_OFF() HAL_GPIO_WritePin(LED2_GPIO_Port, LED2_Pin, GPIO_PIN_SET)
#define LED2_ON() HAL_GPIO_WritePin(LED2_GPIO_Port, LED2_Pin, GPIO_PIN_RESET)
#endif
//蜂鸣器的宏定义函数
#ifdef Buzzer_Pin
#define Buzzer_Toggle() HAL_GPIO_TogglePin(Buzzer_GPIO_Port, Buzzer_Pin)
#define Buzzer_ON() HAL_GPIO_WritePin(Buzzer_GPIO_Port, Buzzer_Pin, GPIO_PIN_SET)
#define Buzzer_OFF() HAL_GPIO_WritePin(Buzzer_GPIO_Port, Buzzer_Pin, GPIO_PIN_RESET)
#endif
while (1)
{
KEYS curKey=ScanPressedKey(KEY_WAIT_ALWAYS);
switch (curKey)
{
case KEY_0:
LED1_Toggle();
break;
case KEY_1:
LED2_Toggle();
break;
case KEY_2:
LED1_Toggle();
LED2_Toggle();
break;
case KEY_UP:
Buzzer_Toggle();
break;
default:
break;
}
HAL_Delay(200);//消除按键弹起时的的抖动影响
有源蜂鸣器原理图
有源蜂鸣器是指自带了震荡电路的蜂鸣器,这种蜂鸣器一接上电就会自己震荡发声。而如
果是无源蜂鸣器,则需要外加一定频率(2~5Khz)的驱动信号,才会发声。
图中 Q4 是用来扩流,R65 则是一个下拉电阻,避免 MCU 复位的时候,蜂鸣器可能发声的
现象。BEEP 信号直接连接在 MCU 的 PF8 上面,PF8 可以做 PWM 输出,可使用 PWM 来控制蜂鸣器实现“唱歌”。
实现功能:
按下KEY_UP按键时,蜂鸣器输出翻转
连接蜂鸣器的引脚选择GPIO_Output
并设置相应的用户标签