键盘之中断法1

本文为LED-执棋困局,csdn原创首发。
> 发布人:LED-执棋困局
> 欢迎大家与LED-执棋困局相互点赞+关注+收藏+评论,也祝大家生活安康,学业愉快,工作顺利。
> 我的格言是:“尽最大努力,做最好的自己!
版权声明:本文为CSDN博主「LCD-执棋困局」的原创文章。

博主原创:LED-执棋困局

目录

一、外部中断

1.1引脚INT0、INT1

1.2外部中断初始化

1.3中断服务函数

二、按键与LED

2.1项目功能

2.2仿真设计

2.3代码解析

2.4项目结果

2.5扩展功能

三、总结

一、外部中断

1.1引脚INT0、INT1

外部中断0引脚为INT0,外部中断1引脚为INT1,通常与键盘连接,键盘一端接引脚,另一端接地。

1.2外部中断初始化

外部中断初始化比较简单,通常设置EA、IT0/IT1、EX0/EX1

打开总中断EA=1——>设置触发方式IT0/IT1——>打开外部中断允许标志位EX0/EX1=1

1.3中断服务函数

外部中断0入口编号为0,外部中断1入口编号为2

格式:void init() interrupt n

二、按键与LED

2.1项目功能

四个按键,要求按键要与2个外部中断结合,第一个按键启动流水灯,第二个按键停止流水灯功能,第三个按键正向流水灯,第四个按键反向流水灯。

2.2仿真设计

由于只有2个外部中断,但时要用4个按键,因此可以借助外设与元件--AND_4,将4个按键先连接到AND_4,在用一根线接到外部中断0。

不论哪个按键按下,该按键左端变成低电平,与另三个按键与运算,引脚INT0变成低电平,从而触发中断(这里是因为下降沿触发方式)。

要判断具体哪个按键按下,需要接P2低4位(等效于矩阵键盘的第一列的4个按键)。

2.3代码解析

以下三个代码块均为main.c

思路:可以先将外部中断0的初始化写出来,根据流水灯要实现启动停止和正反向功能,定义启动停止标志位ledok和流水灯方向标志位updown,接着在中断服务函数中通过判断按键哪个按下来这设置两个标志位,最后书写按键功能服务函数,来实现流水灯功能。

#include <reg51.h>
#include <intrins.h>
#include "delay.h"

void init0();
void key_service();

unsigned char temp;
unsigned char ledok=0;
unsigned char updown=1;

void main()
{
	init0();
	temp=0xfe;
	while(1)
	{
		key_service();
	}	
}
void init0()
{
	IT0=1;//下降沿触发
	EA=1;//总中断打开
	EX0=1;//外部中断
}

void int0() interrupt 0
{
	switch(P2&0x0f)
	{
		case 0x0e:ledok=1;break;//启动
		case 0x0d:ledok=0;break;//停止
		case 0x0b:updown=1;break;//正向
		case 0x07:updown=0;break;//反向
		default:break;
	}
}

P2&0x0f:因为只接P2低4位,4个键盘都在第一列,所以只需判断第几行,就可以判断按键哪个被按下。

key_service()是按键功能服务函数,采用if嵌套来实现流水灯功能,先判断是否启动,在启动条件再判断正向还是反向。此外,还使用了库函数法,_crol_(temp,1)就是将temp对应的8位二进制向左循环移1位,比如01011100循环左移1位就是10111001;_cror_(temp,1)就是将temp对应的8位二进制向右循环移1位,比如01011100循环右移1位就是00101110。

void key_service()
{
	if(ledok)
  {
		P1=temp;
		if(updown)
		{
			temp=_crol_(temp,1);
		}
		else
		{
			temp=_cror_(temp,1);
		}
		delay(2000);
	}		
}

2.4项目结果

2.5扩展功能

可以将前两个按键合成一个一键二义的按键,用于控制流水灯的启动暂停,这时可以定义一个标志位并利用~运算符。

同理,可以将后两个按键合成一个一键二义的按键,用于控制流水灯的正反向,这时可以定义一个标志位并利用~运算符。

三、总结

       本次项目是一个按键、外部中断、LED但又不失基础的综合项目,为接下来的学习大有裨益!

最后,LED-执棋困局希望与大家相互点赞+关注+收藏+评论,相互借鉴,相互学习,不断成长!

下一文章我们将继续介绍按键与中断的综合性项目,我们敬请期待吧!!!

  • 5
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
以下是使用STM32控制GPIO口控制蜂鸣器并使用中断的扫描键盘的相关知识: 1. 控制蜂鸣器 在STM32中,控制GPIO口非常简单,以下是使用STM32 HAL库控制GPIO口控制蜂鸣器的代码示例: ```c #include "stm32f1xx_hal.h" #define BEEP_PIN GPIO_PIN_0 #define BEEP_PORT GPIOA void BeepOn(void) { HAL_GPIO_WritePin(BEEP_PORT, BEEP_PIN, GPIO_PIN_SET); } void BeepOff(void) { HAL_GPIO_WritePin(BEEP_PORT, BEEP_PIN, GPIO_PIN_RESET); } int main(void) { HAL_Init(); __HAL_RCC_GPIOA_CLK_ENABLE(); GPIO_InitTypeDef GPIO_InitStruct; GPIO_InitStruct.Pin = BEEP_PIN; GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP; GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH; HAL_GPIO_Init(BEEP_PORT, &GPIO_InitStruct); while (1) { BeepOn(); HAL_Delay(500); BeepOff(); HAL_Delay(500); } } ``` 在代码中,首先定义了GPIO口的引脚和端口号。然后在main函数中,对GPIO口进行初始化,将其设置为输出模式,并不断地循环控制蜂鸣器亮灭。 2. 使用中断的扫描键盘 在STM32中,使用中断的扫描键盘可以通过以下步骤实现: - 配置GPIO口为输入模式,并使能对应的中断 - 初始化NVIC中断优先级 - 在中断服务函数中读取GPIO口状态,判断键盘按键是否按下 以下是使用STM32 HAL库实现中断的扫描键盘的代码示例: ```c #include "stm32f1xx_hal.h" #define KEY1_PIN GPIO_PIN_0 #define KEY1_PORT GPIOA void initKey() { GPIO_InitTypeDef GPIO_InitStruct; GPIO_InitStruct.Pin = KEY1_PIN; GPIO_InitStruct.Mode = GPIO_MODE_INPUT; GPIO_InitStruct.Pull = GPIO_PULLUP; GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW; HAL_GPIO_Init(KEY1_PORT, &GPIO_InitStruct); HAL_NVIC_SetPriority(EXTI0_IRQn, 0, 1); HAL_NVIC_EnableIRQ(EXTI0_IRQn); } void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin) { if (GPIO_Pin == KEY1_PIN) { if (HAL_GPIO_ReadPin(KEY1_PORT, KEY1_PIN) == GPIO_PIN_RESET) { // KEY1按下 // do something } } } int main(void) { HAL_Init(); __HAL_RCC_GPIOA_CLK_ENABLE(); initKey(); while (1) { // do something } } ``` 在代码中,首先定义了KEY1的引脚和端口号,并在`initKey()`函数中将其配置为输入模式,使能对应的中断,并初始化NVIC中断优先级。然后在`HAL_GPIO_EXTI_Callback()`中断服务函数中读取GPIO口状态,判断KEY1按键是否按下,并在按键按下时执行相应的操作。最后在`main()`函数中不断地循环执行其他操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值