implementing radio

This commit is contained in:
death916 2026-01-07 01:59:06 -08:00
parent b2320fd073
commit 756f8dfd07
4 changed files with 61 additions and 54 deletions

View file

@ -1,7 +1,7 @@
# deathclock.py # deathclock.py
import asyncio import asyncio
# from utils.alarm import Alarm # Commented out import # from utils.alarm import Alarm
import logging import logging
import time import time
from datetime import datetime, timezone from datetime import datetime, timezone
@ -9,17 +9,15 @@ from typing import Any, Dict, List
import reflex as rx import reflex as rx
_background_tasks_registered = False
from utils.news import News from utils.news import News
from utils.radio import Radio from utils.radio import Radio_UI
from utils.scores import NBAScores, mlbScores, nflScores from utils.scores import NBAScores, mlbScores, nflScores
from utils.weather import Weather from utils.weather import Weather
WEATHER_IMAGE_PATH = "/weather.jpg" # Web path in assets folder WEATHER_IMAGE_PATH = "/weather.jpg" # Web path in assets folder
WEATHER_FETCH_INTERVAL = 360 WEATHER_FETCH_INTERVAL = 360
logging.basicConfig( logging.basicConfig(
level=logging.INFO, format="%(asctime)s - %(levelname)s - %(message)s" level=logging.DEBUG, format="%(asctime)s - %(levelname)s - %(message)s"
) )
@ -38,14 +36,15 @@ class State(rx.State):
nfl_scores: List[Dict[str, Any]] = [] nfl_scores: List[Dict[str, Any]] = []
radio_stations: List[str] = [] radio_stations: List[str] = []
current_radio_station: str = "" current_radio_station: str = ""
_news_client: News | None = None # This will be set in the constructor _news_client: News | None = None
last_weather_update: str = "Never" last_weather_update: str = "Never"
weather_img: str = WEATHER_IMAGE_PATH weather_img: str = WEATHER_IMAGE_PATH
_weather_client: Weather | None = None # This will be set in the constructor _weather_client: Weather | None = None
_mlb_client: mlbScores | None = None _mlb_client: mlbScores | None = None
_nba_client: NBAScores | None = None _nba_client: NBAScores | None = None
_nfl_client: nflScores | None = None _nfl_client: nflScores | None = None
_radio_client: Radio = Radio() _radio_client_ui: Radio_UI = Radio_UI()
# _radio_client_control: Radio_Control = Radio_Control()
last_sports_update: float = 0.0 last_sports_update: float = 0.0
last_weather_fetch_time: float = 0.0 last_weather_fetch_time: float = 0.0
last_weather_image_path: str = "" last_weather_image_path: str = ""
@ -60,7 +59,7 @@ class State(rx.State):
self._mlb_client = mlbScores() self._mlb_client = mlbScores()
self._nba_client = NBAScores() self._nba_client = NBAScores()
self._nfl_client = nflScores() self._nfl_client = nflScores()
self._radio_client = Radio() self._radio_client_ui = Radio_UI()
logging.info("Weather client initialized successfully.") logging.info("Weather client initialized successfully.")
except Exception as e: except Exception as e:
@ -73,18 +72,14 @@ class State(rx.State):
self.nba_scores = [] self.nba_scores = []
self.last_sports_update = 0.0 self.last_sports_update = 0.0
# --- on_load Handler --- # --- on_load Handler ---
async def start_background_tasks(self): async def start_background_tasks(self):
global _background_tasks_registered """Starts background tasks when the page loads."""
"""Starts the weather background task when the page loads."""
rx.remove_local_storage("chakra-ui-color-mode") rx.remove_local_storage("chakra-ui-color-mode")
if _background_tasks_registered:
logging.info( logging.info("Triggering background tasks for this session")
"Background tasks already registered in this process; skipping." # Always return the tasks so they start for this specific user/tab
)
return []
_background_tasks_registered = True
logging.info("Triggering background tasks: Weather")
return [ return [
State.fetch_weather, State.fetch_weather,
State.fetch_sports, State.fetch_sports,
@ -258,7 +253,6 @@ class State(rx.State):
logging.info("Weather fetch completed") logging.info("Weather fetch completed")
logging.info("Sleeping for next fetch") logging.info("Sleeping for next fetch")
await asyncio.sleep(WEATHER_FETCH_INTERVAL) await asyncio.sleep(WEATHER_FETCH_INTERVAL)
2
def index() -> rx.Component: def index() -> rx.Component:
@ -444,7 +438,7 @@ def index() -> rx.Component:
rx.flex( rx.flex(
rx.vstack( rx.vstack(
rx.hstack( rx.hstack(
State._radio_client.radio_card(), State._radio_client_ui.radio_card(),
clock_button, clock_button,
), ),
main_flex, main_flex,

View file

@ -16,6 +16,6 @@ pkgs.mkShell {
# export PATH="${pkgs.bun}/bin:$PATH" # export PATH="${pkgs.bun}/bin:$PATH"
# export BUN_INSTALL="${pkgs.bun}/bin/bun" # export BUN_INSTALL="${pkgs.bun}/bin/bun"
export REFLEX_USE_SYSTEM_BUN=True export REFLEX_USE_SYSTEM_BUN=True
echo venv activated and bun version set echo venv activated and bun versions set
''; '';
} }

View file

@ -1,6 +1,3 @@
#!/usr/bin/python3
# connect to rda5807 chip and control it and display the current station
# TODO: reference rd library in readme
import logging import logging
import reflex as rx import reflex as rx
@ -8,40 +5,47 @@ import reflex as rx
# from utils.python_rd5807m.radio import Rda5807m as Radio_lib # from utils.python_rd5807m.radio import Rda5807m as Radio_lib
DEBUG = True DEBUG = True
CURRENT_STATION = "90.9 FM" CURRENT_STATION = 90.9
PLAYING = False PLAYING = False
HARDWARE = True HARDWARE = True
class Radio(rx.Base): class Radio_UI:
def __init__(self):
if DEBUG:
self.device = None
else:
self.device = Radio_Control()
def open_radio_button(self): def open_radio_button(self):
return rx.button("Radio", on_click=self.open_radio_button) return rx.button("Radio", on_click=self.open_radio_button)
def radio_card(self): def radio_card(self):
radio_card = rx.popover.root( """
Radio Card
Main pop open button for radio control
"""
return rx.popover.root(
rx.popover.trigger(rx.button("Radio")), rx.popover.trigger(rx.button("Radio")),
rx.popover.content( rx.popover.content(
rx.vstack( rx.vstack(
rx.heading("Current Station"), rx.heading("Current Station"),
rx.text(CURRENT_STATION), rx.text(CURRENT_STATION),
# rx.text("Volume"), # rx.text("Volume"),
# rx.button("Play" # rx.button("Play", on_click=self.device.play_radio),
# on_click=Radio_Control.play_radio),
# ),
# rx.button("Pause"),
# rx.button("Stop"),
), ),
# rx.button("Pause"),
# rx.button("Stop"),
), ),
) )
return radio_card
"""
class Radio_Control: class Radio_Control:
"""
# Radio Control Class Radio Control Class
#uses rda5807m library, if debugging populates false values for display uses rda5807m library, if debugging populates false values for display
"""
def __init__(self): def __init__(self):
self.debug = DEBUG self.debug = DEBUG
@ -51,29 +55,32 @@ class Radio_Control:
self.volume = 7 self.volume = 7
self.playing = False self.playing = False
self.signal = 0.0 self.signal = 0.0
self._device = None
self._display = None self._display = None
self._device = None
def init_radio(self): def init_radio(self):
# self._device = Radio_lib(self.bus) # self._device = Radio_lib(self.bus)
self._device.init_chip() # self._device.init_chip()
pass
def play_radio(self): def play_radio(self):
if self.debug: if self.debug:
logging.debug("Playing fake radio") logging.debug("Playing fake radio")
self._display = rx.text("Playing") # may not work self._display = rx.text("Playing")
self.playing = True self.playing = True
else: else:
self._device.on() if self._device:
self._device.on()
self.playing = True self.playing = True
def stop_radio(self): def stop_radio(self):
if self.debug: if self.debug:
logging.debug("Stopping radio") logging.debug("Stopping radio")
self._display = rx.text("Stopped") # may not work self._display = rx.text("Stopped")
self.playing = False self.playing = False
else: else:
self._device.off() if self._device:
self._device.off()
self.playing = False self.playing = False
def set_volume(self, volume): def set_volume(self, volume):
@ -81,7 +88,8 @@ class Radio_Control:
logging.debug(f"Setting volume to {volume}") logging.debug(f"Setting volume to {volume}")
self.volume = volume self.volume = volume
else: else:
self._device.set_volume(volume) if self._device:
self._device.set_volume(volume)
self.volume = volume self.volume = volume
def set_station(self, station): def set_station(self, station):
@ -89,12 +97,17 @@ class Radio_Control:
logging.debug(f"Setting station to {station}") logging.debug(f"Setting station to {station}")
self.current_station = station self.current_station = station
else: else:
self._device.set_station(station)
self.current_station = station self.current_station = station
logging.info(f"Station set to {station}") logging.info(f"Station set to {station}")
"""
## for testing chip def station_change_up(self):
# if __name__ == "__main__": if self.debug:
# radio = Radio_Control() pass
# radio.play_radio() else:
self.current_station += 0.1
def station_change_down(self):
if self.debug:
pass
else:
self.current_station -= 0.1

View file

@ -1,6 +1,6 @@
# /home/death916/code/python/deathclock/utils/scores.py # /home/death916/code/python/deathclock/utils/scores.py
import logging # Use logging for consistency import logging
from datetime import datetime, timedelta from datetime import datetime
import reflex as rx import reflex as rx
import statsapi import statsapi