From d6a66844ff138f0b5e4cfe08bfbd2226dee99614 Mon Sep 17 00:00:00 2001 From: Bryan Helmkamp Date: Sat, 25 Jul 2026 08:48:33 -0400 Subject: [PATCH] Keep prompt text inside the Chat bubble MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The prompt bubble is `w-fit max-w-[85%]`, so its width is measured intrinsically and only then clamped. `items-start` left the inner content wrapper intrinsically sized too, so it resolved against the available space from before the clamp — the full column width — and kept that measurement after the bubble shrank. The text laid out at 100% of the column while the background painted at 85%, spilling out the right side. Give the wrapper `w-full` so it fills the bubble's resolved width instead of measuring itself. Short prompts still hug their content: a percentage-width child contributes its content size during intrinsic sizing, so the bubble measures the same and only the final wrap width changes. The expand button keeps hugging its label as a separate flex child. Also break long words in the collapsed preview. That is a separate overflow path: the preview is raw prompt text under `whitespace-pre-wrap`, where an unbreakable path or URL would spill even at the correct width. Co-Authored-By: Claude Fable 5 --- apps/fabro-web/app/routes/run-stages.tsx | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/apps/fabro-web/app/routes/run-stages.tsx b/apps/fabro-web/app/routes/run-stages.tsx index ad5dfc104..7025541cb 100644 --- a/apps/fabro-web/app/routes/run-stages.tsx +++ b/apps/fabro-web/app/routes/run-stages.tsx @@ -1481,11 +1481,18 @@ function ChatUserCard({ content }: { content: string }) { const isLong = content.length > CHAT_PROMPT_PREVIEW_CHARS; return (
-
+ {/* + `w-full` is load-bearing. `items-start` keeps the expand button hugging + its label, but it also leaves this wrapper intrinsically sized, and the + bubble's own `w-fit` width is only clamped to `max-w-[85%]` after that + intrinsic pass. The text then keeps the wider pre-clamp measurement and + spills past the bubble. Filling the resolved width sidesteps it. + */} +
{expanded ? ( ) : ( -

+

{isLong ? `${content.slice(0, CHAT_PROMPT_PREVIEW_CHARS).trimEnd()}…` : content}