STM32F103控制异味传感器和温湿度传感器控制模块

前言:

本次毕业设计智能衣柜使用异味传感器检测衣柜内的异味浓度值,一个温湿度检测衣柜的温度值和湿度值。

一,异味传感器

1.1异味传感器购买渠道

传感器链接

1.2异味传感器---STM32CUBEMAX配置部分

第一步:ADC采集传感器传过来的数据,要打印在串口处,所以先使能串口1。串口的触发方式为异步触发,剩下的按照默认配置就好了,波特率:115200。

第二步:使能ADC通道,这里我选择的串口通道为通道0。其余信息按照默认配置就好了,

第四步:配置时钟树。相关配置如下所示:

第五步:生成keilv5工程,注意,生成KEIL文件时,IDE选择:MDK-ARM,选择的文件目录不要用中文名字命名。

 这里选上就会生成你所需要的.c和.h文件。

 1.3异味传感器---Keil_V5部分

第一步:在usart.c文件中添加代码,串口输出printf打印。

#include "stdio.h"
int fputc(int c,FILE *stream)  
{
		HAL_UART_Transmit(&huart1,(unsigned char *)&c,1,1000);
		
		return 1;
}

第二步:打开魔术棒功能,在LIB方框中打上√

第三步,在main.c函数中printf打印输出日志信息,sscom打印串口输出:

第四步:这里建议自己在工程目录下新建文件夹保存后面功能的.c和.h文件,创建自己的adc.c文件。

第五步:在自己的user_adc.h文件中加入以下代码:

#ifndef  H_USER_ADC_H
#define  H_USER_ADC_H
#include "main.h"
extern ADC_HandleTypeDef hadc1 ;
uint16_t SMOG_IN_(void);

#endif

第六步:在自己创建的user_adc.c中加入以下代码:

#include "user_adc.h"
uint16_t SMOG_IN_(void) //ADCÊý¾Ý²É¼¯Çý¶¯º¯Êý
{
		HAL_ADC_Start(&hadc1);//开启ADC采集
		HAL_ADC_PollForConversion(&hadc1, 1000);//ADC数据采集时间
	if(HAL_IS_BIT_SET(HAL_ADC_GetState(&hadc1), HAL_ADC_STATE_REG_EOC))//读取ADC采集完成标志位
	{
			return HAL_ADC_GetValue(&hadc1);//返回ADC采集数值
	}
			return 0;
}

第七步:在main.c函数中调用user_adc.c中读取异味浓度函数。

注意:在main函数添加user_adc.h,就可以调用user_adc.c中函数

 第六步:sscom串口查看打印异味浓度值。

Attention:注意在测试异味传感器时,使用打火机放气测试,看到异味值在增大。

其实ADC转换器,主要就是采集使能ADC引脚电平的变化,然后转换成数值,存在一定的误差,可以通过异味传感器上的变阻器调节异味传感器的误差值。当然,这款异味传感器还可以通过高地电平触发。有兴趣自己尝试一下哦。

二,温湿度传感器

2.1温湿度传感器

温湿度传感器,既可以采集温度又可以采集湿度,主要就是通过单总线协议去实现的,有兴趣自己去百度一下单总线协议介绍哦。这里就不展开说了。

2.2温湿度传感器---CUBEMAX部分

第一步:设置IO输出引脚为PC5,输出方式为开漏输出,无上下拉电阻,高速输出。

注意:User Labal 那里加了DHT11的名称,建议也改成这个,后面GPIO口配置时,就可以不用改了。

第二步:配置us秒级延时函数,网上有许多的例程,这里是使用单片机定时器配置的,首先配置定时器1,时钟来源选择内部时钟,在参数配置选项哪里,Prescaler:72-1,(看上面时钟树的配置,给定时器的时钟频率为72Mhz),所以,这里选择72-1,计数值:为65535。

 点击生成keil-v5软件。

2.2温湿度传感器---KEIL-V5部分

第一步:在tim.c中加上微妙级的函数:

void delay_us(uint32_t time) 
{

	__HAL_TIM_SetCounter(&htim1,0);	
	__HAL_TIM_ENABLE(&htim1);	

	while(__HAL_TIM_GetCounter(&htim1)<time);
  __HAL_TIM_DISABLE(&htim1);	
}

第二步:新建检测温湿度的.c和.h文件,放到USER这个目录下:

第三步:在user_temple.h中加入以下函数:

#ifndef H_USER_TEMPLE_H
#define H_USER_TEMPLE_H
#include "stm32f1xx_hal.h"
#include "main.h"

void DHT11_OUT(void);   
void DHT11_IN(void);      
void DHT11_RST(void);      
uint8_t Dht11_Check(void);    
uint8_t Dht11_ReadBit(void);
uint8_t Dht11_ReadByte(void);
uint8_t DHT11_Init(void);
uint8_t DHT11_ReadData(uint8_t *h);
#endif

 第四步:在user_temple.c中加入以下函数:

#include "user_temple.h"
#include "delay_us.h"
void DHT11_OUT(void)	//ÉèÖÃÊä³öģʽ²ÎÊý
{
	GPIO_InitTypeDef GPIO_InitStruct ={0};
	GPIO_InitStruct.Pin=DHT11_Pin;	//ÉèÖÃÊä³öÒý½Å
	GPIO_InitStruct.Mode=GPIO_MODE_OUTPUT_PP;//ÉèÖÃÊä³öµÄģʽ
	GPIO_InitStruct.Pull=GPIO_NOPULL; //ÉèÖõÄÉÏÀ­·½Ê½--²»ÉÏÀ­
	GPIO_InitStruct.Speed=GPIO_SPEED_FREQ_HIGH;//ÉèÖÃÊä³öµÄƵÂÊ£¬¸ßµçƽ
	HAL_GPIO_Init(GPIOC,&GPIO_InitStruct);
}
void DHT11_IN(void) //ÉèÖÃÊäÈëģʽ
{
	GPIO_InitTypeDef GPIO_InitStruct ={0};
	GPIO_InitStruct.Pin=DHT11_Pin; //ÉèÖÃÊäÈëµÄÒý½Å
	GPIO_InitStruct.Mode=GPIO_MODE_INPUT;//ÉèÖÃÊäÈëµÄģʽ
	GPIO_InitStruct.Pull =GPIO_PULLUP;//ÉèÖÃÊäÈëÉÏÀ­Ä£Ê½¡ª¡ª¡ª¡ªÉÏÀ­ÊäÈë
	HAL_GPIO_Init(GPIOC,&GPIO_InitStruct);
}
void DHT11_RST(void) //¸´Î»º¯Êý£¬·¢³öÆðʼÐźÅ
{
	DHT11_OUT();
	HAL_GPIO_WritePin(GPIOC,DHT11_Pin,GPIO_PIN_RESET);	//Ä£Äâµ¥×ÜÏ߸øµ½µÍµçƽ
	HAL_Delay(20);
	HAL_GPIO_WritePin(GPIOC,DHT11_Pin,GPIO_PIN_SET);	//Ä£Äâµ¥×ÜÏßЭÒé¸øµ½¸ßµçƽ
	delay_us(30);
}
uint8_t DHT11_Init(void)	//Ä£¿é³õʼ»¯
{
		DHT11_RST();	//¸´Î»£¬Ö÷»ú·¢³öÆðÖ¹ÐźÅ
		return Dht11_Check();	//µÈ´ý»ØÓ¦
}
uint8_t DHT11_ReadData(uint8_t *h)	//¶ÁÈ¡Ò»´ÎÊý¾Ý£¬ÎÂʪ
{
	
	uint8_t buf[5];
	DHT11_RST();	//µ÷Óø´Î»º¯Êý	uint8_t i;
	uint8_t i;
	if(Dht11_Check()==0)	
	{
		for(i=0;i<5;i++)	
		{
			buf[i]=Dht11_ReadByte();		//¶ÁÈ¡ÎåλÊý×Ö´æ·ÅÔÚÊý×éÖÐ
		}
	if((buf[0]+buf[1]+buf[2]+buf[3])==buf[4])	//Êý¾ÝУÑé
		{
			
		*h=buf[0];	//½«Êª¶ÈÖµ´æ·ÅÔÚÖ¸Õë1
			h++;
		*h=buf[2];	//½«Î¶ȴæ·ÅÔÚÖ¸Õë2ÖÐs
		
		}
	}
	else 
	return 1;
	
	return 0;
}
uint8_t Dht11_ReadBit(void)	//¶Á³öÒ»¸öÊý¾Ýλ £¬·µ»ØֵΪ0»òÕß1
{

uint8_t retry=0;
while(HAL_GPIO_ReadPin(GPIOC,DHT11_Pin)&&retry<100)	//µÈ´ý±ä³ÉµÍµçƽ
{
	retry++;
	delay_us(1);
}
	retry=0;
while(!HAL_GPIO_ReadPin(GPIOC, DHT11_Pin )&&retry<100)//µÈ´ý±ä³É¸ßµçƽ
	{
	retry++;
	delay_us(1);
	}
delay_us(40);//µÈ´ý40us //ÓÃÓÚÅжϸߵÍÍÍƽ£¬ ¼´Êý¾Ý1»ò0
if(HAL_GPIO_ReadPin(GPIOC,DHT11_Pin))
	return 1;
else return 0;
}
uint8_t Dht11_ReadByte(void)	//¶ÁÈ¡Ò»¸ö×Ö½Ú£¬ ͨ¹ý·µ»ØÖµµÃµ½Êý¾ÝÖµ
{
	uint8_t i,dat;
	dat=0;
	for(i=0;i<8;i++)
	{
		dat<<=1;
		dat|=Dht11_ReadBit();//Ñ­»·¶ÁÈ¡8´Î¶ÁÈ¡Ò»×éÊý¾Ý
		}
	
	return dat;
}
uint8_t Dht11_Check(void)
{

	uint8_t retry=0;
		DHT11_IN();	//½«Ä£Ê½ÉèÖÃΪÊäÈëģʽ
while((HAL_GPIO_ReadPin(GPIOC,DHT11_Pin))&&retry<100)	//À­µÍµçƽ
{
	retry++;
	delay_us(1);
}
if(retry>=100)
{
	return 1;
}	//0±íʾÉèÖóɹ¦£¬1±íʾÉèÖÃʧ°Ü
else
	retry=0;

while(!HAL_GPIO_ReadPin(GPIOC, DHT11_Pin)&&retry<100) 	//À­¸ßµçƽ
{
		retry++;
		delay_us(1);
}
	if(retry>=100)
	{
		return 1;
	}
	else 
	return 0;
}



第五步,在main函数中初始化函数,并打印输出温湿度值,注意:DHT11_ReadData(DHT11_BUF);这个函数的形参需要自己定义,是一个uint8_t 类型长度为2的一维数组。

第六步:在sscom串口打印观察是否有数据:

 三,总结

温湿度传感器对时序要求很严格,复制代码不成功,试一下改变一下IO口,在stm32cubemax中我用的是PA口,自己测试时,定义其他IO口,在DHT11初始化那儿记得改一下io口,多检查一下IO口是否对得上。本文到此结束,如有什么错误,欢迎评论区指正。

  • 2
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值