tsunami-code 3.11.2 → 3.11.3
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.
- package/index.js +24 -1
- package/lib/ui.js +20 -9
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -60,7 +60,8 @@ const cyan = (s) => chalk.cyan(s);
|
|
|
60
60
|
const red = (s) => chalk.red(s);
|
|
61
61
|
const green = (s) => chalk.green(s);
|
|
62
62
|
const yellow = (s) => chalk.yellow(s);
|
|
63
|
-
const blue
|
|
63
|
+
const blue = (s) => chalk.blue(s);
|
|
64
|
+
const magenta = (s) => chalk.magenta(s);
|
|
64
65
|
|
|
65
66
|
function printBanner(serverUrl) {
|
|
66
67
|
console.log(cyan(bold('\n 🌊 Tsunami Code CLI')) + dim(` v${VERSION}`));
|
|
@@ -510,6 +511,25 @@ async function run() {
|
|
|
510
511
|
ui.start(historyEntries);
|
|
511
512
|
ui.setModelLabel(`Tsunami Code CLI v${VERSION}`);
|
|
512
513
|
|
|
514
|
+
// ── Mode label helper ─────────────────────────────────────────────────────
|
|
515
|
+
// Builds the colored mode badges shown below the version line.
|
|
516
|
+
let _effortLevel = 'medium'; // default
|
|
517
|
+
function updateModeLabel() {
|
|
518
|
+
const badges = [];
|
|
519
|
+
if (planMode) badges.push(yellow('[plan]'));
|
|
520
|
+
const effortColors = {
|
|
521
|
+
low: green,
|
|
522
|
+
medium: dim, // medium is default — show dimmed so it's not noise
|
|
523
|
+
high: red,
|
|
524
|
+
max: magenta,
|
|
525
|
+
};
|
|
526
|
+
if (_effortLevel !== 'medium') {
|
|
527
|
+
const color = effortColors[_effortLevel] || dim;
|
|
528
|
+
badges.push(color(`[${_effortLevel} effort]`));
|
|
529
|
+
}
|
|
530
|
+
ui.setModeLabel(badges.join(' '));
|
|
531
|
+
}
|
|
532
|
+
|
|
513
533
|
// ── Memory commands ───────────────────────────────────────────────────────────
|
|
514
534
|
async function handleMemoryCommand(args) {
|
|
515
535
|
const sub = args[0]?.toLowerCase();
|
|
@@ -736,6 +756,7 @@ async function run() {
|
|
|
736
756
|
if (planMode) console.log(yellow(' Plan mode ON — read-only, no writes or execution.\n'));
|
|
737
757
|
else console.log(green(' Plan mode OFF — full capabilities restored.\n'));
|
|
738
758
|
ui.setPlanMode(planMode);
|
|
759
|
+
updateModeLabel();
|
|
739
760
|
break;
|
|
740
761
|
case 'undo': {
|
|
741
762
|
const restored = undo();
|
|
@@ -756,6 +777,8 @@ async function run() {
|
|
|
756
777
|
break;
|
|
757
778
|
}
|
|
758
779
|
setTemperature(levels[level]);
|
|
780
|
+
_effortLevel = level;
|
|
781
|
+
updateModeLabel();
|
|
759
782
|
console.log(green(` Effort: ${level} (temperature ${levels[level]})\n`));
|
|
760
783
|
break;
|
|
761
784
|
}
|
package/lib/ui.js
CHANGED
|
@@ -13,12 +13,13 @@ const cyan = (s) => chalk.cyan(s);
|
|
|
13
13
|
const yellow = (s) => chalk.yellow(s);
|
|
14
14
|
const dim = (s) => chalk.dim(s);
|
|
15
15
|
|
|
16
|
-
const BOX_LINES =
|
|
16
|
+
const BOX_LINES = 6; // top border + input + bottom border + version label + mode line + blank row
|
|
17
17
|
|
|
18
18
|
export function createUI({ planMode: initPlanMode = false, onLine, onTab, onExit }) {
|
|
19
19
|
let planMode = initPlanMode;
|
|
20
20
|
let continuation = false;
|
|
21
21
|
let modelLabel = '';
|
|
22
|
+
let modeLabel = '';
|
|
22
23
|
let inputBuf = '';
|
|
23
24
|
let cursorPos = 0;
|
|
24
25
|
let history = [];
|
|
@@ -52,10 +53,11 @@ export function createUI({ planMode: initPlanMode = false, onLine, onTab, onExit
|
|
|
52
53
|
function drawBox() {
|
|
53
54
|
const w = cols();
|
|
54
55
|
const r = rows(); // last row of terminal
|
|
55
|
-
const rT = r -
|
|
56
|
-
const rI = r -
|
|
57
|
-
const rB = r -
|
|
58
|
-
const
|
|
56
|
+
const rT = r - 5; // top border ╭─────╮
|
|
57
|
+
const rI = r - 4; // input line │ ❯ │
|
|
58
|
+
const rB = r - 3; // bottom border ╰─────╯
|
|
59
|
+
const rV = r - 2; // version label
|
|
60
|
+
const rMd = r - 1; // mode line
|
|
59
61
|
// r // blank spacing row
|
|
60
62
|
|
|
61
63
|
process.stdout.write('\x1b[s'); // save cursor
|
|
@@ -91,9 +93,13 @@ export function createUI({ planMode: initPlanMode = false, onLine, onTab, onExit
|
|
|
91
93
|
const botLine = `╰${'─'.repeat(w - 2)}╯`;
|
|
92
94
|
process.stdout.write(`\x1b[${rB};1H\x1b[2K${botLine.slice(0, w)}`);
|
|
93
95
|
|
|
94
|
-
//
|
|
95
|
-
const
|
|
96
|
-
process.stdout.write(`\x1b[${
|
|
96
|
+
// Version label ───────────────────────────────────────────────────
|
|
97
|
+
const vl = modelLabel ? ` ${dim(modelLabel)}` : '';
|
|
98
|
+
process.stdout.write(`\x1b[${rV};1H\x1b[2K${vl}`);
|
|
99
|
+
|
|
100
|
+
// Mode line ───────────────────────────────────────────────────────
|
|
101
|
+
const ml = modeLabel ? ` ${modeLabel}` : '';
|
|
102
|
+
process.stdout.write(`\x1b[${rMd};1H\x1b[2K${ml}`);
|
|
97
103
|
|
|
98
104
|
// Blank spacing row at very bottom ────────────────────────────────
|
|
99
105
|
process.stdout.write(`\x1b[${r};1H\x1b[2K`);
|
|
@@ -339,6 +345,11 @@ export function createUI({ planMode: initPlanMode = false, onLine, onTab, onExit
|
|
|
339
345
|
if (!processing) drawBox();
|
|
340
346
|
}
|
|
341
347
|
|
|
348
|
+
function setModeLabel(label) {
|
|
349
|
+
modeLabel = label;
|
|
350
|
+
if (!processing) drawBox();
|
|
351
|
+
}
|
|
352
|
+
|
|
342
353
|
function wasInterrupted() {
|
|
343
354
|
const v = _interrupted;
|
|
344
355
|
_interrupted = false;
|
|
@@ -362,7 +373,7 @@ export function createUI({ planMode: initPlanMode = false, onLine, onTab, onExit
|
|
|
362
373
|
|
|
363
374
|
return {
|
|
364
375
|
start, pause, resume,
|
|
365
|
-
setPlanMode, setContinuation, setModelLabel,
|
|
376
|
+
setPlanMode, setContinuation, setModelLabel, setModeLabel,
|
|
366
377
|
readLine, readChar,
|
|
367
378
|
wasInterrupted, stop, exitUI,
|
|
368
379
|
};
|