STM32-基于HAL库的LED流水灯
STM32-基于HAL库的LED流水灯
实验任务
安装 STM32CubeMX,配合Keil,使用HAL库方式完成下列任务:
- 使用GPIO端口完成3只LED红绿灯的周期闪烁。
- 使用Keil的,观察时序状态和高低电平转换周期。
- 用STM32F103核心板的GPIOA端某一管脚接一个开关(用杜邦线模拟代替)。采用中断模式编程,当开关接高电平时,LED流水灯工作;接低电平时,LED流水灯停止工作。
实验过程
1. HAL库实现流水灯
打开CubeMX,创建好工程并配置完毕后,选择PA5、PA6、PA7三个引脚设置成GPIO_Output,即选择这三个引脚实现流水灯。如下图:
设置完毕后,点击GENERATE CODE,生成Keil项目,打开项目后,在main函数的while循环中,输入如下代码:
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5); // 让PA5的电平反翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5); // 让PA5的电平反翻转一次
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_6); // 让PA6的电平反翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_6); // 让PA6的电平反翻转一次
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_7); // 让PA7的电平反翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_7); // 让PA7的电平反翻转一次
所以完整的main函数如下:
int main(void)
{
HAL_Init();
SystemClock_Config();
MX_GPIO_Init();
while (1)
{
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5); // 让PA5的电平翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5); // 让PA5的电平翻转一次
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_6); // 让PA6的电平翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_6); // 让PA6的电平翻转一次
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_7); // 让PA7的电平翻转一次
HAL_Delay(1000); // 延时1s
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_7); // 让PA7的电平翻转一次
}
}
烧录后,可以看到流水灯效果:
2. 软件仿真逻辑分析仪功能观察时序波形
打开Keil的软件仿真逻辑分析仪,选择PA5、PA、PA7三个引脚进行观察,可以发现三个引脚的电平以1秒为间隔轮流跳变,从而实现流水灯的效果。
3. 中断模式控制流水灯
- 引脚配置如下:
PA5、PA6、PA7控制流水灯
PB15模拟开关,设置为GPIO_EXTI15
-
配置GPIO
-
代码生成时勾选这个
-
Keil中配置代码
-
打开生成的项目,找到stm32f1xx_it.c文件中的EXTI15_10_IRQHandler函数,跳转到内部的HAL_GPIO_EXTI_IRQHandler函数定义,如下:
-
往下找到HAL_GPIO_EXTI_Callback这个函数。该函数是给用户自己重写的,可以在这里根据不同的中断来执行不同的处理。在这里我们需要根据B15的中断来实现流水灯的工作和停止。
-
输入代码:
__weak void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin) { if(GPIO_Pin == SWITCH_Pin){ //获取B15的电位,如果是低电平就一直死循环 while (HAL_GPIO_ReadPin(SWITCH_GPIO_Port,SWITCH_Pin) == GPIO_PIN_RESET) {} } }
-
代码烧录后,运行效果:
-