From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: <pdm-devel-bounces@lists.proxmox.com> Received: from firstgate.proxmox.com (firstgate.proxmox.com [212.224.123.68]) by lore.proxmox.com (Postfix) with ESMTPS id C9AC91FF172 for <inbox@lore.proxmox.com>; Wed, 16 Apr 2025 13:49:35 +0200 (CEST) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id 96B6334EDE; Wed, 16 Apr 2025 13:49:31 +0200 (CEST) From: Dominik Csapak <d.csapak@proxmox.com> To: pdm-devel@lists.proxmox.com Date: Wed, 16 Apr 2025 13:49:22 +0200 Message-Id: <20250416114925.2589063-5-d.csapak@proxmox.com> X-Mailer: git-send-email 2.39.5 In-Reply-To: <20250416114925.2589063-1-d.csapak@proxmox.com> References: <20250416114925.2589063-1-d.csapak@proxmox.com> MIME-Version: 1.0 X-SPAM-LEVEL: Spam detection results: 0 AWL 0.022 Adjusted score from AWL reputation of From: address BAYES_00 -1.9 Bayes spam probability is 0 to 1% DMARC_MISSING 0.1 Missing DMARC policy KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_PASS -0.001 SPF: sender matches SPF record Subject: [pdm-devel] [PATCH datacenter-manager 4/7] ui: add possibility to insert into search box X-BeenThere: pdm-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox Datacenter Manager development discussion <pdm-devel.lists.proxmox.com> List-Unsubscribe: <https://lists.proxmox.com/cgi-bin/mailman/options/pdm-devel>, <mailto:pdm-devel-request@lists.proxmox.com?subject=unsubscribe> List-Archive: <http://lists.proxmox.com/pipermail/pdm-devel/> List-Post: <mailto:pdm-devel@lists.proxmox.com> List-Help: <mailto:pdm-devel-request@lists.proxmox.com?subject=help> List-Subscribe: <https://lists.proxmox.com/cgi-bin/mailman/listinfo/pdm-devel>, <mailto:pdm-devel-request@lists.proxmox.com?subject=subscribe> Reply-To: Proxmox Datacenter Manager development discussion <pdm-devel@lists.proxmox.com> Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: pdm-devel-bounces@lists.proxmox.com Sender: "pdm-devel" <pdm-devel-bounces@lists.proxmox.com> by implementing a 'SearchProvider' context. This enables us to insert a search term from everywhere. This can be helpful e.g. if we want to prefill the search box with a specific pattern Signed-off-by: Dominik Csapak <d.csapak@proxmox.com> --- ui/Cargo.toml | 1 + ui/src/lib.rs | 3 +++ ui/src/main.rs | 17 ++++++++++++----- ui/src/search_provider.rs | 35 +++++++++++++++++++++++++++++++++++ ui/src/widget/search_box.rs | 26 +++++++++++++++++++++----- 5 files changed, 72 insertions(+), 10 deletions(-) create mode 100644 ui/src/search_provider.rs diff --git a/ui/Cargo.toml b/ui/Cargo.toml index 10345a2..96fd07e 100644 --- a/ui/Cargo.toml +++ b/ui/Cargo.toml @@ -42,6 +42,7 @@ pbs-api-types = "0.2.0" pdm-api-types = { version = "0.1", path = "../lib/pdm-api-types" } pdm-ui-shared = { version = "0.1", path = "../lib/pdm-ui-shared" } pdm-client = { version = "0.1", path = "../lib/pdm-client" } +pdm-search = { version = "0.1", path = "../lib/pdm-search" } [patch.crates-io] # proxmox-client = { path = "../../proxmox/proxmox-client" } diff --git a/ui/src/lib.rs b/ui/src/lib.rs index e3755ec..edb50f9 100644 --- a/ui/src/lib.rs +++ b/ui/src/lib.rs @@ -21,6 +21,9 @@ pub use remotes::RemoteConfigPanel; mod top_nav_bar; pub use top_nav_bar::TopNavBar; +mod search_provider; +pub use search_provider::SearchProvider; + mod dashboard; pub use dashboard::Dashboard; use yew_router::prelude::RouterScopeExt; diff --git a/ui/src/main.rs b/ui/src/main.rs index 6e2c9b2..be0c10c 100644 --- a/ui/src/main.rs +++ b/ui/src/main.rs @@ -22,7 +22,7 @@ use proxmox_yew_comp::{ //use pbs::MainMenu; use pdm_api_types::subscription::{RemoteSubscriptionState, RemoteSubscriptions}; -use pdm_ui::{register_pve_tasks, MainMenu, RemoteList, TopNavBar}; +use pdm_ui::{register_pve_tasks, MainMenu, RemoteList, SearchProvider, TopNavBar}; type MsgRemoteList = Result<RemoteList, Error>; @@ -46,6 +46,7 @@ struct DatacenterManagerApp { remote_list: RemoteList, remote_list_error: Option<String>, remote_list_timeout: Option<Timeout>, + search_provider: SearchProvider, } async fn check_subscription() -> Msg { @@ -166,6 +167,7 @@ impl Component for DatacenterManagerApp { remote_list: Vec::new().into(), remote_list_error: None, remote_list_timeout: None, + search_provider: SearchProvider::new(), }; this.on_login(ctx, false); @@ -258,10 +260,15 @@ impl Component for DatacenterManagerApp { .with_optional_child(subscription_alert); let context = self.remote_list.clone(); - - DesktopApp::new( - html! {<ContextProvider<RemoteList> {context}>{body}</ContextProvider<RemoteList>>}, - ) + let search_context = self.search_provider.clone(); + + DesktopApp::new(html! { + <ContextProvider<SearchProvider> context={search_context}> + <ContextProvider<RemoteList> {context}> + {body} + </ContextProvider<RemoteList>> + </ContextProvider<SearchProvider>> + }) .into() } } diff --git a/ui/src/search_provider.rs b/ui/src/search_provider.rs new file mode 100644 index 0000000..441cc2b --- /dev/null +++ b/ui/src/search_provider.rs @@ -0,0 +1,35 @@ +use yew::Callback; + +use pwt::state::{SharedState, SharedStateObserver}; + +use pdm_search::Search; + +#[derive(Clone, PartialEq)] +pub struct SearchProvider { + state: SharedState<String>, +} + +impl SearchProvider { + pub fn new() -> Self { + Self { + state: SharedState::new("".into()), + } + } + + pub fn add_listener( + &self, + cb: impl Into<Callback<SharedState<String>>>, + ) -> SharedStateObserver<String> { + self.state.add_listener(cb) + } + + pub fn search(&self, search_term: Search) { + **self.state.write() = search_term.to_string(); + } +} + +pub fn get_search_provider<T: yew::Component>(ctx: &yew::Context<T>) -> Option<SearchProvider> { + let (provider, _context_listener) = ctx.link().context(Callback::from(|_| {}))?; + + Some(provider) +} diff --git a/ui/src/widget/search_box.rs b/ui/src/widget/search_box.rs index 0aeedb7..6b2478f 100644 --- a/ui/src/widget/search_box.rs +++ b/ui/src/widget/search_box.rs @@ -9,13 +9,15 @@ use yew::{ }; use pwt::{ - dom::focus::FocusTracker, - dom::IntoHtmlElement, + dom::{focus::FocusTracker, IntoHtmlElement}, prelude::*, props::CssLength, + state::{SharedState, SharedStateObserver}, widget::{form::Field, Container}, }; +use crate::search_provider::get_search_provider; + use super::ResourceTree; #[derive(Properties, PartialEq)] @@ -35,7 +37,7 @@ impl From<SearchBox> for VNode { } pub enum Msg { - ChangeTerm(String), + ChangeTerm(String, bool), // force value FocusChange(bool), ToggleFocus, } @@ -48,6 +50,8 @@ pub struct PdmSearchBox { focus: bool, global_shortcut_listener: Closure<dyn Fn(KeyboardEvent)>, toggle_focus: bool, + _observer: Option<SharedStateObserver<String>>, + force_value: bool, } impl Component for PdmSearchBox { @@ -57,6 +61,14 @@ impl Component for PdmSearchBox { fn create(ctx: &yew::Context<Self>) -> Self { let link = ctx.link().clone(); + let _observer = get_search_provider(ctx).map(|search| { + search.add_listener(ctx.link().batch_callback(|value: SharedState<String>| { + vec![ + Msg::ToggleFocus, + Msg::ChangeTerm(value.read().clone(), true), + ] + })) + }); Self { search_field_ref: Default::default(), search_box_ref: Default::default(), @@ -72,13 +84,16 @@ impl Component for PdmSearchBox { _ => {} } })), + _observer, + force_value: false, } } fn update(&mut self, _ctx: &Context<Self>, msg: Self::Message) -> bool { match msg { - Msg::ChangeTerm(term) => { + Msg::ChangeTerm(term, force_value) => { self.search_term = term; + self.force_value = force_value; true } Msg::FocusChange(focus) => { @@ -122,7 +137,8 @@ impl Component for PdmSearchBox { Field::new() .placeholder(tr!("Search (Ctrl+Space / Ctrl+Shift+F)")) .node_ref(self.search_field_ref.clone()) - .on_input(ctx.link().callback(Msg::ChangeTerm)), + .value(self.force_value.then_some(self.search_term.clone())) + .on_input(ctx.link().callback(|term| Msg::ChangeTerm(term, false))), ) .with_child(search_result) .into() -- 2.39.5 _______________________________________________ pdm-devel mailing list pdm-devel@lists.proxmox.com https://lists.proxmox.com/cgi-bin/mailman/listinfo/pdm-devel