diff --git a/ui-tui/src/__tests__/statusRule.test.ts b/ui-tui/src/__tests__/statusRule.test.ts
new file mode 100644
index 00000000000..bf34e37750c
--- /dev/null
+++ b/ui-tui/src/__tests__/statusRule.test.ts
@@ -0,0 +1,25 @@
+import { describe, expect, it } from 'vitest'
+
+import { statusRuleWidths } from '../components/appChrome.js'
+
+describe('statusRuleWidths', () => {
+ it('keeps the status rule within the terminal width', () => {
+ for (const cols of [8, 12, 20, 40, 100]) {
+ const widths = statusRuleWidths(cols, '~/src/hermes-agent/main (some-long-branch-name)')
+
+ expect(widths.leftWidth + widths.separatorWidth + widths.rightWidth).toBeLessThanOrEqual(cols)
+ expect(widths.leftWidth).toBeGreaterThan(0)
+ }
+ })
+
+ it('truncates the cwd segment before it can wrap in skinny terminals', () => {
+ const widths = statusRuleWidths(24, '~/src/hermes-agent/main (bb/some-extremely-long-branch)')
+
+ expect(widths.rightWidth).toBeLessThan('~/src/hermes-agent/main (bb/some-extremely-long-branch)'.length)
+ expect(widths.leftWidth).toBeGreaterThanOrEqual(8)
+ })
+
+ it('omits the cwd segment when there is no room for it', () => {
+ expect(statusRuleWidths(2, 'abcdef')).toEqual({ leftWidth: 1, rightWidth: 0, separatorWidth: 1 })
+ })
+})
diff --git a/ui-tui/src/components/appChrome.tsx b/ui-tui/src/components/appChrome.tsx
index c961f4c2731..8c386200ad6 100644
--- a/ui-tui/src/components/appChrome.tsx
+++ b/ui-tui/src/components/appChrome.tsx
@@ -150,6 +150,17 @@ function ctxBar(pct: number | undefined, w = 10) {
return '█'.repeat(filled) + '░'.repeat(w - filled)
}
+export function statusRuleWidths(cols: number, cwdLabel: string) {
+ const width = Math.max(1, Math.floor(cols || 1))
+ const separatorWidth = width >= 24 ? 3 : 1
+ const minLeftWidth = width >= 24 ? 8 : 1
+ const maxRightWidth = Math.max(0, width - separatorWidth - minLeftWidth)
+ const rightWidth = Math.max(0, Math.min(cwdLabel.length, maxRightWidth))
+ const leftWidth = Math.max(1, width - separatorWidth - rightWidth)
+
+ return { leftWidth, rightWidth, separatorWidth }
+}
+
function SpawnHud({ t }: { t: Theme }) {
// Tight HUD that only appears when the session is actually fanning out.
// Colour escalates to warn/error as depth or concurrency approaches the cap.
@@ -297,7 +308,7 @@ export function StatusRule({
: ''
const bar = usage.context_max ? ctxBar(pct) : ''
- const leftWidth = Math.max(12, cols - cwdLabel.length - 3)
+ const { leftWidth, rightWidth, separatorWidth } = statusRuleWidths(cols, cwdLabel)
return (
@@ -349,8 +360,16 @@ export function StatusRule({
- ─
- {cwdLabel}
+ {rightWidth > 0 ? (
+ <>
+ {separatorWidth >= 3 ? ' ─ ' : ' '}
+
+
+ {cwdLabel}
+
+
+ >
+ ) : null}
)
}