diff --git a/assets/settings/default.json b/assets/settings/default.json index 9f4f2dc34c0d91..60cadbb0d055a2 100644 --- a/assets/settings/default.json +++ b/assets/settings/default.json @@ -256,8 +256,13 @@ "search_results": true, // Whether to show selected symbol occurrences in the scrollbar. "selected_symbol": true, - // Whether to show diagnostic indicators in the scrollbar. - "diagnostics": true, + // Which diagnostic indicator levels to show in the scrollbar: + // - "none" or false: do not show diagnostics + // - "error": show only errors + // - "warning": show only errors and warnings + // - "information": show only errors, warnings, and information + // - "all" or true: show all diagnostics + "diagnostics": "all", /// Forcefully enable or disable the scrollbar for each axis "axes": { /// When false, forcefully disables the horizontal scrollbar. Otherwise, obey other settings. diff --git a/crates/editor/src/editor_settings.rs b/crates/editor/src/editor_settings.rs index d5cbb3e23237de..d1284bfce3d860 100644 --- a/crates/editor/src/editor_settings.rs +++ b/crates/editor/src/editor_settings.rs @@ -105,7 +105,7 @@ pub struct Scrollbar { pub git_diff: bool, pub selected_symbol: bool, pub search_results: bool, - pub diagnostics: bool, + pub diagnostics: ScrollbarDiagnostics, pub cursors: bool, pub axes: ScrollbarAxes, } @@ -150,6 +150,73 @@ pub struct ScrollbarAxes { pub vertical: bool, } +/// Which diagnostic indicator levels to show in the scrollbar. +/// +/// Default: all +#[derive(Copy, Clone, Debug, Serialize, JsonSchema, PartialEq, Eq)] +#[serde(rename_all = "lowercase")] +pub enum ScrollbarDiagnostics { + /// Show all diagnostic levels: hint, information, warnings, error. + All, + /// Show only the following diagnostic levels: information, warning, error. + Information, + /// Show only the following diagnostic levels: warning, error. + Warning, + /// Show only the following diagnostic level: error. + Error, + /// Do not show diagnostics. + None, +} + +impl<'de> Deserialize<'de> for ScrollbarDiagnostics { + fn deserialize(deserializer: D) -> Result + where + D: serde::Deserializer<'de>, + { + struct Visitor; + + impl<'de> serde::de::Visitor<'de> for Visitor { + type Value = ScrollbarDiagnostics; + + fn expecting(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { + write!( + f, + r#"a boolean or one of "all", "information", "warning", "error", "none""# + ) + } + + fn visit_bool(self, b: bool) -> Result + where + E: serde::de::Error, + { + match b { + false => Ok(ScrollbarDiagnostics::None), + true => Ok(ScrollbarDiagnostics::All), + } + } + + fn visit_str(self, s: &str) -> Result + where + E: serde::de::Error, + { + match s { + "all" => Ok(ScrollbarDiagnostics::All), + "information" => Ok(ScrollbarDiagnostics::Information), + "warning" => Ok(ScrollbarDiagnostics::Warning), + "error" => Ok(ScrollbarDiagnostics::Error), + "none" => Ok(ScrollbarDiagnostics::None), + _ => Err(E::unknown_variant( + s, + &["all", "information", "warning", "error", "none"], + )), + } + } + } + + deserializer.deserialize_any(Visitor) + } +} + /// The key to use for adding multiple cursors /// /// Default: alt @@ -348,10 +415,15 @@ pub struct ScrollbarContent { /// /// Default: true pub selected_symbol: Option, - /// Whether to show diagnostic indicators in the scrollbar. + /// Which diagnostic indicator levels to show in the scrollbar: + /// - "none" or false: do not show diagnostics + /// - "error": show only errors + /// - "warning": show only errors and warnings + /// - "information": show only errors, warnings, and information + /// - "all" or true: show all diagnostics /// /// Default: true - pub diagnostics: Option, + pub diagnostics: Option, /// Whether to show cursor positions in the scrollbar. /// /// Default: true diff --git a/crates/editor/src/element.rs b/crates/editor/src/element.rs index 379b16c09b6d72..6a7509ac52a6ac 100644 --- a/crates/editor/src/element.rs +++ b/crates/editor/src/element.rs @@ -6,7 +6,7 @@ use crate::{ }, editor_settings::{ CurrentLineHighlight, DoubleClickInMultibuffer, MultiCursorModifier, ScrollBeyondLastLine, - ShowScrollbar, + ScrollbarDiagnostics, ShowScrollbar, }, git::blame::{CommitDetails, GitBlame}, hover_popover::{ @@ -1207,7 +1207,7 @@ impl EditorElement { (is_singleton && scrollbar_settings.selected_symbol && (editor.has_background_highlights::() || editor.has_background_highlights::())) || // Diagnostics - (is_singleton && scrollbar_settings.diagnostics && snapshot.buffer_snapshot.has_diagnostics()) + (is_singleton && scrollbar_settings.diagnostics != ScrollbarDiagnostics::None && snapshot.buffer_snapshot.has_diagnostics()) || // Cursors out of sight non_visible_cursors @@ -4657,13 +4657,38 @@ impl EditorElement { } } - if scrollbar_settings.diagnostics { + if scrollbar_settings.diagnostics != ScrollbarDiagnostics::None { let diagnostics = snapshot .buffer_snapshot .diagnostics_in_range::<_, Point>( Point::zero()..max_point, false, ) + // Don't show diagnostics the user doesn't care about + .filter(|diagnostic| { + match ( + scrollbar_settings.diagnostics, + diagnostic.diagnostic.severity, + ) { + (ScrollbarDiagnostics::All, _) => true, + ( + ScrollbarDiagnostics::Error, + DiagnosticSeverity::ERROR, + ) => true, + ( + ScrollbarDiagnostics::Warning, + DiagnosticSeverity::ERROR + | DiagnosticSeverity::WARNING, + ) => true, + ( + ScrollbarDiagnostics::Information, + DiagnosticSeverity::ERROR + | DiagnosticSeverity::WARNING + | DiagnosticSeverity::INFORMATION, + ) => true, + (_, _) => false, + } + }) // We want to sort by severity, in order to paint the most severe diagnostics last. .sorted_by_key(|diagnostic| { std::cmp::Reverse(diagnostic.diagnostic.severity)