임베디드/STM32 (ARM Cortex - M4)

[STM32] DHT11 온 습도 측정기

O_oz 2023. 10. 21. 18:10
반응형

이번엔 DHT11 온 습도 측정기를 제어해볼것이다

 

그전에 DHT11 소스파일에서 사용할 1us 타이머를 생성해야한다

tim11 역시 APB2 버스를 사용하고 해당 버스는 168MHz이기 때문에 분주기를 168로 설정하고 Count Period를 100으로 설정하면 1us의 타이머가 생성된다

+ NVIC 세팅을 enabled

설정을 저장하고 코드를 생성하자

main.c에 타이머 시작 함수와 생성된 htim11 구조체를 가지고 위와같이 1us 타이머를 생성한다

 

요게 DHT11 온 습도 측정기고
VCC, GND, DAT 이렇게 3개의 핀을 사용한다

 

먼저 DAT핀으로 사용할 핀을 활성화 해주자

나는 PA0번 핀을 사용할 것이므로

PA0핀을 GPIO_Output으로 활성화하고 라벨링해주었다

저장하면 코드가 생성된다

연결은 요로코롬 해주자

 

 

생성된 코드는 main.h에서 확인할 수 있다

 

// dht11.h

/*
 * DHT11.h
 *
 *  Created on: 2019. 9. 2.
 *      Author: kccistc
 */

#ifndef SRC_DHT11_H_
#define SRC_DHT11_H_

#define DHT11_PORT			GPIOA
#define DHT11_DATA_RIN		GPIO_PIN_0
void DHT11_Init(void);
void DHT11_trriger(void);
void DHT11_DataLine_Input(void);
void DHT11_DataLine_Output(void);
uint8_t DHT11_rx_Data(void);
void DHT11_dumi_read(void);

#endif /* SRC_DHT11_H_ */

dht11.h 파일을 생성해서 위와같이 작성해주고

 

// dht11.c

#include "main.h"
#include "DHT11.h"

#include <stdio.h>
#include <string.h>
#include <stdlib.h>


extern void delay_us (unsigned long us);
extern volatile int TDHT11_timer_counter;
extern volatile int TIM10_10ms_counter;

void DHT11_main(void);
void DHT11_Init(void);
void DHT11_processing(void);

char lcd_buff[20];

void DHT11_main(void)
{
	uint8_t i_RH, d_RH, i_Tmp, d_Tmp;


	// HAL_TIM_Base_Start_IT(&htim2);
	DHT11_Init();



	while(1)
	{
		DHT11_trriger();
		DHT11_DataLine_Input();
		DHT11_dumi_read();

		i_RH = DHT11_rx_Data();
		d_RH = DHT11_rx_Data();
		i_Tmp = DHT11_rx_Data();
		d_Tmp = DHT11_rx_Data();

		DHT11_DataLine_Output();
		HAL_GPIO_WritePin(DHT11_PORT, DHT11_DATA_RIN, GPIO_PIN_SET);
		printf("[Tmp]%d\n",(int)i_Tmp);
		printf("[Wet]%d\n",(int)i_RH);


		HAL_Delay(3000);

	}

}

int dht11time = 150;
void DHT11_processing(void)
{

	uint8_t i_RH, d_RH, i_Tmp, d_Tmp;

	if (TIM10_10ms_counter >= dht11time)
	{
		TIM10_10ms_counter = 0;
		DHT11_trriger();
		DHT11_DataLine_Input();
		DHT11_dumi_read();

		i_RH = DHT11_rx_Data();
		d_RH = DHT11_rx_Data();
		i_Tmp = DHT11_rx_Data();
		d_Tmp = DHT11_rx_Data();

		DHT11_DataLine_Output();
		HAL_GPIO_WritePin(DHT11_PORT, DHT11_DATA_RIN, GPIO_PIN_SET);
		printf("%d\n", dht11time);
		printf("[Tmp]%d\n",(int)i_Tmp);
		printf("[Wet]%d\n",(int)i_RH);

	}
}
void DHT11_Init(void)
{
	HAL_GPIO_WritePin(DHT11_PORT, DHT11_DATA_RIN, GPIO_PIN_SET);
	HAL_Delay(3000);
	return;
}


void DHT11_trriger(void)
{
	HAL_GPIO_WritePin(DHT11_PORT, DHT11_DATA_RIN, GPIO_PIN_RESET);
	HAL_Delay(20);

	HAL_GPIO_WritePin(DHT11_PORT, DHT11_DATA_RIN, GPIO_PIN_SET);
	delay_us(7);
	return;
}


void DHT11_DataLine_Input(void)
{
	GPIO_InitTypeDef GPIO_InitStruct = {0};

	/*Configure GPIO pin : PH0 */
  GPIO_InitStruct.Pin = DHT11_DATA_RIN;
  GPIO_InitStruct.Mode = GPIO_MODE_INPUT;			//Change Output to Input
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  HAL_GPIO_Init(DHT11_PORT, &GPIO_InitStruct);

	return;
}


void DHT11_DataLine_Output(void)
{
	GPIO_InitTypeDef GPIO_InitStruct = {0};

	/*Configure GPIO pin : PH0 */
  GPIO_InitStruct.Pin = DHT11_DATA_RIN;
  GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;			//Change Input to Output
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
  HAL_GPIO_Init(DHT11_PORT, &GPIO_InitStruct);

	return;
}


uint8_t DHT11_rx_Data(void)
{
	uint8_t rx_data = 0;

	for(int i = 0; i < 8; i++)
	{
		//when Input Data == 0
		while( 0 == HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN) );
#if 1
		delay_us(40);
#else  // org
		delay_us(16);
#endif
		rx_data<<=1;

		//when Input Data == 1
		if(HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN))
		{
			rx_data |= 1;
		}
		while( 1 == HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN) );
	}
	return rx_data;
}


void DHT11_dumi_read(void)
{
	while( 1 == HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN) );
	while( 0 == HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN) );
	while( 1 == HAL_GPIO_ReadPin(DHT11_PORT, DHT11_DATA_RIN) );
	return;
}

dht11.c를 생성해서 위와 같이 작성해주자

DHT11_processing() 함수를 호출하면 TIM10_10ms_counter 가 100번 (= 1초)을 넘어가면 온 습도 측정기를 작동시켜 온도와 습도를 측정하고 PC에 출력한다

main.c에 init과 processing 함수를 extern 해주고 main() 안에서 DHT11_Init()을 호출한다

while문 안에서 DHT11_processing()을 호출해서 계속 반복해주면 끝

 

 

 

손가락을 대면 온 습도가 오르고 떼면 내려가는 모습을 볼 수 있다

근데 온도는 잘 안오른다

반응형

'임베디드 > STM32 (ARM Cortex - M4)' 카테고리의 다른 글

[STM32] I2C LCD 출력  (1) 2023.10.22
[STM32] 초음파 측정기  (1) 2023.10.21
[STM32] 타이머  (1) 2023.10.21
[STM32] UART  (0) 2023.10.20
[STM32] BUTTON 제어  (1) 2023.10.19