import React, { useEffect, useRef } from "react"; import { Box, Text, useInput, type Key } from "ink"; import { ScrollView, type ScrollViewRef } from "ink-scroll-view"; import type { StderrLogEntry } from "@inspector/core/mcp/index.js"; interface NotificationsTabProps { stderrLogs: StderrLogEntry[]; width: number; height: number; onCountChange?: (count: number) => void; focused?: boolean; } export function NotificationsTab({ stderrLogs, width, height, onCountChange, focused = false, }: NotificationsTabProps) { const scrollViewRef = useRef(null); const onCountChangeRef = useRef(onCountChange); // Update ref when callback changes useEffect(() => { onCountChangeRef.current = onCountChange; }, [onCountChange]); useEffect(() => { onCountChangeRef.current?.(stderrLogs.length); }, [stderrLogs.length]); // Handle keyboard input for scrolling useInput( (input: string, key: Key) => { if (focused) { if (key.upArrow) { scrollViewRef.current?.scrollBy(-1); } else if (key.downArrow) { scrollViewRef.current?.scrollBy(1); } else if (key.pageUp) { const viewportHeight = scrollViewRef.current?.getViewportHeight() || 1; scrollViewRef.current?.scrollBy(-viewportHeight); } else if (key.pageDown) { const viewportHeight = scrollViewRef.current?.getViewportHeight() || 1; scrollViewRef.current?.scrollBy(viewportHeight); } } }, { isActive: focused }, ); return ( Logging ({stderrLogs.length}) {stderrLogs.length === 0 ? ( No stderr output yet ) : ( {stderrLogs.map((log, index) => ( [{log.timestamp.toLocaleTimeString()}] {log.message} ))} )} ); }