pane: Ignore max tabs on terminal pane (#40740)

Closes #39901

I'm unsure as to which direction the team wants to go with this, but
this is the behavior of VSCode which is what this feature is based off
so i'm going with this.

Changes: 

1. Introduced a new argument to the `new` method on the Pane called
`ignore_max_tabs` that forces the `max_tabs` to None if it's true.
2. Added a new test `test_bypass_max_tabs_limit`.

Release Notes:

- Fixed: `max_tabs` Setting affecting the terminal pane.

---------

Co-authored-by: Joseph T. Lyons <JosephTLyons@gmail.com>
This commit is contained in:
vipex
2025-10-20 21:19:40 -04:00
committed by GitHub
co-authored by Joseph T. Lyons
parent a2c42813c4
commit 36c006828e
4 changed files with 64 additions and 2 deletions
@@ -386,6 +386,7 @@ pub(crate) fn new_debugger_pane(
Default::default(),
None,
NoAction.boxed_clone(),
true,
window,
cx,
);
@@ -1103,6 +1103,7 @@ pub fn new_terminal_pane(
Default::default(),
None,
NewTerminal.boxed_clone(),
false,
window,
cx,
);
@@ -1752,6 +1753,8 @@ impl Render for InlineAssistTabBarButton {
#[cfg(test)]
mod tests {
use std::num::NonZero;
use super::*;
use gpui::{TestAppContext, UpdateGlobal as _};
use pretty_assertions::assert_eq;
@@ -1808,6 +1811,46 @@ mod tests {
.unwrap();
}
#[gpui::test]
async fn test_bypass_max_tabs_limit(cx: &mut TestAppContext) {
init_test(cx);
let fs = FakeFs::new(cx.executor());
let project = Project::test(fs, [], cx).await;
let workspace = cx.add_window(|window, cx| Workspace::test_new(project, window, cx));
let (window_handle, terminal_panel) = workspace
.update(cx, |workspace, window, cx| {
let window_handle = window.window_handle();
let terminal_panel = cx.new(|cx| TerminalPanel::new(workspace, window, cx));
(window_handle, terminal_panel)
})
.unwrap();
set_max_tabs(cx, Some(3));
for _ in 0..5 {
let task = window_handle
.update(cx, |_, window, cx| {
terminal_panel.update(cx, |panel, cx| {
panel.add_terminal_shell(None, RevealStrategy::Always, window, cx)
})
})
.unwrap();
task.await.unwrap();
}
cx.run_until_parked();
let item_count =
terminal_panel.read_with(cx, |panel, cx| panel.active_pane.read(cx).items_len());
assert_eq!(
item_count, 5,
"Terminal panel should bypass max_tabs limit and have all 5 terminals"
);
}
// A complex Unix command won't be properly parsed by the Windows terminal hence omit the test there.
#[cfg(unix)]
#[gpui::test]
@@ -1922,6 +1965,14 @@ mod tests {
.unwrap();
}
fn set_max_tabs(cx: &mut TestAppContext, value: Option<usize>) {
cx.update_global(|store: &mut SettingsStore, cx| {
store.update_user_settings(cx, |settings| {
settings.workspace.max_tabs = value.map(|v| NonZero::new(v).unwrap())
});
});
}
pub fn init_test(cx: &mut TestAppContext) {
cx.update(|cx| {
let store = SettingsStore::test(cx);
+10 -2
View File
@@ -376,6 +376,7 @@ pub struct Pane {
render_tab_bar: Rc<dyn Fn(&mut Pane, &mut Window, &mut Context<Pane>) -> AnyElement>,
show_tab_bar_buttons: bool,
max_tabs: Option<NonZeroUsize>,
use_max_tabs: bool,
_subscriptions: Vec<Subscription>,
tab_bar_scroll_handle: ScrollHandle,
/// This is set to true if a user scroll has occurred more recently than a system scroll
@@ -473,10 +474,16 @@ impl Pane {
next_timestamp: Arc<AtomicUsize>,
can_drop_predicate: Option<Arc<dyn Fn(&dyn Any, &mut Window, &mut App) -> bool + 'static>>,
double_click_dispatch_action: Box<dyn Action>,
use_max_tabs: bool,
window: &mut Window,
cx: &mut Context<Self>,
) -> Self {
let focus_handle = cx.focus_handle();
let max_tabs = if use_max_tabs {
WorkspaceSettings::get_global(cx).max_tabs
} else {
None
};
let subscriptions = vec![
cx.on_focus(&focus_handle, window, Pane::focus_in),
@@ -498,7 +505,8 @@ impl Pane {
zoomed: false,
active_item_index: 0,
preview_item_id: None,
max_tabs: WorkspaceSettings::get_global(cx).max_tabs,
max_tabs,
use_max_tabs,
last_focus_handle_by_item: Default::default(),
nav_history: NavHistory(Arc::new(Mutex::new(NavHistoryState {
mode: NavigationMode::Normal,
@@ -706,7 +714,7 @@ impl Pane {
self.preview_item_id = None;
}
if new_max_tabs != self.max_tabs {
if self.use_max_tabs && new_max_tabs != self.max_tabs {
self.max_tabs = new_max_tabs;
self.close_items_on_settings_change(window, cx);
}
+2
View File
@@ -1331,6 +1331,7 @@ impl Workspace {
pane_history_timestamp.clone(),
None,
NewFile.boxed_clone(),
true,
window,
cx,
);
@@ -3235,6 +3236,7 @@ impl Workspace {
self.pane_history_timestamp.clone(),
None,
NewFile.boxed_clone(),
true,
window,
cx,
);