From 6c608538428820ddd3df182438bb03720498dcdd Mon Sep 17 00:00:00 2001 From: Nathan Sobo Date: Fri, 12 May 2023 15:44:09 -0600 Subject: [PATCH] Don't close panel on event unless active; add tests --- crates/project_panel/src/project_panel.rs | 4 +- crates/workspace/src/dock.rs | 12 ++++-- crates/workspace/src/workspace.rs | 48 ++++++++++++++++++++--- 3 files changed, 52 insertions(+), 12 deletions(-) diff --git a/crates/project_panel/src/project_panel.rs b/crates/project_panel/src/project_panel.rs index c76d2481ef..e271c9970b 100644 --- a/crates/project_panel/src/project_panel.rs +++ b/crates/project_panel/src/project_panel.rs @@ -12,8 +12,8 @@ use gpui::{ geometry::vector::Vector2F, keymap_matcher::KeymapContext, platform::{CursorStyle, MouseButton, PromptLevel}, - AnyElement, AppContext, Axis, ClipboardItem, Element, Entity, ModelHandle, Task, View, - ViewContext, ViewHandle, WeakViewHandle, + AnyElement, AppContext, ClipboardItem, Element, Entity, ModelHandle, Task, View, ViewContext, + ViewHandle, WeakViewHandle, }; use menu::{Confirm, SelectNext, SelectPrev}; use project::{Entry, EntryKind, Project, ProjectEntryId, ProjectPath, Worktree, WorktreeId}; diff --git a/crates/workspace/src/dock.rs b/crates/workspace/src/dock.rs index cafe8bd5dc..86c2cc3929 100644 --- a/crates/workspace/src/dock.rs +++ b/crates/workspace/src/dock.rs @@ -180,16 +180,20 @@ impl Dock { pub fn add_panel(&mut self, panel: ViewHandle, cx: &mut ViewContext) { let subscriptions = [ cx.observe(&panel, |_, _, cx| cx.notify()), - cx.subscribe(&panel, |this, view, event, cx| { - if view.read(cx).should_activate_on_event(event, cx) { + cx.subscribe(&panel, |this, panel, event, cx| { + if panel.read(cx).should_activate_on_event(event, cx) { if let Some(ix) = this .panel_entries .iter() - .position(|entry| entry.panel.id() == view.id()) + .position(|entry| entry.panel.id() == panel.id()) { + this.set_open(true, cx); this.activate_panel(ix, cx); + cx.focus(&panel); } - } else if view.read(cx).should_close_on_event(event, cx) { + } else if panel.read(cx).should_close_on_event(event, cx) + && this.active_panel().map_or(false, |p| p.id() == panel.id()) + { this.set_open(false, cx); } }), diff --git a/crates/workspace/src/workspace.rs b/crates/workspace/src/workspace.rs index 7bfe180d50..ad717c362b 100644 --- a/crates/workspace/src/workspace.rs +++ b/crates/workspace/src/workspace.rs @@ -3091,7 +3091,7 @@ mod tests { use std::{cell::RefCell, rc::Rc}; use crate::{ - dock::test::TestPanel, + dock::test::{TestPanel, TestPanelEvent}, item::test::{TestItem, TestItemEvent, TestProjectItem}, }; @@ -3767,14 +3767,50 @@ mod tests { assert!(!workspace.left_dock().read(cx).is_open()); // The bottom dock is sized based on the panel's default size, // since the panel orientation changed from vertical to horizontal. + let bottom_dock = workspace.bottom_dock(); assert_eq!( - workspace - .bottom_dock() - .read(cx) - .active_panel_size() - .unwrap(), + bottom_dock.read(cx).active_panel_size().unwrap(), panel_1.default_size(cx), ); + // Close bottom dock and move panel_1 back to the left. + bottom_dock.update(cx, |bottom_dock, cx| bottom_dock.set_open(false, cx)); + panel_1.set_position(DockPosition::Left, cx); + }); + + // Emit activated event on panel 1 + panel_1.update(cx, |_, cx| cx.emit(TestPanelEvent::Activated)); + + // Now the left dock is open and panel_1 is active and focused. + workspace.read_with(cx, |workspace, cx| { + let left_dock = workspace.left_dock(); + assert!(left_dock.read(cx).is_open()); + assert_eq!( + left_dock.read(cx).active_panel().unwrap().id(), + panel_1.id() + ); + assert!(panel_1.is_focused(cx)); + }); + + // Emit closed event on panel 2, which is not active + panel_2.update(cx, |_, cx| cx.emit(TestPanelEvent::Closed)); + + // Wo don't close the left dock, because panel_2 wasn't the active panel + workspace.read_with(cx, |workspace, cx| { + let left_dock = workspace.left_dock(); + assert!(left_dock.read(cx).is_open()); + assert_eq!( + left_dock.read(cx).active_panel().unwrap().id(), + panel_1.id() + ); + }); + + // Emit closed event on panel 1, which is active + panel_1.update(cx, |_, cx| cx.emit(TestPanelEvent::Closed)); + + // Now the left dock is closed, because panel_1 was the active panel + workspace.read_with(cx, |workspace, cx| { + let left_dock = workspace.left_dock(); + assert!(!left_dock.read(cx).is_open()); }); } }