refactor(wayland): update data in user data map for everything
This commit is contained in:
@@ -22,6 +22,15 @@ use std::sync::{Arc, Weak};
|
||||
use tracing::{debug, info};
|
||||
|
||||
stardust_xr_server_codegen::codegen_item_panel_protocol!();
|
||||
impl Default for Geometry {
|
||||
fn default() -> Self {
|
||||
Geometry {
|
||||
origin: [0, 0].into(),
|
||||
size: [0, 0].into(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
lazy_static! {
|
||||
pub static ref ITEM_TYPE_INFO_PANEL: TypeInfo = TypeInfo {
|
||||
type_name: "panel",
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
use super::{
|
||||
state::{ClientState, WaylandState},
|
||||
utils::WlSurfaceExt,
|
||||
xdg_shell::{surface_panel_item, ChildInfoExt},
|
||||
utils::{ChildInfoExt, WlSurfaceExt},
|
||||
xdg_shell::surface_panel_item,
|
||||
};
|
||||
use crate::{
|
||||
nodes::items::panel::{ChildInfo, Geometry, SurfaceId},
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
use super::{state::WaylandState, surface::CoreSurface};
|
||||
use super::{state::WaylandState, surface::CoreSurface, utils::WlSurfaceExt};
|
||||
use crate::{
|
||||
core::task,
|
||||
nodes::{
|
||||
@@ -76,8 +76,7 @@ pub struct CursorInfo {
|
||||
}
|
||||
impl CursorInfo {
|
||||
pub fn cursor_data(&self) -> Option<Geometry> {
|
||||
let cursor_size =
|
||||
CoreSurface::from_wl_surface(&self.surface.as_ref()?.upgrade().ok()?)?.size()?;
|
||||
let cursor_size = self.surface.as_ref()?.upgrade().ok()?.get_size()?;
|
||||
Some(Geometry {
|
||||
origin: [self.hotspot_x, self.hotspot_y].into(),
|
||||
size: cursor_size,
|
||||
|
||||
@@ -9,7 +9,6 @@ use crate::{
|
||||
items::camera::TexWrapper,
|
||||
},
|
||||
};
|
||||
use mint::Vector2;
|
||||
use once_cell::sync::OnceCell;
|
||||
use parking_lot::Mutex;
|
||||
use send_wrapper::SendWrapper;
|
||||
@@ -35,7 +34,6 @@ pub static CORE_SURFACES: Registry<CoreSurface> = Registry::new();
|
||||
|
||||
pub struct CoreSurfaceData {
|
||||
wl_tex: Option<SendWrapper<GlesTexture>>,
|
||||
pub size: Vector2<u32>,
|
||||
}
|
||||
impl Drop for CoreSurfaceData {
|
||||
fn drop(&mut self) {
|
||||
@@ -156,16 +154,7 @@ impl CoreSurface {
|
||||
sk_mat.lock().0.queue_offset(*material_offset as i32);
|
||||
}
|
||||
|
||||
let Some(surface_size) = wl_surface
|
||||
.get_data_raw::<RendererSurfaceStateUserData, _, _>(|surface_states| {
|
||||
surface_states.lock().unwrap().surface_size()
|
||||
})
|
||||
.flatten()
|
||||
else {
|
||||
return;
|
||||
};
|
||||
let new_mapped_data = CoreSurfaceData {
|
||||
size: Vector2::from([surface_size.w as u32, surface_size.h as u32]),
|
||||
wl_tex: Some(SendWrapper::new(smithay_tex)),
|
||||
};
|
||||
*mapped_data = Some(new_mapped_data);
|
||||
@@ -206,10 +195,6 @@ impl CoreSurface {
|
||||
pub fn wl_surface(&self) -> Option<WlSurface> {
|
||||
self.weak_surface.upgrade().ok()
|
||||
}
|
||||
|
||||
pub fn size(&self) -> Option<Vector2<u32>> {
|
||||
self.mapped_data.lock().as_ref().map(|d| d.size)
|
||||
}
|
||||
}
|
||||
impl Drop for CoreSurface {
|
||||
fn drop(&mut self) {
|
||||
|
||||
@@ -1,9 +1,25 @@
|
||||
use smithay::{reexports::wayland_server::protocol::wl_surface::WlSurface, wayland::compositor};
|
||||
use mint::Vector2;
|
||||
use parking_lot::Mutex;
|
||||
use smithay::{
|
||||
backend::renderer::utils::RendererSurfaceStateUserData,
|
||||
reexports::wayland_server::protocol::wl_surface::WlSurface,
|
||||
wayland::{
|
||||
compositor,
|
||||
shell::xdg::{SurfaceCachedState, XdgToplevelSurfaceData},
|
||||
},
|
||||
};
|
||||
|
||||
use crate::nodes::items::panel::{ChildInfo, Geometry, ToplevelInfo};
|
||||
|
||||
use super::xdg_shell::surface_panel_item;
|
||||
pub trait WlSurfaceExt {
|
||||
fn insert_data<T: Send + Sync + 'static>(&self, data: T) -> bool;
|
||||
fn get_data<T: Send + Sync + Clone + 'static>(&self) -> Option<T>;
|
||||
fn get_data_raw<T: Send + Sync + 'static, O, F: FnOnce(&T) -> O>(&self, f: F) -> Option<O>;
|
||||
fn get_current_surface_state(&self) -> SurfaceCachedState;
|
||||
fn get_pending_surface_state(&self) -> SurfaceCachedState;
|
||||
fn get_size(&self) -> Option<Vector2<u32>>;
|
||||
fn get_geometry(&self) -> Option<Geometry>;
|
||||
}
|
||||
impl WlSurfaceExt for WlSurface {
|
||||
fn insert_data<T: Send + Sync + 'static>(&self, data: T) -> bool {
|
||||
@@ -17,4 +33,97 @@ impl WlSurfaceExt for WlSurface {
|
||||
fn get_data_raw<T: Send + Sync + 'static, O, F: FnOnce(&T) -> O>(&self, f: F) -> Option<O> {
|
||||
compositor::with_states(self, |d| Some((f)(d.data_map.get::<T>()?)))
|
||||
}
|
||||
fn get_current_surface_state(&self) -> SurfaceCachedState {
|
||||
compositor::with_states(self, |states| {
|
||||
states
|
||||
.cached_state
|
||||
.get::<SurfaceCachedState>()
|
||||
.current()
|
||||
.clone()
|
||||
})
|
||||
}
|
||||
fn get_pending_surface_state(&self) -> SurfaceCachedState {
|
||||
compositor::with_states(self, |states| {
|
||||
states
|
||||
.cached_state
|
||||
.get::<SurfaceCachedState>()
|
||||
.pending()
|
||||
.clone()
|
||||
})
|
||||
}
|
||||
fn get_size(&self) -> Option<Vector2<u32>> {
|
||||
self.get_data_raw::<RendererSurfaceStateUserData, _, _>(|surface_states| {
|
||||
surface_states.lock().unwrap().surface_size()
|
||||
})
|
||||
.flatten()
|
||||
.map(|size| Vector2::from([size.w as u32, size.h as u32]))
|
||||
}
|
||||
fn get_geometry(&self) -> Option<Geometry> {
|
||||
self.get_current_surface_state().geometry.map(|r| r.into())
|
||||
}
|
||||
}
|
||||
|
||||
pub trait ToplevelInfoExt {
|
||||
fn get_toplevel_info(&self) -> Option<ToplevelInfo>;
|
||||
fn with_toplevel_info<O, F: FnOnce(&mut ToplevelInfo) -> O>(&self, f: F) -> Option<O>;
|
||||
|
||||
fn get_parent(&self) -> Option<u64>;
|
||||
fn get_app_id(&self) -> Option<String>;
|
||||
fn get_title(&self) -> Option<String>;
|
||||
fn min_size(&self) -> Option<Vector2<u32>>;
|
||||
fn max_size(&self) -> Option<Vector2<u32>>;
|
||||
}
|
||||
impl ToplevelInfoExt for WlSurface {
|
||||
fn get_toplevel_info(&self) -> Option<ToplevelInfo> {
|
||||
self.get_data_raw::<Mutex<ToplevelInfo>, _, _>(|c| c.lock().clone())
|
||||
}
|
||||
fn with_toplevel_info<O, F: FnOnce(&mut ToplevelInfo) -> O>(&self, f: F) -> Option<O> {
|
||||
self.get_data_raw::<Mutex<ToplevelInfo>, _, _>(|r| (f)(&mut r.lock()))
|
||||
}
|
||||
|
||||
fn get_parent(&self) -> Option<u64> {
|
||||
self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| d.lock().unwrap().parent.clone())
|
||||
.flatten()
|
||||
.and_then(|p| surface_panel_item(&p))
|
||||
.and_then(|p| p.node.upgrade())
|
||||
.map(|p| p.get_id())
|
||||
}
|
||||
fn get_app_id(&self) -> Option<String> {
|
||||
self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| d.lock().ok()?.app_id.clone())
|
||||
.flatten()
|
||||
}
|
||||
fn get_title(&self) -> Option<String> {
|
||||
self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| d.lock().ok()?.title.clone())
|
||||
.flatten()
|
||||
}
|
||||
fn min_size(&self) -> Option<Vector2<u32>> {
|
||||
let state = self.get_pending_surface_state();
|
||||
let size = state.min_size;
|
||||
if size.w == 0 && size.h == 0 {
|
||||
None
|
||||
} else {
|
||||
Some(Vector2::from([size.w as u32, size.h as u32]))
|
||||
}
|
||||
}
|
||||
fn max_size(&self) -> Option<Vector2<u32>> {
|
||||
let state = self.get_pending_surface_state();
|
||||
let size = state.max_size;
|
||||
if size.w == 0 && size.h == 0 {
|
||||
None
|
||||
} else {
|
||||
Some(Vector2::from([size.w as u32, size.h as u32]))
|
||||
}
|
||||
}
|
||||
}
|
||||
pub trait ChildInfoExt {
|
||||
fn get_child_info(&self) -> Option<ChildInfo>;
|
||||
fn with_child_info<O, F: FnOnce(&mut ChildInfo) -> O>(&self, f: F) -> Option<O>;
|
||||
}
|
||||
impl ChildInfoExt for WlSurface {
|
||||
fn get_child_info(&self) -> Option<ChildInfo> {
|
||||
self.get_data_raw::<Mutex<ChildInfo>, _, _>(|c| c.lock().clone())
|
||||
}
|
||||
fn with_child_info<O, F: FnOnce(&mut ChildInfo) -> O>(&self, f: F) -> Option<O> {
|
||||
self.get_data_raw::<Mutex<ChildInfo>, _, _>(|r| (f)(&mut r.lock()))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@ use super::{
|
||||
seat::{handle_cursor, SeatWrapper},
|
||||
state::{ClientState, WaylandState},
|
||||
surface::CoreSurface,
|
||||
utils::WlSurfaceExt,
|
||||
utils::*,
|
||||
};
|
||||
use crate::nodes::{
|
||||
drawable::model::ModelPart,
|
||||
@@ -16,7 +16,6 @@ use parking_lot::Mutex;
|
||||
use rand::Rng;
|
||||
use rustc_hash::FxHashMap;
|
||||
use smithay::{
|
||||
backend::renderer::utils::RendererSurfaceStateUserData,
|
||||
delegate_xdg_shell,
|
||||
reexports::{
|
||||
wayland_protocols::xdg::{
|
||||
@@ -30,16 +29,25 @@ use smithay::{
|
||||
},
|
||||
utils::{Logical, Rectangle, Serial},
|
||||
wayland::{
|
||||
compositor::{self, add_post_commit_hook},
|
||||
compositor::add_post_commit_hook,
|
||||
shell::xdg::{
|
||||
PopupSurface, PositionerState, ShellClient, SurfaceCachedState, ToplevelSurface,
|
||||
XdgShellHandler, XdgShellState, XdgToplevelSurfaceData,
|
||||
PopupSurface, PositionerState, ShellClient, ToplevelSurface, XdgShellHandler,
|
||||
XdgShellState,
|
||||
},
|
||||
},
|
||||
};
|
||||
use std::sync::{Arc, Weak};
|
||||
use tracing::warn;
|
||||
|
||||
fn get_unconstrained_popup_geometry(positioner: &PositionerState) -> Geometry {
|
||||
positioner
|
||||
.get_unconstrained_geometry(Rectangle {
|
||||
loc: (-100000, -100000).into(),
|
||||
size: (200000, 200000).into(),
|
||||
})
|
||||
.into()
|
||||
}
|
||||
|
||||
impl From<Rectangle<i32, Logical>> for Geometry {
|
||||
fn from(value: Rectangle<i32, Logical>) -> Self {
|
||||
Geometry {
|
||||
@@ -49,49 +57,6 @@ impl From<Rectangle<i32, Logical>> for Geometry {
|
||||
}
|
||||
}
|
||||
|
||||
// pub trait ToplevelInfoExt {
|
||||
// fn get_toplevel_info(&self) -> Option<ToplevelInfo>;
|
||||
// fn with_toplevel_info<O, F: FnOnce(&mut ToplevelInfo) -> O>(&self, f: F) -> Option<O>;
|
||||
// fn get_toplevel_state(&self) -> Option<ToplevelState>;
|
||||
|
||||
// fn get_app_id(&self) -> Option<String>;
|
||||
// fn get_title(&self) -> Option<String>;
|
||||
// }
|
||||
// impl ToplevelInfoExt for WlSurface {
|
||||
// fn get_toplevel_info(&self) -> Option<ToplevelInfo> {
|
||||
// self.get_data_raw::<Mutex<ToplevelInfo>, _, _>(|c| c.lock().clone())
|
||||
// }
|
||||
// fn with_toplevel_info<O, F: FnOnce(&mut ToplevelInfo) -> O>(&self, f: F) -> Option<O> {
|
||||
// self.get_data_raw::<Mutex<ToplevelInfo>, _, _>(|r| (f)(&mut r.lock()))
|
||||
// }
|
||||
// fn get_toplevel_state(&self) -> Option<ToplevelState> {
|
||||
// self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|r| r.lock().unwrap().current.clone())
|
||||
// }
|
||||
|
||||
// fn get_app_id(&self) -> Option<String> {
|
||||
// self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| {
|
||||
// d.lock().unwrap().app_id.clone().unwrap()
|
||||
// })
|
||||
// }
|
||||
// fn get_title(&self) -> Option<String> {
|
||||
// self.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| {
|
||||
// d.lock().unwrap().title.clone().unwrap()
|
||||
// })
|
||||
// }
|
||||
// }
|
||||
pub trait ChildInfoExt {
|
||||
fn get_child_info(&self) -> Option<ChildInfo>;
|
||||
fn with_child_info<O, F: FnOnce(&mut ChildInfo) -> O>(&self, f: F) -> Option<O>;
|
||||
}
|
||||
impl ChildInfoExt for WlSurface {
|
||||
fn get_child_info(&self) -> Option<ChildInfo> {
|
||||
self.get_data_raw::<Mutex<ChildInfo>, _, _>(|c| c.lock().clone())
|
||||
}
|
||||
fn with_child_info<O, F: FnOnce(&mut ChildInfo) -> O>(&self, f: F) -> Option<O> {
|
||||
self.get_data_raw::<Mutex<ChildInfo>, _, _>(|r| (f)(&mut r.lock()))
|
||||
}
|
||||
}
|
||||
|
||||
pub fn surface_panel_item(wl_surface: &WlSurface) -> Option<Arc<PanelItem<XdgBackend>>> {
|
||||
let panel_item = wl_surface
|
||||
.get_data::<Weak<PanelItem<XdgBackend>>>()
|
||||
@@ -123,11 +88,76 @@ impl XdgShellHandler for WaylandState {
|
||||
s.states.unset(State::Fullscreen);
|
||||
});
|
||||
toplevel.send_configure();
|
||||
|
||||
let initial_size = toplevel
|
||||
.wl_surface()
|
||||
.get_size()
|
||||
.unwrap_or(Vector2::from([0; 2]));
|
||||
|
||||
let initial_toplevel_info = ToplevelInfo {
|
||||
parent: toplevel.wl_surface().get_parent(),
|
||||
title: toplevel.wl_surface().get_title(),
|
||||
app_id: toplevel.wl_surface().get_app_id(),
|
||||
size: initial_size,
|
||||
min_size: toplevel
|
||||
.wl_surface()
|
||||
.min_size()
|
||||
.map(|s| Vector2::from([s.x as f32, s.y as f32])),
|
||||
max_size: toplevel
|
||||
.wl_surface()
|
||||
.max_size()
|
||||
.map(|s| Vector2::from([s.x as f32, s.y as f32])),
|
||||
logical_rectangle: toplevel
|
||||
.wl_surface()
|
||||
.get_geometry()
|
||||
.map(|r| r.into())
|
||||
.unwrap_or(Geometry {
|
||||
origin: [0; 2].into(),
|
||||
size: initial_size,
|
||||
}),
|
||||
};
|
||||
toplevel
|
||||
.wl_surface()
|
||||
.insert_data(Mutex::new(Vector2::from([0_u32; 2])));
|
||||
.insert_data(Mutex::new(initial_toplevel_info));
|
||||
|
||||
CoreSurface::add_to(toplevel.wl_surface());
|
||||
|
||||
add_post_commit_hook(
|
||||
toplevel.wl_surface(),
|
||||
|_state: &mut WaylandState, _dh, surf| {
|
||||
let parent = surf.get_parent();
|
||||
let new_size = surf.get_size().unwrap_or(Vector2::from([0; 2]));
|
||||
let min_size = surf
|
||||
.min_size()
|
||||
.map(|s| Vector2::from([s.x as f32, s.y as f32]));
|
||||
let max_size = surf
|
||||
.max_size()
|
||||
.map(|s| Vector2::from([s.x as f32, s.y as f32]));
|
||||
let logical_rectangle = surf.get_geometry().unwrap_or_default();
|
||||
|
||||
let mut size_changed = false;
|
||||
surf.with_toplevel_info(|info| {
|
||||
info.parent = parent;
|
||||
if new_size != info.size {
|
||||
info.size = new_size;
|
||||
size_changed = true;
|
||||
}
|
||||
info.min_size = min_size;
|
||||
info.max_size = max_size;
|
||||
info.logical_rectangle = logical_rectangle;
|
||||
});
|
||||
|
||||
if size_changed {
|
||||
let Some(panel_item) = surface_panel_item(surf) else {
|
||||
return;
|
||||
};
|
||||
if let Some(toplevel_info) = surf.get_toplevel_info() {
|
||||
panel_item.toplevel_size_changed(toplevel_info.size);
|
||||
}
|
||||
}
|
||||
},
|
||||
);
|
||||
|
||||
add_post_commit_hook(
|
||||
toplevel.wl_surface(),
|
||||
|state: &mut WaylandState, _dh, surf| {
|
||||
@@ -156,32 +186,6 @@ impl XdgShellHandler for WaylandState {
|
||||
surf.insert_data(node);
|
||||
},
|
||||
);
|
||||
|
||||
add_post_commit_hook(
|
||||
toplevel.wl_surface(),
|
||||
|_state: &mut WaylandState, _dh, surf| {
|
||||
let Some(panel_item) = surface_panel_item(surf) else {
|
||||
return;
|
||||
};
|
||||
let Some(size) = surf
|
||||
.get_data_raw::<RendererSurfaceStateUserData, _, _>(|surface_states| {
|
||||
surface_states.lock().unwrap().surface_size()
|
||||
})
|
||||
.flatten()
|
||||
else {
|
||||
return;
|
||||
};
|
||||
let size = [size.w as u32, size.h as u32].into();
|
||||
surf.get_data_raw::<Mutex<Vector2<u32>>, _, _>(|old_size| {
|
||||
let mut old_size = old_size.lock();
|
||||
|
||||
if *old_size != size {
|
||||
panel_item.toplevel_size_changed(size);
|
||||
*old_size = size;
|
||||
}
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
fn toplevel_destroyed(&mut self, toplevel: ToplevelSurface) {
|
||||
let Some(panel_item) = surface_panel_item(toplevel.wl_surface()) else {
|
||||
@@ -192,32 +196,35 @@ impl XdgShellHandler for WaylandState {
|
||||
panel_item.backend.children.lock().clear();
|
||||
}
|
||||
fn app_id_changed(&mut self, toplevel: ToplevelSurface) {
|
||||
let Some(panel_item) = surface_panel_item(toplevel.wl_surface()) else {
|
||||
let wl_surface = toplevel.wl_surface();
|
||||
let Some(app_id) = wl_surface.get_app_id() else {
|
||||
return;
|
||||
};
|
||||
|
||||
panel_item.toplevel_app_id_changed(
|
||||
&toplevel
|
||||
.wl_surface()
|
||||
.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| {
|
||||
d.lock().unwrap().app_id.clone().unwrap()
|
||||
})
|
||||
.unwrap_or_default(),
|
||||
)
|
||||
wl_surface.with_toplevel_info(|info| {
|
||||
info.app_id = Some(app_id.clone());
|
||||
});
|
||||
|
||||
let Some(panel_item) = surface_panel_item(wl_surface) else {
|
||||
return;
|
||||
};
|
||||
panel_item.toplevel_app_id_changed(&app_id)
|
||||
}
|
||||
|
||||
fn title_changed(&mut self, toplevel: ToplevelSurface) {
|
||||
let Some(panel_item) = surface_panel_item(toplevel.wl_surface()) else {
|
||||
let wl_surface = toplevel.wl_surface();
|
||||
let Some(title) = wl_surface.get_title() else {
|
||||
return;
|
||||
};
|
||||
|
||||
panel_item.toplevel_title_changed(
|
||||
&toplevel
|
||||
.wl_surface()
|
||||
.get_data_raw::<XdgToplevelSurfaceData, _, _>(|d| {
|
||||
d.lock().unwrap().title.clone().unwrap()
|
||||
})
|
||||
.unwrap_or_default(),
|
||||
)
|
||||
wl_surface.with_toplevel_info(|info| {
|
||||
info.title = Some(title.clone());
|
||||
});
|
||||
|
||||
let Some(panel_item) = surface_panel_item(wl_surface) else {
|
||||
return;
|
||||
};
|
||||
panel_item.toplevel_title_changed(&title)
|
||||
}
|
||||
|
||||
fn new_popup(&mut self, popup: PopupSurface, positioner: PositionerState) {
|
||||
@@ -232,12 +239,7 @@ impl XdgShellHandler for WaylandState {
|
||||
popup.wl_surface().insert_data(Mutex::new(ChildInfo {
|
||||
id,
|
||||
parent: parent.get_data::<SurfaceId>().unwrap(),
|
||||
geometry: positioner
|
||||
.get_unconstrained_geometry(Rectangle {
|
||||
loc: (-100000, -100000).into(),
|
||||
size: (200000, 200000).into(),
|
||||
})
|
||||
.into(),
|
||||
geometry: get_unconstrained_popup_geometry(&positioner),
|
||||
z_order: 1,
|
||||
receives_input: true,
|
||||
}));
|
||||
@@ -271,12 +273,7 @@ impl XdgShellHandler for WaylandState {
|
||||
};
|
||||
|
||||
popup.wl_surface().with_child_info(|ci| {
|
||||
ci.geometry = positioner
|
||||
.get_unconstrained_geometry(Rectangle {
|
||||
loc: (-100000, -100000).into(),
|
||||
size: (200000, 200000).into(),
|
||||
})
|
||||
.into()
|
||||
ci.geometry = get_unconstrained_popup_geometry(&positioner);
|
||||
});
|
||||
|
||||
panel_item.backend.reposition_child(popup.wl_surface());
|
||||
@@ -359,7 +356,6 @@ impl XdgBackend {
|
||||
XdgBackend {
|
||||
toplevel: Mutex::new(Some(toplevel)),
|
||||
children: Mutex::new(FxHashMap::default()),
|
||||
// popups: Mutex::new(FxHashMap::default()),
|
||||
seat,
|
||||
}
|
||||
}
|
||||
@@ -415,90 +411,18 @@ impl Backend for XdgBackend {
|
||||
.clone()
|
||||
.and_then(|s| s.upgrade().ok())
|
||||
.as_ref()
|
||||
.and_then(CoreSurface::from_wl_surface)
|
||||
.and_then(|c| c.size())
|
||||
.and_then(|c| c.get_size())
|
||||
.map(|size| Geometry {
|
||||
origin: [0; 2].into(),
|
||||
size,
|
||||
});
|
||||
|
||||
let toplevel = self
|
||||
let toplevel_info = self
|
||||
.toplevel
|
||||
.lock()
|
||||
.clone()
|
||||
.ok_or(eyre!("Internal: no toplevel"))?;
|
||||
let (app_id, title) = compositor::with_states(toplevel.wl_surface(), |states| {
|
||||
let xdg_toplevel_data = states
|
||||
.data_map
|
||||
.get::<XdgToplevelSurfaceData>()
|
||||
.ok_or(eyre!("Internal: XdgToplevelSurfaceData not found"))?;
|
||||
|
||||
let locked_data = xdg_toplevel_data
|
||||
.lock()
|
||||
.map_err(|_| eyre!("Internal: Failed to lock XdgToplevelSurfaceData"))?;
|
||||
|
||||
Ok::<_, color_eyre::eyre::Report>((
|
||||
locked_data.app_id.clone(),
|
||||
locked_data.title.clone(),
|
||||
))
|
||||
})?;
|
||||
let toplevel_cached_state = compositor::with_states(toplevel.wl_surface(), |states| {
|
||||
*states.cached_state.get::<SurfaceCachedState>().current()
|
||||
});
|
||||
let toplevel_core_surface = CoreSurface::from_wl_surface(toplevel.wl_surface())
|
||||
.ok_or(eyre!("Internal: Failed to get CoreSurface from WlSurface"))?;
|
||||
|
||||
let size = toplevel
|
||||
.current_state()
|
||||
.size
|
||||
.map(|s| Vector2::from([s.w as u32, s.h as u32]))
|
||||
.or_else(|| toplevel_core_surface.size())
|
||||
.unwrap_or(Vector2::from([0; 2]));
|
||||
let parent = toplevel
|
||||
.parent()
|
||||
.as_ref()
|
||||
.and_then(surface_panel_item)
|
||||
.and_then(|p| p.node.upgrade())
|
||||
.map(|p| p.get_id());
|
||||
let toplevel = ToplevelInfo {
|
||||
parent,
|
||||
title,
|
||||
app_id,
|
||||
size,
|
||||
min_size: if toplevel_cached_state.min_size.w != 0
|
||||
&& toplevel_cached_state.min_size.h != 0
|
||||
{
|
||||
Some(
|
||||
[
|
||||
toplevel_cached_state.min_size.w as f32,
|
||||
toplevel_cached_state.min_size.h as f32,
|
||||
]
|
||||
.into(),
|
||||
)
|
||||
} else {
|
||||
None
|
||||
},
|
||||
max_size: if toplevel_cached_state.max_size.w != 0
|
||||
&& toplevel_cached_state.max_size.h != 0
|
||||
{
|
||||
Some(
|
||||
[
|
||||
toplevel_cached_state.max_size.w as f32,
|
||||
toplevel_cached_state.max_size.h as f32,
|
||||
]
|
||||
.into(),
|
||||
)
|
||||
} else {
|
||||
None
|
||||
},
|
||||
logical_rectangle: toplevel_cached_state
|
||||
.geometry
|
||||
.map(Into::into)
|
||||
.unwrap_or_else(|| Geometry {
|
||||
origin: [0; 2].into(),
|
||||
size,
|
||||
}),
|
||||
};
|
||||
.and_then(|toplevel| toplevel.wl_surface().get_toplevel_info())
|
||||
.ok_or(eyre!("Internal: no toplevel or ToplevelInfo"))?;
|
||||
|
||||
let children = self
|
||||
.children
|
||||
@@ -509,7 +433,7 @@ impl Backend for XdgBackend {
|
||||
|
||||
Ok(PanelItemInitData {
|
||||
cursor,
|
||||
toplevel,
|
||||
toplevel: toplevel_info,
|
||||
children,
|
||||
pointer_grab: None,
|
||||
keyboard_grab: None,
|
||||
|
||||
Reference in New Issue
Block a user