From 87cc20fa0501ee6589224753c46d18a72d2a9e76 Mon Sep 17 00:00:00 2001 From: Jason Lee Date: Tue, 1 Oct 2024 14:20:24 +0800 Subject: [PATCH] gpui: Fix `hide`, `activate` method on Windows to hide/show application (#18164) Release Notes: - N/A Continue #18161 to fix `cx.hide`, `cx.activate` method on Windows to hide/show application. ## After https://github.com/user-attachments/assets/fe0070f9-7844-4c2a-b859-3e22ee4b8d22 --------- Co-authored-by: Mikayla Maki --- crates/gpui/examples/window.rs | 12 ++++++++++ crates/gpui/src/platform/windows/platform.rs | 24 ++++++++++++++++---- 2 files changed, 32 insertions(+), 4 deletions(-) diff --git a/crates/gpui/examples/window.rs b/crates/gpui/examples/window.rs index 0f0d4287da723f..78a47782c956a8 100644 --- a/crates/gpui/examples/window.rs +++ b/crates/gpui/examples/window.rs @@ -150,6 +150,18 @@ impl Render for WindowDemo { ) .unwrap(); })) + .child(button("Hide Application", |cx| { + cx.hide(); + + // Restore the application after 3 seconds + cx.spawn(|mut cx| async move { + Timer::after(std::time::Duration::from_secs(3)).await; + cx.update(|cx| { + cx.activate(false); + }) + }) + .detach(); + })) } } diff --git a/crates/gpui/src/platform/windows/platform.rs b/crates/gpui/src/platform/windows/platform.rs index 30e7c402d26d85..7f6677973b2fbd 100644 --- a/crates/gpui/src/platform/windows/platform.rs +++ b/crates/gpui/src/platform/windows/platform.rs @@ -33,6 +33,8 @@ use crate::*; pub(crate) struct WindowsPlatform { state: RefCell, raw_window_handles: RwLock>, + // The window handles that are hided by `hide` method. + hidden_windows: RwLock>, // The below members will never change throughout the entire lifecycle of the app. icon: HICON, main_receiver: flume::Receiver, @@ -100,6 +102,7 @@ impl WindowsPlatform { Self { state, raw_window_handles, + hidden_windows: RwLock::new(SmallVec::new()), icon, main_receiver, dispatch_event, @@ -295,12 +298,25 @@ impl Platform for WindowsPlatform { } } - // todo(windows) - fn activate(&self, _ignoring_other_apps: bool) {} + fn activate(&self, _ignoring_other_apps: bool) { + let mut state = self.hidden_windows.write(); + state.iter().for_each(|handle| unsafe { + ShowWindow(*handle, SW_SHOW).ok().log_err(); + }); + state.clear(); + } - // todo(windows) fn hide(&self) { - unimplemented!() + let mut state = self.hidden_windows.write(); + self.raw_window_handles + .read() + .iter() + .for_each(|handle| unsafe { + if IsWindowVisible(*handle).as_bool() { + state.push(*handle); + ShowWindow(*handle, SW_HIDE).ok().log_err(); + } + }); } // todo(windows)