MCPcopy Create free account
hub / github.com/codeaashu/claude-code / ChatWindow

Function ChatWindow

web/components/chat/ChatWindow.tsx:12–94  ·  view source on GitHub ↗
({ conversationId }: ChatWindowProps)

Source from the content-addressed store, hash-verified

10}
11
12export function ChatWindow({ conversationId }: ChatWindowProps) {
13 const bottomRef = useRef<HTMLDivElement>(null);
14 const { conversations } = useChatStore();
15 const conversation = conversations.find((c) => c.id === conversationId);
16 const messages = conversation?.messages ?? [];
17
18 const isStreaming = messages.some((m) => m.status === "streaming");
19
20 // Announce the last completed assistant message to screen readers
21 const [announcement, setAnnouncement] = useState("");
22 const prevLengthRef = useRef(messages.length);
23
24 useEffect(() => {
25 bottomRef.current?.scrollIntoView({ behavior: "smooth" });
26
27 const lastMsg = messages[messages.length - 1];
28 if (
29 messages.length > prevLengthRef.current &&
30 lastMsg?.role === "assistant" &&
31 lastMsg.status === "complete"
32 ) {
33 // Announce a short preview so screen reader users know a reply arrived
34 const preview = lastMsg.content.slice(0, 100);
35 setAnnouncement("");
36 setTimeout(() => setAnnouncement(`Claude replied: ${preview}`), 50);
37 }
38 prevLengthRef.current = messages.length;
39 }, [messages.length, messages]);
40
41 if (messages.length === 0) {
42 return (
43 <div className="flex-1 flex flex-col items-center justify-center gap-4 text-center px-6">
44 <div
45 className="w-12 h-12 rounded-full bg-brand-600/20 flex items-center justify-center"
46 aria-hidden="true"
47 >
48 <Bot className="w-6 h-6 text-brand-400" aria-hidden="true" />
49 </div>
50 <div>
51 <h2 className="text-lg font-semibold text-surface-100">How can I help?</h2>
52 <p className="text-sm text-surface-400 mt-1">
53 Start a conversation with Claude Code
54 </p>
55 </div>
56 </div>
57 );
58 }
59
60 return (
61 <div
62 className="flex-1 overflow-y-auto"
63 aria-busy={isStreaming}
64 aria-label="Conversation"
65 >
66 {/* Polite live region — announces when Claude finishes a reply */}
67 <div
68 role="status"
69 aria-live="polite"

Callers

nothing calls this directly

Calls

no outgoing calls

Tested by

no test coverage detected