Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions niri-config/src/binds.rs
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,8 @@ pub enum Action {
FocusWindowUpOrColumnRight,
FocusWindowOrWorkspaceDown,
FocusWindowOrWorkspaceUp,
FocusWindowOrWorkspaceOrMonitorDown,
FocusWindowOrWorkspaceOrMonitorUp,
FocusWindowTop,
FocusWindowBottom,
FocusWindowDownOrTop,
Expand Down Expand Up @@ -460,6 +462,12 @@ impl From<niri_ipc::Action> for Action {
niri_ipc::Action::FocusWindowUpOrColumnRight {} => Self::FocusWindowUpOrColumnRight,
niri_ipc::Action::FocusWindowOrWorkspaceDown {} => Self::FocusWindowOrWorkspaceDown,
niri_ipc::Action::FocusWindowOrWorkspaceUp {} => Self::FocusWindowOrWorkspaceUp,
niri_ipc::Action::FocusWindowOrWorkspaceOrMonitorDown {} => {
Self::FocusWindowOrWorkspaceOrMonitorDown
}
niri_ipc::Action::FocusWindowOrWorkspaceOrMonitorUp {} => {
Self::FocusWindowOrWorkspaceOrMonitorUp
}
niri_ipc::Action::FocusWindowTop {} => Self::FocusWindowTop,
niri_ipc::Action::FocusWindowBottom {} => Self::FocusWindowBottom,
niri_ipc::Action::FocusWindowDownOrTop {} => Self::FocusWindowDownOrTop,
Expand Down
4 changes: 4 additions & 0 deletions niri-ipc/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -378,6 +378,10 @@ pub enum Action {
FocusWindowOrWorkspaceDown {},
/// Focus the window or the workspace above.
FocusWindowOrWorkspaceUp {},
/// Focus the window, the workspace below, or the monitor below.
FocusWindowOrWorkspaceOrMonitorDown {},
/// Focus the window, the workspace above, or the monitor above.
FocusWindowOrWorkspaceOrMonitorUp {},
/// Focus the topmost window.
FocusWindowTop {},
/// Focus the bottommost window.
Expand Down
34 changes: 34 additions & 0 deletions src/input/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1265,6 +1265,40 @@ impl State {
// FIXME: granular
self.niri.queue_redraw_all();
}
Action::FocusWindowOrWorkspaceOrMonitorDown => {
if !self.niri.layout.focus_window_or_workspace_or_monitor_down() {
// Fall back to monitor below
if let Some(output) = self.niri.output_down() {
self.niri.layout.focus_output(&output);
if !self.maybe_warp_cursor_to_focus_centered() {
self.move_cursor_to_output(&output);
}
self.niri.layer_shell_on_demand_focus = None;
}
} else {
self.maybe_warp_cursor_to_focus();
self.niri.layer_shell_on_demand_focus = None;
}
// FIXME: granular
self.niri.queue_redraw_all();
}
Action::FocusWindowOrWorkspaceOrMonitorUp => {
if !self.niri.layout.focus_window_or_workspace_or_monitor_up() {
// Fall back to monitor above
if let Some(output) = self.niri.output_up() {
self.niri.layout.focus_output(&output);
if !self.maybe_warp_cursor_to_focus_centered() {
self.move_cursor_to_output(&output);
}
self.niri.layer_shell_on_demand_focus = None;
}
} else {
self.maybe_warp_cursor_to_focus();
self.niri.layer_shell_on_demand_focus = None;
}
// FIXME: granular
self.niri.queue_redraw_all();
}
Action::FocusWindowTop => {
self.niri.layout.focus_window_top();
self.maybe_warp_cursor_to_focus();
Expand Down
14 changes: 14 additions & 0 deletions src/layout/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2032,6 +2032,20 @@ impl<W: LayoutElement> Layout<W> {
monitor.focus_window_or_workspace_up();
}

pub fn focus_window_or_workspace_or_monitor_down(&mut self) -> bool {
let Some(monitor) = self.active_monitor() else {
return false;
};
monitor.focus_window_or_workspace_or_monitor_down()
}

pub fn focus_window_or_workspace_or_monitor_up(&mut self) -> bool {
let Some(monitor) = self.active_monitor() else {
return false;
};
monitor.focus_window_or_workspace_or_monitor_up()
}

pub fn focus_window_top(&mut self) {
let Some(workspace) = self.active_workspace_mut() else {
return;
Expand Down
22 changes: 20 additions & 2 deletions src/layout/monitor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -781,6 +781,20 @@ impl<W: LayoutElement> Monitor<W> {
}
}

pub fn focus_window_or_workspace_or_monitor_down(&mut self) -> bool {
if self.active_workspace().focus_down() {
return true;
}
self.switch_workspace_down()
}

pub fn focus_window_or_workspace_or_monitor_up(&mut self) -> bool {
if self.active_workspace().focus_up() {
return true;
}
self.switch_workspace_up()
}

pub fn move_to_workspace_up(&mut self, focus: bool) {
let source_workspace_idx = self.active_workspace_idx;

Expand Down Expand Up @@ -974,7 +988,7 @@ impl<W: LayoutElement> Monitor<W> {
self.add_column(new_idx, column, activate);
}

pub fn switch_workspace_up(&mut self) {
pub fn switch_workspace_up(&mut self) -> bool {
let new_idx = match &self.workspace_switch {
// During a DnD scroll, select the prev apparent workspace.
Some(WorkspaceSwitch::Gesture(gesture)) if gesture.dnd_last_event_time.is_some() => {
Expand All @@ -985,10 +999,12 @@ impl<W: LayoutElement> Monitor<W> {
_ => self.active_workspace_idx.saturating_sub(1),
};

let changed = new_idx != self.active_workspace_idx;
self.activate_workspace(new_idx);
changed
}

pub fn switch_workspace_down(&mut self) {
pub fn switch_workspace_down(&mut self) -> bool {
let new_idx = match &self.workspace_switch {
// During a DnD scroll, select the next apparent workspace.
Some(WorkspaceSwitch::Gesture(gesture)) if gesture.dnd_last_event_time.is_some() => {
Expand All @@ -999,7 +1015,9 @@ impl<W: LayoutElement> Monitor<W> {
_ => min(self.active_workspace_idx + 1, self.workspaces.len() - 1),
};

let changed = new_idx != self.active_workspace_idx;
self.activate_workspace(new_idx);
changed
}

fn previous_workspace_idx(&self) -> Option<usize> {
Expand Down
8 changes: 8 additions & 0 deletions src/layout/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -475,6 +475,8 @@ enum Op {
FocusWindowUpOrColumnRight,
FocusWindowOrWorkspaceDown,
FocusWindowOrWorkspaceUp,
FocusWindowOrWorkspaceOrMonitorDown,
FocusWindowOrWorkspaceOrMonitorUp,
FocusWindow(#[proptest(strategy = "1..=5usize")] usize),
FocusWindowInColumn(#[proptest(strategy = "1..=5u8")] u8),
FocusWindowTop,
Expand Down Expand Up @@ -1123,6 +1125,8 @@ impl Op {
Op::FocusWindowUpOrColumnRight => layout.focus_up_or_right(),
Op::FocusWindowOrWorkspaceDown => layout.focus_window_or_workspace_down(),
Op::FocusWindowOrWorkspaceUp => layout.focus_window_or_workspace_up(),
Op::FocusWindowOrWorkspaceOrMonitorDown => layout.focus_window_or_workspace_or_monitor_down(),
Op::FocusWindowOrWorkspaceOrMonitorUp => layout.focus_window_or_workspace_or_monitor_up(),
Op::FocusWindow(id) => layout.activate_window(&id),
Op::FocusWindowInColumn(index) => layout.focus_window_in_column(index),
Op::FocusWindowTop => layout.focus_window_top(),
Expand Down Expand Up @@ -1706,10 +1710,12 @@ fn operations_dont_panic() {
Op::FocusWindowUpOrColumnLeft,
Op::FocusWindowUpOrColumnRight,
Op::FocusWindowOrWorkspaceUp,
Op::FocusWindowOrWorkspaceOrMonitorUp,
Op::FocusWindowDown,
Op::FocusWindowDownOrColumnLeft,
Op::FocusWindowDownOrColumnRight,
Op::FocusWindowOrWorkspaceDown,
Op::FocusWindowOrWorkspaceOrMonitorDown,
Op::MoveColumnLeft,
Op::MoveColumnRight,
Op::MoveColumnLeftOrToMonitorLeft(0),
Expand Down Expand Up @@ -1880,10 +1886,12 @@ fn operations_from_starting_state_dont_panic() {
Op::FocusWindowUpOrColumnLeft,
Op::FocusWindowUpOrColumnRight,
Op::FocusWindowOrWorkspaceUp,
Op::FocusWindowOrWorkspaceOrMonitorUp,
Op::FocusWindowDown,
Op::FocusWindowDownOrColumnLeft,
Op::FocusWindowDownOrColumnRight,
Op::FocusWindowOrWorkspaceDown,
Op::FocusWindowOrWorkspaceOrMonitorDown,
Op::MoveColumnLeft,
Op::MoveColumnRight,
Op::MoveColumnLeftOrToMonitorLeft(0),
Expand Down