@nmakarov/cli-toolkit 0.81.0 → 0.84.0
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/dist/cli-runner.cjs +85 -27
- package/dist/cli-runner.cjs.map +1 -1
- package/dist/cli-runner.js +87 -29
- package/dist/cli-runner.js.map +1 -1
- package/dist/index.cjs +91 -27
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +87 -29
- package/dist/index.js.map +1 -1
- package/dist/init.cjs +85 -27
- package/dist/init.cjs.map +1 -1
- package/dist/init.js +87 -29
- package/dist/init.js.map +1 -1
- package/dist/screen.cjs +83 -27
- package/dist/screen.cjs.map +1 -1
- package/dist/screen.js +77 -27
- package/dist/screen.js.map +1 -1
- package/package.json +1 -1
package/dist/screen.js
CHANGED
|
@@ -591,23 +591,24 @@ function formatKeyBindings(bindings, mode = "long") {
|
|
|
591
591
|
})));
|
|
592
592
|
groups.sort((a, b) => a.order - b.order);
|
|
593
593
|
const items = [];
|
|
594
|
-
groups.forEach((group) => {
|
|
594
|
+
groups.forEach((group, groupIndex) => {
|
|
595
595
|
const bindingWithCustom = resolvedBindings.find(
|
|
596
|
-
(b) => group.keys.includes(b
|
|
596
|
+
(b) => group.keys.includes(formatBindingKey(b)) && typeof b.resolvedCaption !== "string"
|
|
597
597
|
);
|
|
598
598
|
if (bindingWithCustom && bindingWithCustom.resolvedCaption) {
|
|
599
599
|
items.push(bindingWithCustom.resolvedCaption);
|
|
600
600
|
} else {
|
|
601
|
-
|
|
602
|
-
if (mode === "long") {
|
|
603
|
-
items.push(`${keyStr} to ${group.caption}`);
|
|
604
|
-
} else {
|
|
605
|
-
items.push(keyStr);
|
|
606
|
-
}
|
|
601
|
+
items.push(formatFooterHotkey(formatKeys(group.keys), group.caption, mode, `kb-${groupIndex}`));
|
|
607
602
|
}
|
|
608
603
|
});
|
|
609
604
|
return items;
|
|
610
605
|
}
|
|
606
|
+
var FOOTER_HOTKEY_STYLE = { bold: true, color: "white", dimColor: false };
|
|
607
|
+
function formatFooterHotkey(keyStr, caption = "", mode = "long", reactKey = "hotkey") {
|
|
608
|
+
const keyNode = h3(Text3, { key: `${reactKey}-key`, ...FOOTER_HOTKEY_STYLE }, keyStr);
|
|
609
|
+
if (mode !== "long" || !caption) return keyNode;
|
|
610
|
+
return h3(Text3, { key: reactKey, dimColor: true, color: "white" }, keyNode, ` to ${caption}`);
|
|
611
|
+
}
|
|
611
612
|
function formatKeys(keys) {
|
|
612
613
|
const keyMap = {
|
|
613
614
|
escape: "esc",
|
|
@@ -984,8 +985,45 @@ function nextScrollAfterContentChange({ following, scrollTop, maxScroll }) {
|
|
|
984
985
|
return { scrollTop: next, following: isScrolledToBottom(next, max) };
|
|
985
986
|
}
|
|
986
987
|
|
|
987
|
-
// src/screen/
|
|
988
|
-
var
|
|
988
|
+
// src/screen/visible-text.js
|
|
989
|
+
var ANSI_RE = /\u001b(?:[@-Z\\-_]|\[[0-?]*[ -/]*[@-~])/g;
|
|
990
|
+
function stripAnsi(text) {
|
|
991
|
+
return String(text ?? "").replace(ANSI_RE, "");
|
|
992
|
+
}
|
|
993
|
+
function visibleWidth(text) {
|
|
994
|
+
return [...stripAnsi(text)].length;
|
|
995
|
+
}
|
|
996
|
+
function sliceVisible(text, cols) {
|
|
997
|
+
const w = Math.max(0, Math.floor(Number(cols) || 0));
|
|
998
|
+
const s = String(text ?? "");
|
|
999
|
+
if (w === 0) return "";
|
|
1000
|
+
let vis = 0;
|
|
1001
|
+
let out = "";
|
|
1002
|
+
let i = 0;
|
|
1003
|
+
while (i < s.length && vis < w) {
|
|
1004
|
+
ANSI_RE.lastIndex = i;
|
|
1005
|
+
const m = ANSI_RE.exec(s);
|
|
1006
|
+
if (m && m.index === i) {
|
|
1007
|
+
out += m[0];
|
|
1008
|
+
i += m[0].length;
|
|
1009
|
+
continue;
|
|
1010
|
+
}
|
|
1011
|
+
const cp = s.codePointAt(i);
|
|
1012
|
+
const ch = String.fromCodePoint(cp);
|
|
1013
|
+
out += ch;
|
|
1014
|
+
i += ch.length;
|
|
1015
|
+
vis += 1;
|
|
1016
|
+
}
|
|
1017
|
+
return out;
|
|
1018
|
+
}
|
|
1019
|
+
function padEndVisible(text, cols) {
|
|
1020
|
+
const w = Math.max(0, Math.floor(Number(cols) || 0));
|
|
1021
|
+
const s = String(text ?? "");
|
|
1022
|
+
const vis = visibleWidth(s);
|
|
1023
|
+
if (vis === w) return s;
|
|
1024
|
+
if (vis > w) return sliceVisible(s, w);
|
|
1025
|
+
return s + " ".repeat(w - vis);
|
|
1026
|
+
}
|
|
989
1027
|
function wrapTextLines(text, cols) {
|
|
990
1028
|
const w = Math.max(1, Math.floor(Number(cols) || 1));
|
|
991
1029
|
const out = [];
|
|
@@ -994,20 +1032,23 @@ function wrapTextLines(text, cols) {
|
|
|
994
1032
|
out.push("");
|
|
995
1033
|
continue;
|
|
996
1034
|
}
|
|
1035
|
+
if (visibleWidth(raw) <= w) {
|
|
1036
|
+
out.push(raw);
|
|
1037
|
+
continue;
|
|
1038
|
+
}
|
|
997
1039
|
let rest = raw;
|
|
998
|
-
while (rest
|
|
999
|
-
|
|
1000
|
-
|
|
1040
|
+
while (visibleWidth(rest) > w) {
|
|
1041
|
+
const head = sliceVisible(rest, w);
|
|
1042
|
+
out.push(head);
|
|
1043
|
+
rest = rest.slice(head.length);
|
|
1001
1044
|
}
|
|
1002
1045
|
if (rest.length > 0) out.push(rest);
|
|
1003
1046
|
}
|
|
1004
1047
|
return out;
|
|
1005
1048
|
}
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
return t + " ".repeat(w - t.length);
|
|
1010
|
-
}
|
|
1049
|
+
|
|
1050
|
+
// src/screen/scrollable-text.js
|
|
1051
|
+
var h5 = createElement2;
|
|
1011
1052
|
var SCROLL_KEYS = [
|
|
1012
1053
|
{ key: "upArrow", caption: "scroll", action: "scrollUp", order: 0 },
|
|
1013
1054
|
{ key: "downArrow", caption: "scroll", action: "scrollDown", order: 0 },
|
|
@@ -1080,14 +1121,17 @@ function ScrollableText({
|
|
|
1080
1121
|
}, [ctx, bindKeys, followBottom]);
|
|
1081
1122
|
const status = allLines.length === 0 ? "empty" : `lines ${clamped + 1}-${Math.min(clamped + visible.length, allLines.length)} of ${allLines.length}` + (needsBar ? " \xB7 \u2325\u2191/\u2193 or PgUp/Dn page" : "") + (followBottom && following ? " \xB7 follow" : followBottom ? " \xB7 follow off" : "");
|
|
1082
1123
|
const rowNodes = visible.map((line, i) => {
|
|
1083
|
-
const body = padEndVisible(line, textWidth);
|
|
1084
1124
|
const glyph = bar ? bar[i] ?? BAR_TRACK : showScrollbar ? " " : "";
|
|
1085
1125
|
const isThumb = glyph === BAR_THUMB;
|
|
1086
1126
|
return h5(
|
|
1087
|
-
|
|
1088
|
-
{ key: `L${clamped + i}
|
|
1089
|
-
|
|
1090
|
-
|
|
1127
|
+
Box4,
|
|
1128
|
+
{ key: `L${clamped + i}`, flexDirection: "row", width: contentCols, flexShrink: 0 },
|
|
1129
|
+
h5(
|
|
1130
|
+
Box4,
|
|
1131
|
+
{ width: textWidth, flexShrink: 0 },
|
|
1132
|
+
h5(Text5, { wrap: "truncate" }, padEndVisible(line, textWidth))
|
|
1133
|
+
),
|
|
1134
|
+
showScrollbar ? h5(Box4, { width: 1, flexShrink: 0 }, h5(Text5, { color: isThumb ? "cyan" : "gray" }, glyph)) : null
|
|
1091
1135
|
);
|
|
1092
1136
|
});
|
|
1093
1137
|
if (bar && visible.length < viewportRows) {
|
|
@@ -1095,10 +1139,10 @@ function ScrollableText({
|
|
|
1095
1139
|
const glyph = bar[i] ?? BAR_TRACK;
|
|
1096
1140
|
rowNodes.push(
|
|
1097
1141
|
h5(
|
|
1098
|
-
|
|
1099
|
-
{ key: `pad${i}
|
|
1100
|
-
padEndVisible("", textWidth),
|
|
1101
|
-
h5(Text5, { color: glyph === BAR_THUMB ? "cyan" : "gray" }, glyph)
|
|
1142
|
+
Box4,
|
|
1143
|
+
{ key: `pad${i}`, flexDirection: "row", width: contentCols, flexShrink: 0 },
|
|
1144
|
+
h5(Box4, { width: textWidth, flexShrink: 0 }, h5(Text5, {}, padEndVisible("", textWidth))),
|
|
1145
|
+
h5(Box4, { width: 1, flexShrink: 0 }, h5(Text5, { color: glyph === BAR_THUMB ? "cyan" : "gray" }, glyph))
|
|
1102
1146
|
)
|
|
1103
1147
|
);
|
|
1104
1148
|
}
|
|
@@ -1251,6 +1295,7 @@ export {
|
|
|
1251
1295
|
BAR_TRACK,
|
|
1252
1296
|
Box5 as Box,
|
|
1253
1297
|
Divider,
|
|
1298
|
+
FOOTER_HOTKEY_STYLE,
|
|
1254
1299
|
FooterPresets,
|
|
1255
1300
|
GridCell,
|
|
1256
1301
|
InputField,
|
|
@@ -1276,6 +1321,7 @@ export {
|
|
|
1276
1321
|
buildFooter,
|
|
1277
1322
|
clampScroll,
|
|
1278
1323
|
formatBindingKey,
|
|
1324
|
+
formatFooterHotkey,
|
|
1279
1325
|
createElement3 as h,
|
|
1280
1326
|
isScrolledToBottom,
|
|
1281
1327
|
load,
|
|
@@ -1283,6 +1329,7 @@ export {
|
|
|
1283
1329
|
nextScrollAfterContentChange,
|
|
1284
1330
|
nextScrollAfterUserMove,
|
|
1285
1331
|
organizeFooterMessages,
|
|
1332
|
+
padEndVisible,
|
|
1286
1333
|
scrollbarGlyphs,
|
|
1287
1334
|
showListScreen,
|
|
1288
1335
|
showMenuScreen,
|
|
@@ -1290,6 +1337,8 @@ export {
|
|
|
1290
1337
|
showMultiColumnListWithPreviewScreen,
|
|
1291
1338
|
showScreen,
|
|
1292
1339
|
showWordGridScreen,
|
|
1340
|
+
sliceVisible,
|
|
1341
|
+
stripAnsi,
|
|
1293
1342
|
useCallback,
|
|
1294
1343
|
useEffect3 as useEffect,
|
|
1295
1344
|
useInput2 as useInput,
|
|
@@ -1297,6 +1346,7 @@ export {
|
|
|
1297
1346
|
useMemo2 as useMemo,
|
|
1298
1347
|
useRef3 as useRef,
|
|
1299
1348
|
useState4 as useState,
|
|
1349
|
+
visibleWidth,
|
|
1300
1350
|
wrapTextLines
|
|
1301
1351
|
};
|
|
1302
1352
|
//# sourceMappingURL=screen.js.map
|