From 6cf4c1fe8fbfbc9866f6d37e02f4ff19dad8ded2 Mon Sep 17 00:00:00 2001 From: galister <22305755+galister@users.noreply.github.com> Date: Sat, 10 Jan 2026 04:10:39 +0900 Subject: [PATCH] custom panel icons --- wayvr/src/assets/gui/keyboard.xml | 2 +- wayvr/src/gui/panel/mod.rs | 9 ++++--- wayvr/src/gui/panel/overlay_list.rs | 13 ++++++++-- wayvr/src/overlays/custom.rs | 37 +++++++++++++++++++++++++---- wlx-common/src/overlays.rs | 2 +- 5 files changed, 52 insertions(+), 11 deletions(-) diff --git a/wayvr/src/assets/gui/keyboard.xml b/wayvr/src/assets/gui/keyboard.xml index 6378a1b..be35e18 100644 --- a/wayvr/src/assets/gui/keyboard.xml +++ b/wayvr/src/assets/gui/keyboard.xml @@ -141,7 +141,7 @@ diff --git a/wayvr/src/gui/panel/mod.rs b/wayvr/src/gui/panel/mod.rs index 519294b..88fe379 100644 --- a/wayvr/src/gui/panel/mod.rs +++ b/wayvr/src/gui/panel/mod.rs @@ -1,8 +1,9 @@ -use std::{cell::RefCell, rc::Rc}; +use std::{cell::RefCell, collections::HashMap, rc::Rc}; use anyhow::Context; use button::setup_custom_button; use glam::{Affine2, Vec2, vec2}; +use idmap::IdMap; use label::setup_custom_label; use wgui::{ assets::AssetPath, @@ -67,6 +68,7 @@ pub struct GuiPanel { pub on_notify: Option>, pub initialized: bool, pub doc_extra: Option, + pub extra_attribs: IdMap, interaction_transform: Option, context: WguiContext, timestep: Timestep, @@ -182,6 +184,7 @@ impl GuiPanel { last_content_size: Vec2::ZERO, doc_extra: Some(doc_params.extra), custom_elems, + extra_attribs: Default::default(), context_menu: Default::default(), on_custom_attrib: params.on_custom_attrib, on_custom_attrib_inner, @@ -443,8 +446,8 @@ impl OverlayBackend for GuiPanel { fn get_interaction_transform(&mut self) -> Option { self.interaction_transform } - fn get_attrib(&self, _attrib: BackendAttrib) -> Option { - None + fn get_attrib(&self, attrib: BackendAttrib) -> Option { + self.extra_attribs.get(&attrib).cloned() } fn set_attrib(&mut self, _app: &mut AppState, _value: BackendAttribValue) -> bool { false diff --git a/wayvr/src/gui/panel/overlay_list.rs b/wayvr/src/gui/panel/overlay_list.rs index caa08ce..bf8ea98 100644 --- a/wayvr/src/gui/panel/overlay_list.rs +++ b/wayvr/src/gui/panel/overlay_list.rs @@ -14,7 +14,7 @@ use crate::windowing::{OverlayID, backend::OverlayEventData, window::OverlayCate /// Helper for managing a list of overlays /// Populates `id="panels_root"` with ``, ``, `` templates /// Populates `id="apps_root"` with `` templates (optional) -/// Uses the following parameters: `name` (All), `display` (Screen, Mirror), `icon` (App) +/// Uses the following parameters: `name` (All), `display` (Screen, Mirror), `icon` (App, Panel) pub struct OverlayList { overlay_buttons: SecondaryMap>, } @@ -63,7 +63,16 @@ impl OverlayList { ); ("Mirror", panels_root) } - OverlayCategory::Panel => ("Panel", panels_root), + OverlayCategory::Panel => { + let icon: Rc = if let Some(icon) = meta.icon.as_ref() { + icon.to_string().into() + } else { + "edit/panel.svg".into() + }; + + params.insert("icon".into(), icon); + ("Panel", panels_root) + } OverlayCategory::WayVR => { params.insert( "icon".into(), diff --git a/wayvr/src/overlays/custom.rs b/wayvr/src/overlays/custom.rs index 986fa9f..ee43ce9 100644 --- a/wayvr/src/overlays/custom.rs +++ b/wayvr/src/overlays/custom.rs @@ -1,7 +1,14 @@ -use std::{sync::Arc, time::Duration}; +use std::{ + sync::{Arc, LazyLock}, + time::Duration, +}; use glam::{Affine3A, Quat, Vec3, vec3}; -use wlx_common::windowing::OverlayWindowState; +use regex::Regex; +use wlx_common::{ + overlays::{BackendAttrib, BackendAttribValue}, + windowing::OverlayWindowState, +}; use crate::{ gui::{ @@ -15,7 +22,22 @@ use crate::{ }, }; -struct CustomPanelState {} +static ENV_VAR_REGEX: LazyLock = LazyLock::new(|| { + Regex::new(r"\$\{([A-Z_][A-Z0-9_]*)}|\$([A-Z_][A-Z0-9_]*)").unwrap() // want panic +}); + +pub(super) fn expand_env_vars(template: &str) -> String { + ENV_VAR_REGEX + .replace_all(template, |caps: ®ex::Captures| { + let var_name = caps.get(1).or_else(|| caps.get(2)).unwrap().as_str(); + std::env::var(var_name) + .inspect_err(|e| log::warn!("Unable to substitute env var {var_name}: {e:?}")) + .unwrap_or_default() + }) + .into_owned() +} + +struct CustomPanelState; pub fn create_custom(app: &mut AppState, name: Arc) -> Option { let params = NewGuiPanelParams { @@ -24,10 +46,17 @@ pub fn create_custom(app: &mut AppState, name: Arc) -> Option