@vincemakes/kiso-tui 0.20.3 → 0.20.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/compositor.js +48 -18
  2. package/package.json +2 -2
@@ -47,7 +47,7 @@ import { MENU_ITEMS, displayWidth } from "./editor.js";
47
47
  import { leadWidth } from "./width.js"; // W23: the ONE width authority (the editor, #inputRow, and editCol share it)
48
48
  // KC3.5: the panel-slot reads come from the DISPATCHERS — one source
49
49
  // for four reads, so an ask can never render half as an approval.
50
- import { panelAffordanceOf, panelFrameOf, panelLeadOf, panelRowsOf, panelStatusOf } from "./ask-panel.js";
50
+ import { panelFrameOf, panelLeadOf, panelRowsOf, panelStatusOf } from "./ask-panel.js";
51
51
  import { MOUSE_OFF } from "./editor.js";
52
52
  import { atPanelRows, bandHeader } from "./at-picker.js";
53
53
  // TUI2-R2 ②: the session picker's rows — the band's third occupant.
@@ -1820,8 +1820,25 @@ export class Body {
1820
1820
  * now). */
1821
1821
  #statusSource() {
1822
1822
  const panel = this.#panelState?.() ?? null;
1823
+ // DC-38: the panel's STATUS replaces the CLI's painting status —
1824
+ // that half of W21 stands. The HINT does not come with it, because
1825
+ // the panel block already ends in its own affordance row and has
1826
+ // since TUI2-R1.5 ("the affordance — the phase's key hint, ONE
1827
+ // row"). Both sites read `panelAffordance`, neither knew about the
1828
+ // other, and an approval at W≥100 printed the same 48-cell sentence
1829
+ // twice, six rows apart.
1830
+ //
1831
+ // The block's copy is the one to keep, on two grounds. It sits next
1832
+ // to the options it names. And it never disappears: the status row
1833
+ // drops its hint when the left text plus the hint will not fit, so
1834
+ // the duplicate was width-dependent — one copy on an ask (long left
1835
+ // text), two on an approval (`⏸ run paused`, twelve cells) — which
1836
+ // is why every fixed-width gate was blind to it. Each flavour's
1837
+ // block carries its own row (approval-panel.ts pushes it for the
1838
+ // approval and the pick, ask-panel.ts for the ask), so nothing is
1839
+ // lost anywhere.
1823
1840
  if (panel !== null)
1824
- return { status: panelStatusOf(panel), hint: panelAffordanceOf(panel) };
1841
+ return { status: panelStatusOf(panel), hint: undefined };
1825
1842
  // W22: while turns wait in the queue, the right hint shows the
1826
1843
  // count — the chips below carry the lines themselves.
1827
1844
  const queued = this.#queueState?.().length ?? 0;
@@ -2702,24 +2719,37 @@ export class Body {
2702
2719
  // the steady state for the session's whole life. It repairs a
2703
2720
  // killed predecessor straight into the same state. The visible
2704
2721
  // cursor comes back exactly once, in editor.exit().
2705
- out.push("\x1b[r\x1b[?69l\x1b[?7h\x1b[?25l");
2706
- // REL-0152-D20 the mechanism is understood and the obvious fix
2707
- // is NOT taken here. See the finding.
2722
+ // DC-40 — H line feeds BEFORE the reset, from wherever the shell
2723
+ // left the cursor. The first frame is the full-redraw path and
2724
+ // addresses rows 1..H absolutely; at launch those rows are the
2725
+ // shell's (its prompt, the launch command, the tail of whatever
2726
+ // ran before), and the frame painted over them — gone, not in
2727
+ // the scrollback (REL-0152-D20 established the mechanism; 37/60
2728
+ // shell lines survived on Apple Terminal, every line ON SCREEN
2729
+ // lost). From cursor row r, H feeds move H−r rows and then
2730
+ // scroll exactly r: the shell's rows 1..r enter the scrollback
2731
+ // as CONTENT (at most one blank row — the cursor's own line),
2732
+ // the screen is blank, and the model's assumption "row 0 is the
2733
+ // terminal's row 1" is true by construction. The count does not
2734
+ // depend on r, so nothing is asked of the terminal.
2708
2735
  //
2709
- // The first frame addresses rows 1..H absolutely and draws over
2710
- // whatever the terminal was showing. Scrolling a screenful away
2711
- // first would fix that, and it was built and measured: it pushes
2712
- // up to H BLANK rows into the scrollback, and TUI2-R2pre's
2713
- // blank-share gate went from 14/43 to 29/43 past the "a
2714
- // healthy session's scrollback is mostly content" invariant that
2715
- // gate exists to hold. Trading a symptom with a five-second
2716
- // user-side setting for a broken invariant is a worse deal.
2736
+ // THE ORDER IS THE FIX. `ESC[r` (DECSTBM) HOMES THE CURSOR to
2737
+ // row 1 VT100 semantics, honoured by Apple Terminal, xterm,
2738
+ // xterm.js and tmux alike. Feeds emitted AFTER the reset start
2739
+ // from row 1, move H−1 rows and scroll ONE: measured on Apple
2740
+ // Terminal, 1/20 shell lines survived with an otherwise
2741
+ // byte-identical frame. Feeds BEFORE the reset: 20/20. The house
2742
+ // emulators did not model the homing and passed the wrong order;
2743
+ // VtScrollback does now, and the DC-40 gate is red on it.
2717
2744
  //
2718
- // The correct version scrolls only as far as the terminal's
2719
- // content actually reaches, which needs a cursor-position query
2720
- // at boot its own round, with its own risk (this file already
2721
- // declined a boot-time round-trip once, for racing the editor
2722
- // for stdin).
2745
+ // The reset still precedes the FRAME (REL-0152-D19: a frame
2746
+ // drawn into an inherited sub-region is the defect); only the
2747
+ // feeds run under whatever region the shell left. A region a
2748
+ // killed foreign program left set makes the feeds scroll that
2749
+ // region alone and the frame paint over the rows outside it —
2750
+ // which is what every frame did before this fix, never worse.
2751
+ out.push("\n".repeat(H));
2752
+ out.push("\x1b[r\x1b[?69l\x1b[?7h\x1b[?25l");
2723
2753
  }
2724
2754
  out.push("\x1b[?7l");
2725
2755
  // REL-0161: ?25l is the STEADY state now, not a frame bracket —
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vincemakes/kiso-tui",
3
- "version": "0.20.3",
3
+ "version": "0.20.4",
4
4
  "description": "kiso tui — the pure terminal layer (cell renderer, dock, raw editor, diff, palette). Zero runtime dependencies: input is data, output is bytes.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -35,6 +35,6 @@
35
35
  },
36
36
  "homepage": "https://github.com/vincemakes/kiso/tree/main/packages/tui#readme",
37
37
  "dependencies": {
38
- "@vincemakes/kiso-tui-cells": "0.20.3"
38
+ "@vincemakes/kiso-tui-cells": "0.20.4"
39
39
  }
40
40
  }