From ce768e541a22b5b26d50c343381cb29e1837573b Mon Sep 17 00:00:00 2001 From: Matthew Breedlove Date: Thu, 21 Aug 2025 01:41:05 -0400 Subject: [PATCH] Add session cost widget --- src/utils/widgets.ts | 1 + src/widgets/SessionCost.ts | 35 +++++++++++++++++++++++++++++++++++ src/widgets/index.ts | 1 + 3 files changed, 37 insertions(+) create mode 100644 src/widgets/SessionCost.ts diff --git a/src/utils/widgets.ts b/src/utils/widgets.ts index d838ac3..9b03ab6 100644 --- a/src/utils/widgets.ts +++ b/src/utils/widgets.ts @@ -20,6 +20,7 @@ const widgetRegistry = new Map([ ['context-percentage', new widgets.ContextPercentageWidget()], ['context-percentage-usable', new widgets.ContextPercentageUsableWidget()], ['session-clock', new widgets.SessionClockWidget()], + ['session-cost', new widgets.SessionCostWidget()], ['block-timer', new widgets.BlockTimerWidget()], ['terminal-width', new widgets.TerminalWidthWidget()], ['version', new widgets.VersionWidget()], diff --git a/src/widgets/SessionCost.ts b/src/widgets/SessionCost.ts new file mode 100644 index 0000000..95f8a8e --- /dev/null +++ b/src/widgets/SessionCost.ts @@ -0,0 +1,35 @@ +import type { RenderContext } from '../types/RenderContext'; +import type { Settings } from '../types/Settings'; +import type { + Widget, + WidgetEditorDisplay, + WidgetItem +} from '../types/Widget'; + +export class SessionCostWidget implements Widget { + getDefaultColor(): string { return 'green'; } + getDescription(): string { return 'Shows the total session cost in USD'; } + getDisplayName(): string { return 'Session Cost'; } + getEditorDisplay(item: WidgetItem): WidgetEditorDisplay { + return { displayText: this.getDisplayName() }; + } + + render(item: WidgetItem, context: RenderContext, settings: Settings): string | null { + if (context.isPreview) { + return item.rawValue ? '$2.45' : 'Cost: $2.45'; + } + + const totalCost = context.data?.cost?.total_cost_usd; + if (totalCost === undefined) { + return null; + } + + // Format the cost to 2 decimal places + const formattedCost = `$${totalCost.toFixed(2)}`; + + return item.rawValue ? formattedCost : `Cost: ${formattedCost}`; + } + + supportsRawValue(): boolean { return true; } + supportsColors(item: WidgetItem): boolean { return true; } +} \ No newline at end of file diff --git a/src/widgets/index.ts b/src/widgets/index.ts index b6db363..445b391 100644 --- a/src/widgets/index.ts +++ b/src/widgets/index.ts @@ -10,6 +10,7 @@ export { ContextLengthWidget } from './ContextLength'; export { ContextPercentageWidget } from './ContextPercentage'; export { ContextPercentageUsableWidget } from './ContextPercentageUsable'; export { SessionClockWidget } from './SessionClock'; +export { SessionCostWidget } from './SessionCost'; export { TerminalWidthWidget } from './TerminalWidth'; export { VersionWidget } from './Version'; export { CustomTextWidget } from './CustomText';