@teaui/term 0.1.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/ansi.d.ts +45 -0
- package/.dist/ansi.d.ts.map +1 -0
- package/.dist/ansi.js +254 -0
- package/.dist/ansi.js.map +1 -0
- package/.dist/buffer.d.ts +27 -0
- package/.dist/buffer.d.ts.map +1 -0
- package/.dist/buffer.js +112 -0
- package/.dist/buffer.js.map +1 -0
- package/.dist/colors.d.ts +31 -0
- package/.dist/colors.d.ts.map +1 -0
- package/.dist/colors.js +260 -0
- package/.dist/colors.js.map +1 -0
- package/.dist/cursor.d.ts +20 -0
- package/.dist/cursor.d.ts.map +1 -0
- package/.dist/cursor.js +64 -0
- package/.dist/cursor.js.map +1 -0
- package/.dist/image.d.ts +5 -0
- package/.dist/image.d.ts.map +1 -0
- package/.dist/image.js +49 -0
- package/.dist/image.js.map +1 -0
- package/.dist/index.d.ts +17 -0
- package/.dist/index.d.ts.map +1 -0
- package/.dist/index.js +27 -0
- package/.dist/index.js.map +1 -0
- package/.dist/input.d.ts +11 -0
- package/.dist/input.d.ts.map +1 -0
- package/.dist/input.js +287 -0
- package/.dist/input.js.map +1 -0
- package/.dist/modern.d.ts +14 -0
- package/.dist/modern.d.ts.map +1 -0
- package/.dist/modern.js +83 -0
- package/.dist/modern.js.map +1 -0
- package/.dist/screen.d.ts +17 -0
- package/.dist/screen.d.ts.map +1 -0
- package/.dist/screen.js +82 -0
- package/.dist/screen.js.map +1 -0
- package/.dist/sgr.d.ts +25 -0
- package/.dist/sgr.d.ts.map +1 -0
- package/.dist/sgr.js +160 -0
- package/.dist/sgr.js.map +1 -0
- package/.dist/style.d.ts +25 -0
- package/.dist/style.d.ts.map +1 -0
- package/.dist/style.js +53 -0
- package/.dist/style.js.map +1 -0
- package/.dist/terminal.d.ts +84 -0
- package/.dist/terminal.d.ts.map +1 -0
- package/.dist/terminal.js +325 -0
- package/.dist/terminal.js.map +1 -0
- package/.dist/types.d.ts +80 -0
- package/.dist/types.d.ts.map +1 -0
- package/.dist/types.js +15 -0
- package/.dist/types.js.map +1 -0
- package/.dist/unicode.d.ts +65 -0
- package/.dist/unicode.d.ts.map +1 -0
- package/.dist/unicode.js +574 -0
- package/.dist/unicode.js.map +1 -0
- package/LICENSE +24 -0
- package/package.json +36 -0
package/.dist/sgr.js
ADDED
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Parse blessed-style descriptor strings into ANSI escape codes.
|
|
3
|
+
* Replaces BlessedProgram.prototype.style / _attr.
|
|
4
|
+
*
|
|
5
|
+
* Supports:
|
|
6
|
+
* Attributes: "bold", "dim", "italic", "underline", "strikeout", "blink", "inverse", "invisible"
|
|
7
|
+
* Negated: "!bold", "!dim", etc.
|
|
8
|
+
* Named fg: "red fg", "brightBlue fg", "gray fg", "default fg"
|
|
9
|
+
* Named bg: "red bg", "brightBlue bg", "gray bg", "default bg"
|
|
10
|
+
* Hex fg/bg: "#ff0000 fg", "#ff0000(196) fg", "#aabb00 bg"
|
|
11
|
+
* SGR index: "196 fg", "232 bg"
|
|
12
|
+
* Combined: ["bold", "red fg"] or "bold, red fg"
|
|
13
|
+
* Default: "default"
|
|
14
|
+
*/
|
|
15
|
+
import * as colors from './colors.js';
|
|
16
|
+
const CSI = '\x1b[';
|
|
17
|
+
// Attribute on/off codes
|
|
18
|
+
const attrOn = {
|
|
19
|
+
default: `${CSI}m`,
|
|
20
|
+
bold: `${CSI}1m`,
|
|
21
|
+
dim: `${CSI}2m`,
|
|
22
|
+
italic: `${CSI}3m`,
|
|
23
|
+
underline: `${CSI}4m`,
|
|
24
|
+
ul: `${CSI}4m`,
|
|
25
|
+
underlined: `${CSI}4m`,
|
|
26
|
+
blink: `${CSI}5m`,
|
|
27
|
+
inverse: `${CSI}7m`,
|
|
28
|
+
invisible: `${CSI}8m`,
|
|
29
|
+
strikeout: `${CSI}9m`,
|
|
30
|
+
};
|
|
31
|
+
const attrOff = {
|
|
32
|
+
default: '',
|
|
33
|
+
bold: `${CSI}22m`,
|
|
34
|
+
dim: `${CSI}22m`,
|
|
35
|
+
italic: `${CSI}23m`,
|
|
36
|
+
underline: `${CSI}24m`,
|
|
37
|
+
ul: `${CSI}24m`,
|
|
38
|
+
underlined: `${CSI}24m`,
|
|
39
|
+
blink: `${CSI}25m`,
|
|
40
|
+
inverse: `${CSI}27m`,
|
|
41
|
+
invisible: `${CSI}28m`,
|
|
42
|
+
strikeout: `${CSI}29m`,
|
|
43
|
+
};
|
|
44
|
+
// Named color → SGR code
|
|
45
|
+
const namedFg = {
|
|
46
|
+
black: 30, red: 31, green: 32, yellow: 33,
|
|
47
|
+
blue: 34, magenta: 35, cyan: 36, white: 37,
|
|
48
|
+
brightBlack: 90, grey: 90, gray: 90, brightGrey: 37, brightGray: 37,
|
|
49
|
+
brightRed: 91, brightGreen: 92, brightYellow: 93,
|
|
50
|
+
brightBlue: 94, brightMagenta: 95, brightCyan: 96, brightWhite: 97,
|
|
51
|
+
};
|
|
52
|
+
const namedBg = {
|
|
53
|
+
black: 40, red: 41, green: 42, yellow: 43,
|
|
54
|
+
blue: 44, magenta: 45, cyan: 46, white: 47,
|
|
55
|
+
brightBlack: 100, grey: 100, gray: 100, brightGrey: 47, brightGray: 47,
|
|
56
|
+
brightRed: 101, brightGreen: 102, brightYellow: 103,
|
|
57
|
+
brightBlue: 104, brightMagenta: 105, brightCyan: 106, brightWhite: 107,
|
|
58
|
+
};
|
|
59
|
+
function parseSingle(param, enabled) {
|
|
60
|
+
// Negation prefix
|
|
61
|
+
if (param.startsWith('!')) {
|
|
62
|
+
return parseSingle(param.slice(1), !enabled);
|
|
63
|
+
}
|
|
64
|
+
// Simple attributes
|
|
65
|
+
if (attrOn[param] !== undefined) {
|
|
66
|
+
return enabled ? attrOn[param] : (attrOff[param] ?? '');
|
|
67
|
+
}
|
|
68
|
+
// "default fg bg"
|
|
69
|
+
if (param === 'default fg bg') {
|
|
70
|
+
return enabled ? `${CSI}39;49m` : '';
|
|
71
|
+
}
|
|
72
|
+
// "color fg" or "color bg"
|
|
73
|
+
const fgbgMatch = /^(.+)\s+(fg|bg)$/.exec(param);
|
|
74
|
+
if (fgbgMatch) {
|
|
75
|
+
const [, colorStr, fgbg] = fgbgMatch;
|
|
76
|
+
// "default fg" / "default bg"
|
|
77
|
+
if (colorStr === 'default') {
|
|
78
|
+
if (!enabled)
|
|
79
|
+
return '';
|
|
80
|
+
return fgbg === 'fg' ? `${CSI}39m` : `${CSI}49m`;
|
|
81
|
+
}
|
|
82
|
+
// Named color
|
|
83
|
+
const namedMap = fgbg === 'fg' ? namedFg : namedBg;
|
|
84
|
+
if (namedMap[colorStr] !== undefined) {
|
|
85
|
+
if (!enabled)
|
|
86
|
+
return fgbg === 'fg' ? `${CSI}39m` : `${CSI}49m`;
|
|
87
|
+
return `${CSI}${namedMap[colorStr]}m`;
|
|
88
|
+
}
|
|
89
|
+
// Hex color: "#rrggbb fg" or "#rrggbb(index) fg"
|
|
90
|
+
if (colorStr.startsWith('#')) {
|
|
91
|
+
if (!enabled)
|
|
92
|
+
return fgbg === 'fg' ? `${CSI}39m` : `${CSI}49m`;
|
|
93
|
+
const hex = colorStr.replace(/\(\d+\)$/, '');
|
|
94
|
+
const [r, g, b] = colors.hexToRGB(hex);
|
|
95
|
+
return fgbg === 'fg'
|
|
96
|
+
? `${CSI}38;2;${r};${g};${b}m`
|
|
97
|
+
: `${CSI}48;2;${r};${g};${b}m`;
|
|
98
|
+
}
|
|
99
|
+
// Numeric SGR index: "196 fg"
|
|
100
|
+
const colorNum = parseInt(colorStr, 10);
|
|
101
|
+
if (!isNaN(colorNum)) {
|
|
102
|
+
if (!enabled || colorNum === -1) {
|
|
103
|
+
return fgbg === 'fg' ? `${CSI}39m` : `${CSI}49m`;
|
|
104
|
+
}
|
|
105
|
+
if (colorNum < 8) {
|
|
106
|
+
return `${CSI}${colorNum + (fgbg === 'fg' ? 30 : 40)}m`;
|
|
107
|
+
}
|
|
108
|
+
else if (colorNum < 16) {
|
|
109
|
+
return `${CSI}${colorNum - 8 + (fgbg === 'fg' ? 90 : 100)}m`;
|
|
110
|
+
}
|
|
111
|
+
return fgbg === 'fg'
|
|
112
|
+
? `${CSI}38;5;${colorNum}m`
|
|
113
|
+
: `${CSI}48;5;${colorNum}m`;
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
// Raw numeric codes: "38;5;196"
|
|
117
|
+
if (/^[\d;]*$/.test(param)) {
|
|
118
|
+
return `${CSI}${param}m`;
|
|
119
|
+
}
|
|
120
|
+
return '';
|
|
121
|
+
}
|
|
122
|
+
/**
|
|
123
|
+
* Convert blessed-style descriptor(s) to ANSI escape sequence.
|
|
124
|
+
*
|
|
125
|
+
* @example
|
|
126
|
+
* parseStyleDescriptor('bold') // '\x1b[1m'
|
|
127
|
+
* parseStyleDescriptor('!bold') // '\x1b[22m'
|
|
128
|
+
* parseStyleDescriptor(['bold', 'red fg']) // '\x1b[1;31m'
|
|
129
|
+
* parseStyleDescriptor('bold, red fg') // '\x1b[1;31m'
|
|
130
|
+
*/
|
|
131
|
+
export function parseStyleDescriptor(param) {
|
|
132
|
+
let parts;
|
|
133
|
+
if (Array.isArray(param)) {
|
|
134
|
+
parts = param;
|
|
135
|
+
}
|
|
136
|
+
else {
|
|
137
|
+
parts = param.split(/\s*[,;]\s*/);
|
|
138
|
+
}
|
|
139
|
+
if (parts.length === 0)
|
|
140
|
+
return '';
|
|
141
|
+
if (parts.length === 1) {
|
|
142
|
+
return parseSingle(parts[0], true);
|
|
143
|
+
}
|
|
144
|
+
// Multiple parts: combine into single CSI sequence
|
|
145
|
+
const used = new Set();
|
|
146
|
+
const codes = [];
|
|
147
|
+
for (const part of parts) {
|
|
148
|
+
const code = parseSingle(part, true);
|
|
149
|
+
// Extract the numeric portion between CSI and 'm'
|
|
150
|
+
const inner = code.slice(2, -1);
|
|
151
|
+
if (inner === '' || used.has(inner))
|
|
152
|
+
continue;
|
|
153
|
+
used.add(inner);
|
|
154
|
+
codes.push(inner);
|
|
155
|
+
}
|
|
156
|
+
if (codes.length === 0)
|
|
157
|
+
return '';
|
|
158
|
+
return `${CSI}${codes.join(';')}m`;
|
|
159
|
+
}
|
|
160
|
+
//# sourceMappingURL=sgr.js.map
|
package/.dist/sgr.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sgr.js","sourceRoot":"","sources":["../src/sgr.ts"],"names":[],"mappings":"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"}
|
package/.dist/style.d.ts
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { Color } from './types.js';
|
|
2
|
+
interface StyleEntry {
|
|
3
|
+
open: string;
|
|
4
|
+
close: string;
|
|
5
|
+
}
|
|
6
|
+
export declare class StyleBuilder {
|
|
7
|
+
private readonly entries;
|
|
8
|
+
constructor(entries?: readonly StyleEntry[]);
|
|
9
|
+
private add;
|
|
10
|
+
bold(): StyleBuilder;
|
|
11
|
+
dim(): StyleBuilder;
|
|
12
|
+
italic(): StyleBuilder;
|
|
13
|
+
underline(): StyleBuilder;
|
|
14
|
+
blink(): StyleBuilder;
|
|
15
|
+
inverse(): StyleBuilder;
|
|
16
|
+
hidden(): StyleBuilder;
|
|
17
|
+
strikethrough(): StyleBuilder;
|
|
18
|
+
fg(color: Color): StyleBuilder;
|
|
19
|
+
bg(color: Color): StyleBuilder;
|
|
20
|
+
open(): string;
|
|
21
|
+
close(): string;
|
|
22
|
+
wrap(text: string): string;
|
|
23
|
+
}
|
|
24
|
+
export {};
|
|
25
|
+
//# sourceMappingURL=style.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"style.d.ts","sourceRoot":"","sources":["../src/style.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAiB,MAAM,YAAY,CAAA;AAGtD,UAAU,UAAU;IAClB,IAAI,EAAE,MAAM,CAAA;IACZ,KAAK,EAAE,MAAM,CAAA;CACd;AAED,qBAAa,YAAY;IACvB,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAuB;gBAEnC,OAAO,GAAE,SAAS,UAAU,EAAO;IAI/C,OAAO,CAAC,GAAG;IAIX,IAAI,IAAI,YAAY;IAIpB,GAAG,IAAI,YAAY;IAInB,MAAM,IAAI,YAAY;IAItB,SAAS,IAAI,YAAY;IAIzB,KAAK,IAAI,YAAY;IAIrB,OAAO,IAAI,YAAY;IAIvB,MAAM,IAAI,YAAY;IAItB,aAAa,IAAI,YAAY;IAI7B,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,YAAY;IAI9B,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,YAAY;IAI9B,IAAI,IAAI,MAAM;IAId,KAAK,IAAI,MAAM;IAOf,IAAI,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM;CAG3B"}
|
package/.dist/style.js
ADDED
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { fgColor, fgReset, bgColor, bgReset, textAttr, textAttrOff } from './ansi.js';
|
|
2
|
+
export class StyleBuilder {
|
|
3
|
+
entries;
|
|
4
|
+
constructor(entries = []) {
|
|
5
|
+
this.entries = entries;
|
|
6
|
+
}
|
|
7
|
+
add(open, close) {
|
|
8
|
+
return new StyleBuilder([...this.entries, { open, close }]);
|
|
9
|
+
}
|
|
10
|
+
bold() {
|
|
11
|
+
return this.add(textAttr('bold'), textAttrOff('bold'));
|
|
12
|
+
}
|
|
13
|
+
dim() {
|
|
14
|
+
return this.add(textAttr('dim'), textAttrOff('dim'));
|
|
15
|
+
}
|
|
16
|
+
italic() {
|
|
17
|
+
return this.add(textAttr('italic'), textAttrOff('italic'));
|
|
18
|
+
}
|
|
19
|
+
underline() {
|
|
20
|
+
return this.add(textAttr('underline'), textAttrOff('underline'));
|
|
21
|
+
}
|
|
22
|
+
blink() {
|
|
23
|
+
return this.add(textAttr('blink'), textAttrOff('blink'));
|
|
24
|
+
}
|
|
25
|
+
inverse() {
|
|
26
|
+
return this.add(textAttr('inverse'), textAttrOff('inverse'));
|
|
27
|
+
}
|
|
28
|
+
hidden() {
|
|
29
|
+
return this.add(textAttr('hidden'), textAttrOff('hidden'));
|
|
30
|
+
}
|
|
31
|
+
strikethrough() {
|
|
32
|
+
return this.add(textAttr('strikethrough'), textAttrOff('strikethrough'));
|
|
33
|
+
}
|
|
34
|
+
fg(color) {
|
|
35
|
+
return this.add(fgColor(color), fgReset());
|
|
36
|
+
}
|
|
37
|
+
bg(color) {
|
|
38
|
+
return this.add(bgColor(color), bgReset());
|
|
39
|
+
}
|
|
40
|
+
open() {
|
|
41
|
+
return this.entries.map((e) => e.open).join('');
|
|
42
|
+
}
|
|
43
|
+
close() {
|
|
44
|
+
return [...this.entries]
|
|
45
|
+
.reverse()
|
|
46
|
+
.map((e) => e.close)
|
|
47
|
+
.join('');
|
|
48
|
+
}
|
|
49
|
+
wrap(text) {
|
|
50
|
+
return this.open() + text + this.close();
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
//# sourceMappingURL=style.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"style.js","sourceRoot":"","sources":["../src/style.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,WAAW,CAAA;AAOrF,MAAM,OAAO,YAAY;IACN,OAAO,CAAuB;IAE/C,YAAY,UAAiC,EAAE;QAC7C,IAAI,CAAC,OAAO,GAAG,OAAO,CAAA;IACxB,CAAC;IAEO,GAAG,CAAC,IAAY,EAAE,KAAa;QACrC,OAAO,IAAI,YAAY,CAAC,CAAC,GAAG,IAAI,CAAC,OAAO,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC,CAAA;IAC7D,CAAC;IAED,IAAI;QACF,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC,CAAA;IACxD,CAAC;IAED,GAAG;QACD,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,WAAW,CAAC,KAAK,CAAC,CAAC,CAAA;IACtD,CAAC;IAED,MAAM;QACJ,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,WAAW,CAAC,QAAQ,CAAC,CAAC,CAAA;IAC5D,CAAC;IAED,SAAS;QACP,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,WAAW,CAAC,EAAE,WAAW,CAAC,WAAW,CAAC,CAAC,CAAA;IAClE,CAAC;IAED,KAAK;QACH,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,WAAW,CAAC,OAAO,CAAC,CAAC,CAAA;IAC1D,CAAC;IAED,OAAO;QACL,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,SAAS,CAAC,EAAE,WAAW,CAAC,SAAS,CAAC,CAAC,CAAA;IAC9D,CAAC;IAED,MAAM;QACJ,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,WAAW,CAAC,QAAQ,CAAC,CAAC,CAAA;IAC5D,CAAC;IAED,aAAa;QACX,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,eAAe,CAAC,EAAE,WAAW,CAAC,eAAe,CAAC,CAAC,CAAA;IAC1E,CAAC;IAED,EAAE,CAAC,KAAY;QACb,OAAO,IAAI,CAAC,GAAG,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,OAAO,EAAE,CAAC,CAAA;IAC5C,CAAC;IAED,EAAE,CAAC,KAAY;QACb,OAAO,IAAI,CAAC,GAAG,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,OAAO,EAAE,CAAC,CAAA;IAC5C,CAAC;IAED,IAAI;QACF,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;IACjD,CAAC;IAED,KAAK;QACH,OAAO,CAAC,GAAG,IAAI,CAAC,OAAO,CAAC;aACrB,OAAO,EAAE;aACT,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC;aACnB,IAAI,CAAC,EAAE,CAAC,CAAA;IACb,CAAC;IAED,IAAI,CAAC,IAAY;QACf,OAAO,IAAI,CAAC,IAAI,EAAE,GAAG,IAAI,GAAG,IAAI,CAAC,KAAK,EAAE,CAAA;IAC1C,CAAC;CACF"}
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
import type { Color, ScreenSize, ColorSupport, TerminalOptions, FullscreenOptions, InputEvent, ImageOptions, UnderlineStyle } from './types.js';
|
|
2
|
+
import { StyleBuilder } from './style.js';
|
|
3
|
+
export declare class Terminal {
|
|
4
|
+
private output;
|
|
5
|
+
private input;
|
|
6
|
+
private cursorCtrl;
|
|
7
|
+
private screenCtrl;
|
|
8
|
+
private inputReader;
|
|
9
|
+
private screenBuffer;
|
|
10
|
+
private useBuffer;
|
|
11
|
+
private styleOpen;
|
|
12
|
+
private wasRawMode;
|
|
13
|
+
private resizeCleanup;
|
|
14
|
+
private writeBuffer;
|
|
15
|
+
constructor(options?: TerminalOptions);
|
|
16
|
+
private _write;
|
|
17
|
+
/**
|
|
18
|
+
* Enable write buffering. All writes are collected in memory until
|
|
19
|
+
* `flushWrites()` is called, which emits them as a single `output.write()`.
|
|
20
|
+
*/
|
|
21
|
+
enableWriteBuffer(): this;
|
|
22
|
+
/**
|
|
23
|
+
* Flush buffered writes to the output stream as a single write call.
|
|
24
|
+
* No-op when write buffering is not enabled.
|
|
25
|
+
*/
|
|
26
|
+
flushWrites(): this;
|
|
27
|
+
private addAttr;
|
|
28
|
+
bold(): this;
|
|
29
|
+
dim(): this;
|
|
30
|
+
italic(): this;
|
|
31
|
+
underline(): this;
|
|
32
|
+
strikethrough(): this;
|
|
33
|
+
inverse(): this;
|
|
34
|
+
fg(color: Color): this;
|
|
35
|
+
bg(color: Color): this;
|
|
36
|
+
reset(): this;
|
|
37
|
+
write(text: string): this;
|
|
38
|
+
writeln(text: string): this;
|
|
39
|
+
/** Write directly to the output stream, bypassing the buffer. */
|
|
40
|
+
writeRaw(text: string): this;
|
|
41
|
+
moveTo(x: number, y: number): this;
|
|
42
|
+
moveBy(dx: number, dy: number): this;
|
|
43
|
+
saveCursor(): this;
|
|
44
|
+
restoreCursor(): this;
|
|
45
|
+
showCursor(): this;
|
|
46
|
+
hideCursor(): this;
|
|
47
|
+
get size(): ScreenSize;
|
|
48
|
+
/** Number of columns. Alias for `size.columns`. */
|
|
49
|
+
get cols(): number;
|
|
50
|
+
/** Number of rows. Alias for `size.rows`. */
|
|
51
|
+
get rows(): number;
|
|
52
|
+
get colorSupport(): ColorSupport;
|
|
53
|
+
onResize(cb: (size: ScreenSize) => void): () => void;
|
|
54
|
+
clear(): this;
|
|
55
|
+
/**
|
|
56
|
+
* Flush the screen buffer — diffs against the previous frame and writes
|
|
57
|
+
* only changed cells. Uses synchronized output to prevent tearing.
|
|
58
|
+
* No-op when buffer mode is disabled.
|
|
59
|
+
*/
|
|
60
|
+
flush(): this;
|
|
61
|
+
enterFullscreen(options?: FullscreenOptions): this;
|
|
62
|
+
exitFullscreen(): this;
|
|
63
|
+
onInput(cb: (event: InputEvent) => void): () => void;
|
|
64
|
+
/**
|
|
65
|
+
* Listen for raw data on stdin. Useful for reading proprietary escape
|
|
66
|
+
* sequence responses (e.g. iTerm2 background color query).
|
|
67
|
+
*/
|
|
68
|
+
onRawData(cb: (data: Buffer) => void): () => void;
|
|
69
|
+
/**
|
|
70
|
+
* Listen for raw data once, then remove the listener.
|
|
71
|
+
*/
|
|
72
|
+
onceRawData(cb: (data: Buffer) => void): void;
|
|
73
|
+
link(url: string, text: string): this;
|
|
74
|
+
image(data: Buffer, options?: ImageOptions): this;
|
|
75
|
+
beginSync(): this;
|
|
76
|
+
endSync(): this;
|
|
77
|
+
sync(fn: () => void): this;
|
|
78
|
+
underlineStyle(style: UnderlineStyle): this;
|
|
79
|
+
underlineColor(color: Color): this;
|
|
80
|
+
title(title: string): this;
|
|
81
|
+
notify(title: string, body?: string): this;
|
|
82
|
+
style(): StyleBuilder;
|
|
83
|
+
}
|
|
84
|
+
//# sourceMappingURL=terminal.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"terminal.d.ts","sourceRoot":"","sources":["../src/terminal.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,325 @@
|
|
|
1
|
+
import * as ansi from './ansi.js';
|
|
2
|
+
import { CursorController } from './cursor.js';
|
|
3
|
+
import { ScreenController, detectColorSupport } from './screen.js';
|
|
4
|
+
import { InputReader } from './input.js';
|
|
5
|
+
import { StyleBuilder } from './style.js';
|
|
6
|
+
import { ScreenBuffer } from './buffer.js';
|
|
7
|
+
import { itermImage, kittyImage, detectImageProtocol } from './image.js';
|
|
8
|
+
import * as modern from './modern.js';
|
|
9
|
+
export class Terminal {
|
|
10
|
+
output;
|
|
11
|
+
input;
|
|
12
|
+
cursorCtrl;
|
|
13
|
+
screenCtrl;
|
|
14
|
+
inputReader;
|
|
15
|
+
screenBuffer = null;
|
|
16
|
+
useBuffer;
|
|
17
|
+
styleOpen = [];
|
|
18
|
+
wasRawMode = false;
|
|
19
|
+
resizeCleanup = null;
|
|
20
|
+
writeBuffer = null;
|
|
21
|
+
constructor(options = {}) {
|
|
22
|
+
const stdout = options.stdout ?? process.stdout;
|
|
23
|
+
this.output = stdout;
|
|
24
|
+
this.input = (options.stdin ?? process.stdin);
|
|
25
|
+
this.useBuffer = options.buffer ?? false;
|
|
26
|
+
const write = (s) => {
|
|
27
|
+
this._write(s);
|
|
28
|
+
};
|
|
29
|
+
this.cursorCtrl = new CursorController(write);
|
|
30
|
+
this.screenCtrl = new ScreenController(write);
|
|
31
|
+
this.inputReader = new InputReader();
|
|
32
|
+
if (this.useBuffer) {
|
|
33
|
+
const { columns, rows } = this.size;
|
|
34
|
+
this.screenBuffer = new ScreenBuffer(columns, rows);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
// --- Low-level write (respects write-buffer) ---
|
|
38
|
+
_write(s) {
|
|
39
|
+
if (this.writeBuffer) {
|
|
40
|
+
this.writeBuffer.push(s);
|
|
41
|
+
}
|
|
42
|
+
else {
|
|
43
|
+
this.output.write(s);
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Enable write buffering. All writes are collected in memory until
|
|
48
|
+
* `flushWrites()` is called, which emits them as a single `output.write()`.
|
|
49
|
+
*/
|
|
50
|
+
enableWriteBuffer() {
|
|
51
|
+
if (!this.writeBuffer) {
|
|
52
|
+
this.writeBuffer = [];
|
|
53
|
+
}
|
|
54
|
+
return this;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Flush buffered writes to the output stream as a single write call.
|
|
58
|
+
* No-op when write buffering is not enabled.
|
|
59
|
+
*/
|
|
60
|
+
flushWrites() {
|
|
61
|
+
if (this.writeBuffer && this.writeBuffer.length > 0) {
|
|
62
|
+
this.output.write(this.writeBuffer.join(''));
|
|
63
|
+
this.writeBuffer = [];
|
|
64
|
+
}
|
|
65
|
+
return this;
|
|
66
|
+
}
|
|
67
|
+
// --- Style (mutable state, returns this) ---
|
|
68
|
+
addAttr(attr) {
|
|
69
|
+
this.styleOpen.push(ansi.textAttr(attr));
|
|
70
|
+
return this;
|
|
71
|
+
}
|
|
72
|
+
bold() {
|
|
73
|
+
return this.addAttr('bold');
|
|
74
|
+
}
|
|
75
|
+
dim() {
|
|
76
|
+
return this.addAttr('dim');
|
|
77
|
+
}
|
|
78
|
+
italic() {
|
|
79
|
+
return this.addAttr('italic');
|
|
80
|
+
}
|
|
81
|
+
underline() {
|
|
82
|
+
return this.addAttr('underline');
|
|
83
|
+
}
|
|
84
|
+
strikethrough() {
|
|
85
|
+
return this.addAttr('strikethrough');
|
|
86
|
+
}
|
|
87
|
+
inverse() {
|
|
88
|
+
return this.addAttr('inverse');
|
|
89
|
+
}
|
|
90
|
+
fg(color) {
|
|
91
|
+
this.styleOpen.push(ansi.fgColor(color));
|
|
92
|
+
return this;
|
|
93
|
+
}
|
|
94
|
+
bg(color) {
|
|
95
|
+
this.styleOpen.push(ansi.bgColor(color));
|
|
96
|
+
return this;
|
|
97
|
+
}
|
|
98
|
+
reset() {
|
|
99
|
+
this.styleOpen = [];
|
|
100
|
+
return this;
|
|
101
|
+
}
|
|
102
|
+
// --- Output ---
|
|
103
|
+
write(text) {
|
|
104
|
+
const style = this.styleOpen.join('');
|
|
105
|
+
this.styleOpen = [];
|
|
106
|
+
if (this.screenBuffer) {
|
|
107
|
+
this.screenBuffer.write(text, style);
|
|
108
|
+
}
|
|
109
|
+
else if (style) {
|
|
110
|
+
this._write(style + text + ansi.resetAll());
|
|
111
|
+
}
|
|
112
|
+
else {
|
|
113
|
+
this._write(text);
|
|
114
|
+
}
|
|
115
|
+
return this;
|
|
116
|
+
}
|
|
117
|
+
writeln(text) {
|
|
118
|
+
this.write(text);
|
|
119
|
+
if (this.screenBuffer) {
|
|
120
|
+
this.screenBuffer.write('\n', '');
|
|
121
|
+
}
|
|
122
|
+
else {
|
|
123
|
+
this._write('\n');
|
|
124
|
+
}
|
|
125
|
+
return this;
|
|
126
|
+
}
|
|
127
|
+
/** Write directly to the output stream, bypassing the buffer. */
|
|
128
|
+
writeRaw(text) {
|
|
129
|
+
this.styleOpen = [];
|
|
130
|
+
this.output.write(text);
|
|
131
|
+
return this;
|
|
132
|
+
}
|
|
133
|
+
// --- Cursor delegation ---
|
|
134
|
+
moveTo(x, y) {
|
|
135
|
+
if (this.screenBuffer) {
|
|
136
|
+
this.screenBuffer.moveTo(x, y);
|
|
137
|
+
}
|
|
138
|
+
else {
|
|
139
|
+
this.cursorCtrl.moveTo(x, y);
|
|
140
|
+
}
|
|
141
|
+
return this;
|
|
142
|
+
}
|
|
143
|
+
moveBy(dx, dy) {
|
|
144
|
+
this.cursorCtrl.moveBy(dx, dy);
|
|
145
|
+
return this;
|
|
146
|
+
}
|
|
147
|
+
saveCursor() {
|
|
148
|
+
this.cursorCtrl.save();
|
|
149
|
+
return this;
|
|
150
|
+
}
|
|
151
|
+
restoreCursor() {
|
|
152
|
+
this.cursorCtrl.restore();
|
|
153
|
+
return this;
|
|
154
|
+
}
|
|
155
|
+
showCursor() {
|
|
156
|
+
this.cursorCtrl.show();
|
|
157
|
+
return this;
|
|
158
|
+
}
|
|
159
|
+
hideCursor() {
|
|
160
|
+
this.cursorCtrl.hide();
|
|
161
|
+
return this;
|
|
162
|
+
}
|
|
163
|
+
// --- Screen delegation ---
|
|
164
|
+
get size() {
|
|
165
|
+
return {
|
|
166
|
+
columns: this.output.columns ?? 80,
|
|
167
|
+
rows: this.output.rows ?? 24,
|
|
168
|
+
};
|
|
169
|
+
}
|
|
170
|
+
/** Number of columns. Alias for `size.columns`. */
|
|
171
|
+
get cols() {
|
|
172
|
+
return this.size.columns;
|
|
173
|
+
}
|
|
174
|
+
/** Number of rows. Alias for `size.rows`. */
|
|
175
|
+
get rows() {
|
|
176
|
+
return this.size.rows;
|
|
177
|
+
}
|
|
178
|
+
get colorSupport() {
|
|
179
|
+
return detectColorSupport();
|
|
180
|
+
}
|
|
181
|
+
onResize(cb) {
|
|
182
|
+
const handler = () => cb(this.size);
|
|
183
|
+
process.stdout.on('resize', handler);
|
|
184
|
+
return () => {
|
|
185
|
+
process.stdout.removeListener('resize', handler);
|
|
186
|
+
};
|
|
187
|
+
}
|
|
188
|
+
clear() {
|
|
189
|
+
if (this.screenBuffer) {
|
|
190
|
+
this.screenBuffer.clear();
|
|
191
|
+
}
|
|
192
|
+
else {
|
|
193
|
+
this.screenCtrl.clear();
|
|
194
|
+
}
|
|
195
|
+
return this;
|
|
196
|
+
}
|
|
197
|
+
/**
|
|
198
|
+
* Flush the screen buffer — diffs against the previous frame and writes
|
|
199
|
+
* only changed cells. Uses synchronized output to prevent tearing.
|
|
200
|
+
* No-op when buffer mode is disabled.
|
|
201
|
+
*/
|
|
202
|
+
flush() {
|
|
203
|
+
if (this.screenBuffer) {
|
|
204
|
+
this.screenBuffer.flush((s) => this.output.write(s));
|
|
205
|
+
}
|
|
206
|
+
return this;
|
|
207
|
+
}
|
|
208
|
+
enterFullscreen(options) {
|
|
209
|
+
this.screenCtrl.enterFullscreen(options);
|
|
210
|
+
if (this.input) {
|
|
211
|
+
this.inputReader.attach(this.input);
|
|
212
|
+
// Enable raw mode so we get character-by-character input
|
|
213
|
+
const stream = this.input;
|
|
214
|
+
if (typeof stream.isTTY !== 'undefined' && stream.isTTY) {
|
|
215
|
+
if (typeof stream.setRawMode === 'function') {
|
|
216
|
+
this.wasRawMode = stream.isRaw ?? false;
|
|
217
|
+
stream.setRawMode(true);
|
|
218
|
+
}
|
|
219
|
+
if (typeof stream.resume === 'function') {
|
|
220
|
+
stream.resume();
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
// Resize buffer to match screen and track future resizes
|
|
225
|
+
if (this.screenBuffer) {
|
|
226
|
+
const { columns, rows } = this.size;
|
|
227
|
+
this.screenBuffer.resize(columns, rows);
|
|
228
|
+
this.resizeCleanup = this.onResize(({ columns, rows }) => {
|
|
229
|
+
this.screenBuffer?.resize(columns, rows);
|
|
230
|
+
});
|
|
231
|
+
}
|
|
232
|
+
return this;
|
|
233
|
+
}
|
|
234
|
+
exitFullscreen() {
|
|
235
|
+
this.screenCtrl.exitFullscreen();
|
|
236
|
+
this.inputReader.detach();
|
|
237
|
+
if (this.resizeCleanup) {
|
|
238
|
+
this.resizeCleanup();
|
|
239
|
+
this.resizeCleanup = null;
|
|
240
|
+
}
|
|
241
|
+
// Restore raw mode to previous state
|
|
242
|
+
if (this.input) {
|
|
243
|
+
const stream = this.input;
|
|
244
|
+
if (typeof stream.setRawMode === 'function') {
|
|
245
|
+
stream.setRawMode(this.wasRawMode);
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
return this;
|
|
249
|
+
}
|
|
250
|
+
// --- Input ---
|
|
251
|
+
onInput(cb) {
|
|
252
|
+
return this.inputReader.onInput(cb);
|
|
253
|
+
}
|
|
254
|
+
/**
|
|
255
|
+
* Listen for raw data on stdin. Useful for reading proprietary escape
|
|
256
|
+
* sequence responses (e.g. iTerm2 background color query).
|
|
257
|
+
*/
|
|
258
|
+
onRawData(cb) {
|
|
259
|
+
if (!this.input)
|
|
260
|
+
throw new Error('No input stream');
|
|
261
|
+
const handler = (data) => cb(data);
|
|
262
|
+
this.input.on('data', handler);
|
|
263
|
+
return () => {
|
|
264
|
+
this.input.removeListener('data', handler);
|
|
265
|
+
};
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Listen for raw data once, then remove the listener.
|
|
269
|
+
*/
|
|
270
|
+
onceRawData(cb) {
|
|
271
|
+
if (!this.input)
|
|
272
|
+
throw new Error('No input stream');
|
|
273
|
+
this.input.once('data', cb);
|
|
274
|
+
}
|
|
275
|
+
// --- Modern features ---
|
|
276
|
+
link(url, text) {
|
|
277
|
+
this._write(modern.hyperlink(url, text));
|
|
278
|
+
return this;
|
|
279
|
+
}
|
|
280
|
+
image(data, options) {
|
|
281
|
+
const protocol = detectImageProtocol();
|
|
282
|
+
if (protocol === 'kitty') {
|
|
283
|
+
this._write(kittyImage(data, options));
|
|
284
|
+
}
|
|
285
|
+
else if (protocol === 'iterm') {
|
|
286
|
+
this._write(itermImage(data, options));
|
|
287
|
+
}
|
|
288
|
+
return this;
|
|
289
|
+
}
|
|
290
|
+
beginSync() {
|
|
291
|
+
this._write(modern.syncStart());
|
|
292
|
+
return this;
|
|
293
|
+
}
|
|
294
|
+
endSync() {
|
|
295
|
+
this._write(modern.syncEnd());
|
|
296
|
+
return this;
|
|
297
|
+
}
|
|
298
|
+
sync(fn) {
|
|
299
|
+
this.beginSync();
|
|
300
|
+
fn();
|
|
301
|
+
this.endSync();
|
|
302
|
+
return this;
|
|
303
|
+
}
|
|
304
|
+
underlineStyle(style) {
|
|
305
|
+
this.styleOpen.push(modern.styledUnderline(style));
|
|
306
|
+
return this;
|
|
307
|
+
}
|
|
308
|
+
underlineColor(color) {
|
|
309
|
+
this.styleOpen.push(modern.underlineColor(color));
|
|
310
|
+
return this;
|
|
311
|
+
}
|
|
312
|
+
title(title) {
|
|
313
|
+
this._write(modern.setTitle(title));
|
|
314
|
+
return this;
|
|
315
|
+
}
|
|
316
|
+
notify(title, body) {
|
|
317
|
+
this._write(modern.notification(title, body));
|
|
318
|
+
return this;
|
|
319
|
+
}
|
|
320
|
+
// --- Standalone style builder ---
|
|
321
|
+
style() {
|
|
322
|
+
return new StyleBuilder();
|
|
323
|
+
}
|
|
324
|
+
}
|
|
325
|
+
//# sourceMappingURL=terminal.js.map
|