From 73f651e9857712f09c1644aff2591ac540dc7ebc Mon Sep 17 00:00:00 2001 From: ChaoticByte Date: Sat, 22 Feb 2025 09:53:26 +0100 Subject: [PATCH] Add project files --- LICENSE | 2 +- dashboard/thing.py | 30 ++++++++++++++++++++++++ dashboard/ui.py | 48 ++++++++++++++++++++++++++++++++++++++ example.py | 57 ++++++++++++++++++++++++++++++++++++++++++++++ requirements.txt | 1 + 5 files changed, 137 insertions(+), 1 deletion(-) create mode 100644 dashboard/thing.py create mode 100644 dashboard/ui.py create mode 100644 example.py create mode 100644 requirements.txt diff --git a/LICENSE b/LICENSE index 7000719..ba50b01 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ BSD 3-Clause License -Copyright (c) 2025, Julian Müller +Copyright (c) 2025, Julian Müller (ChaoticByte) Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: diff --git a/dashboard/thing.py b/dashboard/thing.py new file mode 100644 index 0000000..663216e --- /dev/null +++ b/dashboard/thing.py @@ -0,0 +1,30 @@ +# Copyright (c) 2025, Julian Müller (ChaoticByte) + + +from enum import Enum + + +# base classes and types and stuff + +class SystemState(Enum): + OK = 0 + FAILED = 1 + UNKNOWN = 2 + +class System: + + def __init__(self, name: str, description: str): + self.name = name + self.description = description + self.state = SystemState.UNKNOWN + self.state_verbose = "" + + def get_actions(self) -> dict: + # to be overridden + # return {'ActionName': callable, ...} + return {} + + def update_state(self): + # to be overridden + self.state = SystemState.UNKNOWN + self.state_verbose = "" diff --git a/dashboard/ui.py b/dashboard/ui.py new file mode 100644 index 0000000..1473368 --- /dev/null +++ b/dashboard/ui.py @@ -0,0 +1,48 @@ +# Copyright (c) 2025, Julian Müller (ChaoticByte) + + +from typing import List +from .thing import System, SystemState + +from nicegui import ui + + +def init_ui(systems: List[System]): + + @ui.refreshable + def systems_list(): + with ui.column(align_items="center").style("width: 40vw; max-width: 40rem; min-width: 25rem;"): + for t in systems: + card = ui.card().classes("w-full") + if t.state == SystemState.OK: + card = card.style("border-left: 4px solid limegreen") + elif t.state == SystemState.FAILED: + card = card.style("border-left: 4px solid red") + else: + card = card.style("border-left: 4px solid dodgerblue") + + with card: + ui.label(t.name).classes("text-xl font-medium") + if t.description != "": + ui.label(t.description).classes("opacity-75") + if t.state_verbose != "": + ui.label(t.state_verbose).classes("opacity-50") + actions = t.get_actions() + if len(actions) > 0: + if t.description != "" or t.state_verbose != "": + ui.separator() + with ui.card_actions(): + for n, c in actions.items(): + ui.button(text=n, on_click=c) + + with ui.column(align_items="center").classes("w-full"): + systems_list() + + def update_states(): + for t in systems: + t.update_state() + + ui.timer(15, callback=update_states) + ui.timer(2, systems_list.refresh) + + dark = ui.dark_mode(None) # auto diff --git a/example.py b/example.py new file mode 100644 index 0000000..6415110 --- /dev/null +++ b/example.py @@ -0,0 +1,57 @@ +# Copyright (c) 2025, Julian Müller (ChaoticByte) + + +from nicegui import ui + +from dashboard.thing import System, SystemState +from dashboard.ui import init_ui + + +# define systems + + +class ExampleSystem(System): + + pressed = False + + def __init__(self, *args): + super().__init__(*args) + self.started = False + + def update_state(self): + if self.started: + self.state = SystemState.OK + self.state_verbose = f"{self.name} is currently started." + else: + self.state = SystemState.FAILED + self.state_verbose = f"{self.name} is currently stopped." + + def get_actions(self) -> dict: + if self.started: + return {"Stop": self.stop} + else: + return {"Start": self.start} + + def start(self): + self.state = SystemState.UNKNOWN + self.state_verbose = f"{self.name} is currently starting." + self.started = True + ui.notify("Starting " + self.name) + + def stop(self): + self.state = SystemState.UNKNOWN + self.state_verbose = f"{self.name} is currently stopping." + self.started = False + ui.notify("Stopping " + self.name) + +# + +systems = [ + ExampleSystem("Example System 1", "Description text ..."), + ExampleSystem("Example System 2", "Another description text ...") +] + +# + +init_ui(systems) +ui.run(show=False) diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..cdf2536 --- /dev/null +++ b/requirements.txt @@ -0,0 +1 @@ +nicegui~=2.11.1