From b3fd06ee575d785c4db7657076e26b545dc5020e Mon Sep 17 00:00:00 2001 From: Kayshen-X Date: Sat, 20 Jun 2026 13:43:35 +0800 Subject: [PATCH] refactor(editor): extract ai-chat label/feedback helpers to keep file under 800 The IconButton migration pushed ai_chat_panel.rs to 801 lines (over the repo's 800-line cap). Move draw_label / chat_neutral_hover_color / chat_neutral_feedback_color into the ai_chat_panel_controls sibling (backend trait already in scope there) and re-export them, so callers and tests are unchanged. ai_chat_panel.rs is now 780 lines. --- .../op-editor-ui/src/widgets/ai_chat_panel.rs | 27 ++------------ .../src/widgets/ai_chat_panel_controls.rs | 36 ++++++++++++++++++- 2 files changed, 38 insertions(+), 25 deletions(-) diff --git a/crates/op-editor-ui/src/widgets/ai_chat_panel.rs b/crates/op-editor-ui/src/widgets/ai_chat_panel.rs index 98f6cdb5b..ffdec93cb 100644 --- a/crates/op-editor-ui/src/widgets/ai_chat_panel.rs +++ b/crates/op-editor-ui/src/widgets/ai_chat_panel.rs @@ -2,6 +2,9 @@ use crate::theme::Theme; use crate::widgets::ai_chat_checklist::{ fixed_checklist_height, fixed_checklist_rect, paint_fixed_checklist, }; +pub(crate) use crate::widgets::ai_chat_panel_controls::{ + chat_neutral_feedback_color, chat_neutral_hover_color, draw_label, +}; use crate::widgets::ai_chat_panel_controls::{paint_attachment_row, ATTACHMENT_ROW_HEIGHT}; use crate::widgets::ai_chat_panel_footer::{fit_footer_label, footer_label_baseline}; use crate::widgets::ai_chat_panel_paint::{ @@ -765,30 +768,6 @@ impl<'a> Widget for AIChatPlaceholder<'a> { } } -fn draw_label(cx: &mut PaintCx<'_>, text: &str, size: f32, color: Color, x: f32, y: f32) { - let label = TextLayout::single_run( - text, - "system-ui", - size, - (color).to_jian(), - Point2D::new(0.0, 0.0), - ); - cx.backend.draw_text(&label, Point2D::new(x, y)); -} - -fn chat_neutral_hover_color(theme: &Theme) -> Color { - chat_neutral_feedback_color(theme, false) -} - -fn chat_neutral_feedback_color(theme: &Theme, pressed: bool) -> Color { - Color { - r: theme.foreground.r, - g: theme.foreground.g, - b: theme.foreground.b, - a: if pressed { 0.18 } else { 0.12 }, - } -} - #[cfg(test)] #[path = "ai_chat_panel/tests.rs"] mod tests; diff --git a/crates/op-editor-ui/src/widgets/ai_chat_panel_controls.rs b/crates/op-editor-ui/src/widgets/ai_chat_panel_controls.rs index 07d9df3ad..1a4611c5c 100644 --- a/crates/op-editor-ui/src/widgets/ai_chat_panel_controls.rs +++ b/crates/op-editor-ui/src/widgets/ai_chat_panel_controls.rs @@ -15,7 +15,7 @@ use super::ai_chat_hit::AIChatHit; use crate::theme::Theme; use crate::widgets::icons::{draw_icon, Icon}; use crate::widgets::PaintCx; -use crate::{Point2D, Rect, TextLayout}; +use crate::{Color, Point2D, Rect, TextLayout}; use op_editor_core::chat::{ChatState, EffortLevel, ThinkingMode}; /// Height of the per-turn controls strip. @@ -246,6 +246,40 @@ pub fn paint_attachment_row( } } +/// Draw a single text label — shared by the AI-chat panel paint paths. +pub(crate) fn draw_label( + cx: &mut PaintCx<'_>, + text: &str, + size: f32, + color: Color, + x: f32, + y: f32, +) { + let label = TextLayout::single_run( + text, + "system-ui", + size, + (color).to_jian(), + Point2D::new(0.0, 0.0), + ); + cx.backend.draw_text(&label, Point2D::new(x, y)); +} + +/// Neutral hover wash color for the chat panel's borderless controls. +pub(crate) fn chat_neutral_hover_color(theme: &Theme) -> Color { + chat_neutral_feedback_color(theme, false) +} + +/// Neutral hover/press wash color (a faint foreground tint). +pub(crate) fn chat_neutral_feedback_color(theme: &Theme, pressed: bool) -> Color { + Color { + r: theme.foreground.r, + g: theme.foreground.g, + b: theme.foreground.b, + a: if pressed { 0.18 } else { 0.12 }, + } +} + #[cfg(test)] mod tests { use super::*;