#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include "DHT.h"
#define DHTPIN 15
#define DHTTYPE DHT22
#define MQ2_PIN 34
#define BUZZER 25
#define LED_RED 26
#define LED_GREEN 27
DHT dht(DHTPIN, DHTTYPE);
LiquidCrystal_I2C lcd(0x27,16,2);
int gasThreshold = 2000;
float tempThreshold = 40;
// Lọc nhiễu MQ2
#define SAMPLE_SIZE 10
int gasSamples[SAMPLE_SIZE];
int sampleIndex = 0;
bool fireState = false;
bool gasAlert = false;
unsigned long previousMillis = 0;
unsigned long interval = 1000;
int readGasFiltered() {
gasSamples[sampleIndex] = analogRead(MQ2_PIN);
sampleIndex = (sampleIndex + 1) % SAMPLE_SIZE;
int sum = 0;
for(int i = 0; i < SAMPLE_SIZE; i++) {
sum += gasSamples[i];
}
return sum / SAMPLE_SIZE;
}
void setup() {
Serial.begin(115200);
pinMode(BUZZER, OUTPUT);
pinMode(LED_RED, OUTPUT);
pinMode(LED_GREEN, OUTPUT);
digitalWrite(LED_GREEN, HIGH);
dht.begin();
lcd.init();
lcd.backlight();
lcd.setCursor(0,0);
lcd.print("Fire System");
delay(2000);
lcd.clear();
// Khởi tạo mảng lọc
for(int i = 0; i < SAMPLE_SIZE; i++) {
gasSamples[i] = 0;
}
}
void loop() {
unsigned long currentMillis = millis();
if(currentMillis - previousMillis >= interval){
previousMillis = currentMillis;
int gasValue = readGasFiltered();
float temp = dht.readTemperature();
Serial.print("Gas: ");
Serial.println(gasValue);
Serial.print("Temp: ");
Serial.println(temp);
// ===== LOGIC =====
// Cảnh báo gas
if(gasValue > gasThreshold){
gasAlert = true;
} else {
gasAlert = false;
}
// Cảnh báo cháy
if(gasValue > gasThreshold && temp > tempThreshold){
fireState = true;
} else {
fireState = false;
}
// ===== HIỂN THỊ =====
lcd.clear();
lcd.setCursor(0,0);
lcd.print("T:");
lcd.print(temp);
lcd.print(" G:");
lcd.print(gasValue);
// ===== XỬ LÝ =====
if(fireState){
lcd.setCursor(0,1);
lcd.print("!!! FIRE !!!");
digitalWrite(LED_GREEN, LOW);
digitalWrite(LED_RED, HIGH);
tone(BUZZER, 1000);
}
else if(gasAlert){
lcd.setCursor(0,1);
lcd.print("Gas Warning!");
digitalWrite(LED_GREEN, LOW);
digitalWrite(LED_RED, HIGH);
noTone(BUZZER); // chỉ cảnh báo nhẹ
}
else{
lcd.setCursor(0,1);
lcd.print("System Normal");
digitalWrite(LED_GREEN, HIGH);
digitalWrite(LED_RED, LOW);
noTone(BUZZER);
}
}
// Nhấp nháy LED khi cháy (không dùng delay)
if(fireState){
static unsigned long blinkMillis = 0;
static bool ledState = false;
if(millis() - blinkMillis >= 300){
blinkMillis = millis();
ledState = !ledState;
digitalWrite(LED_RED, ledState);
}
}
}