Adjust file finder width configuration (#20819)

Danilo Leal and Kirill Bulatov created

Follow up to: https://github.com/zed-industries/zed/pull/18682

This PR tweaks the setting value, so it's clear we're referring to
`max-width`, meaning the width will change up to a specific value
depending on the available window size. Then, it also makes `Small` the
default value, which, in practice, makes the modal size the same as it
was before the original PR linked above.

Release Notes:

- N/A

---------

Co-authored-by: Kirill Bulatov <mail4score@gmail.com>

Change summary

assets/settings/default.json                   | 28 +++++++------
crates/file_finder/src/file_finder.rs          | 25 +++++++++--
crates/file_finder/src/file_finder_settings.rs | 42 ++-----------------
docs/src/configuring-zed.md                    |  8 +-
4 files changed, 44 insertions(+), 59 deletions(-)

Detailed changes

assets/settings/default.json 🔗

@@ -581,20 +581,22 @@
   "file_finder": {
     // Whether to show file icons in the file finder.
     "file_icons": true,
-    // Width of the file finder modal. This setting can
-    // take four values.
+    // Determines how much space the file finder can take up in relation to the available window width.
+    // There are 5 possible width values:
     //
-    // 1. Small width:
-    //   "modal_width": "small",
-    // 2. Medium width (default):
-    //   "modal_width": "medium",
-    // 3. Large width:
-    //   "modal_width": "large",
-    // 4. Extra Large width:
-    //   "modal_width": "xlarge"
-    // 5. Fullscreen width:
-    //   "modal_width": "full"
-    "modal_width": "medium"
+    // 1. Small: This value is essentially a fixed width.
+    //    "modal_width": "small"
+    // 2. Medium:
+    //    "modal_width": "medium"
+    // 3. Large:
+    //    "modal_width": "large"
+    // 4. Extra Large:
+    //    "modal_width": "xlarge"
+    // 5. Fullscreen: This value removes any horizontal padding, as it consumes the whole viewport width.
+    //    "modal_width": "full"
+    //
+    // Default: small
+    "modal_max_width": "small"
   },
   // Whether or not to remove any trailing whitespace from lines of a buffer
   // before saving it.

crates/file_finder/src/file_finder.rs 🔗

@@ -10,7 +10,7 @@ pub use open_path_prompt::OpenPathDelegate;
 
 use collections::HashMap;
 use editor::{scroll::Autoscroll, Bias, Editor};
-use file_finder_settings::FileFinderSettings;
+use file_finder_settings::{FileFinderSettings, FileFinderWidth};
 use file_icons::FileIcons;
 use fuzzy::{CharBag, PathMatch, PathMatchCandidate};
 use gpui::{
@@ -244,6 +244,22 @@ impl FileFinder {
             }
         })
     }
+
+    pub fn modal_max_width(
+        width_setting: Option<FileFinderWidth>,
+        cx: &mut ViewContext<Self>,
+    ) -> Pixels {
+        let window_width = cx.viewport_size().width;
+        let small_width = Pixels(545.);
+
+        match width_setting {
+            None | Some(FileFinderWidth::Small) => small_width,
+            Some(FileFinderWidth::Full) => window_width,
+            Some(FileFinderWidth::XLarge) => (window_width - Pixels(512.)).max(small_width),
+            Some(FileFinderWidth::Large) => (window_width - Pixels(768.)).max(small_width),
+            Some(FileFinderWidth::Medium) => (window_width - Pixels(1024.)).max(small_width),
+        }
+    }
 }
 
 impl EventEmitter<DismissEvent> for FileFinder {}
@@ -258,13 +274,12 @@ impl Render for FileFinder {
     fn render(&mut self, cx: &mut ViewContext<Self>) -> impl IntoElement {
         let key_context = self.picker.read(cx).delegate.key_context(cx);
 
-        let window_max_width: Pixels = cx.viewport_size().width;
-        let modal_choice = FileFinderSettings::get_global(cx).modal_width;
-        let width = modal_choice.calc_width(window_max_width);
+        let file_finder_settings = FileFinderSettings::get_global(cx);
+        let modal_max_width = Self::modal_max_width(file_finder_settings.modal_max_width, cx);
 
         v_flex()
             .key_context(key_context)
-            .w(width)
+            .w(modal_max_width)
             .on_modifiers_changed(cx.listener(Self::handle_modifiers_changed))
             .on_action(cx.listener(Self::handle_select_prev))
             .on_action(cx.listener(Self::handle_open_menu))

crates/file_finder/src/file_finder_settings.rs 🔗

@@ -2,13 +2,11 @@ use anyhow::Result;
 use schemars::JsonSchema;
 use serde_derive::{Deserialize, Serialize};
 use settings::{Settings, SettingsSources};
-use std::cmp;
-use ui::Pixels;
 
 #[derive(Deserialize, Debug, Clone, Copy, PartialEq)]
 pub struct FileFinderSettings {
     pub file_icons: bool,
-    pub modal_width: FileFinderWidth,
+    pub modal_max_width: Option<FileFinderWidth>,
 }
 
 #[derive(Clone, Default, Serialize, Deserialize, JsonSchema, Debug)]
@@ -17,10 +15,10 @@ pub struct FileFinderSettingsContent {
     ///
     /// Default: true
     pub file_icons: Option<bool>,
-    /// The width of the file finder modal.
+    /// Determines how much space the file finder can take up in relation to the available window width.
     ///
-    /// Default: "medium"
-    pub modal_width: Option<FileFinderWidth>,
+    /// Default: small
+    pub modal_max_width: Option<FileFinderWidth>,
 }
 
 impl Settings for FileFinderSettings {
@@ -36,40 +34,10 @@ impl Settings for FileFinderSettings {
 #[derive(Debug, PartialEq, Eq, Clone, Copy, Default, Serialize, Deserialize, JsonSchema)]
 #[serde(rename_all = "lowercase")]
 pub enum FileFinderWidth {
-    Small,
     #[default]
+    Small,
     Medium,
     Large,
     XLarge,
     Full,
 }
-
-impl FileFinderWidth {
-    const MIN_MODAL_WIDTH_PX: f32 = 384.;
-
-    pub fn padding_px(&self) -> Pixels {
-        let padding_val = match self {
-            FileFinderWidth::Small => 1280.,
-            FileFinderWidth::Medium => 1024.,
-            FileFinderWidth::Large => 768.,
-            FileFinderWidth::XLarge => 512.,
-            FileFinderWidth::Full => 0.,
-        };
-
-        Pixels(padding_val)
-    }
-
-    pub fn calc_width(&self, window_width: Pixels) -> Pixels {
-        if self == &FileFinderWidth::Full {
-            return window_width;
-        }
-
-        let min_modal_width_px = Pixels(FileFinderWidth::MIN_MODAL_WIDTH_PX);
-
-        let padding_px = self.padding_px();
-        let width_val = window_width - padding_px;
-        let finder_width = cmp::max(min_modal_width_px, width_val);
-
-        finder_width
-    }
-}

docs/src/configuring-zed.md 🔗

@@ -1418,11 +1418,11 @@ Or to set a `socks5` proxy:
 
 ## File Finder
 
-### Modal Width
+### Modal Max Width
 
-- Description: Width of the file finder modal. Can take one of a few values: `small`, `medium`, `large`, `xlarge`, and `full`.
-- Setting: `modal_width`
-- Default: `medium`
+- Description: Max-width of the file finder modal. It can take one of these values: `small`, `medium`, `large`, `xlarge`, and `full`.
+- Setting: `max_modal_width`
+- Default: `small`
 
 ## Preferred Line Length