STM32震动感应控制继电器

Posted 行稳方能走远

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了STM32震动感应控制继电器相关的知识,希望对你有一定的参考价值。

摘自:stm32的外部中断 震动感应 控制 继电器
作者:点灯小哥
发布时间: 2021-03-05 22:37:01
网址:https://blog.csdn.net/weixin_46016743/article/details/114417161

继电器模块

relay.c

#include "relay.h"
#include "stm32f10x.h"                  // Device header
 
void Relay_Init(void)
{
		GPIO_InitTypeDef Relay_init ;
		
		//1.使能GPIOA时钟    接入PA3口
		RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOA ,  ENABLE);
		//2.GPIOA3结构体配置
		Relay_init.GPIO_Mode  = GPIO_Mode_Out_PP;//推挽输出
		Relay_init.GPIO_Pin   = GPIO_Pin_3;
		Relay_init.GPIO_Speed = GPIO_Speed_10MHz;
	
		GPIO_Init( GPIOA , &Relay_init);
 
}

单独新建立relay文件夹,里面新建relay.c和relay.h两个文件,先将relay.c文件添加到USER里面,写完第一句代码#include "relay.h"直接编译,relay.h会自动包含到relay.c的子目录下。
若头文件和.c文件不在同一个文件目录下编译将提示找不到头文件,需要手动添加头文件路径。

relay.h

#include "stm32f10x.h"
 
void Relay_Init(void);//先声明,再定义,再调用

震动感应模块

shake.c

#include "shake.h"
#include "stm32f10x.h"                  // Device header
 
void Shake_Init(void)
{

	GPIO_InitTypeDef Shake_init;
	
	//1.打开我们的GPIOA时钟      连接PA1引脚
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
	//2.配置GPIOA1的配置
	Shake_init.GPIO_Mode  = GPIO_Mode_IPD;  //震动传感器初始为高电平,有振动就为低电平 检测从高电平到低电平的变化  所以用下拉模式
	Shake_init.GPIO_Pin   = GPIO_Pin_1;
	Shake_init.GPIO_Speed = GPIO_Speed_10MHz;
		
	 GPIO_Init( GPIOA, &Shake_init);
 
}

shake.h

#include "stm32f10x.h"
 
void Shake_Init(void);

中断配置

中断相关的理论介绍参见我的这篇博文:STM32外部中断EXTI简介
exti.c

#include "exti.h"
#include "stm32f10x.h"                  // Device header
 
void Exti_Init(void)
{

	//1.配置GPIO
	GPIO_InitTypeDef Shake_init; //gpio.h  
	EXTI_InitTypeDef Exti_init;	 //exti.h
	NVIC_InitTypeDef Nvic_init;	 //misc.h
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);     //使能GPIO的时钟
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);      //GPIOA的中断复用 使能时钟
	
	GPIO_EXTILineConfig(GPIO_PortSourceGPIOA,  GPIO_PinSource1); //gpio.h  配置的外部中断源是GPIOA1  是shake震动传感器(GPIOA pin1的复用)
                                           //中断优先级组选第1组(有一张图片介绍)
	
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);  //配置NVIC中断组
	
	Shake_init.GPIO_Mode  = GPIO_Mode_IPD;  //震动传感器初始为高电平  所以用下拉模式 拉到低电平
	Shake_init.GPIO_Pin   = GPIO_Pin_1;
	Shake_init.GPIO_Speed = GPIO_Speed_10MHz;
	GPIO_Init( GPIOA, &Shake_init);
	
	
	//2.配置EXTI外部中断
	Exti_init.EXTI_Line    = EXTI_Line1; //中断线     因为我们用到的中断源是GPIOA1 所以中断线选择Line1  
	Exti_init.EXTI_LineCmd = ENABLE;     //选使能  还一种是静止模式
	Exti_init.EXTI_Mode    = EXTI_Mode_Interrupt;//选择中断模式  还一种是事件模式
	Exti_init.EXTI_Trigger = EXTI_Trigger_Falling;//振动传感器有振动源————>高电平到底电平 所以选择下降沿触发
	EXTI_Init(&Exti_init);
 
 
	//3.配置NVIC中断控制器  在misc.h里
	Nvic_init.NVIC_IRQChannel = EXTI1_IRQn;     //中断通道 因为我们用到的中断源是GPIOA1所以选择中断通道1
	Nvic_init.NVIC_IRQChannelCmd = ENABLE;      //使能  找到FunctionalState字眼 右键goto
	Nvic_init.NVIC_IRQChannelPreemptionPriority = 1;   //因为只配置了一个中断  不考虑优先级 所以只有1个
	Nvic_init.NVIC_IRQChannelSubPriority = 1;         //抢占优先级 从优先级 都是1
	NVIC_Init(&Nvic_init);//中断初始化函数
	
	//4.编写中断服务函数  写在main函数里面了
	
}

exti.h

#include "stm32f10x.h"  
 
void Exti_Init(void);

主函数

main.c

#include "stm32f10x.h"                  // Device header
#include "relay.h"//这个会找不到头文件,需要手动添加头文件路径  点击魔术棒——选择C/C++——include path
#include "shake.h"//下同
#include "exti.h"
 
void delay(uint16_t time)
{
		uint16_t i = 0;
		while(time--)
		{
			i=12000;
			while(i--);
		}
}
int main(void)
{

		LED_Init();
		Relay_Init();
		Shake_Init();
		Exti_Init();
		
		GPIO_SetBits(GPIOA , GPIO_Pin_3); //初始化继电器为关闭状态

		
//    下面这部分没有使用外部中断,直接While()死循环检测振动模块电平,从而控制灯的亮灭(继电器)		
//		while(1)
//		{
//              //if内部判断是否发生电平变化
//				if(GPIO_ReadInputDataBit( GPIOA,  GPIO_Pin_1) == 0) //如果发生震动
//				{
//						GPIO_ResetBits(GPIOA , GPIO_Pin_3);  //开灯
//						delay(1000);												 //持续一秒
//						GPIO_SetBits(GPIOA , GPIO_Pin_3);		 //关灯
//				}else{
//						GPIO_SetBits(GPIOA , GPIO_Pin_3);
//				}
 
			
//			 GPIO_ResetBits( GPIOA,  GPIO_Pin_3);
			
//				delay(1000);
//			GPIO_SetBits(GPIOA , GPIO_Pin_3);
 
			
			
//			  GPIO_ResetBits(GPIOC , GPIO_Pin_13); //void GPIO_ResetBits(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);
//				delay(1000); //1s
//				GPIO_SetBits(GPIOC , GPIO_Pin_13);
//				delay(1000);
		}
}


//4.中断服务函数   中断的好处:不用一直while()死循环,一直占用CPU
void EXTI1_IRQHandler(void)//在启动文件里
{
	
	if (EXTI_GetITStatus( EXTI_Line1 )  != RESET) //判断是否发生了中断  右键 EXTI_GetITStatus goto  //在exit.h
	{
		GPIO_ResetBits(GPIOA , GPIO_Pin_3);  //打开继电器,开灯
		delay(1000);
		GPIO_SetBits(GPIOA , GPIO_Pin_3);	//关闭继电器,关灯
	}
		
		EXTI_ClearFlag( EXTI_Line1);//清除中断标志 不然标志位一直都存在  在exit.h
			
}

以上是关于STM32震动感应控制继电器的主要内容,如果未能解决你的问题,请参考以下文章

433M射频遥控灯震动感应灯WIFI避障小车

STM32单片机驱动宏发12V电磁继电器电路问题

STM32的RFID射频读写控制装置

资料转发分享基于STM32智能路灯灯光自动控制系统设计-基于STM32无刷电机BLDC速度控制器系统设计-基于STM32热释人体感应智能门禁报警系统设计-基于STM32居家加湿器控制仿真系统设计

毕业设计:基于STM32的智能家居无线(蓝牙wifi)语音控制系统

STM32L+BC20+MQTT连接阿里云传输温湿度数据并控制继电器