From 9e8a5de9be23211f83e226a0574c06ff96902461 Mon Sep 17 00:00:00 2001 From: sodiboo Date: Sat, 23 Nov 2024 21:55:47 +0100 Subject: [PATCH] implement WinitVirtualDevice::output() to the one single virtual output --- src/backend/winit.rs | 5 +++++ src/input/backend_ext.rs | 26 ++++++++++++++++---------- src/input/mod.rs | 4 ++-- 3 files changed, 23 insertions(+), 12 deletions(-) diff --git a/src/backend/winit.rs b/src/backend/winit.rs index 500215f7b..a1e499748 100644 --- a/src/backend/winit.rs +++ b/src/backend/winit.rs @@ -268,4 +268,9 @@ impl Winit { pub fn ipc_outputs(&self) -> Arc> { self.ipc_outputs.clone() } + + // FIXME: If/when the winit backend supports multiple outputs, then this method makes no sense. + pub fn single_output(&self) -> &Output { + &self.output + } } diff --git a/src/input/backend_ext.rs b/src/input/backend_ext.rs index 91a2aad45..e79c269a9 100644 --- a/src/input/backend_ext.rs +++ b/src/input/backend_ext.rs @@ -3,6 +3,8 @@ use smithay::backend::input; use smithay::backend::winit::WinitVirtualDevice; use smithay::output::Output; +use crate::backend::Backend; +use crate::niri::State; use crate::protocols::virtual_pointer::VirtualPointer; pub trait NiriInputBackend: input::InputBackend { @@ -16,29 +18,33 @@ where } pub trait NiriInputDevice: input::Device { - // FIXME: should this be per-event? logically yes, - // but right now we only use it for virtual pointers, which have static outputs. - fn output(&self) -> Option; + // FIXME: this should maybe be per-event, not per-device, + // but it's not clear that this matters in practice? + // it might be more obvious once we implement it for libinput + fn output(&self, state: &State) -> Option; } impl NiriInputDevice for libinput::Device { - fn output(&self) -> Option { + fn output(&self, _state: &State) -> Option { // FIXME: Allow specifying the output per-device? - // In that case, change the method to take a reference to our state or config or something - // (because we can't easily change the libinput Device struct) None } } impl NiriInputDevice for WinitVirtualDevice { - fn output(&self) -> Option { - // here it's actually *correct* to return None, because there is only one output. - None + fn output(&self, state: &State) -> Option { + match state.backend { + Backend::Winit(ref winit) => Some(winit.single_output().clone()), + // returning None over panicking here because it's not worth panicking over + // and also, foreseeably, someone might want to, at some point, use `WinitInputBackend` + // for dirty hacks or mocking or whatever, in which case this will be useful. + _ => None, + } } } impl NiriInputDevice for VirtualPointer { - fn output(&self) -> Option { + fn output(&self, _: &State) -> Option { self.output().cloned() } } diff --git a/src/input/mod.rs b/src/input/mod.rs index dff60886a..550ee4591 100644 --- a/src/input/mod.rs +++ b/src/input/mod.rs @@ -271,7 +271,7 @@ impl State { where I::Device: 'static, { - let device_output = event.device().output(); + let device_output = event.device().output(self); let device_output = device_output.as_ref(); let (target_geo, keep_ratio, px, transform) = if let Some(output) = device_output.or_else(|| self.niri.output_for_tablet()) { @@ -2375,7 +2375,7 @@ impl State { evt: &impl AbsolutePositionEvent, fallback_output: Option<&Output>, ) -> Option> { - let output = evt.device().output(); + let output = evt.device().output(self); let output = output.as_ref().or(fallback_output)?; let output_geo = self.niri.global_space.output_geometry(output).unwrap(); let transform = output.current_transform();