aboutsummaryrefslogtreecommitdiff
path: root/src/workspace.rs
diff options
context:
space:
mode:
authorOgulcan Celik <ogulcancelik@gmail.com>2026-04-10 14:15:23 +0300
committerOgulcan Celik <ogulcancelik@gmail.com>2026-04-10 14:16:25 +0300
commit831bb66c0cda103f79b2418389cd6528c03ade56 (patch)
tree0ae176496c492a035f3eb6fb9f8eab13bd397ca1 /src/workspace.rs
parente20be7bdae5c46ff922ee442b4fbd5d79c46cf99 (diff)
feat(tabs): add overflow scrolling and drag reorder
Diffstat (limited to 'src/workspace.rs')
-rw-r--r--src/workspace.rs46
1 files changed, 46 insertions, 0 deletions
diff --git a/src/workspace.rs b/src/workspace.rs
index 5fabe47f..09fa382d 100644
--- a/src/workspace.rs
+++ b/src/workspace.rs
@@ -399,6 +399,32 @@ impl Workspace {
true
}
+ pub fn move_tab(&mut self, source_idx: usize, insert_idx: usize) -> bool {
+ if source_idx >= self.tabs.len() || insert_idx > self.tabs.len() {
+ return false;
+ }
+
+ let target_idx = if source_idx < insert_idx {
+ insert_idx.saturating_sub(1)
+ } else {
+ insert_idx
+ }
+ .min(self.tabs.len().saturating_sub(1));
+
+ if source_idx == target_idx {
+ return false;
+ }
+
+ let active_root_pane = self.tabs.get(self.active_tab).map(|tab| tab.root_pane);
+ let tab = self.tabs.remove(source_idx);
+ self.tabs.insert(target_idx, tab);
+ self.renumber_tabs();
+ self.active_tab = active_root_pane
+ .and_then(|root_pane| self.tabs.iter().position(|tab| tab.root_pane == root_pane))
+ .unwrap_or(target_idx);
+ true
+ }
+
pub fn close_active_tab(&mut self) -> bool {
self.close_tab(self.active_tab)
}
@@ -963,6 +989,26 @@ mod tests {
}
#[test]
+ fn moving_tab_keeps_active_identity_and_renumbers_auto_tabs() {
+ let mut ws = Workspace::test_new("test");
+ let moved_root = ws.tabs[0].root_pane;
+ ws.test_add_tab(Some("foo"));
+ let final_auto_idx = ws.test_add_tab(None);
+ let active_root = ws.tabs[final_auto_idx].root_pane;
+ ws.switch_tab(final_auto_idx);
+
+ assert!(ws.move_tab(0, ws.tabs.len()));
+
+ let labels: Vec<_> = ws.tabs.iter().map(|tab| tab.display_name()).collect();
+ assert_eq!(labels, vec!["foo", "2", "3"]);
+ assert_eq!(ws.tabs[0].custom_name.as_deref(), Some("foo"));
+ assert!(ws.tabs[1].custom_name.is_none());
+ assert!(ws.tabs[2].custom_name.is_none());
+ assert_eq!(ws.tabs[2].root_pane, moved_root);
+ assert_eq!(ws.tabs[ws.active_tab].root_pane, active_root);
+ }
+
+ #[test]
fn pane_details_include_tab_context_when_workspace_has_multiple_tabs() {
let mut ws = Workspace::test_new("test");
ws.tabs[0].set_custom_name("main".into());