forked from TDTP/pantallas-led
fixes
parent
50a47d0f95
commit
82203db513
|
@ -7,6 +7,11 @@ from import_data import export_data
|
||||||
from PIL import Image
|
from PIL import Image
|
||||||
import subprocess
|
import subprocess
|
||||||
from getData import Paradero
|
from getData import Paradero
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
|
||||||
|
os.environ['TZ'] = 'America/Santiago'
|
||||||
|
time.tzset()
|
||||||
|
|
||||||
def reescalar_imagen(input_path, output_path, nuevo_ancho, nuevo_alto):
|
def reescalar_imagen(input_path, output_path, nuevo_ancho, nuevo_alto):
|
||||||
try:
|
try:
|
||||||
|
@ -18,7 +23,7 @@ def reescalar_imagen(input_path, output_path, nuevo_ancho, nuevo_alto):
|
||||||
|
|
||||||
# Guardar la imagen redimensionada en el nuevo archivo
|
# Guardar la imagen redimensionada en el nuevo archivo
|
||||||
imagen_redimensionada.save(output_path)
|
imagen_redimensionada.save(output_path)
|
||||||
print("Imagen redimensionada y guardada con éxito en", output_path)
|
# print("Imagen redimensionada y guardada con éxito en", output_path)
|
||||||
|
|
||||||
except:
|
except:
|
||||||
import traceback
|
import traceback
|
||||||
|
@ -48,7 +53,9 @@ def calc_remaining_time(data):
|
||||||
return remaining_minutes
|
return remaining_minutes
|
||||||
|
|
||||||
def obtain_min_max_time(remaining_time):
|
def obtain_min_max_time(remaining_time):
|
||||||
if remaining_time == 1:
|
if type(remaining_time) != int:
|
||||||
|
return "N/A", "N/A"
|
||||||
|
elif remaining_time == 1:
|
||||||
return 0, 1
|
return 0, 1
|
||||||
elif remaining_time == 2:
|
elif remaining_time == 2:
|
||||||
return 1, 2
|
return 1, 2
|
||||||
|
@ -81,7 +88,7 @@ def main():
|
||||||
data1 = data[0]
|
data1 = data[0]
|
||||||
data2 = data[1]
|
data2 = data[1]
|
||||||
|
|
||||||
print(data)
|
# print(data)
|
||||||
|
|
||||||
# Calcula el tiempo restante a la llegada
|
# Calcula el tiempo restante a la llegada
|
||||||
remaining_time1 = data1['timeRemaining']
|
remaining_time1 = data1['timeRemaining']
|
||||||
|
@ -119,20 +126,21 @@ def main():
|
||||||
full_panel.start_draw()
|
full_panel.start_draw()
|
||||||
|
|
||||||
# Agrega el anuncio de los minutos restante al arribo
|
# Agrega el anuncio de los minutos restante al arribo
|
||||||
time_anmc1 = TimeAnnouncement(aprox((2/5)*height), aprox((1/3)*width))
|
time_anmc1 = TimeAnnouncement(aprox((2/5)*height), aprox((2/5)*width))
|
||||||
time_anmc1.set_theme(theme)
|
time_anmc1.set_theme(theme)
|
||||||
time_anmc1.start_draw()
|
time_anmc1.start_draw()
|
||||||
# time_anmc1.set_background()
|
# time_anmc1.set_background()
|
||||||
# time_anmc1.set_base_text()
|
# time_anmc1.set_base_text()
|
||||||
time_anmc1.set_min_max_text(min_time=min_time1, max_time=max_time1)
|
time_anmc1.set_remaining_text(data[0]['timeRemaining'])
|
||||||
|
|
||||||
# Agrega el anuncio de los minutos restante al arribo
|
# Agrega el anuncio de los minutos restante al arribo
|
||||||
time_anmc2 = TimeAnnouncement(aprox((2/5)*height), aprox((1/3)*width))
|
time_anmc2 = TimeAnnouncement(aprox((2/5)*height), aprox((2/5)*width))
|
||||||
time_anmc2.set_theme(theme)
|
time_anmc2.set_theme(theme)
|
||||||
time_anmc2.start_draw()
|
time_anmc2.start_draw()
|
||||||
# time_anmc2.set_background()
|
# time_anmc2.set_background()
|
||||||
# time_anmc2.set_base_text()
|
# time_anmc2.set_base_text()
|
||||||
time_anmc2.set_min_max_text(min_time=min_time2, max_time=max_time2)
|
# time_anmc2.set_min_max_text(min_time=min_time2, max_time=max_time2)
|
||||||
|
time_anmc2.set_remaining_text(data[1]['timeRemaining'])
|
||||||
|
|
||||||
# Genera la imagen de la linea del bus
|
# Genera la imagen de la linea del bus
|
||||||
poster1 = BusPoster(aprox(1.1*(1/3)*height), aprox(1.1*(1/3)*width))
|
poster1 = BusPoster(aprox(1.1*(1/3)*height), aprox(1.1*(1/3)*width))
|
||||||
|
@ -145,7 +153,7 @@ def main():
|
||||||
# 'font_size': 11,
|
# 'font_size': 11,
|
||||||
'font_size': 80,
|
'font_size': 80,
|
||||||
'number_background_color': 'yellow',
|
'number_background_color': 'yellow',
|
||||||
'letter_background_color': 'green',
|
'letter_background_color': data[0]['number_background_color'],
|
||||||
}
|
}
|
||||||
|
|
||||||
# Se setean los parametros
|
# Se setean los parametros
|
||||||
|
@ -168,7 +176,7 @@ def main():
|
||||||
# 'font_size': 11,
|
# 'font_size': 11,
|
||||||
'font_size': 80,
|
'font_size': 80,
|
||||||
'number_background_color': 'yellow',
|
'number_background_color': 'yellow',
|
||||||
'letter_background_color': 'blue',
|
'letter_background_color': data[1]['number_background_color'],
|
||||||
}
|
}
|
||||||
|
|
||||||
# Se setean los parametros
|
# Se setean los parametros
|
||||||
|
@ -180,8 +188,8 @@ def main():
|
||||||
poster2.set_bus_letter(bus_letter=direccion2)
|
poster2.set_bus_letter(bus_letter=direccion2)
|
||||||
|
|
||||||
# Se agregan todas las imagenes al canvas
|
# Se agregan todas las imagenes al canvas
|
||||||
full_panel.add_image(time_anmc1, (aprox((0.6)*width), aprox(0.05*height)))
|
full_panel.add_image(time_anmc1, (aprox((0.55)*width), aprox(0.05*height)))
|
||||||
full_panel.add_image(time_anmc2, (aprox((0.6)*width), aprox(0.45*height)))
|
full_panel.add_image(time_anmc2, (aprox((0.55)*width), aprox(0.45*height)))
|
||||||
full_panel.add_image(poster1, (aprox((0.05)*width), aprox((0.1)*height)))
|
full_panel.add_image(poster1, (aprox((0.05)*width), aprox((0.1)*height)))
|
||||||
full_panel.add_image(poster2, (aprox((0.05)*width), aprox((0.5)*height)))
|
full_panel.add_image(poster2, (aprox((0.05)*width), aprox((0.5)*height)))
|
||||||
#full_panel.add_image(bm, (aprox(0.02*width),aprox((1/6)*height)))
|
#full_panel.add_image(bm, (aprox(0.02*width),aprox((1/6)*height)))
|
||||||
|
@ -196,5 +204,10 @@ def main():
|
||||||
reescalar_imagen(input_path, output_path, nuevo_ancho, nuevo_alto)
|
reescalar_imagen(input_path, output_path, nuevo_ancho, nuevo_alto)
|
||||||
subprocess.run(['cp', output_path, '/srv/ledram/current.png'])
|
subprocess.run(['cp', output_path, '/srv/ledram/current.png'])
|
||||||
|
|
||||||
|
|
||||||
|
from apscheduler.schedulers.blocking import BlockingScheduler
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
main()
|
sched = BlockingScheduler()
|
||||||
|
sched.add_job(main, 'interval', seconds=15)
|
||||||
|
sched.start()
|
||||||
|
|
|
@ -8,26 +8,27 @@ from datetime import datetime, timedelta
|
||||||
class Paradero:
|
class Paradero:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
# Dispositivo
|
# Dispositivo
|
||||||
self.id = "00000000160f3b42b8:27:eb:0f:3b:42"
|
self.id = "panel-pruebas-2"
|
||||||
|
|
||||||
# Autentificación data
|
# Autentificación data
|
||||||
self.url_auth = 'https://transporte.hz.kursor.cl/api/auth/'
|
self.url_auth = 'https://gestion.tdt-dev.ilab.cl/api/auth/'
|
||||||
self.username = "usuario1"
|
self.rut = "11111111-1"
|
||||||
self.password = "usuario1"
|
self.password = "usuario1"
|
||||||
|
|
||||||
# Token obtenido luego del 'login'
|
# Token obtenido luego del 'login'
|
||||||
self.token = self.__get_token()
|
self.token = self.__get_token()
|
||||||
print(self.token)
|
# print(self.token)
|
||||||
|
|
||||||
# URL de la API para obtener los datos de los recorridos
|
# URL de la API para obtener los datos de los recorridos
|
||||||
self.url_getinfodevice = 'https://transporte.hz.kursor.cl/api/dispositivos/getInfoDevice/'
|
self.url_getinfodevice = 'https://gestion.tdt-dev.ilab.cl/api/dispositivos/getInfoDevice/'
|
||||||
self.data = None
|
self.data = None
|
||||||
self.bus_list = []
|
self.bus_list = []
|
||||||
|
self.servicios = ["12Q", "56O"]
|
||||||
|
|
||||||
|
|
||||||
def __get_token(self):
|
def __get_token(self):
|
||||||
auth = '''{
|
auth = '''{
|
||||||
"username": "usuario1",
|
"rut": "11111111-1",
|
||||||
"password": "usuario1"
|
"password": "usuario1"
|
||||||
}'''
|
}'''
|
||||||
|
|
||||||
|
@ -37,6 +38,7 @@ class Paradero:
|
||||||
if response.status_code == 200:
|
if response.status_code == 200:
|
||||||
return response.json()['token']
|
return response.json()['token']
|
||||||
else:
|
else:
|
||||||
|
# print(response)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
def get_data(self):
|
def get_data(self):
|
||||||
|
@ -52,7 +54,7 @@ class Paradero:
|
||||||
#Aquí se ingresa el token obtenido anteriormente
|
#Aquí se ingresa el token obtenido anteriormente
|
||||||
headers_getinfodevice = {
|
headers_getinfodevice = {
|
||||||
'Authorization': f'Bearer {self.token}',
|
'Authorization': f'Bearer {self.token}',
|
||||||
'Content-Type': 'application/json'
|
'Content-Type': 'application/json'
|
||||||
}
|
}
|
||||||
|
|
||||||
# Request
|
# Request
|
||||||
|
@ -62,42 +64,59 @@ class Paradero:
|
||||||
return self.data
|
return self.data
|
||||||
|
|
||||||
def __generate_bus_list(self, info):
|
def __generate_bus_list(self, info):
|
||||||
data_main = []
|
data_main = {}
|
||||||
zona_horaria_santiago = pytz.timezone('America/Santiago')
|
zona_horaria_santiago = pytz.timezone('America/Santiago')
|
||||||
hora_actual_santiago = datetime.now(zona_horaria_santiago).time()
|
hora_actual_santiago = datetime.now(zona_horaria_santiago).time()
|
||||||
|
|
||||||
for i in range(len(info["GetInfoDeviceResponse"]["DetalleLineas"])):
|
for i in range(len(info["GetInfoDeviceResponse"]["DetalleLineas"])):
|
||||||
|
|
||||||
data = info["GetInfoDeviceResponse"]["DetalleLineas"][i]
|
data = info["GetInfoDeviceResponse"]["DetalleLineas"][i]
|
||||||
|
if data["Descripcion"] not in self.servicios:
|
||||||
|
continue
|
||||||
|
|
||||||
bus_info = {}
|
bus_info = {}
|
||||||
bus_info["distance"] = data["Llegadas"][0]["DistanciaGPS"] if data["Llegadas"][0]["DistanciaGPS"] is not None else "-"
|
if len(data['Llegadas']) > 0 and data["Llegadas"][0]["DistanciaGPS"] is not None:
|
||||||
bus_info["timeLabel"] = data["Llegadas"][0]["EstimadaGPS"] if data["Llegadas"][0]["EstimadaGPS"] is not None else "-"
|
bus_info["distance"] = data["Llegadas"][0]["DistanciaGPS"]
|
||||||
|
bus_info["timeLabel"] = data["Llegadas"][0]["EstimadaGPS"]
|
||||||
|
bus_info["patente"] = data["Llegadas"][0]["patente"]
|
||||||
|
bus_hour = datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().hour if datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().hour != 0 else 24
|
||||||
|
diff = timedelta(
|
||||||
|
hours = bus_hour - hora_actual_santiago.hour,
|
||||||
|
minutes = datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().minute - hora_actual_santiago.minute,
|
||||||
|
seconds=datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().second - hora_actual_santiago.second
|
||||||
|
)
|
||||||
|
# print(diff.total_seconds())
|
||||||
|
bus_info["timeLabel"] = "m"
|
||||||
|
|
||||||
|
if data['Llegadas'][0]['textoLlegada'].startswith("Entre"):
|
||||||
|
data['Llegadas'][0]['textoLlegada'] = data['Llegadas'][0]['textoLlegada'][5:]
|
||||||
|
cut = data['Llegadas'][0]['textoLlegada'].index("min")+3
|
||||||
|
bus_info["timeRemaining"] = data['Llegadas'][0]['textoLlegada'][:cut]
|
||||||
|
else:
|
||||||
|
bus_info["distance"] = "-"
|
||||||
|
bus_info["timeLabel"] = "Sin Info"
|
||||||
|
bus_info["timeRemaining"] = "Sin Dato"
|
||||||
|
|
||||||
bus_info["route"] = data["Descripcion"][:-1] if data["Descripcion"] is not None else "-"
|
bus_info["route"] = data["Descripcion"][:-1] if data["Descripcion"] is not None else "-"
|
||||||
bus_info["direction"] = data["Descripcion"][-1] if data["Descripcion"] is not None else "-"
|
bus_info["direction"] = data["Descripcion"][-1] if data["Descripcion"] is not None else "-"
|
||||||
bus_info["number_background_color"] = data["colorFondo"]
|
bus_info["number_background_color"] = "#{}".format(data["colorFondo"])
|
||||||
bus_info["letter_background_color"] = data["colorTexto"]
|
bus_info["letter_background_color"] = "#{}".format(data["colorTexto"])
|
||||||
bus_info["patente"] = data["Llegadas"][0]["patente"]
|
|
||||||
bus_hour = datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().hour if datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().hour != 0 else 24
|
|
||||||
print(bus_hour, hora_actual_santiago.hour)
|
|
||||||
diff = timedelta(
|
|
||||||
hours = bus_hour - hora_actual_santiago.hour,
|
|
||||||
minutes = datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().minute - hora_actual_santiago.minute,
|
|
||||||
seconds=datetime.strptime(bus_info["timeLabel"], "%H:%M:%S").time().second - hora_actual_santiago.second
|
|
||||||
)
|
|
||||||
print(diff.total_seconds())
|
|
||||||
bus_info["timeRemaining"] = int(abs(diff.total_seconds() // 60))
|
|
||||||
data_main.append(bus_info)
|
|
||||||
|
|
||||||
data_main = sorted(data_main, key=lambda x: x['timeRemaining'])
|
data_main[data["Descripcion"]] = bus_info
|
||||||
self.bus_list = data_main
|
|
||||||
|
|
||||||
for d in data_main:
|
# data_main = sorted(data_main, key=lambda x: x['timeRemaining'])
|
||||||
print(d['timeRemaining'], d['timeLabel'])
|
salida = []
|
||||||
|
for servicio in self.servicios:
|
||||||
|
if servicio in data_main:
|
||||||
|
salida.append(data_main[servicio])
|
||||||
|
|
||||||
|
self.bus_list = salida
|
||||||
|
|
||||||
|
# for d in data_main:
|
||||||
|
# print(d['timeRemaining'], d['timeLabel'])
|
||||||
|
|
||||||
def __serialize_data(self, response):
|
def __serialize_data(self, response):
|
||||||
data = response.json()
|
data = response.json()
|
||||||
self.__generate_bus_list(data)
|
self.__generate_bus_list(data)
|
||||||
data = self.bus_list[:2]
|
|
||||||
|
|
||||||
return data
|
return self.bus_list
|
||||||
|
|
|
@ -0,0 +1,28 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
if [ "$EUID" -ne 0 ]; then
|
||||||
|
echo "Este script requiere permisos de root."
|
||||||
|
exit
|
||||||
|
fi
|
||||||
|
|
||||||
|
# set pwd to current directory
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
|
||||||
|
#limpia el contenido del directorio de trabajo
|
||||||
|
rm -rf /srv/parada*
|
||||||
|
|
||||||
|
mkdir /srv/parada_led
|
||||||
|
|
||||||
|
cp -rf *.py assets scripts /srv/parada_led
|
||||||
|
|
||||||
|
#Crea el servicio
|
||||||
|
cp -rf parada_led.service /etc/systemd/system/parada_led.service
|
||||||
|
|
||||||
|
# Recarga e inicia automaticamente al prender.
|
||||||
|
systemctl daemon-reload
|
||||||
|
systemctl unmask parada_led.service
|
||||||
|
systemctl enable parada_led.service
|
||||||
|
|
||||||
|
# Mensajes de salida
|
||||||
|
echo "Debe reiniciar la Raspberry para que el servicio pueda iniciarse"
|
||||||
|
echo "Luego para actualizar, solo debe modificar el el archivo '/srv/ledram/current.png' para actualizar la pantalla"
|
|
@ -1,3 +0,0 @@
|
||||||
c = get_config()
|
|
||||||
from notebook.auth import passwd
|
|
||||||
c.NotebookApp.password = passwd("...")
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
[Unit]
|
||||||
|
Description=WebService Datos Parada
|
||||||
|
After=local-fs.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
User=root
|
||||||
|
WorkingDirectory=/srv/parada_led
|
||||||
|
ExecStart=/usr/bin/python3 /srv/parada_led/app.py
|
||||||
|
Restart=always
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
|
@ -76,3 +76,23 @@ class TimeAnnouncement(MyDraw):
|
||||||
font=self.font,
|
font=self.font,
|
||||||
align ="center"
|
align ="center"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def set_remaining_text(self, text):
|
||||||
|
|
||||||
|
text_color = self.theme_params['text_color']
|
||||||
|
self.load_barlow(font_size=70)
|
||||||
|
text_bbox = self.font.getbbox(text)
|
||||||
|
font_width, font_height = text_bbox[2] - text_bbox[0], text_bbox[3] - text_bbox[1]
|
||||||
|
# print(font_width, font_height)
|
||||||
|
offset_width = (np.round((self.width-self.border)) - np.round(font_width))/2
|
||||||
|
offset_height = (np.round((self.height-self.border)) - np.round(font_height))/2
|
||||||
|
# text_position = (offset_width,5+offset_height)
|
||||||
|
text_position = (offset_width,offset_height-10)
|
||||||
|
# text_position = (0, 0)
|
||||||
|
self.draw.text(
|
||||||
|
text_position,
|
||||||
|
text,
|
||||||
|
fill=text_color,
|
||||||
|
font=self.font,
|
||||||
|
align ="center"
|
||||||
|
)
|
||||||
|
|
|
@ -24,7 +24,7 @@ sed -i -e 's/ isocpus=3//g' /boot/cmdline.txt
|
||||||
sed -i -e 's/$/ isocpus=3/' /boot/cmdline.txt
|
sed -i -e 's/$/ isocpus=3/' /boot/cmdline.txt
|
||||||
|
|
||||||
#copia la biblioteca al directorio de trabajo
|
#copia la biblioteca al directorio de trabajo
|
||||||
cp -R /home/soporte/rpi-rgb-led-matrix/bindings/python/rgbmatrix /srv/rgbmatrix
|
cp -R /home/raspi/rpi-rgb-led-matrix/bindings/python/rgbmatrix /srv/rgbmatrix
|
||||||
|
|
||||||
#copia el sub-sistema de renderizado
|
#copia el sub-sistema de renderizado
|
||||||
mkdir /srv/subsystem
|
mkdir /srv/subsystem
|
||||||
|
|
|
@ -42,7 +42,7 @@ Requerimientos del LED-MATRIX
|
||||||
|
|
||||||
Requerimientos de pantallas led:
|
Requerimientos de pantallas led:
|
||||||
|
|
||||||
`sudo apt-get install python3-matplotlib python3-requests python3-numpy python3-pytzdata -y`
|
`sudo apt-get install python3-matplotlib python3-requests python3-numpy python3-pytzdata python3-apscheduler -y`
|
||||||
|
|
||||||
### Clonar los repositorios
|
### Clonar los repositorios
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue