Skip to content

Commit d956b8a

Browse files
authored
Merge pull request #1584 from Night-Hunter-NF/RequestUserAttention
add action to request user attention
2 parents 54105a2 + 6855961 commit d956b8a

6 files changed

Lines changed: 75 additions & 12 deletions

File tree

native/src/window.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,9 @@
22
mod action;
33
mod event;
44
mod mode;
5+
mod user_attention;
56

67
pub use action::Action;
78
pub use event::Event;
89
pub use mode::Mode;
10+
pub use user_attention::UserAttention;

native/src/window/action.rs

Lines changed: 25 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use crate::window::Mode;
1+
use crate::window::{Mode, UserAttention};
22

33
use iced_futures::MaybeSend;
44
use std::fmt;
@@ -35,15 +35,29 @@ pub enum Action<T> {
3535
},
3636
/// Set the [`Mode`] of the window.
3737
SetMode(Mode),
38+
/// Fetch the current [`Mode`] of the window.
39+
FetchMode(Box<dyn FnOnce(Mode) -> T + 'static>),
3840
/// Sets the window to maximized or back
3941
ToggleMaximize,
4042
/// Toggles whether window has decorations
4143
/// ## Platform-specific
4244
/// - **X11:** Not implemented.
4345
/// - **Web:** Unsupported.
4446
ToggleDecorations,
45-
/// Fetch the current [`Mode`] of the window.
46-
FetchMode(Box<dyn FnOnce(Mode) -> T + 'static>),
47+
/// Requests user attention to the window, this has no effect if the application
48+
/// is already focused. How requesting for user attention manifests is platform dependent,
49+
/// see [`UserAttentionType`] for details.
50+
///
51+
/// Providing `None` will unset the request for user attention. Unsetting the request for
52+
/// user attention might not be done automatically by the WM when the window receives input.
53+
///
54+
/// ## Platform-specific
55+
///
56+
/// - **iOS / Android / Web:** Unsupported.
57+
/// - **macOS:** `None` has no effect.
58+
/// - **X11:** Requests for user attention must be manually cleared.
59+
/// - **Wayland:** Requires `xdg_activation_v1` protocol, `None` has no effect.
60+
RequestUserAttention(Option<UserAttention>),
4761
}
4862

4963
impl<T> Action<T> {
@@ -63,9 +77,12 @@ impl<T> Action<T> {
6377
Self::Minimize(bool) => Action::Minimize(bool),
6478
Self::Move { x, y } => Action::Move { x, y },
6579
Self::SetMode(mode) => Action::SetMode(mode),
80+
Self::FetchMode(o) => Action::FetchMode(Box::new(move |s| f(o(s)))),
6681
Self::ToggleMaximize => Action::ToggleMaximize,
6782
Self::ToggleDecorations => Action::ToggleDecorations,
68-
Self::FetchMode(o) => Action::FetchMode(Box::new(move |s| f(o(s)))),
83+
Self::RequestUserAttention(attention_type) => {
84+
Action::RequestUserAttention(attention_type)
85+
}
6986
}
7087
}
7188
}
@@ -86,9 +103,12 @@ impl<T> fmt::Debug for Action<T> {
86103
write!(f, "Action::Move {{ x: {}, y: {} }}", x, y)
87104
}
88105
Self::SetMode(mode) => write!(f, "Action::SetMode({:?})", mode),
106+
Self::FetchMode(_) => write!(f, "Action::FetchMode"),
89107
Self::ToggleMaximize => write!(f, "Action::ToggleMaximize"),
90108
Self::ToggleDecorations => write!(f, "Action::ToggleDecorations"),
91-
Self::FetchMode(_) => write!(f, "Action::FetchMode"),
109+
Self::RequestUserAttention(_) => {
110+
write!(f, "Action::RequestUserAttention")
111+
}
92112
}
93113
}
94114
}
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
/// The type of user attention to request.
2+
///
3+
/// ## Platform-specific
4+
///
5+
/// - **X11:** Sets the WM's `XUrgencyHint`. No distinction between [`Critical`] and [`Informational`].
6+
///
7+
/// [`Critical`]: Self::Critical
8+
/// [`Informational`]: Self::Informational
9+
#[derive(Debug, Clone, Copy)]
10+
pub enum UserAttention {
11+
/// ## Platform-specific
12+
///
13+
/// - **macOS:** Bounces the dock icon until the application is in focus.
14+
/// - **Windows:** Flashes both the window and the taskbar button until the application is in focus.
15+
Critical,
16+
/// ## Platform-specific
17+
///
18+
/// - **macOS:** Bounces the dock icon once.
19+
/// - **Windows:** Flashes the taskbar button until the application is in focus.
20+
Informational,
21+
}

winit/src/application.rs

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -657,12 +657,6 @@ pub fn run_command<A, E>(
657657
mode,
658658
));
659659
}
660-
window::Action::ToggleMaximize => {
661-
window.set_maximized(!window.is_maximized())
662-
}
663-
window::Action::ToggleDecorations => {
664-
window.set_decorations(!window.is_decorated())
665-
}
666660
window::Action::FetchMode(tag) => {
667661
let mode = if window.is_visible().unwrap_or(true) {
668662
conversion::mode(window.fullscreen())
@@ -674,6 +668,16 @@ pub fn run_command<A, E>(
674668
.send_event(tag(mode))
675669
.expect("Send message to event loop");
676670
}
671+
window::Action::ToggleMaximize => {
672+
window.set_maximized(!window.is_maximized())
673+
}
674+
window::Action::ToggleDecorations => {
675+
window.set_decorations(!window.is_decorated())
676+
}
677+
window::Action::RequestUserAttention(user_attention) => window
678+
.request_user_attention(
679+
user_attention.map(conversion::user_attention),
680+
),
677681
},
678682
command::Action::System(action) => match action {
679683
system::Action::QueryInformation(_tag) => {

winit/src/conversion.rs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -493,6 +493,22 @@ pub fn key_code(
493493
}
494494
}
495495

496+
/// Converts some [`UserAttention`] into it's `winit` counterpart.
497+
///
498+
/// [`UserAttention`]: window::UserAttention
499+
pub fn user_attention(
500+
user_attention: window::UserAttention,
501+
) -> winit::window::UserAttentionType {
502+
match user_attention {
503+
window::UserAttention::Critical => {
504+
winit::window::UserAttentionType::Critical
505+
}
506+
window::UserAttention::Informational => {
507+
winit::window::UserAttentionType::Informational
508+
}
509+
}
510+
}
511+
496512
// As defined in: http://www.unicode.org/faq/private_use.html
497513
pub(crate) fn is_private_use_character(c: char) -> bool {
498514
matches!(

winit/src/window.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
use crate::command::{self, Command};
33
use iced_native::window;
44

5-
pub use window::{Event, Mode};
5+
pub use window::{Event, Mode, UserAttention};
66

77
/// Closes the current window and exits the application.
88
pub fn close<Message>() -> Command<Message> {

0 commit comments

Comments
 (0)