| Risqi Prasdika | (24051204008) |
| Rahmat Ari Setyarto | (24051204010) |
| Carmelio Sivandra A. | (24051204116) |
| Rifqi Syawal | (24051204198) |
| Azzam Ghifari | (24051204178) |
Suhu dan kelembapan menentukan kenyamanan penghuni ruangan, kualitas hasil budidaya, umur peralatan elektronik, dan mutu barang gudang. Panas berlebih menurunkan kinerja prosesor dan mempercepat kerusakan komponen di ruang server. Kelembapan tinggi memicu korosi dan jamur; kelembapan rendah meningkatkan risiko pelepasan muatan statis. Rumah kaca, kandang ternak, dan ruang penyimpanan makanan pun menuntut suhu stabil dalam rentang tertentu.
Termometer dan higrometer konvensional mengandalkan petugas yang membaca alat pada jam tertentu, dan cara ini menyimpan empat celah: data terputus di antara dua pembacaan, pemantauan bergantung pada kehadiran petugas, tidak ada peringatan saat nilai melewati batas aman, dan kipas atau ventilasi baru menyala setelah petugas menyalakannya secara manual sehingga pendinginan terlambat jika suhu naik di luar jam pemeriksaan.
Internet of Things (IoT) menutup celah ini dengan menghubungkan sensor, mikrokontroler, dan jaringan komputer: sensor membaca kondisi lingkungan, mikrokontroler mengolah dan mengirim data, dan pengguna memantau hasilnya lewat peramban atau ponsel. ESP32 buatan Espressif Systems cocok untuk peran ini. Chip ini membawa dua inti prosesor, modul Wi-Fi dan Bluetooth terintegrasi, ADC, keluaran PWM, dan dukungan pustaka luas di Arduino IDE maupun PlatformIO. Harganya terjangkau, sehingga satu perangkat merangkap node sensor sekaligus pengendali aktuator.
Banyak pengembang menjalankan web server langsung di ESP32: pengguna membuka alamat IP perangkat dari jaringan lokal untuk membaca suhu dan kelembapan, lalu mengubah mode kipas. Pendekatan ini sederhana tetapi terbatas. Jangkauannya hanya mencapai jaringan lokal. Setiap klien yang membuka koneksi TCP menggerus SRAM 520 KB yang tersedia. Halaman web harus melakukan polling berulang untuk data terbaru, dan ESP32 sendiri tidak bisa mendistribusikan data ke banyak penerima sekaligus tanpa perantara.
MQTT (Message Queuing Telemetry Transport) mengatasi keterbatasan ini lewat model publish/subscribe dengan broker sebagai perantara. ESP32 memublikasikan data ke sebuah topic, dan setiap pelanggan topik itu dashboard, aplikasi ponsel, atau Node-RED menerima data tanpa perlu mengetahui alamat ESP32. Header MQTT yang hanya 2 byte membuat protokol ini hemat bandwidth dan memori, sementara fitur Quality of Service (QoS), retained message, dan Last Will and Testament (LWT) menjaga keandalan pada jaringan Wi-Fi yang tidak stabil.
Pengendalian kipas otomatis melengkapi sistem ini. ESP32 membandingkan suhu terukur dengan ambang batas, lalu menggerakkan relay atau MOSFET untuk menyalakan kipas. Histeresis mencegah kipas hidup-mati berulang di sekitar nilai ambang, dan pengguna tetap bisa mengambil alih kipas lewat perintah manual dari MQTT atau halaman web.
Berdasarkan uraian ini, penelitian mengimplementasikan ESP32 sebagai node pemantau lingkungan dengan web server lokal, memublikasikan data sensor ke broker MQTT, dan mengendalikan kipas dalam mode otomatis maupun manual. Penelitian menguji akurasi sensor, latensi pengiriman data, dan ketepatan respons kipas terhadap perubahan suhu.
Bagaimana merancang perangkat keras berbasis ESP32 yang membaca sensor suhu dan kelembapan serta menggerakkan kipas melalui relay atau driver transistor ?
Bagaimana mengimplementasikan web server pada ESP32 untuk menampilkan data suhu dan kelembapan serta mengubah mode kontrol kipas ?
Bagaimana mengimplementasikan protokol MQTT pada ESP32, meliputi struktur topic, format payload, dan pemilihan QoS, untuk mengirim data sensor dan menerima perintah kontrol ?
Bagaimana menerapkan logika kontrol kipas otomatis berbasis ambang suhu dengan histeresis, dan bagaimana logika itu berpindah antara mode otomatis dan manual ?
Bagaimana unjuk kerja sistem, diukur dari akurasi sensor, latensi pengiriman data, tingkat kehilangan paket, dan waktu respons kipas ?
Laporan ini bertujuan menjelaskan rancangan sistem monitoring suhu dan kelembapan berbasis ESP32-C3 dengan sensor DHT22 melalui simulasi Wokwi. Pembahasan mencakup hubungan antarkomponen, persiapan perangkat lunak, dan alur program yang membaca sensor secara berkala, menampilkan data pada LCD 16×2, serta menyimpan hasil pembacaan ke kartu microSD. Laporan ini juga menjelaskan penggunaan Serial Monitor untuk memeriksa status sistem, membaca sensor, dan mengelola catatan pengukuran.
Rancangan tersebut menjadi dasar pengembangan sistem IoT yang dibahas pada bagian pendahuluan, yaitu pemantauan melalui web server, pertukaran data menggunakan MQTT, dan pengendalian kipas otomatis maupun manual. Program yang dicantumkan dalam laporan masih berfokus pada pemantauan dan pencatatan lokal, sehingga evaluasi komunikasi jaringan dan respons kipas memerlukan implementasi serta pengujian lanjutan.
Penulisan laporan ini membantu mahasiswa memahami hubungan antara sensor, mikrokontroler, perangkat tampilan, dan media penyimpanan dalam sistem monitoring lingkungan. Melalui rancangan yang disajikan, mahasiswa dapat mempelajari pembacaan DHT22, komunikasi I2C untuk LCD, komunikasi SPI untuk kartu microSD, serta penjadwalan pembacaan sensor dan perubahan keadaan LED menggunakan fungsi millis().
Laporan ini juga menyediakan acuan untuk menyiapkan simulasi, menelusuri alur program, dan memeriksa fungsi sistem melalui Serial Monitor. Pencatatan suhu dan kelembapan ke dalam berkas memberi dasar untuk pengolahan data pada tahap berikutnya. Rancangan ini dapat dikembangkan lebih lanjut dengan koneksi jaringan dan aktuator, kemudian diuji pada perangkat fisik untuk menilai kesesuaiannya dengan kebutuhan pemantauan lingkungan.
IoT menghubungkan perangkat bersensor ke jaringan agar perangkat bertukar data tanpa perantara manusia. Perangkat berkomunikasi dengan dua cara: pada polling, penerima meminta data berulang kali; pada push, pengirim mengirim data begitu data siap. Soni dan Makwana menilai protokol push lebih cocok untuk perangkat IoT karena ringan dan produktif [1]. Pemantauan lingkungan mencakup suhu (tingkat panas udara dalam derajat Celsius) dan kelembapan relatif (perbandingan tekanan uap air aktual terhadap tekanan uap air jenuh pada suhu yang sama, dalam persen). Macheso dkk. menyebut bahwa menjaga proses pada rentang suhu dan kelembapan tertentu memerlukan web server berbiaya dan berdaya rendah yang memantau kedua besaran itu dalam waktu nyata [2].
ESP32 memenuhi kebutuhan ini. Maier dkk. mendefinisikannya sebagai system on chip berbiaya dan berdaya rendah dengan Wi-Fi dan Bluetooth terintegrasi, memakai prosesor dual-core Tensilica Xtensa LX6 [3]. Modulnya memuat antena, osilator, dan memori flash, sehingga pengembang tidak perlu merangkai komponen itu sendiri [3]. Macheso dkk. memakai papan NodeMCU-32S dan memrogramnya lewat Arduino IDE untuk membangun web server pemantau suhu [2]. Pin GPIO ESP32 berlogika 3,3 V dan tidak mampu mengalirkan arus sebesar kebutuhan kipas, sehingga kipas memerlukan relay atau transistor sebagai penggerak.
DHT22 mengukur suhu dan kelembapan lalu mengirim datanya lewat satu kabel data. Sensor ini memerlukan jeda minimal dua detik antara dua pembacaan, sehingga program membacanya pada interval yang lebih besar. Macheso dkk. menghubungkan DHT22 ke ESP32 untuk memantau suhu dan kelembapan dalam waktu nyata [2], dan Roihan dkk. memakai pasangan yang sama sebagai sumber data untuk kipas otomatis [4]. Sensor berbiaya rendah menyimpang dari alat ukur acuan, sehingga penelitian ini membandingkan DHT22 dengan termohigrometer referensi dan menghitung galatnya.
Roihan dkk. mengendalikan kipas DC 12 V dengan modul relay dari ESP32 [4]. Relay bekerja sebagai saklar elektromekanis yang memisahkan sisi kontrol berdaya kecil dari sisi beban berdaya besar: ESP32 mengirim sinyal HIGH atau LOW ke pin masukan relay, dan relay menutup atau membuka rangkaian kipas. Banyak modul relay berjenis active-low, sehingga relay aktif saat pin berlogika LOW.
HTTP memakai pola permintaan dan balasan, sehingga halaman yang menampilkan data terbaru harus mengirim permintaan berulang. Macheso dkk. merancang web server asinkron berbiaya rendah pada ESP32 dengan DHT22 [2]; server asinkron menerima permintaan tanpa memblokir program utama, sehingga ESP32 tetap membaca sensor selagi melayani klien. Rancangan semacam ini memakai tiga alamat: satu menyajikan halaman dashboard, satu mengembalikan data sensor dalam format JSON, dan satu mengubah mode dan status kipas. Jangkauan server terbatas pada jaringan lokal, dan memori ESP32 membatasi jumlah klien. Pendekatan push milik MQTT mengatasi kedua keterbatasan ini [1].
Soni dan Makwana menyebut MQTT sebagai protokol push paling banyak dipakai dibanding XMPP dan AMQP, dengan ciri ringan dan hemat bandwidth [1]. MQTT memiliki tiga komponen: publisher mengirim pesan ke sebuah topic, subscriber berlangganan topic untuk menerima pesan tertentu, dan broker menerima semua pesan dari publisher, menyaringnya, lalu meneruskannya ke subscriber yang berminat [1]. Broker sebagai perantara membuat publisher dan subscriber tidak perlu tahu alamat satu sama lain. Topic berupa string berjenjang dengan garis miring sebagai pemisah tingkat, misalnya ruang1/sensor/suhu; tanda + menggantikan satu tingkat, dan tanda # menggantikan semua tingkat di bawahnya. MQTT menyediakan tiga level Quality of Service: level 0 mengirim paling banyak satu kali tanpa konfirmasi, level 1 mengirim minimal satu kali dengan konfirmasi, dan level 2 mengirim tepat satu kali lewat empat langkah jabat tangan. Retained message membuat broker menyimpan pesan terakhir sebuah topic untuk subscriber baru, sedangkan Last Will and Testament membuat broker mempublikasikan pesan titipan saat klien terputus tanpa pamit. Soni dan Makwana mencatat bahwa setiap broker memiliki keterbatasan dan belum ada yang menerapkan prioritas data [1]. Karena itu, penelitian ini memilih broker dan level QoS sesuai kebutuhan sistem. Roihan dkk. mengirim data lewat broker shiftr.io setiap 10 detik dan tidak kehilangan paket selama pengujian [4]. Penelitian ini memakai QoS 0 untuk data sensor, karena data berikutnya menggantikan data yang hilang, dan QoS 1 untuk perintah kipas, karena perintah tidak boleh hilang.
Roihan dkk. membangun prototipe kipas otomatis berdasarkan suhu ruangan dengan ESP32 sebagai pengendali utama, dan mencatat waktu respons kontrol sekitar 760 ms [4]. Mereka menyebut penelitian sebelumnya umumnya mengandalkan kontrol lokal, sedangkan sistem mereka menambah pemantauan web lewat MQTT [4]. Kontrol on-off dengan satu ambang menyalakan dan mematikan kipas berulang kali saat suhu bergerak di sekitar ambang tersebut. Gejala ini disebut chattering dan memperpendek umur relay. Histeresis memakai dua ambang, T_on dan T_off, dengan T_on lebih besar daripada T_off: kipas menyala saat suhu mencapai atau melewati T_on, mati saat suhu turun ke T_off atau lebih rendah, dan mempertahankan keadaan sebelumnya di antara keduanya. Sistem memiliki dua mode. Pada mode otomatis, ESP32 menjalankan aturan histeresis ini. Pada mode manual, ESP32 mengikuti perintah pengguna dari halaman web atau MQTT.
Roihan dkk. menilai sistem lewat waktu respons kontrol dan kehilangan paket [4]. Penelitian ini memakai empat parameter sejenis. Penelitian ini mengukur galat sensor dengan RMSE, akar dari rata-rata kuadrat selisih antara pembacaan DHT22 dan alat ukur referensi. Latensi adalah waktu terima dikurangi waktu kirim. Tingkat kehilangan paket adalah jumlah pesan terkirim dikurangi jumlah pesan terterima, dibagi jumlah pesan terkirim, lalu dikali 100%. Waktu respons kipas adalah selang dari suhu melewati ambang sampai kipas menyala.
Berikut adalah daftar perangkat keras dan perangkat lunak yang digunakan dalam simulasi dan implementasi Proyek Minggu Ke-3:
| No | Komponen / Software |
|---|---|
| 1 | 1 half breadboard |
| 2 | 1 ESP32-C3-MINI-1 |
| 3 | 1 dht22 |
| 4 | 1 LED Merah |
| 5 | 1 Resistor 220 ohm |
| 6 | 1 Resistor 10k ohm |
| 7 | 1 microSd card |
| 8 | 1 lcd 16x2 (l2c) |
Langkah 1: Download
Buka: https://arduino.github.io/arduino-cli/latest/installation/
Pilih Windows → Windows 64-bit
Download file: arduino-cli_latest_Windows_64bit.zip
Langkah 2: Ekstrak
Buat folder: C:\arduino-cli\
Ekstrak isi ZIP ke folder tersebut
Pastikan ada file: C:\arduino-cli\arduino-cli.exe
Langkah 3: Tambahkan ke PATH
Tekan Win + R → ketik sysdm.cpl → Enter
Tab Advanced → klik Environment Variables
Di bagian User variables → pilih Path → klik Edit
Klik New → tambahkan: C:\arduino-cli\
OK → OK → OK
Tutup dan buka ulang VS Code
Langkah 4: Verifikasi
Buka Terminal di VS Code (Ctrl + ~), jalankan:
powershell
arduino-cli version
Harus muncul: arduino-cli Version: 1.x.x ...
powershell
arduino-cli core update-index arduino-cli config init arduino-cli config add board_manager.additional_urls https://espressif.github.io/arduino-esp32/package_esp32_index.json arduino-cli core update-index
arduino-cli core install esp32:esp32
⏱️ Proses ini butuh 5-10 menit (~500MB download). Sabar ya!
Verifikasi:
arduino-cli core list
Harus muncul:
| ID | Installed Latest Name |
|---|---|
esp32:esp32 3.3.12 | 3.3.12 esp32 |
powershell
arduino-cli lib install "DHT sensor library" arduino-cli lib install "LiquidCrystal I2C"
⚠️ JANGAN install library SD via CLI! Library SD untuk ESP32 sudah built-in di core esp32:esp32. Kalau sudah terlanjur install, hapus:
powershell
arduino-cli lib uninstall SD
Verifikasi:
powershell
arduino-cli lib list
Harus muncul:
| Name | Installed |
|---|---|
| DHT sensor library | 1.4.6 |
| LiquidCrystal I2C | 1.1.4 |
Buka VS Code
Tekan Ctrl + Shift + X (buka panel Extensions)
Cari: Wokwi Simulator
Pilih yang Publisher: Wokwi (ikon biru)
Klik Install
Restart VS Code saat diminta
Tekan Ctrl + Shift + P → ketik Wokwi: Request a License
Akan muncul notifikasi dengan instruksi
Buka browser → https://wokwi.com/arduino/install
Login dengan akun Wokwi (Google/GitHub/email)
Copy license token yang muncul (format: wokwi-xxxx-xxxx-xxxx)
Kembali ke VS Code → Ctrl + Shift + P → Wokwi: Activate License
Paste token → Enter
✅ Jika berhasil: pojok kanan bawah muncul "Wokwi license activated"
ESP32-SensorMonitor/ │ ├── .vscode/ │ └── settings.json ← Konfigurasi includePath │ ├── build/ ← Auto-generate saat compile │ └── esp32.esp32.esp32c3/ │ ├── ESP32-SensorMonitor.ino.bin │ ├── ESP32-SensorMonitor.ino.elf │ └── ESP32-SensorMonitor.ino.map │ ├── ESP32-SensorMonitor.ino ← Kode utama ESP32 ├── diagram.json ← Konfigurasi komponen & wiring ├── libraries.txt ← Daftar library (untuk Wokwi) ├── wokwi.toml ← Konfigurasi build └── compile.ps1 ← (Opsional) Script compile
Copy seluruh kode dari file ESP32-SensorMonitor.ino yang sudah saya lampirkan ke file ini.
⚠️ PENTING: Pastikan nama file sesuai dengan yang ada di wokwi.toml:
File: ESP32-SensorMonitor.ino
wokwi.toml: ESP32-SensorMonitor.ino.bin ✅
Copy seluruh isi dari file diagram.json yang sudah saya lampirkan.
Copy seluruh isi dari file wokwi.tomlyang sudah saya lampirkan.
Copy seluruh isi dari file libraries.txt yang sudah saya lampirkan.
💡 Catatan: File ini hanya dibaca oleh Wokwi web untuk tahu library apa yang harus di-load. Di VS Code + Arduino CLI, library harus di-install via arduino-cli lib install (sudah dilakukan di langkah 3).
Buat folder .vscode/ di root project, lalu buat file settings.json:
Copy seluruh isi dari file .vscode/settings.json yang sudah saya lampirkan.
📌 Sesuaikan path dengan lokasi install Arduino CLI di komputermu. Cek dengan:
powershell
arduino-cli config dump
Cari baris data.dir dan user.dir.
powershell
# compile.ps1 — Script compile otomatis
Write-Host "🔧 Compiling ESP32-C3..." -ForegroundColor Cyan
Write-Host ""
arduino-cli compile `
--fqbn esp32:esp32:esp32c3 `
--output-dir build/esp32.esp32.esp32c3 `
--warnings none `
.
if ($LASTEXITCODE -eq 0) {
Write-Host ""
Write-Host "✅ Compile sukses!" -ForegroundColor Green
Write-Host "📁 Output:" -ForegroundColor Yellow
Get-ChildItem build\esp32.esp32.esp32c3\ | Format-Table Name, Length
Write-Host ""
Write-Host "▶️ Langkah selanjutnya:" -ForegroundColor Cyan
Write-Host " Ctrl + Shift + P → 'Wokwi: Start Simulator'" -ForegroundColor White
} else {
Write-Host ""
Write-Host "❌ Compile gagal! Cek error di atas." -ForegroundColor Red
}Buka Terminal di VS Code (Ctrl + ~), lalu jalankan:
powershell
arduino-cli compile --fqbn esp32:esp32:esp32c3 --output-dir build/esp32.esp32.esp32c3 .
⏱️ Compile pertama kali: 2-5 menit (download toolchain)
⚡ Compile berikutnya: 10-30 detik (cached)
powershell
.\compile.ps1
💡 Kalau muncul error running scripts is disabled, buka PowerShell as Administrator dan jalankan:
powershell
Set-ExecutionPolicy -Scope CurrentUser RemoteSigned
Setelah compile sukses, cek folder build/esp32.esp32.esp32c3/:
powershell
dir build\esp32.esp32.esp32c3\
Harus muncul:
Name Length ---- ------ ESP32-SensorMonitor.ino.bin ~900KB ← Firmware ESP32-SensorMonitor.ino.elf ~15MB ← Debug symbols ESP32-SensorMonitor.ino.map ~5MB ← Memory map
⚠️ PENTING: Nama file .bin dan .elf HARUS sesuai dengan yang ada di wokwi.toml. Kalau nama berbeda, rename file .ino kamu atau edit wokwi.toml.
Tekan Ctrl + Shift + P (Command Palette)
Ketik: Wokwi: Start Simulator
Pilih dari daftar
Atau via Wokwi Sidebar:
Klik ikon Wokwi di Activity Bar kiri
Klik ▶️ Start Simulation
Panel Wokwi Simulator akan terbuka dengan:
🔴 LED merah berkedip (heartbeat)
📺 LCD menampilkan "Booting..." lalu "Suhu: XX.X C"
🌡️ DHT22 sensor
💾 SD Card adapter
🧩 Breadboard dengan wiring
Untuk melihat log:
Klik ikon Serial Monitor di toolbar bawah Wokwi, atau
Ctrl + Shift + P → Wokwi: Show Serial Monitor
Output yang diharapkan:
========================================= ESP32-C3 Sensor Monitor (Data Logger) ========================================= [LCD] OK (SDA=8, SCL=9) [DHT] OK (pin=4) [SD] Init SPI... [SD] Mounted OK [SD] Total: 7 MB ========================================= Ketik 'help' di Serial Monitor ========================================= [DHT] Suhu: 24.0 C | Hum: 40.0 % [SD] Logged → datalog.txt [DHT] Suhu: 24.1 C | Hum: 40.2 % [SD] Logged → datalog.txt
Semua fitur bisa dites via Serial Monitor. Klik kolom input di bawah Serial Monitor, ketik perintah, tekan Enter.
| Perintah | Fungsi |
|---|---|
| help | Tampilkan menu bantuan |
| status | Status sistem (SD, sensor) |
| data | Baca sensor sekarang |
| log | Tampilkan isi datalog.txt |
| sdinfo | Info SD Card + daftar file |
| clear | Hapus datalog.txt |
ketik status di terminal saat running simulasi seperti ini :
Output:
=== STATUS SISTEM === SD Ready : YES Suhu : 24.0 C Hum : 40.0 % Uptime : 65986 ms =====================
ketik data di terminal
Output:
[DHT] Suhu: 24.1 C | Hum: 40.2 %
ketik log terminal
Output:
=== ISI datalog.txt === Suhu: 24.0 C, Kelembapan: 40.0 % Suhu: 24.1 C, Kelembapan: 40.2 % Suhu: 24.0 C, Kelembapan: 40.1 % =======================
sdinfo
Output:
=== SD CARD INFO ===
Total : 7 MB
Used : 0 MB
Files :
/datalog.txt (150 bytes)
====================clear
Output:
[SD] datalog.txt dihapus
| Fitur | Cara Verifikasi | Status |
|---|---|---|
| LCD | Lihat panel Wokwi LCD menampilkan suhu | ✅/❌ |
| DHT22 | Serial Monitor log [DHT] Suhu: ... | ✅/❌ |
| SD Card | Serial Monitor log [SD] Logged + perintah sdinfo | ✅/❌ |
| LED | LED merah berkedip tiap 1 detik | ✅/❌ |
Berikut adalah seluruh kode sumber (source code) resmi yang digunakan dalam praktikum minggu ketiga:
{
"version": 1,
"author": "Risqi Prasdika",
"editor": "wokwi",
"parts": [
{ "type": "wokwi-breadboard-half", "id": "bb1", "top": 189, "left": -160.4, "attrs": {} },
{ "type": "board-esp32-c3-devkitm-1", "id": "esp", "top": 239.7, "left": 178.62, "attrs": {} },
{ "type": "wokwi-dht22", "id": "dht1", "top": 38.7, "left": 196.2, "attrs": {} },
{
"type": "wokwi-resistor",
"id": "r1",
"top": 167.15,
"left": -172.8,
"attrs": { "value": "10000" }
},
{
"type": "wokwi-lcd1602",
"id": "lcd1",
"top": 25.6,
"left": -119.2,
"attrs": { "pins": "i2c" }
},
{ "type": "wokwi-microsd-card", "id": "sd1", "top": 163.43, "left": 182.47, "attrs": {} },
{ "type": "wokwi-led", "id": "led1", "top": 102, "left": -159.4, "attrs": { "color": "red" } },
{
"type": "wokwi-resistor",
"id": "r2",
"top": 167.15,
"left": -96,
"attrs": { "value": "220" }
}
],
"connections": [
[ "esp:TX", "$serialMonitor:RX", "", [] ],
[ "esp:RX", "$serialMonitor:TX", "", [] ],
[ "esp:3V3.1", "bb1:tp.25", "green", [ "h0" ] ],
[ "esp:GND.1", "bb1:tn.25", "black", [ "h0" ] ],
[ "esp:5V.1", "lcd1:VCC", "red", [ "h0" ] ],
[ "lcd1:GND", "bb1:tn.24", "black", [ "h0" ] ],
[ "lcd1:SDA", "esp:8", "green", [ "h0" ] ],
[ "lcd1:SCL", "esp:9", "green", [ "h0" ] ],
[ "dht1:VCC", "bb1:tp.23", "red", [ "v0" ] ],
[ "dht1:GND", "bb1:tn.23", "black", [ "v0" ] ],
[ "dht1:SDA", "esp:4", "green", [ "v0" ] ],
[ "r1:1", "bb1:tp.22", "green", [ "v0" ] ],
[ "r1:2", "esp:4", "green", [ "v0" ] ],
[ "sd1:VCC", "bb1:tp.21", "red", [ "h0" ] ],
[ "sd1:GND", "bb1:tn.21", "black", [ "h0" ] ],
[ "sd1:CS", "esp:5", "green", [ "h0" ] ],
[ "sd1:SCK", "esp:6", "green", [ "h0" ] ],
[ "sd1:DI", "esp:7", "green", [ "h0" ] ],
[ "sd1:DO", "esp:2", "green", [ "h0" ] ],
[ "led1:A", "r2:2", "green", [ "v0" ] ],
[ "led1:C", "bb1:tn.22", "green", [ "v0" ] ],
[ "r2:1", "esp:1", "green", [ "v0" ] ]
],
"dependencies": {}
}#include <SD.h>
#include <SPI.h>
#include <DHT.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
// ===================== PIN =====================
#define DHT_PIN 4
#define DHT_TYPE DHT22
#define LED_PIN 1
#define SD_CS_PIN 5
#define SD_SCK_PIN 6
#define SD_MISO_PIN 2
#define SD_MOSI_PIN 7
#define LCD_SDA_PIN 8
#define LCD_SCL_PIN 9
#define LCD_ADDR 0x27
// ===================== OBJEK =====================
DHT dht(DHT_PIN, DHT_TYPE);
LiquidCrystal_I2C lcd(LCD_ADDR, 16, 2);
SPIClass sdSPI(FSPI);
// ===================== STATE =====================
unsigned long lastRead = 0;
unsigned long lastBlink = 0;
const unsigned long READ_INTERVAL = 2000;
const unsigned long BLINK_INTERVAL = 1000;
float lastTemp = 0.0;
float lastHum = 0.0;
bool ledState = false;
bool sdReady = false;
// =====================================================================
// FUNGSI BANTU
// =====================================================================
void logToSD(float t, float h) {
if (!sdReady) return;
File f = SD.open("/datalog.txt", FILE_APPEND);
if (f) {
f.printf("Suhu: %.1f C, Kelembapan: %.1f %%\n", t, h);
f.close();
Serial.println("[SD] Logged → datalog.txt");
} else {
Serial.println("[SD] GAGAL buka datalog.txt");
}
}
void updateLCD(float t, float h) {
lcd.clear();
lcd.setCursor(0, 0);
lcd.printf("Suhu: %.1f C", t);
lcd.setCursor(0, 1);
lcd.printf("Hum: %.1f %%", h);
}
void lcdInfo(const char* l1, const char* l2) {
lcd.clear();
lcd.setCursor(0, 0); lcd.print(l1);
lcd.setCursor(0, 1); lcd.print(l2);
}
// =====================================================================
// SERIAL COMMAND HANDLER
// =====================================================================
void handleSerialCommand(String cmd) {
cmd.trim();
cmd.toLowerCase();
if (cmd == "help") {
Serial.println("\n=== Perintah tersedia ===");
Serial.println(" help → tampilkan menu ini");
Serial.println(" status → status sistem");
Serial.println(" data → baca sensor sekarang");
Serial.println(" log → tampilkan datalog.txt");
Serial.println(" sdinfo → info SD Card");
Serial.println(" clear → hapus datalog.txt");
Serial.println("=========================\n");
}
else if (cmd == "status") {
Serial.println("\n=== STATUS SISTEM ===");
Serial.printf(" SD Ready : %s\n", sdReady ? "YES" : "NO");
Serial.printf(" Suhu : %.1f C\n", lastTemp);
Serial.printf(" Hum : %.1f %%\n", lastHum);
Serial.printf(" Uptime : %lu ms\n", millis());
Serial.println("=====================\n");
}
else if (cmd == "data") {
float t = dht.readTemperature();
float h = dht.readHumidity();
if (isnan(t) || isnan(h)) {
Serial.println("[DHT] Error baca sensor!");
} else {
Serial.printf("[DHT] Suhu: %.1f C | Hum: %.1f %%\n", t, h);
}
}
else if (cmd == "log") {
if (!sdReady) { Serial.println("[SD] Tidak siap"); return; }
File f = SD.open("/datalog.txt");
if (f) {
Serial.println("\n=== ISI datalog.txt ===");
while (f.available()) Serial.write(f.read());
Serial.println("=======================\n");
f.close();
} else {
Serial.println("[SD] File kosong");
}
}
else if (cmd == "sdinfo") {
if (!sdReady) { Serial.println("[SD] Tidak siap"); return; }
Serial.println("\n=== SD CARD INFO ===");
Serial.printf(" Total : %llu MB\n", SD.totalBytes() / (1024ULL * 1024ULL));
Serial.printf(" Used : %llu MB\n", SD.usedBytes() / (1024ULL * 1024ULL));
Serial.println(" Files :");
File root = SD.open("/");
File entry = root.openNextFile();
while (entry) {
Serial.printf(" /%-20s (%u bytes)\n", entry.name(), entry.size());
entry = root.openNextFile();
}
root.close();
Serial.println("====================\n");
}
else if (cmd == "clear") {
if (!sdReady) return;
SD.remove("/datalog.txt");
Serial.println("[SD] datalog.txt dihapus");
}
else {
Serial.printf("[CMD] Perintah tidak dikenal: '%s' (ketik 'help')\n", cmd.c_str());
}
}
// =====================================================================
// SETUP
// =====================================================================
void setup() {
Serial.begin(115200);
delay(500);
Serial.println();
Serial.println("=========================================");
Serial.println(" ESP32-C3 Sensor Monitor (Data Logger)");
Serial.println("=========================================");
pinMode(LED_PIN, OUTPUT);
digitalWrite(LED_PIN, LOW);
// ----- I2C + LCD -----
Wire.begin(LCD_SDA_PIN, LCD_SCL_PIN);
lcd.init();
lcd.backlight();
lcdInfo("Booting...", "ESP32-C3");
Serial.println("[LCD] OK (SDA=8, SCL=9)");
// ----- DHT22 -----
dht.begin();
Serial.println("[DHT] OK (pin=4)");
// ----- SD Card -----
Serial.println("[SD] Init SPI...");
sdSPI.begin(SD_SCK_PIN, SD_MISO_PIN, SD_MOSI_PIN, SD_CS_PIN);
delay(200);
if (!SD.begin(SD_CS_PIN, sdSPI)) {
Serial.println("[SD] Mount FAILED!");
sdReady = false;
} else {
sdReady = true;
Serial.println("[SD] Mounted OK");
Serial.printf("[SD] Total: %llu MB\n", SD.totalBytes() / (1024ULL * 1024ULL));
}
Serial.println("=========================================");
Serial.println(" Ketik 'help' di Serial Monitor");
Serial.println("=========================================");
lcd.clear();
}
// =====================================================================
// LOOP
// =====================================================================
void loop() {
// ----- Serial Command -----
if (Serial.available()) {
String cmd = Serial.readStringUntil('\n');
handleSerialCommand(cmd);
}
unsigned long now = millis();
// ----- LED Blink -----
if (now - lastBlink >= BLINK_INTERVAL) {
lastBlink = now;
ledState = !ledState;
digitalWrite(LED_PIN, ledState ? HIGH : LOW);
}
// ----- Baca Sensor -----
if (now - lastRead >= READ_INTERVAL) {
lastRead = now;
float t = dht.readTemperature();
float h = dht.readHumidity();
if (isnan(t) || isnan(h)) {
Serial.println("[DHT] ERROR!");
lcdInfo("Sensor Error!", "Cek DHT22");
return;
}
lastTemp = t;
lastHum = h;
Serial.printf("[DHT] Suhu: %.1f C | Hum: %.1f %%\n", t, h);
updateLCD(t, h);
logToSD(t, h);
}
}# Wokwi Library List # See https://docs.wokwi.com/guides/libraries DHT sensor library LiquidCrystal I2C SD
[wokwi] version = 1 firmware = "build/esp32.esp32.esp32c3/ESP32-SensorMonitor.ino.bin" elf = "build/esp32.esp32.esp32c3/ESP32-SensorMonitor.ino.elf"
{
"wokwi.arduinoCliPath": "C:\\arduino-cli\\arduino-cli.exe",
"wokwi.autoStartSimulation": false,
"files.associations": {
"*.ino": "cpp"
},
"C_Cpp.default.includePath": [
"C:/Users/{username}/AppData/Local/Arduino15/packages/esp32/hardware/esp32/3.3.12/cores/esp32",
"C:/Users/{username}/AppData/Local/Arduino15/packages/esp32/hardware/esp32/3.3.12/libraries/**",
"C:/Users/{username}/AppData/Local/Arduino15/packages/esp32/hardware/esp32/3.3.12/tools/sdk/esp32c3/include/**",
"C:/Users/{username}/Documents/Arduino/libraries/**"
],
"C_Cpp.default.browse.path": [
"C:/Users/{username}/AppData/Local/Arduino15/packages/esp32/hardware/esp32/3.3.12/**"
],
"C_Cpp.default.defines": [
"ARDUINO=200",
"ARDUINO_ARCH_ESP32",
"ESP32"
]
}Berdasarkan rangkaian dan program yang disajikan, sistem dirancang menggunakan ESP32-C3 sebagai pengendali, DHT22 sebagai sensor suhu dan kelembapan, LCD 16×2 sebagai tampilan lokal, dan kartu microSD sebagai media pencatatan. Program menetapkan interval pembacaan sensor sebesar 2.000 ms dan interval perubahan keadaan LED sebesar 1.000 ms. Alur program mengarahkan pembacaan yang valid ke LCD dan Serial Monitor, lalu mencoba menambahkannya ke berkas datalog.txt apabila kartu microSD siap digunakan. Nilai interval tersebut merupakan pengaturan dalam kode, bukan hasil pengukuran waktu pelaksanaan.
Program menyediakan perintah help, status, data, log, sdinfo, dan clear untuk membantu pemeriksaan serta pengelolaan data melalui Serial Monitor. Penanganan kesalahan pembacaan sensor dilakukan dengan menampilkan pesan kesalahan dan melewati pembaruan data pada siklus tersebut. Ketika inisialisasi kartu microSD gagal, program menonaktifkan pencatatan ke kartu tanpa menghentikan fungsi pembacaan sensor dan tampilan lokal.
Cakupan program yang dicantumkan belum meliputi web server, MQTT, dan pengendalian kipas yang dibahas pada pendahuluan. Oleh karena itu, kesimpulan laporan terbatas pada rancangan dan alur kerja pemantauan serta pencatatan lokal. Contoh keluaran dan langkah pengujian yang disajikan belum cukup untuk menetapkan nilai akurasi sensor, latensi pengiriman, kehilangan paket, atau waktu respons kipas.
Pengembangan berikutnya perlu menyelaraskan rumusan masalah dengan fungsi yang diimplementasikan. Apabila cakupan web server, MQTT, dan kontrol kipas dipertahankan, rangkaian serta program perlu dilengkapi dengan koneksi jaringan, pengiriman dan penerimaan pesan, serta aktuator dan penggeraknya. Logika kontrol juga perlu mencakup perpindahan mode otomatis dan manual serta histeresis sesuai rancangan pada bagian teori.
Pengujian sebaiknya mendokumentasikan keluaran aktual untuk setiap fitur, termasuk perubahan pembacaan DHT22, tampilan LCD, penambahan dan pembacaan berkas, serta kondisi kegagalan sensor dan kartu microSD. Pengujian pada perangkat fisik perlu membandingkan pembacaan sensor dengan alat ukur acuan. Pengukuran latensi, kehilangan paket, dan waktu respons kipas dilakukan setelah fungsi terkait tersedia, dengan jumlah percobaan dan metode pengukuran yang dijelaskan agar hasilnya dapat diperiksa kembali.
Pencatatan data dapat ditingkatkan dengan menambahkan waktu atau penanda urutan pada setiap pengukuran agar perubahan kondisi lebih mudah ditelusuri. Program juga perlu memeriksa hasil penghapusan berkas sebelum menampilkan pesan berhasil. Kelengkapan lampiran, status verifikasi fitur, dan identitas pustaka perlu diperiksa sebelum laporan difinalkan.
[1] D. Soni and A. Makwana, "A survey on MQTT: A protocol of Internet of Things (IoT)," in Proc. Int. Conf. Telecommun., Power Anal. Comput. Techn. (ICTPACT), Chennai, India, 2017, pp. 173–177.
[2] P. Macheso, S. Chisale, C. Daka, N. Dzupire, J. Mlatho, and D. Mukanyirigira, "Design of standalone asynchronous ESP32 web-server for temperature and humidity monitoring," in Proc. 7th Int. Conf. Adv. Comput. Commun. Syst. (ICACCS), 2021, pp. 635–638, doi: 10.1109/ICACCS51430.2021.9441845.
[3] A. Maier, A. Sharp, and Y. Vagapov, "Comparative analysis and practical implementation of the ESP32 microcontroller module for the Internet of Things," in Proc. Internet Technol. Appl. (ITA), Wrexham, U.K., 2017, pp. 143–148, doi: 10.1109/ITECHA.2017.8101926.
[4] A. Roihan, M. W. Septiano, and E. E. Kurniawan, "Integrasi sensor–aktuator berbasis IoT untuk pengaturan kipas otomatis dan monitoring lingkungan pada rumah pintar," Jurnal Sistem Informasi dan Teknologi (SINTEK), 2026. [lengkapi volume, nomor, halaman, dan DOI dari halaman artikel]
Video Demo: https://drive.google.com/file/d/1vXkCI_FE5SbISt7SWJd1PGBy5PihcChj/view?usp=sharing
Tidak ada komentar:
Posting Komentar