from machine import Pin, ADC, I2C
import time
# =========================================================
# GAS LEAKAGE ALARM
# Raspberry Pi Pico + MQ-2 + LCD 16x2 I2C
# LED Hijau + LED Merah + Buzzer
# START + RESET
# =========================================================
# KONFIGURASI PIN
# MQ-2
mq2 = ADC(26) # GP26/ADC0
# LED
led_hijau = Pin(14, Pin.OUT)
led_merah = Pin(15, Pin.OUT)
# Tombol (Menggunakan internal PULL-UP)
button_start = Pin(16, Pin.IN, Pin.PULL_UP)
button_reset = Pin(17, Pin.IN, Pin.PULL_UP)
# Buzzer
buzzer = Pin(18, Pin.OUT)
# LCD I2C
i2c = I2C(0, scl=Pin(5), sda=Pin(4), freq=400000)
# KONFIGURASI LCD
LCD_ADDR = 0x27
# BATAS GAS MANUAL
# MASUKKAN NILAI ADC BATAS BAHAYA DI SINI
# =========================================================
BATAS_GAS = 25000
# VARIABEL SISTEM
# =========================================================
sistem_aktif = False
# CLASS LCD 16x2 I2C
class LCD1602:
def __init__(self, i2c, addr):
self.i2c = i2c
self.addr = addr
self.init_lcd()
def write_byte(self, data):
self.i2c.writeto(self.addr, bytes([data]))
def pulse_enable(self, data):
self.write_byte(data | 0x04)
time.sleep_us(500)
self.write_byte(data & ~0x04)
time.sleep_us(100)
def send_nibble(self, nibble, mode=0):
data = nibble | mode | 0x08
self.write_byte(data)
self.pulse_enable(data)
def send(self, value, mode=0):
self.send_nibble(value & 0xF0, mode)
self.send_nibble((value << 4) & 0xF0, mode)
def command(self, cmd):
self.send(cmd, 0)
def write_char(self, char):
self.send(ord(char), 1)
def clear(self):
self.command(0x01)
time.sleep_ms(2)
def move_to(self, row, col):
if row == 0:
address = 0x80 + col
else:
address = 0xC0 + col
self.command(address)
def putstr(self, text):
for char in text:
self.write_char(char)
def init_lcd(self):
time.sleep_ms(50)
self.send_nibble(0x30)
time.sleep_ms(5)
self.send_nibble(0x30)
time.sleep_ms(1)
self.send_nibble(0x30)
time.sleep_ms(1)
self.send_nibble(0x20)
# 4-bit mode, 2 line
self.command(0x28)
# Display ON
self.command(0x0C)
# Cursor increment
self.command(0x06)
self.clear()
# INISIALISASI LCD
lcd = LCD1602(i2c, LCD_ADDR)
# FUNGSI MATIKAN OUTPUT
# =========================================================
def output_off():
led_hijau.value(0)
led_merah.value(0)
buzzer.value(0)
# FUNGSI STANDBY
def standby_screen():
output_off()
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("SYSTEM STANDBY")
lcd.move_to(1, 0)
lcd.putstr("Tekan START")
# FUNGSI SISTEM AKTIF
def active_screen():
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("ALARM AKTIF")
lcd.move_to(1, 0)
lcd.putstr("Monitoring...")
# STARTUP
output_off()
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("GAS DETECTOR")
lcd.move_to(1, 0)
lcd.putstr("SYSTEM START")
time.sleep(2)
# TAMPILKAN BATAS GAS
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("BATAS BAHAYA")
lcd.move_to(1, 0)
lcd.putstr("ADC:{:5d}".format(BATAS_GAS))
print("===========================")
print(" GAS DETECTOR ")
print("===========================")
print("Batas bahaya ADC =", BATAS_GAS)
print("===========================")
time.sleep(3)
# MASUK STANDBY
sistem_aktif = False
standby_screen()
# =========================================================
# MAIN LOOP
# =========================================================
while True:
# =========================================================
# TOMBOL RESET
# =========================================================
if button_reset.value() == 0:
# Debounce
time.sleep_ms(50)
if button_reset.value() == 0:
print("RESET SYSTEM")
# Matikan sistem
sistem_aktif = False
# Matikan semua output
output_off()
# Tampilkan standby
standby_screen()
# Tunggu tombol dilepas
while button_reset.value() == 0:
time.sleep_ms(10)
# =========================================================
# TOMBOL START
# =========================================================
if button_start.value() == 0:
# Debounce
time.sleep_ms(50)
if button_start.value() == 0:
print("SYSTEM START")
# Aktifkan sistem
sistem_aktif = True
active_screen()
# Tunggu tombol dilepas
while button_start.value() == 0:
time.sleep_ms(10)
# =========================================================
# SISTEM BELUM AKTIF
# =========================================================
if not sistem_aktif:
output_off()
time.sleep_ms(100)
continue
# =========================================================
# BACA SENSOR MQ-2
# =========================================================
nilai_adc = mq2.read_u16()
# SERIAL MONITOR
# =========================================================
print("ADC:", nilai_adc, "Batas:", BATAS_GAS)
# =========================================================
# KONDISI NORMAL
# =========================================================
if nilai_adc < BATAS_GAS:
# LED HIJAU ON
led_hijau.value(1)
# LED MERAH OFF
led_merah.value(0)
# BUZZER OFF
buzzer.value(0)
# LCD
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("STATUS: NORMAL")
lcd.move_to(1, 0)
lcd.putstr("ADC:{:5d}".format(nilai_adc))
time.sleep_ms(500)
# =========================================================
# KONDISI BAHAYA
# =========================================================
else:
# LED HIJAU OFF
led_hijau.value(0)
# LED MERAH ON
led_merah.value(1)
# LCD
lcd.clear()
lcd.move_to(0, 0)
lcd.putstr("!!! GAS !!!")
lcd.move_to(1, 0)
lcd.putstr("ADC:{:5d}".format(nilai_adc))
# Serial Monitor
print("!!! BAHAYA !!! ADC =", nilai_adc)
# BUZZER
buzzer.value(1)
time.sleep_ms(200)
buzzer.value(0)
time.sleep_ms(200)