diff --git a/src/browser/components/Messages/CompactionBackground.tsx b/src/browser/components/Messages/CompactionBackground.tsx index ae3050b03f..ff9153ca4d 100644 --- a/src/browser/components/Messages/CompactionBackground.tsx +++ b/src/browser/components/Messages/CompactionBackground.tsx @@ -1,27 +1,35 @@ import React from "react"; /** - * Animated background for compaction streaming - * Shimmer effect with moving gradient and particles for dynamic appearance + * Animated background for compaction streaming. + * Combines a subtle gradient with a GPU-accelerated shimmer effect. + * + * Uses CSS transform animation (compositor thread) instead of background-position + * (main thread repaint) to avoid frame drops during heavy streaming work. */ - export const CompactionBackground: React.FC = () => { return (
+ {/* Subtle gradient background */}
+ {/* Shimmer uses CSS transform animation - runs on compositor thread, not main thread */} + {/* Math: element is 300% wide, highlight at 50% = 150% from left edge. + marginLeft -180% puts highlight at -30% (off-screen left). + translateX 53.33% (of 300%) = 160%, moving highlight to 130% (off-screen right). */}
diff --git a/src/browser/stories/App.chat.stories.tsx b/src/browser/stories/App.chat.stories.tsx index 0ee0c8550a..b3fbfe402c 100644 --- a/src/browser/stories/App.chat.stories.tsx +++ b/src/browser/stories/App.chat.stories.tsx @@ -7,6 +7,7 @@ import { STABLE_TIMESTAMP, createUserMessage, createAssistantMessage, + createCompactionRequestMessage, createFileReadTool, createFileEditTool, createTerminalTool, @@ -325,3 +326,46 @@ export const GenericTool: AppStory = { }); }, }; + +/** Streaming compaction with shimmer effect - tests GPU-accelerated animation */ +export const StreamingCompaction: AppStory = { + render: () => ( + + setupStreamingChatStory({ + workspaceId: "ws-compaction", + messages: [ + createUserMessage("msg-1", "Help me refactor this codebase", { + historySequence: 1, + timestamp: STABLE_TIMESTAMP - 300000, + }), + createAssistantMessage( + "msg-2", + "I've analyzed the codebase and made several improvements to the architecture.", + { + historySequence: 2, + timestamp: STABLE_TIMESTAMP - 200000, + } + ), + createCompactionRequestMessage("msg-3", { + historySequence: 3, + timestamp: STABLE_TIMESTAMP - 3000, + }), + ], + streamingMessageId: "msg-4", + historySequence: 4, + streamText: + "## Conversation Summary\n\nThe user requested help refactoring the codebase. Key changes made:\n\n- Restructured component hierarchy for better separation of concerns\n- Extracted shared utilities into dedicated modules\n- Improved type safety across API boundaries", + }) + } + /> + ), + parameters: { + docs: { + description: { + story: + "Shows the compaction shimmer effect during streaming. The shimmer uses GPU-accelerated CSS transforms instead of background-position animations to prevent frame drops.", + }, + }, + }, +}; diff --git a/src/browser/stories/mockFactory.ts b/src/browser/stories/mockFactory.ts index 1a99141144..3c36c55b9c 100644 --- a/src/browser/stories/mockFactory.ts +++ b/src/browser/stories/mockFactory.ts @@ -171,6 +171,29 @@ export function createUserMessage( }; } +/** Create a compaction request user message (triggers shimmer effect on streaming response) */ +export function createCompactionRequestMessage( + id: string, + opts: { historySequence: number; timestamp?: number; rawCommand?: string } +): ChatMuxMessage { + const rawCommand = opts.rawCommand ?? "/compact"; + return { + type: "message", + id, + role: "user", + parts: [{ type: "text", text: rawCommand }], + metadata: { + historySequence: opts.historySequence, + timestamp: opts.timestamp ?? STABLE_TIMESTAMP, + muxMetadata: { + type: "compaction-request", + rawCommand, + parsed: {}, + }, + }, + }; +} + export function createAssistantMessage( id: string, text: string, diff --git a/src/browser/styles/globals.css b/src/browser/styles/globals.css index 710513b9b6..ed412722f6 100644 --- a/src/browser/styles/globals.css +++ b/src/browser/styles/globals.css @@ -1655,13 +1655,13 @@ pre code { box-shadow: var(--thumb-shadow, none); } -/* Custom animations for CompactionBackground */ -@keyframes shimmer { - 0% { - background-position: -1000px 0; +/* GPU-accelerated shimmer for CompactionBackground - runs on compositor thread */ +@keyframes shimmer-slide { + from { + transform: translateX(0); } - 100% { - background-position: 1000px 0; + to { + transform: translateX(53.33%); } }