1+ import { TextAttributes } from '@opentui/core'
12import { useCallback , useEffect , useMemo , useRef , useState } from 'react'
23import { useShallow } from 'zustand/react/shallow'
34
@@ -20,6 +21,7 @@ import { useAgentValidation } from './hooks/use-agent-validation'
2021import { useAuthState } from './hooks/use-auth-state'
2122import { useChatInput } from './hooks/use-chat-input'
2223import { useClipboard } from './hooks/use-clipboard'
24+ import { useConnectionStatus } from './hooks/use-connection-status'
2325import { useElapsedTime } from './hooks/use-elapsed-time'
2426import { useExitHandler } from './hooks/use-exit-handler'
2527import { useInputHistory } from './hooks/use-input-history'
@@ -33,24 +35,19 @@ import { useSuggestionMenuHandlers } from './hooks/use-suggestion-menu-handlers'
3335import { useTerminalDimensions } from './hooks/use-terminal-dimensions'
3436import { useTheme } from './hooks/use-theme'
3537import { useValidationBanner } from './hooks/use-validation-banner'
36- import { useConnectionStatus } from './hooks/use-connection-status'
3738import { useChatStore } from './state/chat-store'
3839import { createChatScrollAcceleration } from './utils/chat-scroll-accel'
3940import { formatQueuedPreview } from './utils/helpers'
4041import { loadLocalAgents } from './utils/local-agent-registry'
4142import { buildMessageTree } from './utils/message-tree-utils'
43+ import { computeInputLayoutMetrics } from './utils/text-layout'
4244import { createMarkdownPalette } from './utils/theme-system'
4345import { BORDER_CHARS } from './utils/ui-constants'
44- import { computeInputLayoutMetrics } from './utils/text-layout'
4546
4647import type { SendMessageTimerEvent } from './hooks/use-send-message'
4748import type { ContentBlock } from './types/chat'
4849import type { SendMessageFn } from './types/contracts/send-message'
49- import type { KeyEvent , ScrollBoxRenderable } from '@opentui/core'
50- import { TextAttributes } from '@opentui/core'
51-
52- const MAX_VIRTUALIZED_TOP_LEVEL = 60
53- const VIRTUAL_OVERSCAN = 12
50+ import type { ScrollBoxRenderable } from '@opentui/core'
5451
5552const DEFAULT_AGENT_IDS = {
5653 DEFAULT : 'base2' ,
@@ -81,7 +78,7 @@ export const Chat = ({
8178 const scrollRef = useRef < ScrollBoxRenderable | null > ( null )
8279 const inputRef = useRef < MultilineInputHandle | null > ( null )
8380
84- const { terminalWidth , separatorWidth } = useTerminalDimensions ( )
81+ const { separatorWidth } = useTerminalDimensions ( )
8582
8683 const theme = useTheme ( )
8784 const markdownPalette = useMemo ( ( ) => createMarkdownPalette ( theme ) , [ theme ] )
@@ -119,7 +116,6 @@ export const Chat = ({
119116 agentMode,
120117 setAgentMode,
121118 toggleAgentMode,
122- hasReceivedPlanResponse,
123119 setHasReceivedPlanResponse,
124120 lastMessageMode,
125121 setLastMessageMode,
@@ -185,7 +181,6 @@ export const Chat = ({
185181 const {
186182 isAuthenticated,
187183 setIsAuthenticated,
188- user,
189184 setUser,
190185 handleLoginSuccess,
191186 logoutMutation,
@@ -378,26 +373,7 @@ export const Chat = ({
378373 const isStreaming = streamStatus !== 'idle'
379374
380375 const handleTimerEvent = useCallback (
381- ( event : SendMessageTimerEvent ) => {
382- const payload = {
383- event : 'cli_main_agent_timer' ,
384- timerEventType : event . type ,
385- agentId : agentId ?? 'main' ,
386- messageId : event . messageId ,
387- startedAt : event . startedAt ,
388- ...( event . type === 'stop'
389- ? {
390- finishedAt : event . finishedAt ,
391- elapsedMs : event . elapsedMs ,
392- outcome : event . outcome ,
393- }
394- : { } ) ,
395- }
396- const message =
397- event . type === 'start'
398- ? 'Main agent timer started'
399- : `Main agent timer stopped (${ event . outcome } )`
400- } ,
376+ ( event : SendMessageTimerEvent ) => { } ,
401377 [ agentId ] ,
402378 )
403379
@@ -544,16 +520,22 @@ export const Chat = ({
544520 const previewWidth = Math . max ( 30 , separatorWidth - 20 )
545521 return formatQueuedPreview ( queuedMessages , previewWidth )
546522 } , [ queuedMessages , separatorWidth , shouldShowQueuePreview ] )
547- const hasSlashSuggestions = slashContext . active && slashSuggestionItems . length > 0
523+ const hasSlashSuggestions =
524+ slashContext . active && slashSuggestionItems . length > 0
548525 const hasMentionSuggestions =
549- ! slashContext . active && mentionContext . active && agentSuggestionItems . length > 0
526+ ! slashContext . active &&
527+ mentionContext . active &&
528+ agentSuggestionItems . length > 0
550529 const hasSuggestionMenu = hasSlashSuggestions || hasMentionSuggestions
551530 const showAgentStatusLine = showAgentDisplayName && loadedAgentsData
552531
553532 const inputLayoutMetrics = useMemo ( ( ) => {
554533 const text = inputValue ?? ''
555534 const layoutContent = text . length > 0 ? text : ' '
556- const safeCursor = Math . max ( 0 , Math . min ( cursorPosition , layoutContent . length ) )
535+ const safeCursor = Math . max (
536+ 0 ,
537+ Math . min ( cursorPosition , layoutContent . length ) ,
538+ )
557539 const cursorProbe =
558540 safeCursor >= layoutContent . length
559541 ? layoutContent
@@ -591,7 +573,10 @@ export const Chat = ({
591573 )
592574
593575 const elapsedTimeNode = (
594- < StatusElapsedTime streamStatus = { streamStatus } timerStartTime = { timerStartTime } />
576+ < StatusElapsedTime
577+ streamStatus = { streamStatus }
578+ timerStartTime = { timerStartTime }
579+ />
595580 )
596581
597582 const validationBanner = useValidationBanner ( {
@@ -749,7 +734,6 @@ export const Chat = ({
749734 < text style = { { wrapMode : 'none' } } > { elapsedTimeNode } </ text >
750735 </ box >
751736 </ box >
752-
753737 </ box >
754738 ) }
755739
@@ -802,7 +786,9 @@ export const Chat = ({
802786 < box
803787 style = { {
804788 flexDirection : 'row' ,
805- alignItems : shouldCenterInputVertically ? 'center' : 'flex-start' ,
789+ alignItems : shouldCenterInputVertically
790+ ? 'center'
791+ : 'flex-start' ,
806792 width : '100%' ,
807793 } }
808794 >
0 commit comments