#include #include #include #include #include // === KREDENSIAL === #define WIFI_SSID "nanaaaaa" #define WIFI_PASSWORD "nanaaaaa" #define API_KEY "AIzaSyBB40eRLlP7kp52g2Hvmx3PkrkzYjuFnpo" #define DATABASE_URL "https://smartfarming-7bd96-default-rtdb.firebaseio.com/" #define LEGACY_TOKEN "ShlkXYkTpTh2o4b38tqZozBv2oLXyUSnZUUXUCslu" // === PIN === #define DHTPIN 14 #define DHTTYPE DHT11 #define RELAY_KIPAS 26 #define RELAY_POMPA 27 // === OBJEK === FirebaseData fbdo; FirebaseAuth auth; FirebaseConfig config; DHT dht(DHTPIN, DHTTYPE); LiquidCrystal_I2C lcd(0x27, 16, 2); // Alamat I2C umum // === VARIABEL === unsigned long lastUpdate = 0; unsigned long interval = 5000; float thresholdSuhu = 29.0; float thresholdKelembaban = 50.0; bool isManual = true; void setup() { Serial.begin(115200); dht.begin(); pinMode(RELAY_KIPAS, OUTPUT); pinMode(RELAY_POMPA, OUTPUT); digitalWrite(RELAY_KIPAS, HIGH); // Active LOW digitalWrite(RELAY_POMPA, HIGH); Wire.begin(21, 22); // LCD I2C pin SDA = 21, SCL = 22 lcd.init(); lcd.backlight(); lcd.setCursor(0, 0); lcd.print("Menghubungkan..."); WiFi.begin(WIFI_SSID, WIFI_PASSWORD); while (WiFi.status() != WL_CONNECTED) { delay(500); Serial.print("."); } lcd.clear(); lcd.setCursor(0, 0); lcd.print("WiFi Terhubung"); delay(1000); config.api_key = API_KEY; config.database_url = DATABASE_URL; config.signer.tokens.legacy_token = LEGACY_TOKEN; Firebase.begin(&config, &auth); Firebase.reconnectWiFi(true); lcd.clear(); } void loop() { if (millis() - lastUpdate >= interval && Firebase.ready()) { lastUpdate = millis(); float suhu = dht.readTemperature(); float kelembaban = dht.readHumidity(); // Ambil nilai kontrol manual dari Firebase if (Firebase.RTDB.getBool(&fbdo, "/control/manual")) { isManual = fbdo.boolData(); Serial.println(isManual ? "Mode: MANUAL" : "Mode: OTOMATIS"); } else { Serial.println("Gagal ambil mode manual, pakai default (MANUAL)"); } // Ambil threshold suhu & kelembaban if (!isManual) { if (Firebase.RTDB.getFloat(&fbdo, "/treshold/suhu")) { thresholdSuhu = fbdo.floatData(); } if (Firebase.RTDB.getFloat(&fbdo, "/treshold/kelembaban")) { thresholdKelembaban = fbdo.floatData(); } } Serial.printf("Suhu: %.2f °C, Kelembaban: %.2f %%\n", suhu, kelembaban); // Tampilkan ke LCD lcd.setCursor(0, 0); lcd.print("Suhu: "); lcd.print(suhu, 1); lcd.print((char)223); lcd.print("C "); lcd.setCursor(0, 1); lcd.print("Lembab: "); lcd.print(kelembaban, 1); lcd.print("% "); // Kirim sensor ke Firebase Firebase.RTDB.setFloat(&fbdo, "/dht11/suhu", suhu); Firebase.RTDB.setFloat(&fbdo, "/dht11/humidity", kelembaban); // === MODE MANUAL === if (isManual) { // Ambil status kipas & pompa dari Firebase if (Firebase.RTDB.getBool(&fbdo, "/status/kipas")) { bool kipas_status = fbdo.boolData(); digitalWrite(RELAY_KIPAS, kipas_status ? LOW : HIGH); Serial.println("Kipas: " + String(kipas_status ? "ON (manual)" : "OFF")); } if (Firebase.RTDB.getBool(&fbdo, "/status/pompa")) { bool pompa_status = fbdo.boolData(); digitalWrite(RELAY_POMPA, pompa_status ? LOW : HIGH); Serial.println("Pompa: " + String(pompa_status ? "ON (manual)" : "OFF")); } } // === MODE OTOMATIS === else { // Pompa otomatis if (kelembaban <= thresholdKelembaban) { digitalWrite(RELAY_POMPA, LOW); Firebase.RTDB.setBool(&fbdo, "/status/pompa", true); Serial.println("Pompa ON (otomatis)"); } else { digitalWrite(RELAY_POMPA, HIGH); Firebase.RTDB.setBool(&fbdo, "/status/pompa", false); Serial.println("Pompa OFF (otomatis)"); } // Kipas otomatis if (suhu >= thresholdSuhu) { digitalWrite(RELAY_KIPAS, LOW); Firebase.RTDB.setBool(&fbdo, "/status/kipas", true); Serial.println("Kipas ON (otomatis)"); } else { digitalWrite(RELAY_KIPAS, HIGH); Firebase.RTDB.setBool(&fbdo, "/status/kipas", false); Serial.println("Kipas OFF (otomatis)"); } } } }