From 2ce9572fa0d2e5c031d82ee86eb30224df22e7bd Mon Sep 17 00:00:00 2001 From: Mads Marquart Date: Wed, 30 Aug 2023 12:55:32 +0200 Subject: [PATCH] Refactor window errors --- src/error.rs | 69 ------------- src/platform/startup_notify.rs | 29 +++++- src/platform_impl/android/mod.rs | 48 ++++----- src/platform_impl/ios/window.rs | 27 +++--- src/platform_impl/linux/mod.rs | 22 +++-- src/platform_impl/linux/wayland/window/mod.rs | 23 ++--- .../linux/wayland/window/state.rs | 21 ++-- src/platform_impl/linux/x11/window.rs | 57 ++++++----- src/platform_impl/macos/window.rs | 27 +++--- src/platform_impl/orbital/window.rs | 40 +++----- src/platform_impl/web/window.rs | 29 +++--- src/platform_impl/windows/window.rs | 24 ++--- src/window.rs | 97 ++++++++++++++++--- 13 files changed, 259 insertions(+), 254 deletions(-) diff --git a/src/error.rs b/src/error.rs index 8e76955ea9..84d5263f74 100644 --- a/src/error.rs +++ b/src/error.rs @@ -2,22 +2,6 @@ use std::{error, fmt}; use crate::platform_impl; -// TODO: Rename -/// An error that may be generated when requesting Winit state -#[derive(Debug)] -pub enum ExternalError { - /// The operation is not supported by the backend. - NotSupported(NotSupportedError), - /// The OS cannot perform the operation. - Os(OsError), -} - -/// The error type for when the requested operation is not supported by the backend. -#[derive(Clone)] -pub struct NotSupportedError { - _marker: (), -} - /// The error type for when the OS cannot perform the requested operation. #[derive(Debug)] pub struct OsError { @@ -26,14 +10,6 @@ pub struct OsError { error: platform_impl::OsError, } -impl NotSupportedError { - #[inline] - #[allow(dead_code)] - pub(crate) fn new() -> NotSupportedError { - NotSupportedError { _marker: () } - } -} - impl OsError { #[allow(dead_code)] pub(crate) fn new(line: u32, file: &'static str, error: platform_impl::OsError) -> OsError { @@ -57,49 +33,4 @@ impl fmt::Display for OsError { } } -impl fmt::Display for ExternalError { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { - match self { - ExternalError::NotSupported(e) => e.fmt(f), - ExternalError::Os(e) => e.fmt(f), - } - } -} - -impl fmt::Debug for NotSupportedError { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { - f.debug_struct("NotSupportedError").finish() - } -} - -impl fmt::Display for NotSupportedError { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { - f.pad("the requested operation is not supported by Winit") - } -} - impl error::Error for OsError {} -impl error::Error for ExternalError {} -impl error::Error for NotSupportedError {} - -#[cfg(test)] -mod tests { - #![allow(clippy::redundant_clone)] - - use super::*; - - // Eat attributes for testing - #[test] - fn ensure_fmt_does_not_panic() { - let _ = format!( - "{:?}, {}", - NotSupportedError::new(), - NotSupportedError::new().clone() - ); - let _ = format!( - "{:?}, {}", - ExternalError::NotSupported(NotSupportedError::new()), - ExternalError::NotSupported(NotSupportedError::new()) - ); - } -} diff --git a/src/platform/startup_notify.rs b/src/platform/startup_notify.rs index 2548be98be..03ac8ccf9d 100644 --- a/src/platform/startup_notify.rs +++ b/src/platform/startup_notify.rs @@ -22,8 +22,9 @@ //! [`here`]: https://specifications.freedesktop.org/startup-notification-spec/startup-notification-latest.txt use std::env; +use std::error::Error; +use std::fmt; -use crate::error::NotSupportedError; use crate::event_loop::{AsyncRequestSerial, EventLoopWindowTarget}; use crate::window::{ActivationToken, Window, WindowBuilder}; @@ -33,6 +34,28 @@ const X11_VAR: &str = "DESKTOP_STARTUP_ID"; /// The variable which is used mostly on Wayland. const WAYLAND_VAR: &str = "XDG_ACTIVATION_TOKEN"; +/// The error type for when the requested operation is not supported by the backend. +#[derive(Debug)] +pub struct ActivationTokenNotFound { + _marker: (), +} + +impl fmt::Display for ActivationTokenNotFound { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { + write!(f, "the requested operation is not supported by Winit") + } +} + +impl ActivationTokenNotFound { + #[inline] + #[allow(dead_code)] + pub(crate) fn new() -> ActivationTokenNotFound { + ActivationTokenNotFound { _marker: () } + } +} + +impl Error for ActivationTokenNotFound {} + pub trait EventLoopExtStartupNotify { /// Read the token from the environment. /// @@ -44,7 +67,7 @@ pub trait WindowExtStartupNotify { /// Request a new activation token. /// /// The token will be delivered inside - fn request_activation_token(&self) -> Result; + fn request_activation_token(&self) -> Result; } pub trait WindowBuilderExtStartupNotify { @@ -69,7 +92,7 @@ impl EventLoopExtStartupNotify for EventLoopWindowTarget { } impl WindowExtStartupNotify for Window { - fn request_activation_token(&self) -> Result { + fn request_activation_token(&self) -> Result { self.window.request_activation_token() } } diff --git a/src/platform_impl/android/mod.rs b/src/platform_impl/android/mod.rs index 7a518fdf0d..9cdfe2afb3 100644 --- a/src/platform_impl/android/mod.rs +++ b/src/platform_impl/android/mod.rs @@ -22,7 +22,7 @@ use raw_window_handle::{ use crate::platform_impl::Fullscreen; use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error, + error::OsError as RootOsError, event::{self, InnerSizeWriter, StartCause}, event_loop::{ self, ControlFlow, EventLoopCreationError, EventLoopRunError, @@ -30,7 +30,8 @@ use crate::{ }, platform::pump_events::PumpStatus, window::{ - self, CursorGrabMode, ImePurpose, ResizeDirection, Theme, WindowButtons, WindowLevel, + self, CursorGrabMode, ImePurpose, NotSupportedError, ResizeDirection, Theme, WindowButtons, + WindowError, WindowLevel, }, }; @@ -794,7 +795,7 @@ impl Window { el: &EventLoopWindowTarget, _window_attrs: window::WindowAttributes, _: PlatformSpecificWindowBuilderAttributes, - ) -> Result { + ) -> Result { // FIXME this ignores requested window attributes Ok(Self { @@ -839,12 +840,12 @@ impl Window { pub fn pre_present_notify(&self) {} - pub fn inner_position(&self) -> Result, error::NotSupportedError> { - Err(error::NotSupportedError::new()) + pub fn inner_position(&self) -> Result, NotSupportedError> { + Err(NotSupportedError::new()) } - pub fn outer_position(&self) -> Result, error::NotSupportedError> { - Err(error::NotSupportedError::new()) + pub fn outer_position(&self) -> Result, NotSupportedError> { + Err(NotSupportedError::new()) } pub fn set_outer_position(&self, _position: Position) { @@ -937,39 +938,26 @@ impl Window { pub fn set_cursor_icon(&self, _: window::CursorIcon) {} - pub fn set_cursor_position(&self, _: Position) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_position(&self, _: Position) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn set_cursor_grab(&self, _: CursorGrabMode) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_grab(&self, _: CursorGrabMode) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } pub fn set_cursor_visible(&self, _: bool) {} - pub fn drag_window(&self) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn drag_window(&self) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn drag_resize_window( - &self, - _direction: ResizeDirection, - ) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } pub fn raw_window_handle(&self) -> RawWindowHandle { diff --git a/src/platform_impl/ios/window.rs b/src/platform_impl/ios/window.rs index 336d0191f6..45991892d5 100644 --- a/src/platform_impl/ios/window.rs +++ b/src/platform_impl/ios/window.rs @@ -13,7 +13,7 @@ use super::uikit::{UIApplication, UIScreen, UIScreenOverscanCompensation}; use super::view::{WinitUIWindow, WinitView, WinitViewController}; use crate::{ dpi::{self, LogicalPosition, LogicalSize, PhysicalPosition, PhysicalSize, Position, Size}, - error::{ExternalError, NotSupportedError, OsError as RootOsError}, + error::OsError as RootOsError, event::{Event, WindowEvent}, icon::Icon, platform::ios::{ScreenEdge, ValidOrientations}, @@ -21,8 +21,9 @@ use crate::{ app_state, monitor, EventLoopWindowTarget, Fullscreen, MonitorHandle, }, window::{ - CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, WindowId as RootWindowId, WindowLevel, + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, WindowId as RootWindowId, + WindowLevel, }, }; @@ -174,28 +175,28 @@ impl Inner { debug!("`Window::set_cursor_icon` ignored on iOS") } - pub fn set_cursor_position(&self, _position: Position) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_position(&self, _position: Position) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn set_cursor_grab(&self, _: CursorGrabMode) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_grab(&self, _: CursorGrabMode) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } pub fn set_cursor_visible(&self, _visible: bool) { debug!("`Window::set_cursor_visible` is ignored on iOS") } - pub fn drag_window(&self) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn drag_window(&self) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } - pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } pub fn set_minimized(&self, _minimized: bool) { diff --git a/src/platform_impl/linux/mod.rs b/src/platform_impl/linux/mod.rs index 848476d1e1..ee5e6901af 100644 --- a/src/platform_impl/linux/mod.rs +++ b/src/platform_impl/linux/mod.rs @@ -14,11 +14,12 @@ use once_cell::sync::Lazy; use raw_window_handle::{RawDisplayHandle, RawWindowHandle}; use smol_str::SmolStr; +use crate::platform::startup_notify::ActivationTokenNotFound; #[cfg(x11_platform)] use crate::platform::x11::XlibErrorHook; use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error::{ExternalError, NotSupportedError, OsError as RootOsError}, + error::OsError as RootOsError, event::{Event, KeyEvent}, event_loop::{ AsyncRequestSerial, ControlFlow, DeviceEvents, EventLoopClosed, EventLoopCreationError, @@ -31,8 +32,9 @@ use crate::{ scancode::KeyCodeExtScancode, }, window::{ - ActivationToken, CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, - UserAttentionType, WindowAttributes, WindowButtons, WindowLevel, + ActivationToken, CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, + ResizeDirection, Theme, UserAttentionType, WindowAttributes, WindowButtons, WindowError, + WindowLevel, }, }; #[cfg(x11_platform)] @@ -375,7 +377,9 @@ impl Window { } #[inline] - pub(crate) fn request_activation_token(&self) -> Result { + pub(crate) fn request_activation_token( + &self, + ) -> Result { x11_or_wayland!(match self; Window(w) => w.request_activation_token()) } @@ -425,7 +429,7 @@ impl Window { } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { x11_or_wayland!(match self; Window(window) => window.set_cursor_grab(mode)) } @@ -435,17 +439,17 @@ impl Window { } #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { x11_or_wayland!(match self; Window(window) => window.drag_window()) } #[inline] - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { x11_or_wayland!(match self; Window(window) => window.drag_resize_window(direction)) } #[inline] - pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), ExternalError> { + pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), WindowError> { x11_or_wayland!(match self; Window(w) => w.set_cursor_hittest(hittest)) } @@ -455,7 +459,7 @@ impl Window { } #[inline] - pub fn set_cursor_position(&self, position: Position) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, position: Position) -> Result<(), WindowError> { x11_or_wayland!(match self; Window(w) => w.set_cursor_position(position)) } diff --git a/src/platform_impl/linux/wayland/window/mod.rs b/src/platform_impl/linux/wayland/window/mod.rs index 14085808fe..68e464e1f0 100644 --- a/src/platform_impl/linux/wayland/window/mod.rs +++ b/src/platform_impl/linux/wayland/window/mod.rs @@ -20,16 +20,17 @@ use sctk::shell::xdg::window::WindowDecorations; use sctk::shell::WaylandSurface; use crate::dpi::{LogicalSize, PhysicalPosition, PhysicalSize, Position, Size}; -use crate::error::{ExternalError, NotSupportedError, OsError as RootOsError}; +use crate::error::OsError as RootOsError; use crate::event::{Ime, WindowEvent}; use crate::event_loop::AsyncRequestSerial; +use crate::platform::startup_notify::ActivationTokenNotFound; use crate::platform_impl::{ Fullscreen, MonitorHandle as PlatformMonitorHandle, OsError, PlatformSpecificWindowBuilderAttributes as PlatformAttributes, }; use crate::window::{ - CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, }; use super::event_loop::sink::EventSink; @@ -376,7 +377,7 @@ impl Window { } #[inline] - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { self.window_state .lock() .unwrap() @@ -527,10 +528,10 @@ impl Window { xdg_activation_token.commit(); } - pub fn request_activation_token(&self) -> Result { + pub fn request_activation_token(&self) -> Result { let xdg_activation = match self.xdg_activation.as_ref() { Some(xdg_activation) => xdg_activation, - None => return Err(NotSupportedError::new()), + None => return Err(ActivationTokenNotFound::new()), }; let serial = AsyncRequestSerial::get(); @@ -544,12 +545,12 @@ impl Window { } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { self.window_state.lock().unwrap().set_cursor_grab(mode) } #[inline] - pub fn set_cursor_position(&self, position: Position) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, position: Position) -> Result<(), WindowError> { let scale_factor = self.scale_factor(); let position = position.to_logical(scale_factor); self.window_state @@ -561,12 +562,12 @@ impl Window { } #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { self.window_state.lock().unwrap().drag_window() } #[inline] - pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), ExternalError> { + pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), WindowError> { let surface = self.window.wl_surface(); if hittest { @@ -574,7 +575,7 @@ impl Window { Ok(()) } else { let region = Region::new(&*self.compositor).map_err(|_| { - ExternalError::Os(os_error!(OsError::Misc("failed to set input region."))) + WindowError::Os(os_error!(OsError::Misc("failed to set input region."))) })?; region.add(0, 0, 0, 0); surface.set_input_region(Some(region.wl_region())); diff --git a/src/platform_impl/linux/wayland/window/state.rs b/src/platform_impl/linux/wayland/window/state.rs index abe8887991..f7a423ef06 100644 --- a/src/platform_impl/linux/wayland/window/state.rs +++ b/src/platform_impl/linux/wayland/window/state.rs @@ -25,9 +25,10 @@ use sctk::shm::Shm; use sctk::subcompositor::SubcompositorState; use crate::dpi::{LogicalPosition, LogicalSize}; -use crate::error::{ExternalError, NotSupportedError}; use crate::platform_impl::WindowId; -use crate::window::{CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme}; +use crate::window::{ + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, WindowError, +}; use crate::platform_impl::wayland::seat::{ PointerConstraintsState, WinitPointerData, WinitPointerDataExt, ZwpTextInputV3Ext, @@ -309,7 +310,7 @@ impl WindowState { } /// Start interacting drag resize. - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { let xdg_toplevel = self.window.xdg_toplevel(); // TODO(kchibisov) handle touch serials. @@ -323,7 +324,7 @@ impl WindowState { } /// Start the window drag. - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { let xdg_toplevel = self.window.xdg_toplevel(); // TODO(kchibisov) handle touch serials. self.apply_on_poiner(|_, data| { @@ -652,7 +653,7 @@ impl WindowState { } /// Set the cursor grabbing state on the top-level. - pub fn set_cursor_grab(&mut self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&mut self, mode: CursorGrabMode) -> Result<(), WindowError> { // Replace the user grabbing mode. self.cursor_grab_mode.user_grab_mode = mode; self.set_cursor_grab_inner(mode) @@ -665,11 +666,11 @@ impl WindowState { } /// Set the grabbing state on the surface. - fn set_cursor_grab_inner(&mut self, mode: CursorGrabMode) -> Result<(), ExternalError> { + fn set_cursor_grab_inner(&mut self, mode: CursorGrabMode) -> Result<(), WindowError> { let pointer_constraints = match self.pointer_constraints.as_ref() { Some(pointer_constraints) => pointer_constraints, None if mode == CursorGrabMode::None => return Ok(()), - None => return Err(ExternalError::NotSupported(NotSupportedError::new())), + None => return Err(WindowError::NotSupported(NotSupportedError::new())), }; // Replace the current mode. @@ -704,14 +705,14 @@ impl WindowState { } /// Set the position of the cursor. - pub fn set_cursor_position(&self, position: LogicalPosition) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, position: LogicalPosition) -> Result<(), WindowError> { if self.pointer_constraints.is_none() { - return Err(ExternalError::NotSupported(NotSupportedError::new())); + return Err(WindowError::NotSupported(NotSupportedError::new())); } // Positon can be set only for locked cursor. if self.cursor_grab_mode.current_grab_mode != CursorGrabMode::Locked { - return Err(ExternalError::Os(os_error!( + return Err(WindowError::Os(os_error!( crate::platform_impl::OsError::Misc( "cursor position can be set only for locked cursor." ) diff --git a/src/platform_impl/linux/x11/window.rs b/src/platform_impl/linux/x11/window.rs index 916aad01ac..c0d1d03edb 100644 --- a/src/platform_impl/linux/x11/window.rs +++ b/src/platform_impl/linux/x11/window.rs @@ -17,9 +17,10 @@ use x11rb::{ }, }; +use crate::platform::startup_notify::ActivationTokenNotFound; use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error::{ExternalError, NotSupportedError, OsError as RootOsError}, + error::OsError as RootOsError, event_loop::AsyncRequestSerial, platform_impl::{ x11::{atoms::*, MonitorHandle as X11MonitorHandle, WakeSender, X11Error}, @@ -27,8 +28,8 @@ use crate::{ PlatformSpecificWindowBuilderAttributes, VideoMode as PlatformVideoMode, }, window::{ - CursorGrabMode, CursorIcon, Icon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, WindowLevel, + CursorGrabMode, CursorIcon, Icon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, WindowLevel, }, }; @@ -1469,7 +1470,7 @@ impl UnownedWindow { } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { let mut grabbed_lock = self.cursor_grabbed_mode.lock().unwrap(); if mode == *grabbed_lock { return Ok(()); @@ -1484,7 +1485,7 @@ impl UnownedWindow { let result = match mode { CursorGrabMode::None => self.xconn.flush_requests().map_err(|err| { - ExternalError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into()))) + WindowError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into()))) }), CursorGrabMode::Confined => { let result = { @@ -1532,10 +1533,10 @@ impl UnownedWindow { } _ => unreachable!(), } - .map_err(|err| ExternalError::Os(os_error!(OsError::Misc(err)))) + .map_err(|err| WindowError::Os(os_error!(OsError::Misc(err)))) } CursorGrabMode::Locked => { - return Err(ExternalError::NotSupported(NotSupportedError::new())); + return Err(WindowError::NotSupported(NotSupportedError::new())); } }; @@ -1568,38 +1569,38 @@ impl UnownedWindow { self.current_monitor().scale_factor } - pub fn set_cursor_position_physical(&self, x: i32, y: i32) -> Result<(), ExternalError> { + pub fn set_cursor_position_physical(&self, x: i32, y: i32) -> Result<(), WindowError> { { self.xconn .xcb_connection() .warp_pointer(x11rb::NONE, self.xwindow, 0, 0, 0, 0, x as _, y as _) .map_err(|e| { - ExternalError::Os(os_error!(OsError::XError(X11Error::from(e).into()))) + WindowError::Os(os_error!(OsError::XError(X11Error::from(e).into()))) })?; - self.xconn.flush_requests().map_err(|e| { - ExternalError::Os(os_error!(OsError::XError(X11Error::Xlib(e).into()))) - }) + self.xconn + .flush_requests() + .map_err(|e| WindowError::Os(os_error!(OsError::XError(X11Error::Xlib(e).into())))) } } #[inline] - pub fn set_cursor_position(&self, position: Position) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, position: Position) -> Result<(), WindowError> { let (x, y) = position.to_physical::(self.scale_factor()).into(); self.set_cursor_position_physical(x, y) } #[inline] - pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } /// Moves the window while it is being dragged. - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { self.drag_initiate(util::MOVERESIZE_MOVE) } /// Resizes the window while it is being dragged. - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { self.drag_initiate(match direction { ResizeDirection::East => util::MOVERESIZE_RIGHT, ResizeDirection::North => util::MOVERESIZE_TOP, @@ -1613,13 +1614,13 @@ impl UnownedWindow { } /// Initiates a drag operation while the left mouse button is pressed. - fn drag_initiate(&self, action: isize) -> Result<(), ExternalError> { + fn drag_initiate(&self, action: isize) -> Result<(), WindowError> { let pointer = self .xconn .query_pointer(self.xwindow, util::VIRTUAL_CORE_POINTER) - .map_err(|err| ExternalError::Os(os_error!(OsError::XError(err.into()))))?; + .map_err(|err| WindowError::Os(os_error!(OsError::XError(err.into()))))?; - let window = self.inner_position().map_err(ExternalError::NotSupported)?; + let window = self.inner_position().map_err(WindowError::NotSupported)?; let atoms = self.xconn.atoms(); let message = atoms[_NET_WM_MOVERESIZE]; @@ -1630,12 +1631,10 @@ impl UnownedWindow { self.xconn .xcb_connection() .ungrab_pointer(x11rb::CURRENT_TIME) - .map_err(|err| { - ExternalError::Os(os_error!(OsError::XError(X11Error::from(err).into()))) - })? + .map_err(|err| WindowError::Os(os_error!(OsError::XError(X11Error::from(err).into()))))? .ignore_error(); self.xconn.flush_requests().map_err(|err| { - ExternalError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into()))) + WindowError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into()))) })?; *grabbed_lock = CursorGrabMode::None; @@ -1657,11 +1656,11 @@ impl UnownedWindow { 1, ], ) - .map_err(|err| ExternalError::Os(os_error!(OsError::XError(err.into()))))?; + .map_err(|err| WindowError::Os(os_error!(OsError::XError(err.into()))))?; - self.xconn.flush_requests().map_err(|err| { - ExternalError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into()))) - }) + self.xconn + .flush_requests() + .map_err(|err| WindowError::Os(os_error!(OsError::XError(X11Error::Xlib(err).into())))) } #[inline] @@ -1760,7 +1759,7 @@ impl UnownedWindow { } #[inline] - pub fn request_activation_token(&self) -> Result { + pub fn request_activation_token(&self) -> Result { let serial = AsyncRequestSerial::get(); self.activation_sender .send((self.id(), serial)) diff --git a/src/platform_impl/macos/window.rs b/src/platform_impl/macos/window.rs index 5ec9c5e5cf..f4daee3170 100644 --- a/src/platform_impl/macos/window.rs +++ b/src/platform_impl/macos/window.rs @@ -15,7 +15,7 @@ use crate::{ dpi::{ LogicalPosition, LogicalSize, PhysicalPosition, PhysicalSize, Position, Size, Size::Logical, }, - error::{ExternalError, NotSupportedError, OsError as RootOsError}, + error::OsError as RootOsError, event::WindowEvent, icon::Icon, platform::macos::{OptionAsAlt, WindowExtMacOS}, @@ -31,8 +31,9 @@ use crate::{ Fullscreen, OsError, }, window::{ - CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, WindowId as RootWindowId, WindowLevel, + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, WindowId as RootWindowId, + WindowLevel, }, }; use core_graphics::display::{CGDisplay, CGPoint}; @@ -833,18 +834,18 @@ impl WinitWindow { } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { let associate_mouse_cursor = match mode { CursorGrabMode::Locked => false, CursorGrabMode::None => true, CursorGrabMode::Confined => { - return Err(ExternalError::NotSupported(NotSupportedError::new())) + return Err(WindowError::NotSupported(NotSupportedError::new())) } }; // TODO: Do this for real https://stackoverflow.com/a/40922095/5435443 CGDisplay::associate_mouse_and_mouse_cursor_position(associate_mouse_cursor) - .map_err(|status| ExternalError::Os(os_error!(OsError::CGError(status)))) + .map_err(|status| WindowError::Os(os_error!(OsError::CGError(status)))) } #[inline] @@ -862,7 +863,7 @@ impl WinitWindow { } #[inline] - pub fn set_cursor_position(&self, cursor_position: Position) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, cursor_position: Position) -> Result<(), WindowError> { let physical_window_position = self.inner_position().unwrap(); let scale_factor = self.scale_factor(); let window_position = physical_window_position.to_logical::(scale_factor); @@ -872,27 +873,27 @@ impl WinitWindow { y: logical_cursor_position.y + window_position.y, }; CGDisplay::warp_mouse_cursor_position(point) - .map_err(|e| ExternalError::Os(os_error!(OsError::CGError(e))))?; + .map_err(|e| WindowError::Os(os_error!(OsError::CGError(e))))?; CGDisplay::associate_mouse_and_mouse_cursor_position(true) - .map_err(|e| ExternalError::Os(os_error!(OsError::CGError(e))))?; + .map_err(|e| WindowError::Os(os_error!(OsError::CGError(e))))?; Ok(()) } #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { let event = NSApp().currentEvent(); self.performWindowDragWithEvent(event.as_deref()); Ok(()) } #[inline] - pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), ExternalError> { + pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), WindowError> { self.setIgnoresMouseEvents(!hittest); Ok(()) } diff --git a/src/platform_impl/orbital/window.rs b/src/platform_impl/orbital/window.rs index 47e11aa1d9..f0821b00cb 100644 --- a/src/platform_impl/orbital/window.rs +++ b/src/platform_impl/orbital/window.rs @@ -9,10 +9,10 @@ use raw_window_handle::{ use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error, + error::OsError, platform_impl::Fullscreen, - window, window::ImePurpose, + window::{self, NotSupportedError, WindowError}, }; use super::{ @@ -41,7 +41,7 @@ impl Window { el: &EventLoopWindowTarget, attrs: window::WindowAttributes, _: PlatformSpecificWindowBuilderAttributes, - ) -> Result { + ) -> Result { let scale = MonitorHandle.scale_factor(); let (x, y) = if let Some(pos) = attrs.position { @@ -183,7 +183,7 @@ impl Window { } #[inline] - pub fn inner_position(&self) -> Result, error::NotSupportedError> { + pub fn inner_position(&self) -> Result, NotSupportedError> { let mut buf: [u8; 4096] = [0; 4096]; let path = self .window_socket @@ -194,7 +194,7 @@ impl Window { } #[inline] - pub fn outer_position(&self) -> Result, error::NotSupportedError> { + pub fn outer_position(&self) -> Result, NotSupportedError> { //TODO: adjust for window decorations self.inner_position() } @@ -354,44 +354,34 @@ impl Window { pub fn set_cursor_icon(&self, _: window::CursorIcon) {} #[inline] - pub fn set_cursor_position(&self, _: Position) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_position(&self, _: Position) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn set_cursor_grab(&self, _: window::CursorGrabMode) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_grab(&self, _: window::CursorGrabMode) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] pub fn set_cursor_visible(&self, _: bool) {} #[inline] - pub fn drag_window(&self) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn drag_window(&self) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] pub fn drag_resize_window( &self, _direction: window::ResizeDirection, - ) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + ) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), error::ExternalError> { - Err(error::ExternalError::NotSupported( - error::NotSupportedError::new(), - )) + pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] diff --git a/src/platform_impl/web/window.rs b/src/platform_impl/web/window.rs index 97fa7ef260..707b8d3667 100644 --- a/src/platform_impl/web/window.rs +++ b/src/platform_impl/web/window.rs @@ -1,9 +1,10 @@ use crate::dpi::{PhysicalPosition, PhysicalSize, Position, Size}; -use crate::error::{ExternalError, NotSupportedError, OsError as RootOE}; +use crate::error::OsError as RootOE; use crate::icon::Icon; use crate::window::{ - CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, WindowId as RootWI, WindowLevel, + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, WindowId as RootWI, + WindowLevel, }; use raw_window_handle::{RawDisplayHandle, RawWindowHandle, WebDisplayHandle, WebWindowHandle}; @@ -199,24 +200,24 @@ impl Inner { } #[inline] - pub fn set_cursor_position(&self, _position: Position) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_position(&self, _position: Position) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { let lock = match mode { CursorGrabMode::None => false, CursorGrabMode::Locked => true, CursorGrabMode::Confined => { - return Err(ExternalError::NotSupported(NotSupportedError::new())) + return Err(WindowError::NotSupported(NotSupportedError::new())) } }; self.canvas .borrow() .set_cursor_lock(lock) - .map_err(ExternalError::Os) + .map_err(WindowError::Os) } #[inline] @@ -233,18 +234,18 @@ impl Inner { } #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn drag_window(&self) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn drag_resize_window(&self, _direction: ResizeDirection) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] - pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), ExternalError> { - Err(ExternalError::NotSupported(NotSupportedError::new())) + pub fn set_cursor_hittest(&self, _hittest: bool) -> Result<(), WindowError> { + Err(WindowError::NotSupported(NotSupportedError::new())) } #[inline] diff --git a/src/platform_impl/windows/window.rs b/src/platform_impl/windows/window.rs index d90deb76df..05d088b792 100644 --- a/src/platform_impl/windows/window.rs +++ b/src/platform_impl/windows/window.rs @@ -55,7 +55,7 @@ use windows_sys::Win32::{ use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error::{ExternalError, NotSupportedError, OsError as RootOsError}, + error::OsError as RootOsError, icon::Icon, platform_impl::platform::{ dark_mode::try_theme, @@ -74,8 +74,8 @@ use crate::{ Fullscreen, PlatformSpecificWindowBuilderAttributes, WindowId, }, window::{ - CursorGrabMode, CursorIcon, ImePurpose, ResizeDirection, Theme, UserAttentionType, - WindowAttributes, WindowButtons, WindowLevel, + CursorGrabMode, CursorIcon, ImePurpose, NotSupportedError, ResizeDirection, Theme, + UserAttentionType, WindowAttributes, WindowButtons, WindowError, WindowLevel, }, }; @@ -355,12 +355,12 @@ impl Window { } #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { let confine = match mode { CursorGrabMode::None => false, CursorGrabMode::Confined => true, CursorGrabMode::Locked => { - return Err(ExternalError::NotSupported(NotSupportedError::new())) + return Err(WindowError::NotSupported(NotSupportedError::new())) } }; @@ -375,7 +375,7 @@ impl Window { .unwrap() .mouse .set_cursor_flags(window.0, |f| f.set(CursorFlags::GRABBED, confine)) - .map_err(|e| ExternalError::Os(os_error!(e))); + .map_err(|e| WindowError::Os(os_error!(e))); let _ = tx.send(result); }); rx.recv().unwrap() @@ -406,17 +406,17 @@ impl Window { } #[inline] - pub fn set_cursor_position(&self, position: Position) -> Result<(), ExternalError> { + pub fn set_cursor_position(&self, position: Position) -> Result<(), WindowError> { let scale_factor = self.scale_factor(); let (x, y) = position.to_physical::(scale_factor).into(); let mut point = POINT { x, y }; unsafe { if ClientToScreen(self.hwnd(), &mut point) == false.into() { - return Err(ExternalError::Os(os_error!(io::Error::last_os_error()))); + return Err(WindowError::Os(os_error!(io::Error::last_os_error()))); } if SetCursorPos(point.x, point.y) == false.into() { - return Err(ExternalError::Os(os_error!(io::Error::last_os_error()))); + return Err(WindowError::Os(os_error!(io::Error::last_os_error()))); } } Ok(()) @@ -445,7 +445,7 @@ impl Window { } #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { unsafe { self.handle_os_dragging(HTCAPTION as WPARAM); } @@ -454,7 +454,7 @@ impl Window { } #[inline] - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { unsafe { self.handle_os_dragging(match direction { ResizeDirection::East => HTRIGHT, @@ -472,7 +472,7 @@ impl Window { } #[inline] - pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), ExternalError> { + pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), WindowError> { let window = self.window.clone(); let window_state = Arc::clone(&self.window_state); self.thread_executor.execute_in_thread(move || { diff --git a/src/window.rs b/src/window.rs index 3b995cc464..cb88f492a3 100644 --- a/src/window.rs +++ b/src/window.rs @@ -1,5 +1,5 @@ //! The [`Window`] struct and associated types. -use std::fmt; +use std::{error::Error, fmt}; use raw_window_handle::{ HasRawDisplayHandle, HasRawWindowHandle, RawDisplayHandle, RawWindowHandle, @@ -7,7 +7,7 @@ use raw_window_handle::{ use crate::{ dpi::{PhysicalPosition, PhysicalSize, Position, Size}, - error::{ExternalError, NotSupportedError, OsError}, + error::OsError, event_loop::EventLoopWindowTarget, monitor::{MonitorHandle, VideoMode}, platform_impl, @@ -1328,9 +1328,9 @@ impl Window { /// /// ## Platform-specific /// - /// - **iOS / Android / Web / Wayland / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **iOS / Android / Web / Wayland / Orbital:** Always returns an [`WindowError::NotSupported`]. #[inline] - pub fn set_cursor_position>(&self, position: P) -> Result<(), ExternalError> { + pub fn set_cursor_position>(&self, position: P) -> Result<(), WindowError> { let position = position.into(); self.window .maybe_wait_on_main(|w| w.set_cursor_position(position)) @@ -1352,7 +1352,7 @@ impl Window { /// .unwrap(); /// ``` #[inline] - pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), ExternalError> { + pub fn set_cursor_grab(&self, mode: CursorGrabMode) -> Result<(), WindowError> { self.window.maybe_wait_on_main(|w| w.set_cursor_grab(mode)) } @@ -1384,9 +1384,9 @@ impl Window { /// - **X11:** Un-grabs the cursor. /// - **Wayland:** Requires the cursor to be inside the window to be dragged. /// - **macOS:** May prevent the button release event to be triggered. - /// - **iOS / Android / Web / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **iOS / Android / Web / Orbital:** Always returns an [`WindowError::NotSupported`]. #[inline] - pub fn drag_window(&self) -> Result<(), ExternalError> { + pub fn drag_window(&self) -> Result<(), WindowError> { self.window.maybe_wait_on_main(|w| w.drag_window()) } @@ -1397,10 +1397,10 @@ impl Window { /// /// ## Platform-specific /// - /// - **macOS:** Always returns an [`ExternalError::NotSupported`] - /// - **iOS / Android / Web / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **macOS:** Always returns an [`WindowError::NotSupported`] + /// - **iOS / Android / Web / Orbital:** Always returns an [`WindowError::NotSupported`]. #[inline] - pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), ExternalError> { + pub fn drag_resize_window(&self, direction: ResizeDirection) -> Result<(), WindowError> { self.window .maybe_wait_on_main(|w| w.drag_resize_window(direction)) } @@ -1412,9 +1412,9 @@ impl Window { /// /// ## Platform-specific /// - /// - **iOS / Android / Web / X11 / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **iOS / Android / Web / X11 / Orbital:** Always returns an [`WindowError::NotSupported`]. #[inline] - pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), ExternalError> { + pub fn set_cursor_hittest(&self, hittest: bool) -> Result<(), WindowError> { self.window .maybe_wait_on_main(|w| w.set_cursor_hittest(hittest)) } @@ -1511,6 +1511,49 @@ unsafe impl HasRawDisplayHandle for Window { } } +/// An error that may be generated when requesting window state. +// TODO(madsmtm): Split this into further variants. +#[derive(Debug)] +pub enum WindowError { + /// The operation is not supported by the backend. + NotSupported(NotSupportedError), + /// The OS cannot perform the operation. + Os(OsError), +} + +impl fmt::Display for WindowError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { + match self { + Self::NotSupported(e) => write!(f, "{e}"), + Self::Os(e) => write!(f, "{e}"), + } + } +} + +impl Error for WindowError {} + +/// The error type for when the requested operation is not supported by the backend. +#[derive(Debug)] +pub struct NotSupportedError { + _marker: (), +} + +impl fmt::Display for NotSupportedError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { + write!(f, "the requested operation is not supported by Winit") + } +} + +impl NotSupportedError { + #[inline] + #[allow(dead_code)] + pub(crate) fn new() -> NotSupportedError { + NotSupportedError { _marker: () } + } +} + +impl Error for NotSupportedError {} + /// The behavior of cursor grabbing. /// /// Use this enum with [`Window::set_cursor_grab`] to grab the cursor. @@ -1527,8 +1570,8 @@ pub enum CursorGrabMode { /// /// ## Platform-specific /// - /// - **macOS:** Not implemented. Always returns [`ExternalError::NotSupported`] for now. - /// - **iOS / Android / Web / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **macOS:** Not implemented. Always returns [`WindowError::NotSupported`] for now. + /// - **iOS / Android / Web / Orbital:** Always returns an [`WindowError::NotSupported`]. Confined, /// The cursor is locked inside the window area to the certain position. @@ -1538,8 +1581,8 @@ pub enum CursorGrabMode { /// /// ## Platform-specific /// - /// - **X11 / Windows:** Not implemented. Always returns [`ExternalError::NotSupported`] for now. - /// - **iOS / Android / Orbital:** Always returns an [`ExternalError::NotSupported`]. + /// - **X11 / Windows:** Not implemented. Always returns [`WindowError::NotSupported`] for now. + /// - **iOS / Android / Orbital:** Always returns an [`WindowError::NotSupported`]. Locked, } @@ -1686,3 +1729,25 @@ impl ActivationToken { Self { _token } } } + +#[cfg(test)] +mod tests { + #![allow(clippy::redundant_clone)] + + use super::*; + + // Eat attributes for testing + #[test] + fn ensure_fmt_does_not_panic() { + let _ = format!( + "{:?}, {}", + NotSupportedError::new(), + NotSupportedError::new(), + ); + let _ = format!( + "{:?}, {}", + WindowError::NotSupported(NotSupportedError::new()), + WindowError::NotSupported(NotSupportedError::new()) + ); + } +}