diff --git a/apps/cli/src/divider.ts b/apps/cli/src/divider.ts index 41d8b99..c6b08e9 100644 --- a/apps/cli/src/divider.ts +++ b/apps/cli/src/divider.ts @@ -19,15 +19,21 @@ const SHOW_CURSOR = '\x1b[?25h'; * @param text - The label to display. */ export function runDivider(text: string): void { + // Terminal size, falling back to COLUMNS/LINES env then a default — the env + // fallback lets a non-TTY (piped) run render at an explicit size for preview. + const dims = (): [number, number] => [ + process.stdout.columns || Number(process.env.COLUMNS) || 80, + process.stdout.rows || Number(process.env.LINES) || 24, + ]; const paint = (): void => { - const cols = process.stdout.columns || 80; - const rows = process.stdout.rows || 24; + const [cols, rows] = dims(); process.stdout.write(CLEAR + renderBanner(text, cols, rows)); }; // Non-interactive (piped) stdout: emit once and return, no hold. if (!process.stdout.isTTY) { - process.stdout.write(renderBanner(text, process.stdout.columns || 80, process.stdout.rows || 24) + '\n'); + const [cols, rows] = dims(); + process.stdout.write(renderBanner(text, cols, rows) + '\n'); return; } diff --git a/docs/history.md b/docs/history.md index d0269cf..46b7185 100644 --- a/docs/history.md +++ b/docs/history.md @@ -2,6 +2,10 @@ What each release brought. Reverse-chronological. Dates reflect when the corresponding tag was pushed. +## 3.6.1 — 2026-07-09 + +**`mx divider` renders much larger.** The banner now scales to fill the terminal (chunky letters at the largest cell size the width allows, height grown to match) instead of strict proportional scaling, which left a long label like `IN REVIEWS` tiny on a fullscreen window (7 rows). Also honors `COLUMNS`/`LINES` env vars as a size fallback for non-TTY (piped) output, so you can preview a size without going fullscreen. Renderer-only change in `@mx/core` (`renderBanner`) plus the CLI size fallback. + ## 3.6.0 — 2026-07-08 **`mx divider [-o]`** — fill a terminal with `` as large block letters, a visual separator for macOS Mission Control Spaces (e.g. an `IN REVIEWS` / `PR REVIEWS` window between clusters of work windows). Bare, it takes over the current terminal, draws the banner, and holds it (Ctrl-C or `q` to quit); `-o` opens a new fullscreen Terminal running the same banner (macOS). The text auto-scales to fill the terminal and re-renders on resize. diff --git a/npm/package.json b/npm/package.json index 5e29d0e..2f89cf0 100644 --- a/npm/package.json +++ b/npm/package.json @@ -1,6 +1,6 @@ { "name": "@roulabs/mx", - "version": "3.6.0", + "version": "3.6.1", "description": "mx — run several features in parallel across shared repos using git worktrees", "type": "module", "bin": { diff --git a/packages/core/src/banner.ts b/packages/core/src/banner.ts index 97adbf7..c990479 100644 --- a/packages/core/src/banner.ts +++ b/packages/core/src/banner.ts @@ -102,16 +102,18 @@ export function renderBanner(text: string, cols: number, rows: number): string { baseRows.push(glyphs.map((g) => g[r]).join(' ')); } - // Pick a scale that fits both dimensions. A character cell is about twice as - // tall as wide, so we aim for xscale ≈ 2·yscale to keep letters looking - // square, but never exceed the width/height budget (each axis is clamped - // independently, so long text scales down instead of overflowing). + // Scale up to fill the terminal. Width is the usual constraint (a long label + // caps how wide each cell can be), so take the largest cell width that fits + // and then grow the height to match — capped at the same factor so letters + // stay chunky (roughly square in cell counts) rather than proportional-but- + // tiny. This fills far more of a large fullscreen window than strict + // proportional scaling, which is what makes the banner readable at a glance. const marginH = 2; const marginV = 2; const xMax = Math.floor((cols - marginH) / Math.max(1, baseW)); const yMax = Math.floor((rows - marginV) / GLYPH_H); - const yscale = Math.max(1, Math.min(yMax, Math.floor(xMax / 2))); - const xscale = Math.max(1, Math.min(xMax, yscale * 2)); + const xscale = Math.max(1, xMax); + const yscale = Math.max(1, Math.min(yMax, xscale)); // Scale each base row up (horizontally by xscale, vertically by yscale). const scaled: string[] = [];