1
1
mirror of https://github.com/wez/wezterm.git synced 2024-12-27 15:37:29 +03:00

wayland: implement wezterm.gui.screens()

Hook it up for resolving geometry, but note that wayland doesn't
allow positioning and we don't expose a way to set width/height
based on screen right now.
This commit is contained in:
Wez Furlong 2022-07-08 09:54:42 -07:00
parent 5c6312c6a5
commit fdb5fc2d66
2 changed files with 70 additions and 17 deletions

View File

@ -3,8 +3,9 @@ use super::pointer::*;
use super::window::*;
use crate::connection::ConnectionOps;
use crate::os::x11::keyboard::Keyboard;
use crate::screen::{ScreenInfo, Screens};
use crate::spawn::*;
use crate::Connection;
use crate::{Connection, ScreenRect};
use anyhow::{bail, Context};
use mio::unix::SourceFd;
use mio::{Events, Interest, Poll, Token};
@ -365,4 +366,62 @@ impl ConnectionOps for WaylandConnection {
self.windows.borrow_mut().clear();
res
}
fn screens(&self) -> anyhow::Result<Screens> {
let mut by_name = HashMap::new();
let mut virtual_rect: ScreenRect = euclid::rect(0, 0, 0, 0);
for output in self.environment.borrow().get_all_outputs() {
toolkit::output::with_output_info(&output, |info| {
let name = if info.name.is_empty() {
format!("{} {}", info.model, info.make)
} else {
info.name.clone()
};
let (width, height) = info
.modes
.iter()
.find(|mode| mode.is_current)
.map(|mode| mode.dimensions)
.unwrap_or((info.physical_size.0, info.physical_size.1));
let rect = euclid::rect(
info.location.0 as isize,
info.location.1 as isize,
width as isize,
height as isize,
);
virtual_rect = virtual_rect.union(&rect);
by_name.insert(name.clone(), ScreenInfo { name, rect });
});
}
// The main screen is the one either at the origin of
// the virtual area, or if that doesn't exist for some weird
// reason, the screen closest to the origin.
let main = by_name
.values()
.min_by_key(|screen| {
screen
.rect
.origin
.to_f32()
.distance_to(euclid::Point2D::origin())
.abs() as isize
})
.ok_or_else(|| anyhow::anyhow!("no screens were found"))?
.clone();
// We don't yet know how to determine the active screen,
// so assume the main screen.
let active = main.clone();
Ok(Screens {
main,
active,
by_name,
virtual_rect,
})
}
}

View File

@ -5,13 +5,14 @@ use crate::connection::ConnectionOps;
use crate::os::wayland::connection::WaylandConnection;
use crate::os::x11::keyboard::Keyboard;
use crate::{
Clipboard, Connection, Dimensions, MouseCursor, Point, RequestedWindowGeometry, ScreenPoint,
Window, WindowEvent, WindowEventSender, WindowKeyEvent, WindowOps, WindowState,
Clipboard, Connection, Dimensions, MouseCursor, Point, RequestedWindowGeometry,
ResolvedGeometry, ScreenPoint, Window, WindowEvent, WindowEventSender, WindowKeyEvent,
WindowOps, WindowState,
};
use anyhow::{anyhow, bail, Context};
use async_io::Timer;
use async_trait::async_trait;
use config::{ConfigHandle, DimensionContext};
use config::ConfigHandle;
use filedescriptor::FileDescriptor;
use promise::{Future, Promise};
use raw_window_handle::unix::WaylandHandle;
@ -275,19 +276,12 @@ impl WaylandWindow {
.borrow_mut()
.insert(surface.as_ref().id(), window_id);
// TODO: populate these dimension contexts based on the wayland OutputInfo
let width_context = DimensionContext {
dpi: crate::DEFAULT_DPI as f32,
pixel_max: 65535.,
pixel_cell: 65535.,
};
let height_context = DimensionContext {
dpi: crate::DEFAULT_DPI as f32,
pixel_max: 65535.,
pixel_cell: 65535.,
};
let width = geometry.width.evaluate_as_pixels(width_context) as usize;
let height = geometry.height.evaluate_as_pixels(height_context) as usize;
let ResolvedGeometry {
x: _,
y: _,
width,
height,
} = conn.resolve_geometry(geometry);
let dimensions = Dimensions {
pixel_width: width,