wayland: toplevel management protocol
This commit is contained in:
parent
4f142d50b3
commit
6b659eb107
9 changed files with 340 additions and 54 deletions
|
|
@ -1,6 +1,9 @@
|
|||
// SPDX-License-Identifier: GPL-3.0-only
|
||||
|
||||
use std::sync::Mutex;
|
||||
use std::{
|
||||
collections::HashMap,
|
||||
sync::Mutex,
|
||||
};
|
||||
|
||||
use smithay::{
|
||||
desktop::Window,
|
||||
|
|
@ -8,11 +11,12 @@ use smithay::{
|
|||
wayland_protocols::xdg::shell::server::xdg_toplevel,
|
||||
wayland_server::{
|
||||
backend::{ClientId, GlobalId, ObjectId},
|
||||
protocol::wl_surface::WlSurface,
|
||||
Client, DataInit, Dispatch, DisplayHandle,
|
||||
GlobalDispatch, New, Resource,
|
||||
},
|
||||
},
|
||||
utils::IsAlive,
|
||||
utils::{IsAlive, Rectangle, Logical},
|
||||
wayland::{
|
||||
compositor::with_states, output::Output, shell::xdg::XdgToplevelSurfaceRoleAttributes,
|
||||
},
|
||||
|
|
@ -27,7 +31,7 @@ use cosmic_protocols::toplevel_info::v1::server::{
|
|||
|
||||
pub struct ToplevelInfoState<D> {
|
||||
dh: DisplayHandle,
|
||||
toplevels: Vec<Window>,
|
||||
pub(super) toplevels: Vec<Window>,
|
||||
instances: Vec<ZcosmicToplevelInfoV1>,
|
||||
global: GlobalId,
|
||||
_dispatch_data: std::marker::PhantomData<D>,
|
||||
|
|
@ -43,24 +47,40 @@ pub struct ToplevelInfoGlobalData {
|
|||
}
|
||||
|
||||
#[derive(Default)]
|
||||
struct ToplevelStateInner {
|
||||
pub(super) struct ToplevelStateInner {
|
||||
instances: Vec<ZcosmicToplevelHandleV1>,
|
||||
outputs: Vec<Output>,
|
||||
workspaces: Vec<WorkspaceHandle>,
|
||||
minimized: bool,
|
||||
pub(super) rectangles: HashMap<ClientId, (WlSurface, Rectangle<i32, Logical>)>,
|
||||
}
|
||||
type ToplevelState = Mutex<ToplevelStateInner>;
|
||||
pub(super) type ToplevelState = Mutex<ToplevelStateInner>;
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct ToplevelHandleStateInner {
|
||||
outputs: Vec<Output>,
|
||||
workspaces: Vec<WorkspaceHandle>,
|
||||
title: String,
|
||||
app_id: String,
|
||||
states: Vec<States>,
|
||||
pub(super) window: Window,
|
||||
}
|
||||
pub type ToplevelHandleState = Mutex<ToplevelHandleStateInner>;
|
||||
|
||||
impl ToplevelHandleStateInner {
|
||||
fn from_window(window: &Window) -> ToplevelHandleState {
|
||||
ToplevelHandleState::new(
|
||||
ToplevelHandleStateInner {
|
||||
outputs: Vec::new(),
|
||||
workspaces: Vec::new(),
|
||||
title: String::new(),
|
||||
app_id: String::new(),
|
||||
states: Vec::new(),
|
||||
window: window.clone(),
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
impl<D> GlobalDispatch<ZcosmicToplevelInfoV1, ToplevelInfoGlobalData, D>
|
||||
for ToplevelInfoState<D>
|
||||
where
|
||||
|
|
@ -82,6 +102,7 @@ where
|
|||
for window in &state.toplevel_info_state().toplevels {
|
||||
send_toplevel_to_client::<D>(dh, Some(state.workspace_state()), &instance, window);
|
||||
}
|
||||
state.toplevel_info_state_mut().instances.push(instance);
|
||||
}
|
||||
|
||||
fn can_view(client: Client, global_data: &ToplevelInfoGlobalData) -> bool {
|
||||
|
|
@ -229,18 +250,21 @@ where
|
|||
|
||||
pub fn refresh(&mut self, workspace_state: Option<&WorkspaceState<D>>) {
|
||||
self.toplevels.retain(|window| {
|
||||
let mut state = window
|
||||
.user_data()
|
||||
.get::<ToplevelState>()
|
||||
.unwrap()
|
||||
.lock()
|
||||
.unwrap();
|
||||
state.rectangles
|
||||
.retain(|_, (surface, _)| surface.alive());
|
||||
if window.alive() {
|
||||
std::mem::drop(state);
|
||||
for instance in &self.instances {
|
||||
send_toplevel_to_client::<D>(&self.dh, workspace_state, instance, window);
|
||||
}
|
||||
true
|
||||
} else {
|
||||
let state = window
|
||||
.user_data()
|
||||
.get::<ToplevelState>()
|
||||
.unwrap()
|
||||
.lock()
|
||||
.unwrap();
|
||||
for handle in &state.instances {
|
||||
// don't send events to stopped instances
|
||||
if self
|
||||
|
|
@ -291,7 +315,7 @@ fn send_toplevel_to_client<D>(
|
|||
.create_resource::<ZcosmicToplevelHandleV1, _, D>(
|
||||
dh,
|
||||
info.version(),
|
||||
ToplevelHandleState::default(),
|
||||
ToplevelHandleStateInner::from_window(window),
|
||||
)
|
||||
{
|
||||
state.instances.push(toplevel_handle);
|
||||
|
|
@ -448,6 +472,16 @@ fn send_toplevel_to_client<D>(
|
|||
}
|
||||
}
|
||||
|
||||
pub(super) fn window_from_handle(handle: ZcosmicToplevelHandleV1) -> Window {
|
||||
handle
|
||||
.data::<ToplevelHandleState>()
|
||||
.unwrap()
|
||||
.lock()
|
||||
.unwrap()
|
||||
.window
|
||||
.clone()
|
||||
}
|
||||
|
||||
macro_rules! delegate_toplevel_info {
|
||||
($(@<$( $lt:tt $( : $clt:tt $(+ $dlt:tt )* )? ),+>)? $ty: ty) => {
|
||||
smithay::reexports::wayland_server::delegate_global_dispatch!($(@< $( $lt $( : $clt $(+ $dlt )* )? ),+ >)? $ty: [
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue