@@ -558,6 +558,37 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
558558 return false
559559 } , [ modifiedMessages , clineAsk , enableButtons , primaryButtonText ] )
560560
561+ // Track the actual streaming state for the cancel button separately.
562+ // This ensures the cancel button remains enabled during API requests,
563+ // even when there's a tool approval dialog.
564+ const isApiRequestInProgress = useMemo ( ( ) => {
565+ const isLastMessagePartial = modifiedMessages . at ( - 1 ) ?. partial === true
566+
567+ if ( isLastMessagePartial ) {
568+ return true
569+ }
570+
571+ const lastApiReqStarted = findLast (
572+ modifiedMessages ,
573+ ( message : ClineMessage ) => message . say === "api_req_started" ,
574+ )
575+
576+ if (
577+ lastApiReqStarted &&
578+ lastApiReqStarted . text !== null &&
579+ lastApiReqStarted . text !== undefined &&
580+ lastApiReqStarted . say === "api_req_started"
581+ ) {
582+ const cost = JSON . parse ( lastApiReqStarted . text ) . cost
583+
584+ if ( cost === undefined ) {
585+ return true // API request has not finished yet.
586+ }
587+ }
588+
589+ return false
590+ } , [ modifiedMessages ] )
591+
561592 const markFollowUpAsAnswered = useCallback ( ( ) => {
562593 const lastFollowUpMessage = messagesRef . current . findLast ( ( msg : ClineMessage ) => msg . ask === "followup" )
563594 if ( lastFollowUpMessage ) {
@@ -733,7 +764,7 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
733764
734765 const trimmedInput = text ?. trim ( )
735766
736- if ( isStreaming ) {
767+ if ( isStreaming || isApiRequestInProgress ) {
737768 vscode . postMessage ( { type : "cancelTask" } )
738769 setDidClickCancel ( true )
739770 return
@@ -773,7 +804,7 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
773804 setClineAsk ( undefined )
774805 setEnableButtons ( false )
775806 } ,
776- [ clineAsk , startNewTask , isStreaming ] ,
807+ [ clineAsk , startNewTask , isStreaming , isApiRequestInProgress ] ,
777808 )
778809
779810 const { info : model } = useSelectedModel ( apiConfiguration )
@@ -1763,7 +1794,8 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
17631794 vscode . postMessage ( { type : "condenseTaskContextRequest" , text : taskId } )
17641795 }
17651796
1766- const areButtonsVisible = showScrollToBottom || primaryButtonText || secondaryButtonText || isStreaming
1797+ const areButtonsVisible =
1798+ showScrollToBottom || primaryButtonText || secondaryButtonText || isStreaming || isApiRequestInProgress
17671799
17681800 return (
17691801 < div
@@ -1887,7 +1919,7 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
18871919 className = { `flex h-9 items-center mb-1 px-[15px] ${
18881920 showScrollToBottom
18891921 ? "opacity-100"
1890- : enableButtons || ( isStreaming && ! didClickCancel )
1922+ : enableButtons || ( ( isStreaming || isApiRequestInProgress ) && ! didClickCancel )
18911923 ? "opacity-100"
18921924 : "opacity-50"
18931925 } `} >
@@ -1937,10 +1969,10 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
19371969 </ VSCodeButton >
19381970 </ StandardTooltip >
19391971 ) }
1940- { ( secondaryButtonText || isStreaming ) && (
1972+ { ( secondaryButtonText || isStreaming || isApiRequestInProgress ) && (
19411973 < StandardTooltip
19421974 content = {
1943- isStreaming
1975+ isStreaming || isApiRequestInProgress
19441976 ? t ( "chat:cancel.tooltip" )
19451977 : secondaryButtonText === t ( "chat:startNewTask.title" )
19461978 ? t ( "chat:startNewTask.tooltip" )
@@ -1952,10 +1984,18 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro
19521984 } >
19531985 < VSCodeButton
19541986 appearance = "secondary"
1955- disabled = { ! enableButtons && ! ( isStreaming && ! didClickCancel ) }
1956- className = { isStreaming ? "flex-[2] ml-0" : "flex-1 ml-[6px]" }
1987+ disabled = {
1988+ ! enableButtons && ! ( isApiRequestInProgress && ! didClickCancel )
1989+ }
1990+ className = {
1991+ isStreaming || isApiRequestInProgress
1992+ ? "flex-[2] ml-0"
1993+ : "flex-1 ml-[6px]"
1994+ }
19571995 onClick = { ( ) => handleSecondaryButtonClick ( inputValue , selectedImages ) } >
1958- { isStreaming ? t ( "chat:cancel.title" ) : secondaryButtonText }
1996+ { isStreaming || isApiRequestInProgress
1997+ ? t ( "chat:cancel.title" )
1998+ : secondaryButtonText }
19591999 </ VSCodeButton >
19602000 </ StandardTooltip >
19612001 ) }
0 commit comments