Don't prompt to save unchanged files (#3053)

Conrad Irwin created

- don't prompt to save a set of unchanged files when closing
(preview-only)

Change summary

crates/vim/src/command.rs         |  4 +
crates/workspace/src/pane.rs      | 83 +++++++++++++++++---------------
crates/workspace/src/workspace.rs |  2 
3 files changed, 50 insertions(+), 39 deletions(-)

Detailed changes

crates/vim/src/command.rs 🔗

@@ -430,5 +430,9 @@ mod test {
         cx.workspace(|workspace, cx| assert_eq!(workspace.items(cx).count(), 2));
         cx.simulate_keystrokes([":", "q", "enter"]);
         cx.workspace(|workspace, cx| assert_eq!(workspace.items(cx).count(), 1));
+        cx.simulate_keystrokes([":", "n", "e", "w", "enter"]);
+        cx.workspace(|workspace, cx| assert_eq!(workspace.items(cx).count(), 2));
+        cx.simulate_keystrokes([":", "q", "a", "enter"]);
+        cx.workspace(|workspace, cx| assert_eq!(workspace.items(cx).count(), 0));
     }
 }

crates/workspace/src/pane.rs 🔗

@@ -893,9 +893,13 @@ impl Pane {
     ) -> Task<Result<()>> {
         // Find the items to close.
         let mut items_to_close = Vec::new();
+        let mut dirty_items = Vec::new();
         for item in &self.items {
             if should_close(item.id()) {
                 items_to_close.push(item.boxed_clone());
+                if item.is_dirty(cx) {
+                    dirty_items.push(item.boxed_clone());
+                }
             }
         }
 
@@ -907,13 +911,10 @@ impl Pane {
 
         let workspace = self.workspace.clone();
         cx.spawn(|pane, mut cx| async move {
-            if save_intent == SaveIntent::Close && items_to_close.len() > 1 {
+            if save_intent == SaveIntent::Close && dirty_items.len() > 1 {
                 let mut answer = pane.update(&mut cx, |_, cx| {
-                    let prompt = Self::file_names_for_prompt(
-                        &mut items_to_close.iter(),
-                        items_to_close.len(),
-                        cx,
-                    );
+                    let prompt =
+                        Self::file_names_for_prompt(&mut dirty_items.iter(), dirty_items.len(), cx);
                     cx.prompt(
                         PromptLevel::Warning,
                         &prompt,
@@ -921,7 +922,7 @@ impl Pane {
                     )
                 })?;
                 match answer.next().await {
-                    Some(0) => save_intent = SaveIntent::Save,
+                    Some(0) => save_intent = SaveIntent::SaveAll,
                     Some(1) => save_intent = SaveIntent::Skip,
                     _ => {}
                 }
@@ -2537,14 +2538,12 @@ mod tests {
 
         set_labeled_items(&pane, ["A", "B", "C*", "D", "E"], cx);
 
-        let task = pane
-            .update(cx, |pane, cx| {
-                pane.close_inactive_items(&CloseInactiveItems, cx)
-            })
-            .unwrap();
-        cx.foreground().run_until_parked();
-        window.simulate_prompt_answer(2, cx);
-        task.await.unwrap();
+        pane.update(cx, |pane, cx| {
+            pane.close_inactive_items(&CloseInactiveItems, cx)
+        })
+        .unwrap()
+        .await
+        .unwrap();
         assert_item_labels(&pane, ["C*"], cx);
     }
 
@@ -2565,12 +2564,10 @@ mod tests {
         add_labeled_item(&pane, "E", false, cx);
         assert_item_labels(&pane, ["A^", "B", "C^", "D", "E*"], cx);
 
-        let task = pane
-            .update(cx, |pane, cx| pane.close_clean_items(&CloseCleanItems, cx))
+        pane.update(cx, |pane, cx| pane.close_clean_items(&CloseCleanItems, cx))
+            .unwrap()
+            .await
             .unwrap();
-        cx.foreground().run_until_parked();
-        window.simulate_prompt_answer(2, cx);
-        task.await.unwrap();
         assert_item_labels(&pane, ["A^", "C*^"], cx);
     }
 
@@ -2586,14 +2583,12 @@ mod tests {
 
         set_labeled_items(&pane, ["A", "B", "C*", "D", "E"], cx);
 
-        let task = pane
-            .update(cx, |pane, cx| {
-                pane.close_items_to_the_left(&CloseItemsToTheLeft, cx)
-            })
-            .unwrap();
-        cx.foreground().run_until_parked();
-        window.simulate_prompt_answer(2, cx);
-        task.await.unwrap();
+        pane.update(cx, |pane, cx| {
+            pane.close_items_to_the_left(&CloseItemsToTheLeft, cx)
+        })
+        .unwrap()
+        .await
+        .unwrap();
         assert_item_labels(&pane, ["C*", "D", "E"], cx);
     }
 
@@ -2609,14 +2604,12 @@ mod tests {
 
         set_labeled_items(&pane, ["A", "B", "C*", "D", "E"], cx);
 
-        let task = pane
-            .update(cx, |pane, cx| {
-                pane.close_items_to_the_right(&CloseItemsToTheRight, cx)
-            })
-            .unwrap();
-        cx.foreground().run_until_parked();
-        window.simulate_prompt_answer(2, cx);
-        task.await.unwrap();
+        pane.update(cx, |pane, cx| {
+            pane.close_items_to_the_right(&CloseItemsToTheRight, cx)
+        })
+        .unwrap()
+        .await
+        .unwrap();
         assert_item_labels(&pane, ["A", "B", "C*"], cx);
     }
 
@@ -2635,14 +2628,28 @@ mod tests {
         add_labeled_item(&pane, "C", false, cx);
         assert_item_labels(&pane, ["A", "B", "C*"], cx);
 
-        let t = pane
+        pane.update(cx, |pane, cx| {
+            pane.close_all_items(&CloseAllItems { save_intent: None }, cx)
+        })
+        .unwrap()
+        .await
+        .unwrap();
+        assert_item_labels(&pane, [], cx);
+
+        add_labeled_item(&pane, "A", true, cx);
+        add_labeled_item(&pane, "B", true, cx);
+        add_labeled_item(&pane, "C", true, cx);
+        assert_item_labels(&pane, ["A^", "B^", "C*^"], cx);
+
+        let save = pane
             .update(cx, |pane, cx| {
                 pane.close_all_items(&CloseAllItems { save_intent: None }, cx)
             })
             .unwrap();
+
         cx.foreground().run_until_parked();
         window.simulate_prompt_answer(2, cx);
-        t.await.unwrap();
+        save.await.unwrap();
         assert_item_labels(&pane, [], cx);
     }
 

crates/workspace/src/workspace.rs 🔗

@@ -1419,7 +1419,7 @@ impl Workspace {
                     )
                 })?;
                 match answer.next().await {
-                    Some(0) => save_intent = SaveIntent::Save,
+                    Some(0) => save_intent = SaveIntent::SaveAll,
                     Some(1) => save_intent = SaveIntent::Skip,
                     _ => {}
                 }