Skip to content

Commit

Permalink
wip: overlap workspace filtering
Browse files Browse the repository at this point in the history
  • Loading branch information
wash2 committed Dec 5, 2024
1 parent fcd5378 commit 92b3e1c
Show file tree
Hide file tree
Showing 3 changed files with 37 additions and 33 deletions.
3 changes: 1 addition & 2 deletions src/state.rs
Original file line number Diff line number Diff line change
Expand Up @@ -501,8 +501,7 @@ impl State {
let output_state = OutputManagerState::new_with_xdg_output::<Self>(dh);
let output_configuration_state = OutputConfigurationState::new(dh, client_is_privileged);
let output_power_state = OutputPowerState::new::<Self, _>(dh, client_is_privileged);
let overlap_notify_state =
OverlapNotifyState::new::<Self, _>(dh, client_has_no_security_context);
let overlap_notify_state = OverlapNotifyState::new::<_>(dh, client_has_no_security_context);
let presentation_state = PresentationState::new::<Self>(dh, clock.id() as u32);
let primary_selection_state = PrimarySelectionState::new::<Self>(dh);
let image_source_state = ImageSourceState::new::<Self, _>(dh, client_is_privileged);
Expand Down
61 changes: 31 additions & 30 deletions src/wayland/protocols/overlap_notify.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,18 +23,13 @@ use smithay::{
wayland_server::{Client, Dispatch, DisplayHandle, GlobalDispatch, Resource, Weak},
},
utils::{Logical, Rectangle},
wayland::{
foreign_toplevel_list::ForeignToplevelListHandler,
shell::wlr_layer::{ExclusiveZone, Layer},
},
wayland::shell::wlr_layer::{ExclusiveZone, Layer},
};
use wayland_backend::server::{GlobalId, ObjectId};

use crate::utils::prelude::{RectExt, RectGlobalExt, RectLocalExt};
use crate::utils::prelude::{RectExt, RectGlobalExt, RectLocalExt, State};

use super::toplevel_info::{
ToplevelHandleState, ToplevelInfoGlobalData, ToplevelInfoHandler, ToplevelState, Window,
};
use super::toplevel_info::{ToplevelHandleStateInner, ToplevelInfoHandler, ToplevelState, Window};

#[derive(Debug)]
pub struct OverlapNotifyState {
Expand All @@ -43,16 +38,11 @@ pub struct OverlapNotifyState {
}

impl OverlapNotifyState {
pub fn new<D, F>(dh: &DisplayHandle, client_filter: F) -> OverlapNotifyState
pub fn new<F>(dh: &DisplayHandle, client_filter: F) -> OverlapNotifyState
where
D: GlobalDispatch<ZcosmicOverlapNotifyV1, OverlapNotifyGlobalData>
+ Dispatch<ZcosmicOverlapNotifyV1, ()>
+ Dispatch<ZcosmicOverlapNotificationV1, ()>
+ OverlapNotifyHandler
+ 'static,
F: for<'a> Fn(&'a Client) -> bool + Send + Sync + 'static,
{
let global = dh.create_global::<D, ZcosmicOverlapNotifyV1, _>(
let global = dh.create_global::<State, ZcosmicOverlapNotifyV1, _>(
1,
OverlapNotifyGlobalData {
filter: Box::new(client_filter),
Expand All @@ -68,27 +58,24 @@ impl OverlapNotifyState {
self.global.clone()
}

pub fn refresh<D, W>(state: &mut D)
where
D: GlobalDispatch<ZcosmicOverlapNotifyV1, OverlapNotifyGlobalData>
+ Dispatch<ZcosmicOverlapNotifyV1, ()>
+ Dispatch<ZcosmicOverlapNotificationV1, ()>
+ OverlapNotifyHandler
+ GlobalDispatch<ZcosmicToplevelInfoV1, ToplevelInfoGlobalData>
+ Dispatch<ZcosmicToplevelInfoV1, ()>
+ Dispatch<ZcosmicToplevelHandleV1, ToplevelHandleState<W>>
+ ForeignToplevelListHandler
+ ToplevelInfoHandler<Window = W>
+ 'static,
W: Window + 'static,
{
pub fn refresh(state: &mut State) {
let shell = state.common.shell.read().unwrap();
let active_workspaces: HashMap<_, _> = shell
.workspaces
.sets
.iter()
.map(|(output, set)| (output.clone(), set.workspaces[set.active].handle))
.collect();
drop(shell);
for output in state.outputs() {
let map = layer_map_for_output(&output);

for layer_surface in map.layers() {
if let Some(data) = layer_surface
.user_data()
.get::<LayerOverlapNotificationData>()
{
let active_workspace = active_workspaces.get(&output);
let mut inner = data.lock().unwrap();

if inner.has_active_notifications() {
Expand All @@ -100,7 +87,21 @@ impl OverlapNotifyState {
.as_local()
.to_global(&output);

for window in state.toplevel_info_state().registered_toplevels() {
for window in
state
.toplevel_info_state()
.registered_toplevels()
.filter(|w| {
if let Some(active_workspace) = active_workspace.as_ref() {
ToplevelHandleStateInner::from_window(*w)
.lock()
.unwrap()
.in_workspace(&active_workspace)
} else {
true
}
})
{
if let Some(window_geo) = window.global_geometry() {
if let Some(intersection) = layer_geo.intersection(window_geo) {
// relative to layer location
Expand Down
6 changes: 5 additions & 1 deletion src/wayland/protocols/toplevel_info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ pub struct ToplevelHandleStateInner<W: Window> {
pub type ToplevelHandleState<W> = Mutex<ToplevelHandleStateInner<W>>;

impl<W: Window> ToplevelHandleStateInner<W> {
fn from_window(window: &W) -> ToplevelHandleState<W> {
pub fn from_window(window: &W) -> ToplevelHandleState<W> {
ToplevelHandleState::new(ToplevelHandleStateInner {
outputs: Vec::new(),
geometry: None,
Expand All @@ -120,6 +120,10 @@ impl<W: Window> ToplevelHandleStateInner<W> {
window: None,
})
}

pub fn in_workspace(&self, handle: &WorkspaceHandle) -> bool {
self.workspaces.contains(handle)
}
}

impl<D, W> GlobalDispatch<ZcosmicToplevelInfoV1, ToplevelInfoGlobalData, D>
Expand Down

0 comments on commit 92b3e1c

Please sign in to comment.