Implement settings tab with config editor and error logs viewer; refactor error logging functionality

This commit is contained in:
Sudo-Ivan
2025-05-29 00:38:24 -05:00
parent 30086984de
commit b62d855e54
3 changed files with 90 additions and 30 deletions

View File

@@ -1,6 +1,8 @@
import argparse
import subprocess
import sys
import pathlib
import datetime
import flet as ft
from flet import AppView, Page
@@ -10,6 +12,12 @@ from ren_browser.ui.ui import build_ui
# Current renderer name
RENDERER = "plaintext"
ERROR_LOGS: list[str] = []
def log_error(msg: str):
timestamp = datetime.datetime.now().isoformat()
ERROR_LOGS.append(f"[{timestamp}] {msg}")
async def main(page: Page):
# Build the main UI layout
build_ui(page)
@@ -37,37 +45,44 @@ if __name__ == "__main__":
def web():
"""Launch Ren Browser in web mode via Flet CLI."""
rc = subprocess.call(["flet", "run", "ren_browser/app.py", "--web"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", str(script_path), "--web"])
sys.exit(rc)
def android():
"""Launch Ren Browser in Android mode via Flet CLI."""
rc = subprocess.call(["flet", "run", "ren_browser/app.py", "--android"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", str(script_path), "--android"])
sys.exit(rc)
def ios():
"""Launch Ren Browser in iOS mode via Flet CLI."""
rc = subprocess.call(["flet", "run", "ren_browser/app.py", "--ios"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", str(script_path), "--ios"])
sys.exit(rc)
# Hot reload (dev) mode entrypoints
def run_dev():
"""Launch Ren Browser in desktop mode via Flet CLI with hot reload."""
rc = subprocess.call(["flet", "run", "-d", "-r", "ren_browser/app.py"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", "-d", "-r", str(script_path)])
sys.exit(rc)
def web_dev():
"""Launch Ren Browser in web mode via Flet CLI with hot reload."""
rc = subprocess.call(["flet", "run", "--web", "-d", "-r", "ren_browser/app.py"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", "--web", "-d", "-r", str(script_path)])
sys.exit(rc)
def android_dev():
"""Launch Ren Browser in Android mode via Flet CLI with hot reload."""
rc = subprocess.call(["flet", "run", "--android", "-d", "-r", "ren_browser/app.py"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", "--android", "-d", "-r", str(script_path)])
sys.exit(rc)
def ios_dev():
"""Launch Ren Browser in iOS mode via Flet CLI with hot reload."""
rc = subprocess.call(["flet", "run", "--ios", "-d", "-r", "ren_browser/app.py"])
script_path = pathlib.Path(__file__).resolve()
rc = subprocess.call(["flet", "run", "--ios", "-d", "-r", str(script_path)])
sys.exit(rc)

View File

@@ -0,0 +1,63 @@
import flet as ft
import pathlib
from ren_browser.app import ERROR_LOGS
def open_settings_tab(page: ft.Page, tab_manager):
# Locate Reticulum config file
config_path = pathlib.Path(__file__).resolve().parents[2] / "config" / "config"
try:
config_text = config_path.read_text()
except Exception as ex:
config_text = f"Error reading config: {ex}"
# Config editor
config_field = ft.TextField(
label="Reticulum config",
value=config_text,
expand=True,
multiline=True,
)
# Save button handler
def on_save_config(ev):
try:
config_path.write_text(config_field.value)
page.snack_bar = ft.SnackBar(ft.Text("Config saved. Please restart the app."), open=True)
except Exception as ex:
page.snack_bar = ft.SnackBar(ft.Text(f"Error saving config: {ex}"), open=True)
page.update()
save_btn = ft.ElevatedButton("Save and Restart", on_click=on_save_config)
# Error logs viewer
error_text = "\n".join(ERROR_LOGS) or "No errors logged."
error_field = ft.TextField(
label="Error Logs",
value=error_text,
expand=True,
multiline=True,
read_only=True,
)
# Placeholder for content switching
content_placeholder = ft.Container(expand=True)
# View switch handlers
def show_config(ev):
content_placeholder.content = config_field
page.update()
def show_errors(ev):
content_placeholder.content = error_field
page.update()
btn_config = ft.ElevatedButton("Config", on_click=show_config)
btn_errors = ft.ElevatedButton("Errors", on_click=show_errors)
button_row = ft.Row(controls=[btn_config, btn_errors])
# Initialize to config view
content_placeholder.content = config_field
# Assemble settings UI
settings_content = ft.Column(
expand=True,
controls=[
button_row,
content_placeholder,
ft.Row([save_btn]),
],
)
tab_manager._add_tab_internal("Settings", settings_content)
idx = len(tab_manager.manager.tabs) - 1
tab_manager.select_tab(idx)
page.update()

View File

@@ -46,6 +46,8 @@ def build_ui(page: Page):
try:
result = page_fetcher.fetch_page(req)
except Exception as ex:
import ren_browser.app as app_module
app_module.log_error(str(ex))
result = f"Error: {ex}"
# Skip update if tab has been closed or index out of range
try:
@@ -84,29 +86,9 @@ def build_ui(page: Page):
# Dynamic tabs manager for pages
tab_manager = TabsManager(page)
def open_settings_tab(e=None):
import pathlib
config_path = pathlib.Path(__file__).resolve().parents[2] / "config" / "config"
try:
config_text = config_path.read_text()
except Exception as ex:
config_text = f"Error reading config: {ex}"
config_field = ft.TextField(label="Reticulum config", value=config_text, expand=True, multiline=True)
def on_save_config(ev):
try:
config_path.write_text(config_field.value)
page.snack_bar = ft.SnackBar(ft.Text("Config saved. Please restart the app."), open=True)
except Exception as ex:
page.snack_bar = ft.SnackBar(ft.Text(f"Error saving config: {ex}"), open=True)
page.update()
save_btn = ft.ElevatedButton("Save and Restart", on_click=on_save_config)
settings_content = ft.Column(expand=True, controls=[config_field, ft.Row([save_btn])])
tab_manager._add_tab_internal("Settings", settings_content)
idx = len(tab_manager.manager.tabs) - 1
tab_manager.select_tab(idx)
page.update()
page.appbar.actions = [ft.IconButton(ft.Icons.SETTINGS, tooltip="Settings", on_click=open_settings_tab)]
# Add Settings button using external settings module
from ren_browser.ui.settings import open_settings_tab
page.appbar.actions = [ft.IconButton(ft.Icons.SETTINGS, tooltip="Settings", on_click=lambda e: open_settings_tab(page, tab_manager))]
Shortcuts(page, tab_manager)
url_bar = ft.Row(
controls=[