from machine import I2C, Pin, PWM
from pico_i2c_lcd import I2cLcd
from lcd_api import LcdApi
import utime
import gc
class DS1307:
def __init__(self, i2c):
self.i2c = i2c
self.address = 0x68
def dec2bcd(self, val):
return (val // 10) << 4 | (val % 10)
def bcd2dec(self, val):
return ((val >> 4) * 10) + (val & 0x0F)
def read_time(self):
data = self.i2c.readfrom_mem(self.address, 0x00, 7)
ss = self.bcd2dec(data[0] & 0x7F)
mm = self.bcd2dec(data[1])
hh = self.bcd2dec(data[2])
dd = self.bcd2dec(data[4])
mo = self.bcd2dec(data[5])
yy = self.bcd2dec(data[6]) + 2000
return dd, mo, yy, hh, mm, ss
def write_time(self, dd, mo, yy, hh, mm, ss):
data = bytearray(7)
data[0] = self.dec2bcd(ss)
data[1] = self.dec2bcd(mm)
data[2] = self.dec2bcd(hh)
data[3] = 0
data[4] = self.dec2bcd(dd)
data[5] = self.dec2bcd(mo)
data[6] = self.dec2bcd(yy - 2000)
self.i2c.writeto_mem(self.address, 0x00, data)
i2c = I2C(0, sda=Pin(0), scl=Pin(1), freq=400000)
lcd = I2cLcd(i2c, 0x27, 2, 16)
rtc = DS1307(i2c)
buzzer = PWM(Pin(10))
ren_pin = [2, 3, 4, 5]
col_pin = [6, 7, 8, 9]
rens = []
cols = []
teclas = [
['1', '2', '3', 'A'],
['4', '5', '6', 'B'],
['7', '8', '9', 'C'],
['*', '0', '#', 'D']
]
for i in range(4):
rens.append(Pin(ren_pin[i], Pin.OUT))
cols.append(Pin(col_pin[i], Pin.IN, Pin.PULL_DOWN))
rens[i].value(0)
def leer_tecla():
for r in range(4):
rens[r].value(1)
for c in range(4):
if cols[c].value() == 1:
utime.sleep_ms(200)
rens[r].value(0)
return teclas[r][c]
rens[r].value(0)
return None
alarma_hh = 0
alarma_mm = 0
alarma_activada = False
def reproducir_melodia():
notas = [523, 659, 784, 1046]
duraciones = [300, 300, 300, 600]
for i in range(len(notas)):
buzzer.freq(notas[i])
buzzer.duty_u16(32768)
utime.sleep_ms(duraciones[i])
buzzer.duty_u16(0)
utime.sleep_ms(100)
def mostrar_hora_fecha():
dd, mo, yy, hh, mm, ss = rtc.read_time()
lcd.clear()
lcd.putstr("{:02d}/{:02d}/{}".format(dd, mo, yy))
lcd.move_to(0, 1)
lcd.putstr("{:02d}:{:02d}:{:02d}".format(hh, mm, ss))
def ingresar_valor(mensaje, num_digitos):
lcd.clear()
lcd.putstr(mensaje)
lcd.move_to(0, 1)
valor = ""
while True:
tecla = leer_tecla()
if tecla:
if tecla == '#':
if len(valor) == num_digitos:
return int(valor)
else:
lcd.clear()
lcd.putstr("Valor invalido")
utime.sleep(1)
return None
elif tecla == '*':
return None
elif tecla.isdigit() and len(valor) < num_digitos:
valor += tecla
lcd.putstr(tecla)
def editar_fecha():
lcd.clear()
lcd.putstr("Editar Fecha")
utime.sleep(1)
dd = ingresar_valor("Dia (DD):", 2)
if dd is None: return
mo = ingresar_valor("Mes (MM):", 2)
if mo is None: return
yy = ingresar_valor("Ano (AA):", 2)
if yy is None: return
d, m, y, h, mi, s = rtc.read_time()
rtc.write_time(dd, mo, 2000 + yy, h, mi, s)
lcd.clear()
lcd.putstr("Fecha guardada!")
utime.sleep(1)
def editar_hora():
lcd.clear()
lcd.putstr("Editar Hora")
utime.sleep(1)
hh = ingresar_valor("Hora (HH):", 2)
if hh is None: return
mm = ingresar_valor("Min (MM):", 2)
if mm is None: return
ss = ingresar_valor("Seg (SS):", 2)
if ss is None: return
d, m, y, h, mi, s = rtc.read_time()
rtc.write_time(d, m, y, hh, mm, ss)
lcd.clear()
lcd.putstr("Hora guardada!")
utime.sleep(1)
def configurar_alarma():
global alarma_hh, alarma_mm
lcd.clear()
lcd.putstr("Config Alarma")
utime.sleep(1)
h = ingresar_valor("Hora (HH):", 2)
if h is None: return
m = ingresar_valor("Min (MM):", 2)
if m is None: return
alarma_hh = h
alarma_mm = m
lcd.clear()
lcd.putstr("Alarma: {:02d}:{:02d}".format(h, m))
utime.sleep(1)
def toggle_alarma():
global alarma_activada
alarma_activada = not alarma_activada
lcd.clear()
if alarma_activada:
lcd.putstr("Alarma ACTIVADA")
else:
lcd.putstr("Alarma DESACT.")
utime.sleep(1)
def menu():
pagina = 1
while True:
lcd.clear()
if pagina == 1:
lcd.putstr("1.Ver 2.Fecha 3.Hora")
lcd.move_to(0, 1)
lcd.putstr("4.Sig.Pag")
else:
lcd.putstr("5.Ant 6.Alarm 7.OnOff")
lcd.move_to(0, 1)
lcd.putstr("8.Salir")
tecla = None
while tecla is None:
tecla = leer_tecla()
if pagina == 1:
if tecla == '1':
mostrar_hora_fecha()
utime.sleep(2)
elif tecla == '2':
editar_fecha()
elif tecla == '3':
editar_hora()
elif tecla == '4':
pagina = 2
elif pagina == 2:
if tecla == '5':
pagina = 1
elif tecla == '6':
configurar_alarma()
elif tecla == '7':
toggle_alarma()
elif tecla == '8' or tecla == '*':
lcd.clear()
lcd.putstr("Saliendo...")
utime.sleep(1)
break
while True:
dd, mo, yy, hh, mm, ss = rtc.read_time()
mostrar_hora_fecha()
if alarma_activada and hh == alarma_hh and mm == alarma_mm and ss == 0:
reproducir_melodia()
tecla = leer_tecla()
if tecla == 'A':
menu()
utime.sleep(1)