光敏传感器控制led灯的亮度

本文详细介绍了STM32F407微控制器上的ADC转换器工作原理,包括采样、量化和编码过程,并展示了如何配置ADC电路、时钟、模拟输入以及光敏电阻的应用,以实现通过ADC测量光强并控制LED亮度。
摘要由CSDN通过智能技术生成

adc.c 

/*
ADC转换器三大步骤
	1、采样:在时间轴上对信号数字化。也就是,按照固定的时间间隔抽取模拟信号的值,这样,采样后就可以使
	一个时间连续的信息波变为在时间上取值数目有限的离散信号。
	2、量化:在幅度轴上对信号数字化。也就是,用有限个幅度值近似还原原来连续变化的幅度值,把模拟信号的
	连续幅度变为有限数量的有一定间隔的离散值。
	3、编码:用二进制数表示每个采样的量化值(十进制数)。
	
	
四、ADC转换配置如下
	1、理解电路原理图
	可调电阻连接在PA5 -- ADC12_IN5
	可调电阻电压范围:0~3.3V
		

	2、开启PA口时钟和ADC1时钟,设置PA1为模拟输入。
	  RCC_AHB1PeriphClockCmd (RCC_AHB1Periph_GPIOA, ENABLE);
	  RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE);  
	  GPIO_Init();      

	3、初始化ADC_CCR寄存器。
		 ADC_CommonInit();
	4、初始化ADC1参数,设置ADC1的工作模式以及规则序列的相关信息。
		 void ADC_Init(ADC_TypeDef* ADCx, ADC_InitTypeDef* ADC_InitStruct);
	5、使能ADC。
			ADC_Cmd(ADC1, ENABLE);
	6、配置规则通道参数:
		 ADC_RegularChannelConfig();
	7、开启软件转换:ADC_SoftwareStartConv(ADC1);
	8、等待转换完成,读取ADC值。
	   ADC_GetConversionValue(ADC1);
*/


#include "adc.h"

/*
光敏电阻连接在PA5 -- ADC12_IN5
可调电阻电压范围:0~3.3V
*/

void Adc_Init(void)
{
	ADC_CommonInitTypeDef	ADC_CommonInitStruct;
	GPIO_InitTypeDef  		GPIO_InitStruct;
	ADC_InitTypeDef			ADC_InitStruct;
	//2、开启PA口时钟和ADC1时钟,设置PA1为模拟模式。
	RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE);  
	
	
	GPIO_InitStruct.GPIO_Pin	= GPIO_Pin_5; 						//引脚5
	GPIO_InitStruct.GPIO_Mode	= GPIO_Mode_AN;						//模拟
	GPIO_InitStruct.GPIO_PuPd	= GPIO_PuPd_NOPULL;					//浮空
	GPIO_Init(GPIOA, &GPIO_InitStruct);  
	//ADC不是复用,所以不用做映射

	


	ADC_CommonInitStruct.ADC_Mode 				= ADC_Mode_Independent;			//独立模式 规则通道
	ADC_CommonInitStruct.ADC_TwoSamplingDelay 	= ADC_TwoSamplingDelay_5Cycles;	//两个采样阶段之间的延迟5个时钟
	ADC_CommonInitStruct.ADC_DMAAccessMode 		= ADC_DMAAccessMode_Disabled; 	//DMA失能 通过CPU获取数据
	ADC_CommonInitStruct.ADC_Prescaler 			= ADC_Prescaler_Div4;			//84/4 = 21MHZ 这个值不能大于36MHZ
	//3、初始化ADC_CCR寄存器。
	ADC_CommonInit(&ADC_CommonInitStruct);	
	


	//4、初始化ADC1参数,设置ADC1的工作模式以及规则序列的相关信息。
	ADC_InitStruct.ADC_Resolution 				= ADC_Resolution_12b;			//12位模式
	ADC_InitStruct.ADC_ScanConvMode 			= DISABLE;						//非扫描模式	
	ADC_InitStruct.ADC_ContinuousConvMode 		= DISABLE;						//关闭连续转换
	ADC_InitStruct.ADC_ExternalTrigConvEdge  	= ADC_ExternalTrigConvEdge_None;//禁止触发检测,使用软件触发
	ADC_InitStruct.ADC_DataAlign 				= ADC_DataAlign_Right;			//右对齐 12位对齐(跟中国人使用习惯有关)	
	ADC_InitStruct.ADC_NbrOfConversion 			= 1;							//1个转换在规则序列中 
	ADC_Init(ADC1, &ADC_InitStruct);//ADC初始化

	
	
	//5、使能ADC。
	ADC_Cmd(ADC1, ENABLE);
	//6、配置规则通道参数:通道5 第三个参数为:转换次数 ,第四个参数:两个模拟量转换时间间隔
	ADC_RegularChannelConfig(ADC1, ADC_Channel_5,1,ADC_SampleTime_15Cycles);

}	



u16 Get_Adc_Value(void)
{
	u16 value;
	
	//7、开启软件转换:
	ADC_SoftwareStartConv(ADC1);
	//8、等待转换完成,读取ADC值。
	while(ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC) == RESET);
	
	value = ADC_GetConversionValue(ADC1);

	return value;
	
}


adc.h 

#ifndef __ADC_H
#define __ADC_H
#include "stm32f4xx.h"


void Adc_Init(void);
u16  Get_Adc_Value(void);


#endif

main.c

/*
芯片:stm32f407vet6
引脚连接:A0--PA5
PB6--RX
PB7--TX
实现功能:通过光敏电阻调节灯的亮度
需要用到ADC(光敏电阻)、pwm(控制灯的亮度)
*/
#include "stm32f4xx.h"
#include "led.h"
#include "key.h"
#include "exti.h"
#include "delay.h"
#include "pwm.h"
#include "usart.h"
#include "string.h"
//#include "hcsr04.h"
//#include "infrared.h"
//#include "iwdg.h"
//#include "rtc.h"
#include "ad.h"


#define LED0_ON 	GPIO_ResetBits(GPIOA,GPIO_Pin_6)      	//开灯
#define LED0_OFF 	GPIO_SetBits(GPIOA,GPIO_Pin_6)      	//关灯

u8 Usart_Data;
u8 rx_flag = 0;  		//表示串口接收标志 rx_flag = 1表示接收完成 rx_flag = 0未完成
u8 buffer[64] = {0};	//接收存储数据数组
u8 rx_buffer[64] = {0};	//接收存储数据数组
u8 rx_i,rx_count=0;



void USART1_IRQHandler(void)
{
	
	
   //若是非空,则返回值为1,与RESET(0)判断,不相等则判断为真
   if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)
   {	

		/* DR读取接受到的数据*/
		buffer[rx_count++] = USART_ReceiveData(USART1);	 //先赋值再加
		
	   if(buffer[rx_count-1] == ':')  //判断是否接收到结束标志
	   {
		    for(rx_i=0; rx_i<rx_count-1; rx_i++)
		   {
				rx_buffer[rx_i] = buffer[rx_i]; //将数据存储在rx_buffer数组中
		   }
	   
		   rx_flag 	= 1; 	//rx_flag = 1表示接收字符串完成
		   rx_count = 0;
		   
		   memset(buffer, 0, sizeof(buffer));
	   }
 
		//判断为真后,为下次中断做准备,则需要对中断的标志清零
		USART_ClearITPendingBit(USART1,USART_IT_RXNE);	   
   }	

}



//这是一个主函数
int main(void)
{
	
	u16 	ADC_value;
	float PWM_value;
	float	DZ_value;
	
	//NVIC分组 抢占优先级两位:0~3  响应优先级两位:0~3 
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
	
	Delay_Init();
	Led_Init();
	Usart1_Init();
	Adc_Init();
	Pwm_Init();
	LED0_OFF;
	//GPIO_ResetBits(GPIOA,GPIO_Pin_7);
	
	while(1)
	{
		
		ADC_value = Get_Adc_Value();
		printf("ADC_value  = %d\n",ADC_value);  //0~4000

		TIM_SetCompare1(TIM3,ADC_value);//ADC_value的数值决定灯的亮度
		
		//LED0_ON;
		delay_s(1);

	}
	
	return 0;
}

README

在这里使用了adc、pwm和串口。这里串口用的代码就是上几篇的usart.c和usart.h,没有改动。

经过实验,这样就能实现。在这里,串口直接使用printf,就会输出光度值。 

但在一些教程 ,好像需要串口通过重定向标准输出流(stdio.h库中的标准输出函数)到USART1串口。

这样,在调用printf()函数时,输出的数据就会自动发送到USART1串口上。这通常需要在编译器或者工程设置中进行配置,以确保printf()函数正确地发送数据到串口。

怎么printf重定向?有待研究。

 

  • 11
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
使用STM32控制光敏传感器控制LED的步骤如下: 1. 接线:将光敏传感器的VCC连接到STM32的5V电源引脚,将GND连接到STM32的GND引脚,将传感器的输出引脚连接到STM32的GPIO输入引脚,将LED的正极连接到STM32的GPIO输出引脚,将LED的负极连接到STM32的GND引脚。 2. 编写程序:使用STM32的开发工具,编写程序,读取光敏传感器的输出状态,如果输出为高电平,则将LED输出为低电平,;如果输出为低电平,则将LED输出为高电平,亮。 3. 调试程序:将STM32连接到计算机,下载程序到STM32中,进行调试,查看LED的亮状态是否符合预期。 下面是一个简单的示例代码,用于控制光敏传感器LED的亮: ```c #include "stm32f10x.h" // 包含STM32的头文件 int main(void) { GPIO_InitTypeDef GPIO_InitStructure; ADC_InitTypeDef ADC_InitStructure; int value; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_ADC1, ENABLE); // 使能GPIOA和ADC1的时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; // 将GPIOA的0号引脚作为输入 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN; GPIO_Init(GPIOA, &GPIO_InitStructure); ADC_InitStructure.ADC_Mode = ADC_Mode_Independent; ADC_InitStructure.ADC_ScanConvMode = DISABLE; ADC_InitStructure.ADC_ContinuousConvMode = DISABLE; ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None; ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; ADC_InitStructure.ADC_NbrOfChannel = 1; ADC_Init(ADC1, &ADC_InitStructure); ADC_Cmd(ADC1, ENABLE); while(1) { ADC_SoftwareStartConvCmd(ADC1, ENABLE); while(ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC) == RESET); value = ADC_GetConversionValue(ADC1); if(value > 1000) { GPIO_SetBits(GPIOA, GPIO_Pin_1); } else { GPIO_ResetBits(GPIOA, GPIO_Pin_1); } } } ``` 在这个示例代码中,PA0引脚连接光敏传感器,PA1引脚连接LED,通过ADC采集光敏传感器的输出电压值,如果电压值大于1000,则LED,否则LED灯亮起。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值