From f88e3bc659c676e3c2a9717147124078f62c0ec6 Mon Sep 17 00:00:00 2001 From: Matt Revell Date: Sun, 17 Aug 2025 18:19:23 -0500 Subject: [PATCH 1/4] Update debug modal to include more context about its source. --- crates/debugger_ui/src/new_process_modal.rs | 92 ++++++++++++++------- 1 file changed, 64 insertions(+), 28 deletions(-) diff --git a/crates/debugger_ui/src/new_process_modal.rs b/crates/debugger_ui/src/new_process_modal.rs index b30e3995ff..7c2ddd074b 100644 --- a/crates/debugger_ui/src/new_process_modal.rs +++ b/crates/debugger_ui/src/new_process_modal.rs @@ -22,7 +22,7 @@ use itertools::Itertools as _; use picker::{Picker, PickerDelegate, highlighted_match_with_paths::HighlightedMatch}; use project::{DebugScenarioContext, TaskContexts, TaskSourceKind, task_store::TaskStore}; use settings::Settings; -use task::{DebugScenario, RevealTarget, ZedDebugConfig}; +use task::{DebugScenario, RevealTarget, VariableName, ZedDebugConfig}; use theme::ThemeSettings; use ui::{ ActiveTheme, Button, ButtonCommon, ButtonSize, CheckboxWithLabel, Clickable, Color, Context, @@ -1429,7 +1429,8 @@ impl PickerDelegate for DebugDelegate { window: &mut Window, cx: &mut Context>, ) -> Option { - let hit = &self.matches[ix]; + let hit = self.matches.get(ix)?; + let (task_kind, _scenario, context) = &self.candidates[hit.candidate_id]; let highlighted_location = HighlightedMatch { text: hit.string.clone(), @@ -1437,44 +1438,79 @@ impl PickerDelegate for DebugDelegate { char_count: hit.string.chars().count(), color: Color::Default, }; - let task_kind = &self.candidates[hit.candidate_id].0; - let icon = match task_kind { - Some(TaskSourceKind::UserInput) => Some(Icon::new(IconName::Terminal)), - Some(TaskSourceKind::AbsPath { .. }) => Some(Icon::new(IconName::Settings)), - Some(TaskSourceKind::Worktree { .. }) => Some(Icon::new(IconName::FileTree)), - Some(TaskSourceKind::Lsp { - language_name: name, + let subtitle = match task_kind { + Some(TaskSourceKind::Worktree { + directory_in_worktree, .. - }) - | Some(TaskSourceKind::Language { name }) => file_icons::FileIcons::get(cx) - .get_icon_for_type(&name.to_lowercase(), cx) - .map(Icon::from_path), - None => Some(Icon::new(IconName::HistoryRerun)), - } - .map(|icon| icon.color(Color::Muted).size(IconSize::Small)); - let indicator = if matches!(task_kind, Some(TaskSourceKind::Lsp { .. })) { - Some(Indicator::icon( - Icon::new(IconName::BoltFilled) - .color(Color::Muted) - .size(IconSize::Small), - )) - } else { - None + }) => Some(directory_in_worktree.display().to_string()), + Some(TaskSourceKind::AbsPath { abs_path, .. }) => abs_path + .file_name() + .map(|n| format!("From Global {}", n.to_string_lossy())), + Some(TaskSourceKind::Lsp { language_name, .. }) => { + Some(format!("LSP: {language_name}")) + } + Some(TaskSourceKind::Language { name }) => Some(format!("Language: {name}")), + _ => context.clone().and_then(|ctx| { + ctx.task_context + .task_variables + .get(&VariableName::RelativeFile) + .map(|f| format!("in {f}")) + .or_else(|| { + ctx.task_context + .task_variables + .get(&VariableName::Dirname) + .map(|d| format!("in {d}/")) + }) + }), }; + + let (icon, indicator) = match task_kind { + Some(TaskSourceKind::UserInput) => (Some(Icon::new(IconName::Terminal)), None), + Some(TaskSourceKind::AbsPath { .. }) => (Some(Icon::new(IconName::Settings)), None), + Some(TaskSourceKind::Worktree { .. }) => (Some(Icon::new(IconName::FileTree)), None), + Some(TaskSourceKind::Lsp { language_name, .. }) => ( + file_icons::FileIcons::get(cx) + .get_icon_for_type(&language_name.to_lowercase(), cx) + .map(Icon::from_path), + Some(Indicator::icon( + Icon::new(IconName::BoltFilled) + .color(Color::Muted) + .size(IconSize::Small), + )), + ), + Some(TaskSourceKind::Language { name }) => ( + file_icons::FileIcons::get(cx) + .get_icon_for_type(&name.to_lowercase(), cx) + .map(Icon::from_path), + None, + ), + None => (Some(Icon::new(IconName::HistoryRerun)), None), + }; + let icon = icon.map(|icon| { - IconWithIndicator::new(icon, indicator) + IconWithIndicator::new(icon.color(Color::Muted).size(IconSize::Small), indicator) .indicator_border_color(Some(cx.theme().colors().border_transparent)) }); - Some( + let mut list_item = ListItem::new(SharedString::from(format!("debug-scenario-selection-{ix}"))) .inset(true) .start_slot::(icon) .spacing(ListItemSpacing::Sparse) .toggle_state(selected) - .child(highlighted_location.render(window, cx)), - ) + .child(highlighted_location.render(window, cx)); + + if let Some(subtitle_text) = subtitle { + list_item = list_item.child( + div() + .text_xs() + .text_color(cx.theme().colors().text_muted) + .child(subtitle_text), + ); + } + + Some(list_item) } } From 877f9438fc532d1f0f9fb9ce76250865eb32e36c Mon Sep 17 00:00:00 2001 From: Matt Revell Date: Mon, 25 Aug 2025 18:47:13 -0500 Subject: [PATCH 2/4] More consistant formatting for task file location. Update the new process modal to have the path to the file containing the task configuration to be under instead of next to the name. --- crates/debugger_ui/src/new_process_modal.rs | 27 +++++++++++---------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/crates/debugger_ui/src/new_process_modal.rs b/crates/debugger_ui/src/new_process_modal.rs index 7c2ddd074b..f020ebdde1 100644 --- a/crates/debugger_ui/src/new_process_modal.rs +++ b/crates/debugger_ui/src/new_process_modal.rs @@ -1493,24 +1493,25 @@ impl PickerDelegate for DebugDelegate { .indicator_border_color(Some(cx.theme().colors().border_transparent)) }); - let mut list_item = + Some( ListItem::new(SharedString::from(format!("debug-scenario-selection-{ix}"))) .inset(true) .start_slot::(icon) .spacing(ListItemSpacing::Sparse) .toggle_state(selected) - .child(highlighted_location.render(window, cx)); - - if let Some(subtitle_text) = subtitle { - list_item = list_item.child( - div() - .text_xs() - .text_color(cx.theme().colors().text_muted) - .child(subtitle_text), - ); - } - - Some(list_item) + .child( + v_flex() + .items_start() + .child(highlighted_location.render(window, cx)) + .when_some(subtitle.clone(), |this, subtitle_text| { + this.child( + Label::new(subtitle_text) + .size(LabelSize::Small) + .color(Color::Muted), + ) + }), + ), + ) } } From a71267580db0a331ae394ed01cfef052805df21d Mon Sep 17 00:00:00 2001 From: Matt Revell Date: Mon, 25 Aug 2025 19:14:20 -0500 Subject: [PATCH 3/4] run clipply ... --- crates/debugger_ui/src/new_process_modal.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/debugger_ui/src/new_process_modal.rs b/crates/debugger_ui/src/new_process_modal.rs index f020ebdde1..84e2d2652f 100644 --- a/crates/debugger_ui/src/new_process_modal.rs +++ b/crates/debugger_ui/src/new_process_modal.rs @@ -1503,7 +1503,7 @@ impl PickerDelegate for DebugDelegate { v_flex() .items_start() .child(highlighted_location.render(window, cx)) - .when_some(subtitle.clone(), |this, subtitle_text| { + .when_some(subtitle, |this, subtitle_text| { this.child( Label::new(subtitle_text) .size(LabelSize::Small) From 6795875084b1f7eae81541c1ea19ee27f5c4fd49 Mon Sep 17 00:00:00 2001 From: Matt Revell Date: Mon, 25 Aug 2025 21:00:08 -0500 Subject: [PATCH 4/4] Use the full path for global config --- crates/debugger_ui/src/new_process_modal.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/crates/debugger_ui/src/new_process_modal.rs b/crates/debugger_ui/src/new_process_modal.rs index 84e2d2652f..ff7523f1ba 100644 --- a/crates/debugger_ui/src/new_process_modal.rs +++ b/crates/debugger_ui/src/new_process_modal.rs @@ -1444,9 +1444,9 @@ impl PickerDelegate for DebugDelegate { directory_in_worktree, .. }) => Some(directory_in_worktree.display().to_string()), - Some(TaskSourceKind::AbsPath { abs_path, .. }) => abs_path - .file_name() - .map(|n| format!("From Global {}", n.to_string_lossy())), + Some(TaskSourceKind::AbsPath { abs_path, .. }) => { + Some(abs_path.to_string_lossy().into_owned()) + } Some(TaskSourceKind::Lsp { language_name, .. }) => { Some(format!("LSP: {language_name}")) }