Fix terminal pane showing welcome screen during loading (#48930)

Bennet Bo Fenner created

This fixes an issue where we would show the welcome screen when opening
the terminal panel.
The issue could technically occur in any panel, but was only occurred in
the terminal panel since we only render some content after the
`cx.spawn` inside `new_terminal_pane` completes. This caused the welcome
screen to show up for a single frame. This PR fixes this by showing a
blank panel instead.

Before


https://github.com/user-attachments/assets/4b805c42-5dc5-4742-b090-2f62e8839f3e

After 


https://github.com/user-attachments/assets/5da16b73-5999-461d-9057-438714d8d4ee

Screenshot from the videos:

Before

<img width="1164" height="579" alt="image"
src="https://github.com/user-attachments/assets/87ba2dff-d7c0-4104-b983-31bdd21cf0f9"
/>

After

<img width="1537" height="803" alt="image"
src="https://github.com/user-attachments/assets/359bc413-9794-4565-832d-83548b67cea5"
/>

- [x] Tests or screenshots needed?
- [x] Code Reviewed
- [x] Manual QA

Release Notes:

- Fixed an issue where the welcome screen would show up in the terminal
panel if the terminal was slow to load

Change summary

crates/workspace/src/pane.rs      | 12 ++++++++++--
crates/workspace/src/workspace.rs |  1 +
2 files changed, 11 insertions(+), 2 deletions(-)

Detailed changes

crates/workspace/src/pane.rs 🔗

@@ -391,6 +391,7 @@ pub struct Pane {
         Option<Arc<dyn Fn(&mut Self, &dyn Any, &mut Window, &mut Context<Self>) -> bool>>,
     can_toggle_zoom: bool,
     should_display_tab_bar: Rc<dyn Fn(&Window, &mut Context<Pane>) -> bool>,
+    should_display_welcome_page: bool,
     render_tab_bar_buttons: Rc<
         dyn Fn(
             &mut Pane,
@@ -574,6 +575,7 @@ impl Pane {
             can_split_predicate: None,
             can_toggle_zoom: true,
             should_display_tab_bar: Rc::new(|_, cx| TabBarSettings::get_global(cx).show),
+            should_display_welcome_page: false,
             render_tab_bar_buttons: Rc::new(default_render_tab_bar_buttons),
             render_tab_bar: Rc::new(Self::render_tab_bar),
             show_tab_bar_buttons: TabBarSettings::get_global(cx).show_tab_bar_buttons,
@@ -681,7 +683,9 @@ impl Pane {
                 self.last_focus_handle_by_item
                     .insert(active_item.item_id(), focused.downgrade());
             }
-        } else if let Some(welcome_page) = self.welcome_page.as_ref() {
+        } else if self.should_display_welcome_page
+            && let Some(welcome_page) = self.welcome_page.as_ref()
+        {
             if self.focus_handle.is_focused(window) {
                 welcome_page.read(cx).focus_handle(cx).focus(window, cx);
             }
@@ -793,6 +797,10 @@ impl Pane {
         self.should_display_tab_bar = Rc::new(should_display_tab_bar);
     }
 
+    pub fn set_should_display_welcome_page(&mut self, should_display_welcome_page: bool) {
+        self.should_display_welcome_page = should_display_welcome_page;
+    }
+
     pub fn set_can_split(
         &mut self,
         can_split_predicate: Option<
@@ -4391,7 +4399,7 @@ impl Render for Pane {
                                         }
                                     },
                                 ));
-                            if has_worktrees {
+                            if has_worktrees || !self.should_display_welcome_page {
                                 placeholder
                             } else {
                                 if self.welcome_page.is_none() {

crates/workspace/src/workspace.rs 🔗

@@ -1446,6 +1446,7 @@ impl Workspace {
                 cx,
             );
             center_pane.set_can_split(Some(Arc::new(|_, _, _, _| true)));
+            center_pane.set_should_display_welcome_page(true);
             center_pane
         });
         cx.subscribe_in(&center_pane, window, Self::handle_pane_event)