Add setting to toggle workspace wrapping

This commit is contained in:
olekawaii 2026-03-22 01:01:33 -04:00 committed by Victoria Brekenfeld
parent 7ec23b0527
commit 4df95190db
2 changed files with 117 additions and 82 deletions

View file

@ -4,13 +4,30 @@ use serde::{Deserialize, Serialize};
use crate::EdidProduct; use crate::EdidProduct;
#[derive(Debug, Clone, Default, PartialEq, Serialize, Deserialize)] #[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct WorkspaceConfig { pub struct WorkspaceConfig {
pub workspace_mode: WorkspaceMode, pub workspace_mode: WorkspaceMode,
#[serde(default)] #[serde(default)]
pub workspace_layout: WorkspaceLayout, pub workspace_layout: WorkspaceLayout,
#[serde(default)] #[serde(default)]
pub action_on_typing: Action, pub action_on_typing: Action,
#[serde(default = "default_wraparound")]
pub workspace_wraparound: bool,
}
fn default_wraparound() -> bool {
true
}
impl Default for WorkspaceConfig {
fn default() -> Self {
Self {
workspace_mode: WorkspaceMode::default(),
workspace_layout: WorkspaceLayout::default(),
action_on_typing: Action::default(),
workspace_wraparound: default_wraparound(),
}
}
} }
#[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Serialize, Deserialize)] #[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Serialize, Deserialize)]

View file

@ -102,6 +102,12 @@ impl State {
pub fn handle_swipe_action(&mut self, action: gestures::SwipeAction, seat: &Seat<State>) { pub fn handle_swipe_action(&mut self, action: gestures::SwipeAction, seat: &Seat<State>) {
use gestures::SwipeAction; use gestures::SwipeAction;
let wraparound: bool = self
.common
.config
.cosmic_conf
.workspaces
.workspace_wraparound;
match action { match action {
SwipeAction::NextWorkspace => { SwipeAction::NextWorkspace => {
@ -109,6 +115,7 @@ impl State {
&mut self.common.shell.write(), &mut self.common.shell.write(),
seat, seat,
true, true,
wraparound,
&mut self.common.workspace_state.update(), &mut self.common.workspace_state.update(),
); );
} }
@ -117,6 +124,7 @@ impl State {
&mut self.common.shell.write(), &mut self.common.shell.write(),
seat, seat,
true, true,
wraparound,
&mut self.common.workspace_state.update(), &mut self.common.workspace_state.update(),
); );
} }
@ -203,32 +211,26 @@ impl State {
&mut self.common.shell.write(), &mut self.common.shell.write(),
seat, seat,
false, false,
self.common
.config
.cosmic_conf
.workspaces
.workspace_wraparound,
&mut self.common.workspace_state.update(), &mut self.common.workspace_state.update(),
); );
if next.is_err() { if next.is_err()
if propagate { && propagate
if let Some(inferred) = pattern.inferred_direction() { && let Some(inferred) = pattern.inferred_direction()
self.handle_shortcut_action( {
Action::SwitchOutput(inferred), self.handle_shortcut_action(
seat, Action::SwitchOutput(inferred),
serial, seat,
time, serial,
pattern, time,
direction, pattern,
true, direction,
) true,
}; )
} else {
self.handle_shortcut_action(
Action::Workspace(1),
seat,
serial,
time,
pattern,
direction,
false,
)
}
} }
} }
@ -248,33 +250,27 @@ impl State {
&mut self.common.shell.write(), &mut self.common.shell.write(),
seat, seat,
false, false,
self.common
.config
.cosmic_conf
.workspaces
.workspace_wraparound,
&mut self.common.workspace_state.update(), &mut self.common.workspace_state.update(),
); );
if previous.is_err() { if previous.is_err()
if propagate { && propagate
if let Some(inferred) = pattern.inferred_direction() { && let Some(inferred) = pattern.inferred_direction()
self.handle_shortcut_action( {
Action::SwitchOutput(inferred), self.handle_shortcut_action(
seat, Action::SwitchOutput(inferred),
serial, seat,
time, serial,
pattern, time,
direction, pattern,
true, direction,
) true,
}; )
} else { };
self.handle_shortcut_action(
Action::LastWorkspace,
seat,
serial,
time,
pattern,
direction,
false,
)
}
}
} }
x @ Action::MoveToWorkspace(_) | x @ Action::SendToWorkspace(_) => { x @ Action::MoveToWorkspace(_) | x @ Action::SendToWorkspace(_) => {
@ -398,20 +394,29 @@ impl State {
} }
} }
Err(_) => { Err(_) => {
// cycle through let wraparound = self
self.handle_shortcut_action( .common
if matches!(x, Action::MoveToNextWorkspace) { .config
Action::MoveToWorkspace(1) .cosmic_conf
} else { .workspaces
Action::SendToWorkspace(1) .workspace_wraparound;
},
seat, if wraparound {
serial, // cycle through
time, self.handle_shortcut_action(
pattern, if matches!(x, Action::MoveToNextWorkspace) {
direction, Action::MoveToWorkspace(1)
false, } else {
) Action::SendToWorkspace(1)
},
seat,
serial,
time,
pattern,
direction,
false,
)
}
} }
} }
} }
@ -480,20 +485,29 @@ impl State {
} }
} }
Err(_) => { Err(_) => {
// cycle through let wraparound = self
self.handle_shortcut_action( .common
if matches!(x, Action::MoveToPreviousWorkspace) { .config
Action::MoveToLastWorkspace .cosmic_conf
} else { .workspaces
Action::SendToLastWorkspace .workspace_wraparound;
},
seat, if wraparound {
serial, // cycle through
time, self.handle_shortcut_action(
pattern, if matches!(x, Action::MoveToPreviousWorkspace) {
direction, Action::MoveToLastWorkspace
false, } else {
) Action::SendToLastWorkspace
},
seat,
serial,
time,
pattern,
direction,
false,
)
}
} }
} }
} }
@ -1096,6 +1110,7 @@ fn to_next_workspace(
shell: &mut Shell, shell: &mut Shell,
seat: &Seat<State>, seat: &Seat<State>,
gesture: bool, gesture: bool,
wraparound: bool,
workspace_state: &mut WorkspaceUpdateGuard<'_, State>, workspace_state: &mut WorkspaceUpdateGuard<'_, State>,
) -> Result<Point<i32, Global>, InvalidWorkspaceIndex> { ) -> Result<Point<i32, Global>, InvalidWorkspaceIndex> {
let current_output = seat.active_output(); let current_output = seat.active_output();
@ -1103,7 +1118,7 @@ fn to_next_workspace(
let mut workspace = active.checked_add(1).ok_or(InvalidWorkspaceIndex)?; let mut workspace = active.checked_add(1).ok_or(InvalidWorkspaceIndex)?;
if workspace >= shell.workspaces.len(&current_output) { if workspace >= shell.workspaces.len(&current_output) {
workspace = 0; workspace = if wraparound { 0 } else { active }
} }
if workspace == active { if workspace == active {
return Err(InvalidWorkspaceIndex); return Err(InvalidWorkspaceIndex);
@ -1125,17 +1140,20 @@ fn to_previous_workspace(
shell: &mut Shell, shell: &mut Shell,
seat: &Seat<State>, seat: &Seat<State>,
gesture: bool, gesture: bool,
wraparound: bool,
workspace_state: &mut WorkspaceUpdateGuard<'_, State>, workspace_state: &mut WorkspaceUpdateGuard<'_, State>,
) -> Result<Point<i32, Global>, InvalidWorkspaceIndex> { ) -> Result<Point<i32, Global>, InvalidWorkspaceIndex> {
let current_output = seat.active_output(); let current_output = seat.active_output();
let active = shell.workspaces.active_num(&current_output).1; let active = shell.workspaces.active_num(&current_output).1;
let workspace = active.checked_sub(1).unwrap_or( let workspace = active.checked_sub(1).unwrap_or(if wraparound {
shell shell
.workspaces .workspaces
.len(&current_output) .len(&current_output)
.checked_sub(1) .checked_sub(1)
.ok_or(InvalidWorkspaceIndex)?, .ok_or(InvalidWorkspaceIndex)?
); } else {
0
});
if workspace == active { if workspace == active {
return Err(InvalidWorkspaceIndex); return Err(InvalidWorkspaceIndex);