diff --git a/codex-rs/tui/src/bottom_pane/chat_composer.rs b/codex-rs/tui/src/bottom_pane/chat_composer.rs index 470afbdab..df506fb6f 100644 --- a/codex-rs/tui/src/bottom_pane/chat_composer.rs +++ b/codex-rs/tui/src/bottom_pane/chat_composer.rs @@ -206,6 +206,7 @@ use crate::bottom_pane::textarea::TextAreaState; use crate::clipboard_paste::normalize_pasted_path; use crate::clipboard_paste::pasted_image_format; use crate::history_cell; +use crate::skills_helpers::skill_display_name; use crate::tui::FrameRequester; use crate::ui_consts::LIVE_PREFIX_COLS; use codex_app_server_protocol::AppInfo; @@ -3455,7 +3456,7 @@ impl ChatComposer { let mut mentions = Vec::new(); if let Some(skills) = self.skills.as_ref() { for skill in skills { - let display_name = skill_display_name(skill).to_string(); + let display_name = skill_display_name(skill); let description = skill_description(skill); let skill_name = skill.name.clone(); let search_terms = if display_name == skill.name { @@ -3659,14 +3660,6 @@ impl ChatComposer { } } -fn skill_display_name(skill: &SkillMetadata) -> &str { - skill - .interface - .as_ref() - .and_then(|interface| interface.display_name.as_deref()) - .unwrap_or(&skill.name) -} - fn skill_description(skill: &SkillMetadata) -> Option { let description = skill .interface diff --git a/codex-rs/tui/src/bottom_pane/skill_popup.rs b/codex-rs/tui/src/bottom_pane/skill_popup.rs index 836bad636..a0d427839 100644 --- a/codex-rs/tui/src/bottom_pane/skill_popup.rs +++ b/codex-rs/tui/src/bottom_pane/skill_popup.rs @@ -28,7 +28,7 @@ pub(crate) struct MentionItem { pub(crate) sort_rank: u8, } -const MENTION_NAME_TRUNCATE_LEN: usize = 24; +const MENTION_NAME_TRUNCATE_LEN: usize = 28; pub(crate) struct SkillPopup { query: String, diff --git a/codex-rs/tui/src/chatwidget/skills.rs b/codex-rs/tui/src/chatwidget/skills.rs index 0f0261ffe..904678003 100644 --- a/codex-rs/tui/src/chatwidget/skills.rs +++ b/codex-rs/tui/src/chatwidget/skills.rs @@ -75,7 +75,7 @@ impl ChatWidget { .iter() .map(|skill| { let core_skill = protocol_skill_to_core(skill); - let display_name = skill_display_name(&core_skill).to_string(); + let display_name = skill_display_name(&core_skill); let description = skill_description(&core_skill).to_string(); let name = core_skill.name.clone(); let path = core_skill.path_to_skills_md; diff --git a/codex-rs/tui/src/skills_helpers.rs b/codex-rs/tui/src/skills_helpers.rs index e02e929d4..730acdcaa 100644 --- a/codex-rs/tui/src/skills_helpers.rs +++ b/codex-rs/tui/src/skills_helpers.rs @@ -5,12 +5,23 @@ use crate::text_formatting::truncate_text; pub(crate) const SKILL_NAME_TRUNCATE_LEN: usize = 21; -pub(crate) fn skill_display_name(skill: &SkillMetadata) -> &str { - skill +pub(crate) fn skill_display_name(skill: &SkillMetadata) -> String { + if let Some(display_name) = skill .interface .as_ref() .and_then(|interface| interface.display_name.as_deref()) - .unwrap_or(&skill.name) + { + return display_name.to_string(); + } + + if let Some((plugin_name, skill_name)) = skill.name.split_once(':') + && !plugin_name.is_empty() + && !skill_name.is_empty() + { + return format!("{skill_name} ({plugin_name})"); + } + + skill.name.clone() } pub(crate) fn skill_description(skill: &SkillMetadata) -> &str {