mirror of
https://github.com/BetterCorp/BetterFrame.git
synced 2026-05-26 16:56:33 +00:00
- All bundle struct ID fields (kiosk_id, display_id, layout_id, camera_id, stream_id, gpio_id) now String with de_flexible_id deserializer accepting both JSON numbers and strings. - PoolKey, DisplayState hashmap, WorkerMsg, ServerMsg all use String IDs throughout. Zero u32 ID references remain. - ONVIF event image proxy: kiosk detects PictureUri in event data, downloads image from camera (basic/digest auth), base64 encodes, attaches to event payload before forwarding to server. - Add md5 crate for HTTP Digest auth on camera image fetch. - ws_client: flexible_id_from_value helper for WS message ID parsing. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
71 lines
2 KiB
Rust
71 lines
2 KiB
Rust
mod at_rest;
|
|
mod axiom;
|
|
mod bundle;
|
|
mod cec;
|
|
mod firmware;
|
|
mod gpio;
|
|
mod hwmon;
|
|
mod local_server;
|
|
mod onvif_events;
|
|
mod os_update;
|
|
mod pipeline;
|
|
mod remote_debug;
|
|
mod server;
|
|
mod ui;
|
|
mod ws_client;
|
|
|
|
pub use ui::WorkerMsg;
|
|
|
|
pub enum ServerMsg {
|
|
ReloadBundle,
|
|
Standby(Option<String>),
|
|
Wake(Option<String>),
|
|
/// Some(0..=255) = manual PWM. None = restore auto.
|
|
Fan(Option<u32>),
|
|
/// Switch to a specific layout by ID, optionally scoped to one display.
|
|
SwitchLayout {
|
|
display_id: Option<String>,
|
|
layout_id: String,
|
|
},
|
|
/// Server-pushed "go check for a firmware update now".
|
|
FirmwareCheck,
|
|
/// Server-pushed "go check for an OS update now".
|
|
OsCheck,
|
|
/// Show terminal auth code on screen (overlay).
|
|
ShowTerminalCode(String),
|
|
/// Dismiss the terminal code overlay.
|
|
DismissTerminalCode,
|
|
}
|
|
|
|
use gstreamer::prelude::PluginFeatureExtManual;
|
|
use gtk4::prelude::{ApplicationExt, ApplicationExtManual};
|
|
use tracing::info;
|
|
use tracing_subscriber::{EnvFilter, layer::SubscriberExt, util::SubscriberInitExt};
|
|
|
|
fn main() {
|
|
let env_filter = EnvFilter::from_default_env()
|
|
.add_directive("betterframe_kiosk=info".parse().unwrap());
|
|
|
|
let registry = tracing_subscriber::registry()
|
|
.with(env_filter)
|
|
.with(tracing_subscriber::fmt::layer());
|
|
|
|
if let Some(axiom_layer) = axiom::AxiomLayer::new() {
|
|
info!("axiom logging enabled");
|
|
registry.with(axiom_layer).init();
|
|
} else {
|
|
registry.init();
|
|
}
|
|
|
|
gstreamer::init().expect("Failed to init GStreamer");
|
|
|
|
// Demote Pi5 hw H265 decoder — rejects non-standard resolutions like 960x1080
|
|
if let Some(factory) = gstreamer::ElementFactory::find("v4l2slh265dec") {
|
|
factory.set_rank(gstreamer::Rank::NONE);
|
|
info!("demoted v4l2slh265dec to NONE (sw fallback)");
|
|
}
|
|
let app = ui::build_app();
|
|
// Pass empty args to GTK — server URL handled via env or argv directly
|
|
app.set_flags(gtk4::gio::ApplicationFlags::NON_UNIQUE);
|
|
std::process::exit(app.run_with_args::<&str>(&[]).into());
|
|
}
|