diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/input/mod.rs | 14 | ||||
| -rw-r--r-- | src/layout/floating.rs | 6 | ||||
| -rw-r--r-- | src/layout/mod.rs | 21 | ||||
| -rw-r--r-- | src/layout/scrolling.rs | 22 | ||||
| -rw-r--r-- | src/layout/workspace.rs | 12 |
5 files changed, 71 insertions, 4 deletions
diff --git a/src/input/mod.rs b/src/input/mod.rs index d45d0e8a..98bbbb8e 100644 --- a/src/input/mod.rs +++ b/src/input/mod.rs @@ -1127,6 +1127,20 @@ impl State { // FIXME: granular self.niri.queue_redraw_all(); } + Action::CenterWindow => { + self.niri.layout.center_window(None); + // FIXME: granular + self.niri.queue_redraw_all(); + } + Action::CenterWindowById(id) => { + let window = self.niri.layout.windows().find(|(_, m)| m.id().get() == id); + let window = window.map(|(_, m)| m.window.clone()); + if let Some(window) = window { + self.niri.layout.center_window(Some(&window)); + // FIXME: granular + self.niri.queue_redraw_all(); + } + } Action::MaximizeColumn => { self.niri.layout.toggle_full_width(); } diff --git a/src/layout/floating.rs b/src/layout/floating.rs index 6192d119..5302e158 100644 --- a/src/layout/floating.rs +++ b/src/layout/floating.rs @@ -902,11 +902,11 @@ impl<W: LayoutElement> FloatingSpace<W> { self.move_to(idx, new_pos, animate); } - pub fn center_window(&mut self) { - let Some(active_id) = &self.active_window_id else { + pub fn center_window(&mut self, id: Option<&W::Id>) { + let Some(id) = id.or(self.active_window_id.as_ref()).cloned() else { return; }; - let idx = self.idx_of(active_id).unwrap(); + let idx = self.idx_of(&id).unwrap(); let new_pos = center_preferring_top_left_in_area(self.working_area, self.data[idx].size); self.move_to(idx, new_pos, true); diff --git a/src/layout/mod.rs b/src/layout/mod.rs index 433cae43..571411fc 100644 --- a/src/layout/mod.rs +++ b/src/layout/mod.rs @@ -1993,6 +1993,19 @@ impl<W: LayoutElement> Layout<W> { monitor.center_column(); } + pub fn center_window(&mut self, id: Option<&W::Id>) { + let workspace = if let Some(id) = id { + Some(self.workspaces_mut().find(|ws| ws.has_window(id)).unwrap()) + } else { + self.active_workspace_mut() + }; + + let Some(workspace) = workspace else { + return; + }; + workspace.center_window(id); + } + pub fn focus(&self) -> Option<&W> { self.focus_with_output().map(|(win, _out)| win) } @@ -4390,6 +4403,10 @@ mod tests { ConsumeWindowIntoColumn, ExpelWindowFromColumn, CenterColumn, + CenterWindow { + #[proptest(strategy = "proptest::option::of(1..=5usize)")] + id: Option<usize>, + }, FocusWorkspaceDown, FocusWorkspaceUp, FocusWorkspace(#[proptest(strategy = "0..=4usize")] usize), @@ -4901,6 +4918,10 @@ mod tests { Op::ConsumeWindowIntoColumn => layout.consume_into_column(), Op::ExpelWindowFromColumn => layout.expel_from_column(), Op::CenterColumn => layout.center_column(), + Op::CenterWindow { id } => { + let id = id.filter(|id| layout.has_window(id)); + layout.center_window(id.as_ref()); + } Op::FocusWorkspaceDown => layout.switch_workspace_down(), Op::FocusWorkspaceUp => layout.switch_workspace_up(), Op::FocusWorkspace(idx) => layout.switch_workspace(idx), diff --git a/src/layout/scrolling.rs b/src/layout/scrolling.rs index a378c461..6fa6fbfc 100644 --- a/src/layout/scrolling.rs +++ b/src/layout/scrolling.rs @@ -1747,6 +1747,28 @@ impl<W: LayoutElement> ScrollingSpace<W> { cancel_resize_for_column(&mut self.interactive_resize, col); } + pub fn center_window(&mut self, window: Option<&W::Id>) { + if self.columns.is_empty() { + return; + } + + let col_idx = if let Some(window) = window { + self.columns + .iter() + .position(|col| col.contains(window)) + .unwrap() + } else { + self.active_column_idx + }; + + // We can reasonably center only the active column. + if col_idx != self.active_column_idx { + return; + } + + self.center_column(); + } + pub fn view_pos(&self) -> f64 { self.column_x(self.active_column_idx) + self.view_offset.current() } diff --git a/src/layout/workspace.rs b/src/layout/workspace.rs index 991e7e42..0e67f3b3 100644 --- a/src/layout/workspace.rs +++ b/src/layout/workspace.rs @@ -971,12 +971,22 @@ impl<W: LayoutElement> Workspace<W> { pub fn center_column(&mut self) { if self.floating_is_active.get() { - self.floating.center_window(); + self.floating.center_window(None); } else { self.scrolling.center_column(); } } + pub fn center_window(&mut self, id: Option<&W::Id>) { + if id.map_or(self.floating_is_active.get(), |id| { + self.floating.has_window(id) + }) { + self.floating.center_window(id); + } else { + self.scrolling.center_window(id); + } + } + pub fn toggle_width(&mut self) { if self.floating_is_active.get() { self.floating.toggle_window_width(None); |
