mirror of
https://github.com/RooVetGit/Roo-Code.git
synced 2026-08-28 05:27:24 +00:00
Task header theme fixes (#2721)
This commit is contained in:
parent
b077267b4a
commit
3c937c3827
6 changed files with 85 additions and 135 deletions
|
|
@ -57,7 +57,17 @@ const copyRun = async (runId: number) => {
|
|||
tasks,
|
||||
async (task) => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const { id: _, ...newTaskMetricsValues } = task.taskMetrics!
|
||||
const { id: _, ...newTaskMetricsValues } = task.taskMetrics || {
|
||||
duration: 0,
|
||||
tokensIn: 0,
|
||||
tokensOut: 0,
|
||||
tokensContext: 0,
|
||||
cacheWrites: 0,
|
||||
cacheReads: 0,
|
||||
cost: 0,
|
||||
createdAt: new Date(),
|
||||
}
|
||||
|
||||
const [newTaskMetrics] = await destDb.insert(schema.taskMetrics).values(newTaskMetricsValues).returning()
|
||||
|
||||
if (!newTaskMetrics) {
|
||||
|
|
|
|||
|
|
@ -1,9 +1,12 @@
|
|||
import { VSCodeBadge, VSCodeButton, VSCodeProgressRing } from "@vscode/webview-ui-toolkit/react"
|
||||
import deepEqual from "fast-deep-equal"
|
||||
import React, { memo, useEffect, useMemo, useRef, useState } from "react"
|
||||
import { useSize } from "react-use"
|
||||
import { useCopyToClipboard } from "../../utils/clipboard"
|
||||
import { useTranslation, Trans } from "react-i18next"
|
||||
import deepEqual from "fast-deep-equal"
|
||||
import { VSCodeBadge, VSCodeButton, VSCodeProgressRing } from "@vscode/webview-ui-toolkit/react"
|
||||
|
||||
import { Button } from "@/components/ui"
|
||||
|
||||
import { useCopyToClipboard } from "../../utils/clipboard"
|
||||
import { safeJsonParse } from "../../utils/json"
|
||||
import {
|
||||
ClineApiReqInfo,
|
||||
|
|
@ -25,7 +28,7 @@ import McpResourceRow from "../mcp/McpResourceRow"
|
|||
import McpToolRow from "../mcp/McpToolRow"
|
||||
import { highlightMentions } from "./TaskHeader"
|
||||
import { CheckpointSaved } from "./checkpoints/CheckpointSaved"
|
||||
import FollowUpSuggest from "./FollowUpSuggest"
|
||||
import { FollowUpSuggest } from "./FollowUpSuggest"
|
||||
|
||||
interface ChatRowProps {
|
||||
message: ClineMessage
|
||||
|
|
@ -230,7 +233,8 @@ export const ChatRowContent = ({
|
|||
return [
|
||||
<span
|
||||
className="codicon codicon-question"
|
||||
style={{ color: normalColor, marginBottom: "-1.5px" }}></span>,
|
||||
style={{ color: normalColor, marginBottom: "-1.5px" }}
|
||||
/>,
|
||||
<span style={{ color: normalColor, fontWeight: "bold" }}>{t("chat:questions.hasQuestion")}</span>,
|
||||
]
|
||||
default:
|
||||
|
|
@ -795,39 +799,6 @@ export const ChatRowContent = ({
|
|||
</>
|
||||
)}
|
||||
</p>
|
||||
|
||||
{/* {apiProvider === "" && (
|
||||
<div
|
||||
style={{
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
backgroundColor:
|
||||
"color-mix(in srgb, var(--vscode-errorForeground) 20%, transparent)",
|
||||
color: "var(--vscode-editor-foreground)",
|
||||
padding: "6px 8px",
|
||||
borderRadius: "3px",
|
||||
margin: "10px 0 0 0",
|
||||
fontSize: "12px",
|
||||
}}>
|
||||
<i
|
||||
className="codicon codicon-warning"
|
||||
style={{
|
||||
marginRight: 6,
|
||||
fontSize: 16,
|
||||
color: "var(--vscode-errorForeground)",
|
||||
}}></i>
|
||||
<span>
|
||||
Uh-oh, this could be a problem on end. We've been alerted and
|
||||
will resolve this ASAP. You can also{" "}
|
||||
<a
|
||||
href=""
|
||||
style={{ color: "inherit", textDecoration: "underline" }}>
|
||||
contact us
|
||||
</a>
|
||||
.
|
||||
</span>
|
||||
</div>
|
||||
)} */}
|
||||
</>
|
||||
)}
|
||||
|
||||
|
|
@ -853,46 +824,19 @@ export const ChatRowContent = ({
|
|||
)
|
||||
case "user_feedback":
|
||||
return (
|
||||
<div
|
||||
className="outline rounded p-4"
|
||||
style={{
|
||||
color: "var(--vscode-badge-foreground)",
|
||||
padding: "4px",
|
||||
overflow: "hidden",
|
||||
whiteSpace: "pre-wrap",
|
||||
wordBreak: "break-word",
|
||||
overflowWrap: "anywhere",
|
||||
}}>
|
||||
<div
|
||||
style={{
|
||||
display: "flex",
|
||||
justifyContent: "space-between",
|
||||
alignItems: "flex-start",
|
||||
gap: "10px",
|
||||
}}>
|
||||
<span style={{ display: "block", flexGrow: 1, padding: "4px" }}>
|
||||
{highlightMentions(message.text)}
|
||||
</span>
|
||||
<VSCodeButton
|
||||
appearance="icon"
|
||||
style={{
|
||||
padding: "3px",
|
||||
flexShrink: 0,
|
||||
height: "24px",
|
||||
marginTop: "-3px",
|
||||
marginBottom: "-3px",
|
||||
marginRight: "-6px",
|
||||
}}
|
||||
<div className="bg-vscode-editor-background border rounded-xs p-1 overflow-hidden whitespace-pre-wrap word-break-break-word overflow-wrap-anywhere">
|
||||
<div className="flex justify-between gap-2">
|
||||
<div className="flex-grow px-2 py-1">{highlightMentions(message.text)}</div>
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
disabled={isStreaming}
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
vscode.postMessage({
|
||||
type: "deleteMessage",
|
||||
value: message.ts,
|
||||
})
|
||||
vscode.postMessage({ type: "deleteMessage", value: message.ts })
|
||||
}}>
|
||||
<span className="codicon codicon-trash"></span>
|
||||
</VSCodeButton>
|
||||
<span className="codicon codicon-trash" />
|
||||
</Button>
|
||||
</div>
|
||||
{message.images && message.images.length > 0 && (
|
||||
<Thumbnails images={message.images} style={{ marginTop: "8px" }} />
|
||||
|
|
|
|||
|
|
@ -1,7 +1,8 @@
|
|||
import { useCallback } from "react"
|
||||
import { cn } from "../../lib/utils"
|
||||
import { Button } from "../ui/button"
|
||||
import { Edit } from "lucide-react"
|
||||
import { ArrowRight, Edit } from "lucide-react"
|
||||
|
||||
import { Button } from "@/components/ui"
|
||||
|
||||
import { useAppTranslation } from "../../i18n/TranslationContext"
|
||||
|
||||
interface FollowUpSuggestProps {
|
||||
|
|
@ -10,7 +11,7 @@ interface FollowUpSuggestProps {
|
|||
ts: number
|
||||
}
|
||||
|
||||
const FollowUpSuggest = ({ suggestions = [], onSuggestionClick, ts = 1 }: FollowUpSuggestProps) => {
|
||||
export const FollowUpSuggest = ({ suggestions = [], onSuggestionClick, ts = 1 }: FollowUpSuggestProps) => {
|
||||
const { t } = useAppTranslation()
|
||||
const handleSuggestionClick = useCallback(
|
||||
(suggestion: string, event: React.MouseEvent) => {
|
||||
|
|
@ -19,45 +20,39 @@ const FollowUpSuggest = ({ suggestions = [], onSuggestionClick, ts = 1 }: Follow
|
|||
[onSuggestionClick],
|
||||
)
|
||||
|
||||
// Don't render if there are no suggestions or no click handler
|
||||
// Don't render if there are no suggestions or no click handler.
|
||||
if (!suggestions?.length || !onSuggestionClick) {
|
||||
return null
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="h-full">
|
||||
<div className="h-full scrollbar-thin scrollbar-thumb-vscode-scrollbarSlider-background scrollbar-track-transparent">
|
||||
<div className={cn("flex gap-2.5 pb-2 flex-col h-full")}>
|
||||
{suggestions.map((suggestion) => (
|
||||
<div key={`${suggestion}-${ts}`} className="w-full relative group">
|
||||
<Button
|
||||
variant="secondary"
|
||||
className="w-full text-left whitespace-normal break-words h-auto min-h-[28px] py-2 justify-start pr-8"
|
||||
onClick={(event) => handleSuggestionClick(suggestion, event)}
|
||||
aria-label={suggestion}>
|
||||
<span className="text-left">{suggestion}</span>
|
||||
</Button>
|
||||
<div
|
||||
className="absolute top-1 right-1 opacity-0 group-hover:opacity-100 transition-opacity"
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
// Simulate shift-click by directly calling the handler with shiftKey=true
|
||||
onSuggestionClick?.(suggestion, { ...e, shiftKey: true })
|
||||
}}
|
||||
title={t("chat:followUpSuggest.copyToInput")}>
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
className="h-6 w-6 p-1 hover:bg-vscode-button-hoverBackground">
|
||||
<Edit className="h-4 w-4" />
|
||||
</Button>
|
||||
</div>
|
||||
<div className="flex mb-2 flex-col h-full border rounded-xs">
|
||||
{suggestions.map((suggestion) => (
|
||||
<div key={`${suggestion}-${ts}`} className="w-full relative group">
|
||||
<Button
|
||||
variant="ghost"
|
||||
className="text-left whitespace-normal break-words w-full h-auto py-3 justify-start pr-8"
|
||||
onClick={(event) => handleSuggestionClick(suggestion, event)}
|
||||
aria-label={suggestion}>
|
||||
<div className="flex flex-row items-center gap-2">
|
||||
<ArrowRight />
|
||||
<div>{suggestion}</div>
|
||||
</div>
|
||||
))}
|
||||
</Button>
|
||||
<div
|
||||
className="absolute top-1 right-1 opacity-0 group-hover:opacity-100 transition-opacity"
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
// Simulate shift-click by directly calling the handler with shiftKey=true.
|
||||
onSuggestionClick?.(suggestion, { ...e, shiftKey: true })
|
||||
}}
|
||||
title={t("chat:followUpSuggest.copyToInput")}>
|
||||
<Button variant="ghost" size="icon">
|
||||
<Edit />
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
export default FollowUpSuggest
|
||||
|
|
|
|||
|
|
@ -1,13 +1,12 @@
|
|||
import React, { memo, useMemo, useRef, useState } from "react"
|
||||
import { useWindowSize } from "react-use"
|
||||
import { VSCodeButton } from "@vscode/webview-ui-toolkit/react"
|
||||
import prettyBytes from "pretty-bytes"
|
||||
import { useTranslation } from "react-i18next"
|
||||
|
||||
import { vscode } from "@/utils/vscode"
|
||||
import { formatLargeNumber } from "@/utils/format"
|
||||
import { calculateTokenDistribution, getMaxTokensForModel } from "@/utils/model-utils"
|
||||
import { Button } from "@/components/ui"
|
||||
import { Button, Badge } from "@/components/ui"
|
||||
|
||||
import { ClineMessage } from "../../../../src/shared/ExtensionMessage"
|
||||
import { mentionRegexGlobal } from "../../../../src/shared/context-mentions"
|
||||
|
|
@ -17,6 +16,7 @@ import { useExtensionState } from "../../context/ExtensionStateContext"
|
|||
import Thumbnails from "../common/Thumbnails"
|
||||
import { normalizeApiConfiguration } from "../settings/ApiOptions"
|
||||
import { DeleteTaskDialog } from "../history/DeleteTaskDialog"
|
||||
import { cn } from "@/lib/utils"
|
||||
|
||||
interface TaskHeaderProps {
|
||||
task: ClineMessage
|
||||
|
|
@ -55,10 +55,15 @@ const TaskHeader: React.FC<TaskHeaderProps> = ({
|
|||
const shouldShowPromptCacheInfo = doesModelSupportPromptCache && apiConfiguration?.apiProvider !== "openrouter"
|
||||
|
||||
return (
|
||||
<div className="py-[10px] px-[13px]">
|
||||
<div className="py-2 px-3">
|
||||
<div
|
||||
className={`rounded p-[10px] flex flex-col gap-[6px] relative z-1 outline hover:outline-vscode-badge-foreground hover:text-vscode-badge-foreground transition-color duration-500 ${!!isTaskExpanded ? "outline-vscode-badge-foreground text-vscode-badge-foreground" : "outline-vscode-badge-foreground/80 text-vscode-badge-foreground/80"}`}>
|
||||
<div className="flex justify-between items-center">
|
||||
className={cn(
|
||||
"rounded-xs p-2.5 flex flex-col gap-1.5 relative z-1 border",
|
||||
!!isTaskExpanded
|
||||
? "border-vscode-panel-border text-vscode-foreground"
|
||||
: "border-vscode-panel-border/80 text-vscode-foreground/80",
|
||||
)}>
|
||||
<div className="flex justify-between items-center gap-2">
|
||||
<div
|
||||
className="flex items-center cursor-pointer -ml-0.5 select-none grow min-w-0"
|
||||
onClick={() => setIsTaskExpanded(!isTaskExpanded)}>
|
||||
|
|
@ -73,14 +78,14 @@ const TaskHeader: React.FC<TaskHeaderProps> = ({
|
|||
{!isTaskExpanded && <span className="ml-1">{highlightMentions(task.text, false)}</span>}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<VSCodeButton
|
||||
appearance="icon"
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
onClick={onClose}
|
||||
className="ml-1.5 shrink-0 text-vscode-badge-foreground"
|
||||
title={t("chat:task.closeAndStart")}>
|
||||
<span className="codicon codicon-close"></span>
|
||||
</VSCodeButton>
|
||||
title={t("chat:task.closeAndStart")}
|
||||
className="shrink-0 w-5 h-5">
|
||||
<span className="codicon codicon-close" />
|
||||
</Button>
|
||||
</div>
|
||||
{/* Collapsed state: Track context and cost if we have any */}
|
||||
{!isTaskExpanded && contextWindow > 0 && (
|
||||
|
|
@ -90,11 +95,7 @@ const TaskHeader: React.FC<TaskHeaderProps> = ({
|
|||
contextTokens={contextTokens || 0}
|
||||
maxTokens={getMaxTokensForModel(selectedModelInfo, apiConfiguration)}
|
||||
/>
|
||||
{!!totalCost && (
|
||||
<div className="ml-2.5 bg-vscode-editor-foreground text-vscode-editor-background py-0.5 px-1 rounded-full text-[11px] font-medium inline-block shrink-0">
|
||||
${totalCost?.toFixed(2)}
|
||||
</div>
|
||||
)}
|
||||
{!!totalCost && <Badge>${totalCost.toFixed(2)}</Badge>}
|
||||
</div>
|
||||
)}
|
||||
{/* Expanded state: Show task text and images */}
|
||||
|
|
@ -271,7 +272,7 @@ const ContextWindowProgress = ({ contextWindow, contextTokens, maxTokens }: Cont
|
|||
<div className="flex-1 relative">
|
||||
{/* Invisible overlay for hover area */}
|
||||
<div
|
||||
className="absolute w-full cursor-pointer h-4 -top-[7px] z-5"
|
||||
className="absolute w-full h-4 -top-[7px] z-5"
|
||||
title={t("chat:tokenProgress.availableSpace", { amount: formatLargeNumber(availableSize) })}
|
||||
data-testid="context-available-space"
|
||||
/>
|
||||
|
|
@ -282,7 +283,7 @@ const ContextWindowProgress = ({ contextWindow, contextTokens, maxTokens }: Cont
|
|||
<div className="relative h-full" style={{ width: `${currentPercent}%` }}>
|
||||
{/* Invisible overlay for current tokens section */}
|
||||
<div
|
||||
className="absolute cursor-pointer h-4 -top-[7px] w-full z-6"
|
||||
className="absolute h-4 -top-[7px] w-full z-6"
|
||||
title={t("chat:tokenProgress.tokensUsed", {
|
||||
used: formatLargeNumber(safeContextTokens),
|
||||
total: formatLargeNumber(safeContextWindow),
|
||||
|
|
@ -297,7 +298,7 @@ const ContextWindowProgress = ({ contextWindow, contextTokens, maxTokens }: Cont
|
|||
<div className="relative h-full" style={{ width: `${reservedPercent}%` }}>
|
||||
{/* Invisible overlay for reserved section */}
|
||||
<div
|
||||
className="absolute cursor-pointer h-4 -top-[7px] w-full z-6"
|
||||
className="absolute h-4 -top-[7px] w-full z-6"
|
||||
title={t("chat:tokenProgress.reservedForResponse", {
|
||||
amount: formatLargeNumber(reservedForOutput),
|
||||
})}
|
||||
|
|
@ -312,7 +313,7 @@ const ContextWindowProgress = ({ contextWindow, contextTokens, maxTokens }: Cont
|
|||
<div className="relative h-full" style={{ width: `${availablePercent}%` }}>
|
||||
{/* Invisible overlay for available space */}
|
||||
<div
|
||||
className="absolute cursor-pointer h-4 -top-[7px] w-full z-6"
|
||||
className="absolute h-4 -top-[7px] w-full z-6"
|
||||
title={t("chat:tokenProgress.availableSpace", {
|
||||
amount: formatLargeNumber(availableSize),
|
||||
})}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ import { cva, type VariantProps } from "class-variance-authority"
|
|||
import { cn } from "@/lib/utils"
|
||||
|
||||
const badgeVariants = cva(
|
||||
"inline-flex items-center rounded-xs border border-transparent shadow px-2 py-0.5 text-xs font-semibold transition-colors focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2",
|
||||
"inline-flex items-center rounded-full border border-transparent px-2 py-0.5 text-xs font-semibold transition-colors focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2",
|
||||
{
|
||||
variants: {
|
||||
variant: {
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ import { cva, type VariantProps } from "class-variance-authority"
|
|||
import { cn } from "@/lib/utils"
|
||||
|
||||
const buttonVariants = cva(
|
||||
"inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-xs text-base font-medium transition-colors focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg]:size-4 [&_svg]:shrink-0 cursor-pointer",
|
||||
"inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-xs text-base font-medium transition-colors focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg]:size-4 [&_svg]:shrink-0 cursor-pointer active:opacity-80",
|
||||
{
|
||||
variants: {
|
||||
variant: {
|
||||
|
|
@ -13,7 +13,7 @@ const buttonVariants = cva(
|
|||
"border border-vscode-input-border bg-primary text-primary-foreground shadow hover:bg-primary/90",
|
||||
destructive: "bg-destructive text-destructive-foreground shadow-sm hover:bg-destructive/90",
|
||||
outline:
|
||||
"border border-vscode-input-border bg-background shadow-sm hover:bg-accent hover:text-accent-foreground",
|
||||
"border border-vscode-input-border bg-transparent shadow-sm hover:bg-accent hover:text-accent-foreground",
|
||||
secondary:
|
||||
"border border-vscode-input-border bg-secondary text-secondary-foreground shadow-sm hover:bg-secondary/80",
|
||||
ghost: "hover:bg-accent hover:text-accent-foreground",
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue