@fairyhunter13/opentui-core 0.1.102 → 0.1.104
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/3d.js +1 -1
- package/3d.js.map +2 -2
- package/README.md +2 -2
- package/assets/markdown_inline/highlights.scm +25 -12
- package/buffer.d.ts +2 -0
- package/{index-km01g6g8.js → index-8z2zcznw.js} +2647 -1077
- package/index-8z2zcznw.js.map +67 -0
- package/index-rghvzce0.js +411 -0
- package/index-rghvzce0.js.map +10 -0
- package/{index-ryzjamvx.js → index-vvxmgn7j.js} +5249 -6645
- package/index-vvxmgn7j.js.map +42 -0
- package/index.js +11 -5
- package/index.js.map +1 -1
- package/lib/border.d.ts +2 -0
- package/lib/stdin-parser.d.ts +1 -0
- package/package.json +9 -12
- package/parser.worker.js +8 -15
- package/parser.worker.js.map +3 -3
- package/plugins/registry.d.ts +4 -0
- package/renderables/Box.d.ts +9 -0
- package/renderables/EditBufferRenderable.d.ts +76 -1
- package/renderables/LineNumberRenderable.d.ts +4 -0
- package/renderables/Markdown.d.ts +0 -4
- package/renderables/Textarea.d.ts +0 -51
- package/renderables/index.d.ts +1 -0
- package/renderer.d.ts +31 -11
- package/runtime-plugin-support.js +3 -3
- package/runtime-plugin.d.ts +5 -0
- package/runtime-plugin.js +3 -3
- package/testing.js +33 -11
- package/testing.js.map +5 -5
- package/types.d.ts +3 -0
- package/zig.d.ts +1 -1
- package/index-kj3abj37.js +0 -188
- package/index-kj3abj37.js.map +0 -10
- package/index-km01g6g8.js.map +0 -64
- package/index-ryzjamvx.js.map +0 -45
|
@@ -5168,7 +5168,7 @@ function visualizeRenderableTree(renderable, maxDepth = 10) {
|
|
|
5168
5168
|
}
|
|
5169
5169
|
|
|
5170
5170
|
// src/lib/styled-text.ts
|
|
5171
|
-
var BrandedStyledText = Symbol.for("@
|
|
5171
|
+
var BrandedStyledText = Symbol.for("@opentui/core/StyledText");
|
|
5172
5172
|
function isStyledText(obj) {
|
|
5173
5173
|
return obj && obj[BrandedStyledText];
|
|
5174
5174
|
}
|
|
@@ -6666,7 +6666,7 @@ class ASCIIFontSelectionHelper {
|
|
|
6666
6666
|
}
|
|
6667
6667
|
|
|
6668
6668
|
// src/lib/singleton.ts
|
|
6669
|
-
var singletonCacheSymbol = Symbol.for("@
|
|
6669
|
+
var singletonCacheSymbol = Symbol.for("@opentui/core/singleton");
|
|
6670
6670
|
function singleton(key, factory) {
|
|
6671
6671
|
const bag = globalThis[singletonCacheSymbol] ??= {};
|
|
6672
6672
|
if (!(key in bag)) {
|
|
@@ -6843,7 +6843,7 @@ var env = new Proxy({}, {
|
|
|
6843
6843
|
|
|
6844
6844
|
// src/lib/stdin-parser.ts
|
|
6845
6845
|
import { Buffer as Buffer3 } from "buffer";
|
|
6846
|
-
var DEFAULT_TIMEOUT_MS =
|
|
6846
|
+
var DEFAULT_TIMEOUT_MS = 20;
|
|
6847
6847
|
var DEFAULT_MAX_PENDING_BYTES = 64 * 1024;
|
|
6848
6848
|
var INITIAL_PENDING_CAPACITY = 256;
|
|
6849
6849
|
var ESC = 27;
|
|
@@ -7014,6 +7014,28 @@ function parsePositiveDecimalPrefix(sequence, start, endExclusive) {
|
|
|
7014
7014
|
}
|
|
7015
7015
|
return sawDigit ? value : null;
|
|
7016
7016
|
}
|
|
7017
|
+
function parseKittyFirstFieldCodepoint(sequence, start, endExclusive) {
|
|
7018
|
+
if (start >= endExclusive)
|
|
7019
|
+
return null;
|
|
7020
|
+
let firstColon = -1;
|
|
7021
|
+
for (let index = start;index < endExclusive; index += 1) {
|
|
7022
|
+
if (sequence[index] === 58) {
|
|
7023
|
+
firstColon = index;
|
|
7024
|
+
break;
|
|
7025
|
+
}
|
|
7026
|
+
}
|
|
7027
|
+
if (firstColon === -1)
|
|
7028
|
+
return null;
|
|
7029
|
+
const codepoint = parsePositiveDecimalPrefix(sequence, start, firstColon);
|
|
7030
|
+
if (codepoint === null)
|
|
7031
|
+
return null;
|
|
7032
|
+
for (let index = firstColon + 1;index < endExclusive; index += 1) {
|
|
7033
|
+
const byte = sequence[index];
|
|
7034
|
+
if (byte !== 58 && !isAsciiDigit(byte))
|
|
7035
|
+
return null;
|
|
7036
|
+
}
|
|
7037
|
+
return codepoint;
|
|
7038
|
+
}
|
|
7017
7039
|
function canStillBeKittyU(state) {
|
|
7018
7040
|
return state.semicolons >= 1;
|
|
7019
7041
|
}
|
|
@@ -7215,10 +7237,13 @@ class StdinParser {
|
|
|
7215
7237
|
}
|
|
7216
7238
|
flushTimeout(nowMsValue = this.clock.now()) {
|
|
7217
7239
|
this.ensureAlive();
|
|
7218
|
-
if (this.
|
|
7240
|
+
if (this.pendingSinceMs !== null && (nowMsValue < this.pendingSinceMs || nowMsValue - this.pendingSinceMs < this.timeoutMs)) {
|
|
7219
7241
|
return;
|
|
7220
7242
|
}
|
|
7221
|
-
|
|
7243
|
+
this.tryForceFlush();
|
|
7244
|
+
}
|
|
7245
|
+
tryForceFlush() {
|
|
7246
|
+
if (this.paste || this.pendingSinceMs === null || this.pending.length === 0) {
|
|
7222
7247
|
return;
|
|
7223
7248
|
}
|
|
7224
7249
|
this.forceFlush = true;
|
|
@@ -7480,7 +7505,12 @@ class StdinParser {
|
|
|
7480
7505
|
continue;
|
|
7481
7506
|
}
|
|
7482
7507
|
if (byte === 59) {
|
|
7483
|
-
const
|
|
7508
|
+
const firstParamStart = this.unitStart + 2;
|
|
7509
|
+
const firstParamEnd = this.cursor;
|
|
7510
|
+
let firstParamValue = parsePositiveDecimalPrefix(bytes, firstParamStart, firstParamEnd);
|
|
7511
|
+
if (firstParamValue === null && this.protocolContext.kittyKeyboardEnabled) {
|
|
7512
|
+
firstParamValue = parseKittyFirstFieldCodepoint(bytes, firstParamStart, firstParamEnd);
|
|
7513
|
+
}
|
|
7484
7514
|
if (firstParamValue !== null) {
|
|
7485
7515
|
this.cursor += 1;
|
|
7486
7516
|
this.state = {
|
|
@@ -8078,7 +8108,7 @@ class StdinParser {
|
|
|
8078
8108
|
return;
|
|
8079
8109
|
}
|
|
8080
8110
|
try {
|
|
8081
|
-
this.
|
|
8111
|
+
this.tryForceFlush();
|
|
8082
8112
|
this.onTimeoutFlush?.();
|
|
8083
8113
|
} catch (error) {
|
|
8084
8114
|
console.error("stdin parser timeout flush failed", error);
|
|
@@ -8782,13 +8812,6 @@ class TreeSitterClient extends EventEmitter2 {
|
|
|
8782
8812
|
const { logType, data } = event.data;
|
|
8783
8813
|
const message = data.join(" ");
|
|
8784
8814
|
this.emit("worker:log", logType, message);
|
|
8785
|
-
if (logType === "log") {
|
|
8786
|
-
console.log("TSWorker:", ...data);
|
|
8787
|
-
} else if (logType === "error") {
|
|
8788
|
-
console.error("TSWorker:", ...data);
|
|
8789
|
-
} else if (logType === "warn") {
|
|
8790
|
-
console.warn("TSWorker:", ...data);
|
|
8791
|
-
}
|
|
8792
8815
|
return;
|
|
8793
8816
|
}
|
|
8794
8817
|
}
|
|
@@ -9416,7 +9439,7 @@ class DownloadUtils {
|
|
|
9416
9439
|
|
|
9417
9440
|
// src/lib/tree-sitter/assets/update.ts
|
|
9418
9441
|
import { readdir } from "fs/promises";
|
|
9419
|
-
var __dirname = "/
|
|
9442
|
+
var __dirname = "/home/hafiz/git/github.com/fairyhunter13/opencode/vendor/opentui/packages/core/src/lib/tree-sitter/assets";
|
|
9420
9443
|
function getDefaultOptions() {
|
|
9421
9444
|
return {
|
|
9422
9445
|
configPath: path4.resolve(__dirname, "../parsers-config"),
|
|
@@ -10670,7 +10693,7 @@ import { EventEmitter as EventEmitter4 } from "events";
|
|
|
10670
10693
|
|
|
10671
10694
|
// src/buffer.ts
|
|
10672
10695
|
import { toArrayBuffer, ptr } from "bun:ffi";
|
|
10673
|
-
function packDrawOptions(border2, shouldFill, titleAlignment) {
|
|
10696
|
+
function packDrawOptions(border2, shouldFill, titleAlignment, bottomTitleAlignment) {
|
|
10674
10697
|
let packed = 0;
|
|
10675
10698
|
if (border2 === true) {
|
|
10676
10699
|
packed |= 15;
|
|
@@ -10693,7 +10716,9 @@ function packDrawOptions(border2, shouldFill, titleAlignment) {
|
|
|
10693
10716
|
right: 2
|
|
10694
10717
|
};
|
|
10695
10718
|
const alignment = alignmentMap[titleAlignment];
|
|
10719
|
+
const bottomAlignment = alignmentMap[bottomTitleAlignment];
|
|
10696
10720
|
packed |= alignment << 5;
|
|
10721
|
+
packed |= bottomAlignment << 7;
|
|
10697
10722
|
return packed;
|
|
10698
10723
|
}
|
|
10699
10724
|
|
|
@@ -10925,8 +10950,8 @@ class OptimizedBuffer {
|
|
|
10925
10950
|
this.guard();
|
|
10926
10951
|
const style = parseBorderStyle(options.borderStyle, "single");
|
|
10927
10952
|
const borderChars = options.customBorderChars ?? BorderCharArrays[style];
|
|
10928
|
-
const packedOptions = packDrawOptions(options.border, options.shouldFill ?? false, options.titleAlignment || "left");
|
|
10929
|
-
this.lib.bufferDrawBox(this.bufferPtr, options.x, options.y, options.width, options.height, borderChars, packedOptions, options.borderColor, options.backgroundColor, options.title ?? null);
|
|
10953
|
+
const packedOptions = packDrawOptions(options.border, options.shouldFill ?? false, options.titleAlignment || "left", options.bottomTitleAlignment || "left");
|
|
10954
|
+
this.lib.bufferDrawBox(this.bufferPtr, options.x, options.y, options.width, options.height, borderChars, packedOptions, options.borderColor, options.backgroundColor, options.title ?? null, options.bottomTitle ?? null);
|
|
10930
10955
|
}
|
|
10931
10956
|
pushScissorRect(x, y, width, height) {
|
|
10932
10957
|
this.guard();
|
|
@@ -11768,7 +11793,7 @@ var ReserveInfoStruct = defineStruct([
|
|
|
11768
11793
|
});
|
|
11769
11794
|
|
|
11770
11795
|
// src/zig.ts
|
|
11771
|
-
var module = await import(`@
|
|
11796
|
+
var module = await import(`@opentui/core-${process.platform}-${process.arch}/index.ts`);
|
|
11772
11797
|
var targetLibPath = module.default;
|
|
11773
11798
|
if (isBunfsPath(targetLibPath)) {
|
|
11774
11799
|
targetLibPath = targetLibPath.replace("../", "");
|
|
@@ -12054,7 +12079,7 @@ function getOpenTUILib(libPath) {
|
|
|
12054
12079
|
returns: "void"
|
|
12055
12080
|
},
|
|
12056
12081
|
bufferDrawBox: {
|
|
12057
|
-
args: ["ptr", "i32", "i32", "u32", "u32", "ptr", "u32", "ptr", "ptr", "ptr", "u32"],
|
|
12082
|
+
args: ["ptr", "i32", "i32", "u32", "u32", "ptr", "u32", "ptr", "ptr", "ptr", "u32", "ptr", "u32"],
|
|
12058
12083
|
returns: "void"
|
|
12059
12084
|
},
|
|
12060
12085
|
bufferPushScissorRect: {
|
|
@@ -13222,11 +13247,14 @@ class FFIRenderLib {
|
|
|
13222
13247
|
});
|
|
13223
13248
|
this.opentui.symbols.bufferDrawGrid(buffer, borderChars, borderFg.buffer, borderBg.buffer, columnOffsets, columnCount, rowOffsets, rowCount, ptr4(optionsBuffer));
|
|
13224
13249
|
}
|
|
13225
|
-
bufferDrawBox(buffer, x, y, width, height, borderChars, packedOptions, borderColor, backgroundColor, title) {
|
|
13250
|
+
bufferDrawBox(buffer, x, y, width, height, borderChars, packedOptions, borderColor, backgroundColor, title, bottomTitle) {
|
|
13226
13251
|
const titleBytes = title ? this.encoder.encode(title) : null;
|
|
13227
13252
|
const titleLen = title ? titleBytes.length : 0;
|
|
13228
13253
|
const titlePtr = title ? titleBytes : null;
|
|
13229
|
-
|
|
13254
|
+
const bottomTitleBytes = bottomTitle ? this.encoder.encode(bottomTitle) : null;
|
|
13255
|
+
const bottomTitleLen = bottomTitle ? bottomTitleBytes.length : 0;
|
|
13256
|
+
const bottomTitlePtr = bottomTitle ? bottomTitleBytes : null;
|
|
13257
|
+
this.opentui.symbols.bufferDrawBox(buffer, x, y, width, height, borderChars, packedOptions, borderColor.buffer, backgroundColor.buffer, titlePtr, titleLen, bottomTitlePtr, bottomTitleLen);
|
|
13230
13258
|
}
|
|
13231
13259
|
bufferResize(buffer, width, height) {
|
|
13232
13260
|
this.opentui.symbols.bufferResize(buffer, width, height);
|
|
@@ -14544,7 +14572,7 @@ function isSizeType(value) {
|
|
|
14544
14572
|
}
|
|
14545
14573
|
|
|
14546
14574
|
// src/Renderable.ts
|
|
14547
|
-
var BrandedRenderable = Symbol.for("@
|
|
14575
|
+
var BrandedRenderable = Symbol.for("@opentui/core/Renderable");
|
|
14548
14576
|
var LayoutEvents;
|
|
14549
14577
|
((LayoutEvents2) => {
|
|
14550
14578
|
LayoutEvents2["LAYOUT_CHANGED"] = "layout-changed";
|
|
@@ -14900,29 +14928,31 @@ class Renderable extends BaseRenderable {
|
|
|
14900
14928
|
return this._widthValue;
|
|
14901
14929
|
}
|
|
14902
14930
|
set width(value) {
|
|
14903
|
-
if (isDimensionType(value)) {
|
|
14904
|
-
|
|
14905
|
-
this.yogaNode.setWidth(value);
|
|
14906
|
-
if (typeof value === "number" && this._flexShrink === 1) {
|
|
14907
|
-
this._flexShrink = 0;
|
|
14908
|
-
this.yogaNode.setFlexShrink(0);
|
|
14909
|
-
}
|
|
14910
|
-
this.requestRender();
|
|
14931
|
+
if (!isDimensionType(value) || this._width === value) {
|
|
14932
|
+
return;
|
|
14911
14933
|
}
|
|
14934
|
+
this._width = value;
|
|
14935
|
+
this.yogaNode.setWidth(value);
|
|
14936
|
+
if (typeof value === "number" && this._flexShrink === 1) {
|
|
14937
|
+
this._flexShrink = 0;
|
|
14938
|
+
this.yogaNode.setFlexShrink(0);
|
|
14939
|
+
}
|
|
14940
|
+
this.requestRender();
|
|
14912
14941
|
}
|
|
14913
14942
|
get height() {
|
|
14914
14943
|
return this._heightValue;
|
|
14915
14944
|
}
|
|
14916
14945
|
set height(value) {
|
|
14917
|
-
if (isDimensionType(value)) {
|
|
14918
|
-
|
|
14919
|
-
|
|
14920
|
-
|
|
14921
|
-
|
|
14922
|
-
|
|
14923
|
-
|
|
14924
|
-
this.
|
|
14946
|
+
if (!isDimensionType(value) || this._height === value) {
|
|
14947
|
+
return;
|
|
14948
|
+
}
|
|
14949
|
+
this._height = value;
|
|
14950
|
+
this.yogaNode.setHeight(value);
|
|
14951
|
+
if (typeof value === "number" && this._flexShrink === 1) {
|
|
14952
|
+
this._flexShrink = 0;
|
|
14953
|
+
this.yogaNode.setFlexShrink(0);
|
|
14925
14954
|
}
|
|
14955
|
+
this.requestRender();
|
|
14926
14956
|
}
|
|
14927
14957
|
get zIndex() {
|
|
14928
14958
|
return this._zIndex;
|
|
@@ -15778,7 +15808,7 @@ class RootRenderable extends Renderable {
|
|
|
15778
15808
|
|
|
15779
15809
|
// src/renderables/composition/vnode.ts
|
|
15780
15810
|
import util from "util";
|
|
15781
|
-
var BrandedVNode = Symbol.for("@
|
|
15811
|
+
var BrandedVNode = Symbol.for("@opentui/core/VNode");
|
|
15782
15812
|
function isRenderableConstructor(value) {
|
|
15783
15813
|
return typeof value === "function" && value.prototype && Renderable.prototype.isPrototypeOf(value.prototype);
|
|
15784
15814
|
}
|
|
@@ -15942,1084 +15972,2506 @@ function delegate(mapping, vnode) {
|
|
|
15942
15972
|
return vnode;
|
|
15943
15973
|
}
|
|
15944
15974
|
|
|
15945
|
-
// src/
|
|
15946
|
-
import { EventEmitter as EventEmitter7 } from "events";
|
|
15947
|
-
import { Console } from "console";
|
|
15948
|
-
import fs from "fs";
|
|
15949
|
-
import path5 from "path";
|
|
15950
|
-
import util2 from "util";
|
|
15951
|
-
|
|
15952
|
-
// src/lib/output.capture.ts
|
|
15953
|
-
import { Writable } from "stream";
|
|
15975
|
+
// src/edit-buffer.ts
|
|
15954
15976
|
import { EventEmitter as EventEmitter6 } from "events";
|
|
15955
15977
|
|
|
15956
|
-
class
|
|
15957
|
-
|
|
15958
|
-
|
|
15978
|
+
class EditBuffer extends EventEmitter6 {
|
|
15979
|
+
static registry = new Map;
|
|
15980
|
+
static nativeEventsSubscribed = false;
|
|
15981
|
+
lib;
|
|
15982
|
+
bufferPtr;
|
|
15983
|
+
textBufferPtr;
|
|
15984
|
+
id;
|
|
15985
|
+
_destroyed = false;
|
|
15986
|
+
_textBytes = [];
|
|
15987
|
+
_singleTextBytes = null;
|
|
15988
|
+
_singleTextMemId = null;
|
|
15989
|
+
_syntaxStyle;
|
|
15990
|
+
constructor(lib, ptr5) {
|
|
15959
15991
|
super();
|
|
15992
|
+
this.lib = lib;
|
|
15993
|
+
this.bufferPtr = ptr5;
|
|
15994
|
+
this.textBufferPtr = lib.editBufferGetTextBuffer(ptr5);
|
|
15995
|
+
this.id = lib.editBufferGetId(ptr5);
|
|
15996
|
+
EditBuffer.registry.set(this.id, this);
|
|
15997
|
+
EditBuffer.subscribeToNativeEvents(lib);
|
|
15960
15998
|
}
|
|
15961
|
-
|
|
15962
|
-
|
|
15999
|
+
static create(widthMethod) {
|
|
16000
|
+
const lib = resolveRenderLib();
|
|
16001
|
+
const ptr5 = lib.createEditBuffer(widthMethod);
|
|
16002
|
+
return new EditBuffer(lib, ptr5);
|
|
15963
16003
|
}
|
|
15964
|
-
|
|
15965
|
-
|
|
15966
|
-
|
|
16004
|
+
static subscribeToNativeEvents(lib) {
|
|
16005
|
+
if (EditBuffer.nativeEventsSubscribed)
|
|
16006
|
+
return;
|
|
16007
|
+
EditBuffer.nativeEventsSubscribed = true;
|
|
16008
|
+
lib.onAnyNativeEvent((name, data) => {
|
|
16009
|
+
const buffer = new Uint16Array(data);
|
|
16010
|
+
if (name.startsWith("eb_") && buffer.length >= 1) {
|
|
16011
|
+
const id = buffer[0];
|
|
16012
|
+
const instance = EditBuffer.registry.get(id);
|
|
16013
|
+
if (instance) {
|
|
16014
|
+
const eventName = name.slice(3);
|
|
16015
|
+
const eventData = data.slice(2);
|
|
16016
|
+
instance.emit(eventName, eventData);
|
|
16017
|
+
}
|
|
16018
|
+
}
|
|
16019
|
+
});
|
|
15967
16020
|
}
|
|
15968
|
-
|
|
15969
|
-
|
|
15970
|
-
|
|
15971
|
-
return output;
|
|
16021
|
+
guard() {
|
|
16022
|
+
if (this._destroyed)
|
|
16023
|
+
throw new Error("EditBuffer is destroyed");
|
|
15972
16024
|
}
|
|
15973
|
-
|
|
15974
|
-
this.
|
|
16025
|
+
get ptr() {
|
|
16026
|
+
this.guard();
|
|
16027
|
+
return this.bufferPtr;
|
|
15975
16028
|
}
|
|
15976
|
-
|
|
15977
|
-
|
|
15978
|
-
|
|
15979
|
-
|
|
15980
|
-
|
|
15981
|
-
|
|
15982
|
-
|
|
15983
|
-
|
|
15984
|
-
|
|
15985
|
-
|
|
15986
|
-
this.stream = stream;
|
|
15987
|
-
this.capture = capture;
|
|
16029
|
+
setText(text) {
|
|
16030
|
+
this.guard();
|
|
16031
|
+
const textBytes = this.lib.encoder.encode(text);
|
|
16032
|
+
if (this._singleTextMemId !== null) {
|
|
16033
|
+
this.lib.textBufferReplaceMemBuffer(this.textBufferPtr, this._singleTextMemId, textBytes, false);
|
|
16034
|
+
} else {
|
|
16035
|
+
this._singleTextMemId = this.lib.textBufferRegisterMemBuffer(this.textBufferPtr, textBytes, false);
|
|
16036
|
+
}
|
|
16037
|
+
this._singleTextBytes = textBytes;
|
|
16038
|
+
this.lib.editBufferSetTextFromMem(this.bufferPtr, this._singleTextMemId);
|
|
15988
16039
|
}
|
|
15989
|
-
|
|
15990
|
-
|
|
15991
|
-
this.
|
|
15992
|
-
|
|
16040
|
+
setTextOwned(text) {
|
|
16041
|
+
this.guard();
|
|
16042
|
+
const textBytes = this.lib.encoder.encode(text);
|
|
16043
|
+
this.lib.editBufferSetText(this.bufferPtr, textBytes);
|
|
15993
16044
|
}
|
|
15994
|
-
|
|
15995
|
-
|
|
16045
|
+
replaceText(text) {
|
|
16046
|
+
this.guard();
|
|
16047
|
+
const textBytes = this.lib.encoder.encode(text);
|
|
16048
|
+
this._textBytes.push(textBytes);
|
|
16049
|
+
const memId = this.lib.textBufferRegisterMemBuffer(this.textBufferPtr, textBytes, false);
|
|
16050
|
+
this.lib.editBufferReplaceTextFromMem(this.bufferPtr, memId);
|
|
15996
16051
|
}
|
|
15997
|
-
|
|
15998
|
-
|
|
15999
|
-
|
|
16000
|
-
|
|
16001
|
-
enter: "return",
|
|
16002
|
-
esc: "escape"
|
|
16003
|
-
};
|
|
16004
|
-
function mergeKeyAliases(defaults, custom) {
|
|
16005
|
-
return { ...defaults, ...custom };
|
|
16006
|
-
}
|
|
16007
|
-
function mergeKeyBindings(defaults, custom) {
|
|
16008
|
-
const map = new Map;
|
|
16009
|
-
for (const binding of defaults) {
|
|
16010
|
-
const key = getKeyBindingKey(binding);
|
|
16011
|
-
map.set(key, binding);
|
|
16052
|
+
replaceTextOwned(text) {
|
|
16053
|
+
this.guard();
|
|
16054
|
+
const textBytes = this.lib.encoder.encode(text);
|
|
16055
|
+
this.lib.editBufferReplaceText(this.bufferPtr, textBytes);
|
|
16012
16056
|
}
|
|
16013
|
-
|
|
16014
|
-
|
|
16015
|
-
|
|
16057
|
+
getLineCount() {
|
|
16058
|
+
this.guard();
|
|
16059
|
+
return this.lib.textBufferGetLineCount(this.textBufferPtr);
|
|
16016
16060
|
}
|
|
16017
|
-
|
|
16018
|
-
|
|
16019
|
-
|
|
16020
|
-
|
|
16021
|
-
|
|
16022
|
-
|
|
16023
|
-
|
|
16024
|
-
const aliases = aliasMap || {};
|
|
16025
|
-
for (const binding of bindings) {
|
|
16026
|
-
const key = getKeyBindingKey(binding);
|
|
16027
|
-
map.set(key, binding.action);
|
|
16061
|
+
getText() {
|
|
16062
|
+
this.guard();
|
|
16063
|
+
const maxSize = 1024 * 1024;
|
|
16064
|
+
const textBytes = this.lib.editBufferGetText(this.bufferPtr, maxSize);
|
|
16065
|
+
if (!textBytes)
|
|
16066
|
+
return "";
|
|
16067
|
+
return this.lib.decoder.decode(textBytes);
|
|
16028
16068
|
}
|
|
16029
|
-
|
|
16030
|
-
|
|
16031
|
-
|
|
16032
|
-
const aliasedKey = getKeyBindingKey({ ...binding, name: normalizedName });
|
|
16033
|
-
map.set(aliasedKey, binding.action);
|
|
16034
|
-
}
|
|
16069
|
+
insertChar(char) {
|
|
16070
|
+
this.guard();
|
|
16071
|
+
this.lib.editBufferInsertChar(this.bufferPtr, char);
|
|
16035
16072
|
}
|
|
16036
|
-
|
|
16037
|
-
|
|
16038
|
-
|
|
16039
|
-
const parts = [];
|
|
16040
|
-
if (binding.ctrl)
|
|
16041
|
-
parts.push("ctrl");
|
|
16042
|
-
if (binding.shift)
|
|
16043
|
-
parts.push("shift");
|
|
16044
|
-
if (binding.meta)
|
|
16045
|
-
parts.push("meta");
|
|
16046
|
-
if (binding.super)
|
|
16047
|
-
parts.push("super");
|
|
16048
|
-
parts.push(binding.name);
|
|
16049
|
-
return parts.join("+");
|
|
16050
|
-
}
|
|
16051
|
-
|
|
16052
|
-
// src/console.ts
|
|
16053
|
-
function getCallerInfo() {
|
|
16054
|
-
const err = new Error;
|
|
16055
|
-
const stackLines = err.stack?.split(`
|
|
16056
|
-
`).slice(5) || [];
|
|
16057
|
-
if (!stackLines.length)
|
|
16058
|
-
return null;
|
|
16059
|
-
const callerLine = stackLines[0].trim();
|
|
16060
|
-
const regex = /at\s+(?:([\w$.<>]+)\s+\()?((?:\/|[A-Za-z]:\\)[^:]+):(\d+):(\d+)\)?/;
|
|
16061
|
-
const match = callerLine.match(regex);
|
|
16062
|
-
if (!match)
|
|
16063
|
-
return null;
|
|
16064
|
-
const functionName = match[1] || "<anonymous>";
|
|
16065
|
-
const fullPath = match[2];
|
|
16066
|
-
const fileName = fullPath.split(/[\\/]/).pop() || "<unknown>";
|
|
16067
|
-
const lineNumber = parseInt(match[3], 10) || 0;
|
|
16068
|
-
const columnNumber = parseInt(match[4], 10) || 0;
|
|
16069
|
-
return { functionName, fullPath, fileName, lineNumber, columnNumber };
|
|
16070
|
-
}
|
|
16071
|
-
var capture = singleton("ConsoleCapture", () => new Capture);
|
|
16072
|
-
registerEnvVar({
|
|
16073
|
-
name: "OTUI_USE_CONSOLE",
|
|
16074
|
-
description: "Whether to use the console. Will not capture console output if set to false.",
|
|
16075
|
-
type: "boolean",
|
|
16076
|
-
default: true
|
|
16077
|
-
});
|
|
16078
|
-
registerEnvVar({
|
|
16079
|
-
name: "SHOW_CONSOLE",
|
|
16080
|
-
description: "Show the console at startup if set to true.",
|
|
16081
|
-
type: "boolean",
|
|
16082
|
-
default: false
|
|
16083
|
-
});
|
|
16084
|
-
|
|
16085
|
-
class TerminalConsoleCache extends EventEmitter7 {
|
|
16086
|
-
_cachedLogs = [];
|
|
16087
|
-
MAX_CACHE_SIZE = 1000;
|
|
16088
|
-
_collectCallerInfo = false;
|
|
16089
|
-
_cachingEnabled = true;
|
|
16090
|
-
_originalConsole = null;
|
|
16091
|
-
get cachedLogs() {
|
|
16092
|
-
return this._cachedLogs;
|
|
16073
|
+
insertText(text) {
|
|
16074
|
+
this.guard();
|
|
16075
|
+
this.lib.editBufferInsertText(this.bufferPtr, text);
|
|
16093
16076
|
}
|
|
16094
|
-
|
|
16095
|
-
|
|
16077
|
+
deleteChar() {
|
|
16078
|
+
this.guard();
|
|
16079
|
+
this.lib.editBufferDeleteChar(this.bufferPtr);
|
|
16096
16080
|
}
|
|
16097
|
-
|
|
16098
|
-
|
|
16099
|
-
|
|
16100
|
-
}
|
|
16101
|
-
this.setupConsoleCapture();
|
|
16102
|
-
this.overrideConsoleMethods();
|
|
16081
|
+
deleteCharBackward() {
|
|
16082
|
+
this.guard();
|
|
16083
|
+
this.lib.editBufferDeleteCharBackward(this.bufferPtr);
|
|
16103
16084
|
}
|
|
16104
|
-
|
|
16105
|
-
|
|
16106
|
-
|
|
16107
|
-
const mockStdout = new CapturedWritableStream("stdout", capture);
|
|
16108
|
-
const mockStderr = new CapturedWritableStream("stderr", capture);
|
|
16109
|
-
global.console = new Console({
|
|
16110
|
-
stdout: mockStdout,
|
|
16111
|
-
stderr: mockStderr,
|
|
16112
|
-
colorMode: true,
|
|
16113
|
-
inspectOptions: {
|
|
16114
|
-
compact: false,
|
|
16115
|
-
breakLength: 80,
|
|
16116
|
-
depth: 2
|
|
16117
|
-
}
|
|
16118
|
-
});
|
|
16085
|
+
deleteRange(startLine, startCol, endLine, endCol) {
|
|
16086
|
+
this.guard();
|
|
16087
|
+
this.lib.editBufferDeleteRange(this.bufferPtr, startLine, startCol, endLine, endCol);
|
|
16119
16088
|
}
|
|
16120
|
-
|
|
16121
|
-
|
|
16122
|
-
|
|
16123
|
-
};
|
|
16124
|
-
console.info = (...args) => {
|
|
16125
|
-
this.appendToConsole("INFO" /* INFO */, ...args);
|
|
16126
|
-
};
|
|
16127
|
-
console.warn = (...args) => {
|
|
16128
|
-
this.appendToConsole("WARN" /* WARN */, ...args);
|
|
16129
|
-
};
|
|
16130
|
-
console.error = (...args) => {
|
|
16131
|
-
this.appendToConsole("ERROR" /* ERROR */, ...args);
|
|
16132
|
-
};
|
|
16133
|
-
console.debug = (...args) => {
|
|
16134
|
-
this.appendToConsole("DEBUG" /* DEBUG */, ...args);
|
|
16135
|
-
};
|
|
16089
|
+
newLine() {
|
|
16090
|
+
this.guard();
|
|
16091
|
+
this.lib.editBufferNewLine(this.bufferPtr);
|
|
16136
16092
|
}
|
|
16137
|
-
|
|
16138
|
-
this.
|
|
16093
|
+
deleteLine() {
|
|
16094
|
+
this.guard();
|
|
16095
|
+
this.lib.editBufferDeleteLine(this.bufferPtr);
|
|
16139
16096
|
}
|
|
16140
|
-
|
|
16141
|
-
this.
|
|
16097
|
+
moveCursorLeft() {
|
|
16098
|
+
this.guard();
|
|
16099
|
+
this.lib.editBufferMoveCursorLeft(this.bufferPtr);
|
|
16142
16100
|
}
|
|
16143
|
-
|
|
16144
|
-
this.
|
|
16101
|
+
moveCursorRight() {
|
|
16102
|
+
this.guard();
|
|
16103
|
+
this.lib.editBufferMoveCursorRight(this.bufferPtr);
|
|
16145
16104
|
}
|
|
16146
|
-
|
|
16147
|
-
this.
|
|
16105
|
+
moveCursorUp() {
|
|
16106
|
+
this.guard();
|
|
16107
|
+
this.lib.editBufferMoveCursorUp(this.bufferPtr);
|
|
16148
16108
|
}
|
|
16149
|
-
|
|
16150
|
-
|
|
16151
|
-
|
|
16152
|
-
}
|
|
16153
|
-
this.setupConsoleCapture();
|
|
16109
|
+
moveCursorDown() {
|
|
16110
|
+
this.guard();
|
|
16111
|
+
this.lib.editBufferMoveCursorDown(this.bufferPtr);
|
|
16154
16112
|
}
|
|
16155
|
-
|
|
16156
|
-
|
|
16113
|
+
gotoLine(line) {
|
|
16114
|
+
this.guard();
|
|
16115
|
+
this.lib.editBufferGotoLine(this.bufferPtr, line);
|
|
16116
|
+
}
|
|
16117
|
+
setCursor(line, col) {
|
|
16118
|
+
this.guard();
|
|
16119
|
+
this.lib.editBufferSetCursor(this.bufferPtr, line, col);
|
|
16120
|
+
}
|
|
16121
|
+
setCursorToLineCol(line, col) {
|
|
16122
|
+
this.guard();
|
|
16123
|
+
this.lib.editBufferSetCursorToLineCol(this.bufferPtr, line, col);
|
|
16124
|
+
}
|
|
16125
|
+
setCursorByOffset(offset) {
|
|
16126
|
+
this.guard();
|
|
16127
|
+
this.lib.editBufferSetCursorByOffset(this.bufferPtr, offset);
|
|
16128
|
+
}
|
|
16129
|
+
getCursorPosition() {
|
|
16130
|
+
this.guard();
|
|
16131
|
+
return this.lib.editBufferGetCursorPosition(this.bufferPtr);
|
|
16132
|
+
}
|
|
16133
|
+
getNextWordBoundary() {
|
|
16134
|
+
this.guard();
|
|
16135
|
+
const boundary = this.lib.editBufferGetNextWordBoundary(this.bufferPtr);
|
|
16136
|
+
return {
|
|
16137
|
+
row: boundary.row,
|
|
16138
|
+
col: boundary.col,
|
|
16139
|
+
offset: boundary.offset
|
|
16140
|
+
};
|
|
16141
|
+
}
|
|
16142
|
+
getPrevWordBoundary() {
|
|
16143
|
+
this.guard();
|
|
16144
|
+
const boundary = this.lib.editBufferGetPrevWordBoundary(this.bufferPtr);
|
|
16145
|
+
return {
|
|
16146
|
+
row: boundary.row,
|
|
16147
|
+
col: boundary.col,
|
|
16148
|
+
offset: boundary.offset
|
|
16149
|
+
};
|
|
16150
|
+
}
|
|
16151
|
+
getEOL() {
|
|
16152
|
+
this.guard();
|
|
16153
|
+
const boundary = this.lib.editBufferGetEOL(this.bufferPtr);
|
|
16154
|
+
return {
|
|
16155
|
+
row: boundary.row,
|
|
16156
|
+
col: boundary.col,
|
|
16157
|
+
offset: boundary.offset
|
|
16158
|
+
};
|
|
16159
|
+
}
|
|
16160
|
+
offsetToPosition(offset) {
|
|
16161
|
+
this.guard();
|
|
16162
|
+
const result = this.lib.editBufferOffsetToPosition(this.bufferPtr, offset);
|
|
16163
|
+
if (!result)
|
|
16164
|
+
return null;
|
|
16165
|
+
return { row: result.row, col: result.col };
|
|
16166
|
+
}
|
|
16167
|
+
positionToOffset(row, col) {
|
|
16168
|
+
this.guard();
|
|
16169
|
+
return this.lib.editBufferPositionToOffset(this.bufferPtr, row, col);
|
|
16170
|
+
}
|
|
16171
|
+
getLineStartOffset(row) {
|
|
16172
|
+
this.guard();
|
|
16173
|
+
return this.lib.editBufferGetLineStartOffset(this.bufferPtr, row);
|
|
16174
|
+
}
|
|
16175
|
+
getTextRange(startOffset, endOffset) {
|
|
16176
|
+
this.guard();
|
|
16177
|
+
if (startOffset >= endOffset)
|
|
16178
|
+
return "";
|
|
16179
|
+
const maxSize = 1024 * 1024;
|
|
16180
|
+
const textBytes = this.lib.editBufferGetTextRange(this.bufferPtr, startOffset, endOffset, maxSize);
|
|
16181
|
+
if (!textBytes)
|
|
16182
|
+
return "";
|
|
16183
|
+
return this.lib.decoder.decode(textBytes);
|
|
16184
|
+
}
|
|
16185
|
+
getTextRangeByCoords(startRow, startCol, endRow, endCol) {
|
|
16186
|
+
this.guard();
|
|
16187
|
+
const maxSize = 1024 * 1024;
|
|
16188
|
+
const textBytes = this.lib.editBufferGetTextRangeByCoords(this.bufferPtr, startRow, startCol, endRow, endCol, maxSize);
|
|
16189
|
+
if (!textBytes)
|
|
16190
|
+
return "";
|
|
16191
|
+
return this.lib.decoder.decode(textBytes);
|
|
16192
|
+
}
|
|
16193
|
+
debugLogRope() {
|
|
16194
|
+
this.guard();
|
|
16195
|
+
this.lib.editBufferDebugLogRope(this.bufferPtr);
|
|
16196
|
+
}
|
|
16197
|
+
undo() {
|
|
16198
|
+
this.guard();
|
|
16199
|
+
const maxSize = 256;
|
|
16200
|
+
const metaBytes = this.lib.editBufferUndo(this.bufferPtr, maxSize);
|
|
16201
|
+
if (!metaBytes)
|
|
16202
|
+
return null;
|
|
16203
|
+
return this.lib.decoder.decode(metaBytes);
|
|
16204
|
+
}
|
|
16205
|
+
redo() {
|
|
16206
|
+
this.guard();
|
|
16207
|
+
const maxSize = 256;
|
|
16208
|
+
const metaBytes = this.lib.editBufferRedo(this.bufferPtr, maxSize);
|
|
16209
|
+
if (!metaBytes)
|
|
16210
|
+
return null;
|
|
16211
|
+
return this.lib.decoder.decode(metaBytes);
|
|
16212
|
+
}
|
|
16213
|
+
canUndo() {
|
|
16214
|
+
this.guard();
|
|
16215
|
+
return this.lib.editBufferCanUndo(this.bufferPtr);
|
|
16216
|
+
}
|
|
16217
|
+
canRedo() {
|
|
16218
|
+
this.guard();
|
|
16219
|
+
return this.lib.editBufferCanRedo(this.bufferPtr);
|
|
16220
|
+
}
|
|
16221
|
+
clearHistory() {
|
|
16222
|
+
this.guard();
|
|
16223
|
+
this.lib.editBufferClearHistory(this.bufferPtr);
|
|
16224
|
+
}
|
|
16225
|
+
setDefaultFg(fg2) {
|
|
16226
|
+
this.guard();
|
|
16227
|
+
this.lib.textBufferSetDefaultFg(this.textBufferPtr, fg2);
|
|
16228
|
+
}
|
|
16229
|
+
setDefaultBg(bg2) {
|
|
16230
|
+
this.guard();
|
|
16231
|
+
this.lib.textBufferSetDefaultBg(this.textBufferPtr, bg2);
|
|
16232
|
+
}
|
|
16233
|
+
setDefaultAttributes(attributes) {
|
|
16234
|
+
this.guard();
|
|
16235
|
+
this.lib.textBufferSetDefaultAttributes(this.textBufferPtr, attributes);
|
|
16236
|
+
}
|
|
16237
|
+
resetDefaults() {
|
|
16238
|
+
this.guard();
|
|
16239
|
+
this.lib.textBufferResetDefaults(this.textBufferPtr);
|
|
16240
|
+
}
|
|
16241
|
+
setSyntaxStyle(style) {
|
|
16242
|
+
this.guard();
|
|
16243
|
+
this._syntaxStyle = style ?? undefined;
|
|
16244
|
+
this.lib.textBufferSetSyntaxStyle(this.textBufferPtr, style?.ptr ?? null);
|
|
16245
|
+
}
|
|
16246
|
+
getSyntaxStyle() {
|
|
16247
|
+
this.guard();
|
|
16248
|
+
return this._syntaxStyle ?? null;
|
|
16249
|
+
}
|
|
16250
|
+
addHighlight(lineIdx, highlight) {
|
|
16251
|
+
this.guard();
|
|
16252
|
+
this.lib.textBufferAddHighlight(this.textBufferPtr, lineIdx, highlight);
|
|
16253
|
+
}
|
|
16254
|
+
addHighlightByCharRange(highlight) {
|
|
16255
|
+
this.guard();
|
|
16256
|
+
this.lib.textBufferAddHighlightByCharRange(this.textBufferPtr, highlight);
|
|
16257
|
+
}
|
|
16258
|
+
removeHighlightsByRef(hlRef) {
|
|
16259
|
+
this.guard();
|
|
16260
|
+
this.lib.textBufferRemoveHighlightsByRef(this.textBufferPtr, hlRef);
|
|
16261
|
+
}
|
|
16262
|
+
clearLineHighlights(lineIdx) {
|
|
16263
|
+
this.guard();
|
|
16264
|
+
this.lib.textBufferClearLineHighlights(this.textBufferPtr, lineIdx);
|
|
16265
|
+
}
|
|
16266
|
+
clearAllHighlights() {
|
|
16267
|
+
this.guard();
|
|
16268
|
+
this.lib.textBufferClearAllHighlights(this.textBufferPtr);
|
|
16269
|
+
}
|
|
16270
|
+
getLineHighlights(lineIdx) {
|
|
16271
|
+
this.guard();
|
|
16272
|
+
return this.lib.textBufferGetLineHighlights(this.textBufferPtr, lineIdx);
|
|
16273
|
+
}
|
|
16274
|
+
clear() {
|
|
16275
|
+
this.guard();
|
|
16276
|
+
this.lib.editBufferClear(this.bufferPtr);
|
|
16277
|
+
}
|
|
16278
|
+
destroy() {
|
|
16279
|
+
if (this._destroyed)
|
|
16280
|
+
return;
|
|
16281
|
+
this._destroyed = true;
|
|
16282
|
+
EditBuffer.registry.delete(this.id);
|
|
16283
|
+
this.lib.destroyEditBuffer(this.bufferPtr);
|
|
16284
|
+
}
|
|
16285
|
+
}
|
|
16286
|
+
|
|
16287
|
+
// src/editor-view.ts
|
|
16288
|
+
class EditorView {
|
|
16289
|
+
lib;
|
|
16290
|
+
viewPtr;
|
|
16291
|
+
editBuffer;
|
|
16292
|
+
_destroyed = false;
|
|
16293
|
+
_extmarksController;
|
|
16294
|
+
_textBufferViewPtr;
|
|
16295
|
+
constructor(lib, ptr5, editBuffer) {
|
|
16296
|
+
this.lib = lib;
|
|
16297
|
+
this.viewPtr = ptr5;
|
|
16298
|
+
this.editBuffer = editBuffer;
|
|
16299
|
+
}
|
|
16300
|
+
static create(editBuffer, viewportWidth, viewportHeight) {
|
|
16301
|
+
const lib = resolveRenderLib();
|
|
16302
|
+
const viewPtr = lib.createEditorView(editBuffer.ptr, viewportWidth, viewportHeight);
|
|
16303
|
+
return new EditorView(lib, viewPtr, editBuffer);
|
|
16304
|
+
}
|
|
16305
|
+
guard() {
|
|
16306
|
+
if (this._destroyed)
|
|
16307
|
+
throw new Error("EditorView is destroyed");
|
|
16308
|
+
}
|
|
16309
|
+
get ptr() {
|
|
16310
|
+
this.guard();
|
|
16311
|
+
return this.viewPtr;
|
|
16312
|
+
}
|
|
16313
|
+
setViewportSize(width, height) {
|
|
16314
|
+
this.guard();
|
|
16315
|
+
this.lib.editorViewSetViewportSize(this.viewPtr, width, height);
|
|
16316
|
+
}
|
|
16317
|
+
setViewport(x, y, width, height, moveCursor = true) {
|
|
16318
|
+
this.guard();
|
|
16319
|
+
this.lib.editorViewSetViewport(this.viewPtr, x, y, width, height, moveCursor);
|
|
16320
|
+
}
|
|
16321
|
+
getViewport() {
|
|
16322
|
+
this.guard();
|
|
16323
|
+
return this.lib.editorViewGetViewport(this.viewPtr);
|
|
16324
|
+
}
|
|
16325
|
+
setScrollMargin(margin) {
|
|
16326
|
+
this.guard();
|
|
16327
|
+
this.lib.editorViewSetScrollMargin(this.viewPtr, margin);
|
|
16328
|
+
}
|
|
16329
|
+
setWrapMode(mode) {
|
|
16330
|
+
this.guard();
|
|
16331
|
+
this.lib.editorViewSetWrapMode(this.viewPtr, mode);
|
|
16332
|
+
}
|
|
16333
|
+
getVirtualLineCount() {
|
|
16334
|
+
this.guard();
|
|
16335
|
+
return this.lib.editorViewGetVirtualLineCount(this.viewPtr);
|
|
16336
|
+
}
|
|
16337
|
+
getTotalVirtualLineCount() {
|
|
16338
|
+
this.guard();
|
|
16339
|
+
return this.lib.editorViewGetTotalVirtualLineCount(this.viewPtr);
|
|
16340
|
+
}
|
|
16341
|
+
setSelection(start, end, bgColor, fgColor) {
|
|
16342
|
+
this.guard();
|
|
16343
|
+
this.lib.editorViewSetSelection(this.viewPtr, start, end, bgColor || null, fgColor || null);
|
|
16344
|
+
}
|
|
16345
|
+
updateSelection(end, bgColor, fgColor) {
|
|
16346
|
+
this.guard();
|
|
16347
|
+
this.lib.editorViewUpdateSelection(this.viewPtr, end, bgColor || null, fgColor || null);
|
|
16348
|
+
}
|
|
16349
|
+
resetSelection() {
|
|
16350
|
+
this.guard();
|
|
16351
|
+
this.lib.editorViewResetSelection(this.viewPtr);
|
|
16352
|
+
}
|
|
16353
|
+
getSelection() {
|
|
16354
|
+
this.guard();
|
|
16355
|
+
return this.lib.editorViewGetSelection(this.viewPtr);
|
|
16356
|
+
}
|
|
16357
|
+
hasSelection() {
|
|
16358
|
+
this.guard();
|
|
16359
|
+
return this.getSelection() !== null;
|
|
16360
|
+
}
|
|
16361
|
+
setLocalSelection(anchorX, anchorY, focusX, focusY, bgColor, fgColor, updateCursor, followCursor) {
|
|
16362
|
+
this.guard();
|
|
16363
|
+
return this.lib.editorViewSetLocalSelection(this.viewPtr, anchorX, anchorY, focusX, focusY, bgColor || null, fgColor || null, updateCursor ?? false, followCursor ?? false);
|
|
16364
|
+
}
|
|
16365
|
+
updateLocalSelection(anchorX, anchorY, focusX, focusY, bgColor, fgColor, updateCursor, followCursor) {
|
|
16366
|
+
this.guard();
|
|
16367
|
+
return this.lib.editorViewUpdateLocalSelection(this.viewPtr, anchorX, anchorY, focusX, focusY, bgColor || null, fgColor || null, updateCursor ?? false, followCursor ?? false);
|
|
16368
|
+
}
|
|
16369
|
+
resetLocalSelection() {
|
|
16370
|
+
this.guard();
|
|
16371
|
+
this.lib.editorViewResetLocalSelection(this.viewPtr);
|
|
16372
|
+
}
|
|
16373
|
+
getSelectedText() {
|
|
16374
|
+
this.guard();
|
|
16375
|
+
const maxLength = 1024 * 1024;
|
|
16376
|
+
const selectedBytes = this.lib.editorViewGetSelectedTextBytes(this.viewPtr, maxLength);
|
|
16377
|
+
if (!selectedBytes)
|
|
16378
|
+
return "";
|
|
16379
|
+
return this.lib.decoder.decode(selectedBytes);
|
|
16380
|
+
}
|
|
16381
|
+
getCursor() {
|
|
16382
|
+
this.guard();
|
|
16383
|
+
return this.lib.editorViewGetCursor(this.viewPtr);
|
|
16384
|
+
}
|
|
16385
|
+
getText() {
|
|
16386
|
+
this.guard();
|
|
16387
|
+
const maxLength = 1024 * 1024;
|
|
16388
|
+
const textBytes = this.lib.editorViewGetText(this.viewPtr, maxLength);
|
|
16389
|
+
if (!textBytes)
|
|
16390
|
+
return "";
|
|
16391
|
+
return this.lib.decoder.decode(textBytes);
|
|
16392
|
+
}
|
|
16393
|
+
getVisualCursor() {
|
|
16394
|
+
this.guard();
|
|
16395
|
+
return this.lib.editorViewGetVisualCursor(this.viewPtr);
|
|
16396
|
+
}
|
|
16397
|
+
moveUpVisual() {
|
|
16398
|
+
this.guard();
|
|
16399
|
+
this.lib.editorViewMoveUpVisual(this.viewPtr);
|
|
16400
|
+
}
|
|
16401
|
+
moveDownVisual() {
|
|
16402
|
+
this.guard();
|
|
16403
|
+
this.lib.editorViewMoveDownVisual(this.viewPtr);
|
|
16404
|
+
}
|
|
16405
|
+
deleteSelectedText() {
|
|
16406
|
+
this.guard();
|
|
16407
|
+
this.lib.editorViewDeleteSelectedText(this.viewPtr);
|
|
16408
|
+
}
|
|
16409
|
+
setCursorByOffset(offset) {
|
|
16410
|
+
this.guard();
|
|
16411
|
+
this.lib.editorViewSetCursorByOffset(this.viewPtr, offset);
|
|
16412
|
+
}
|
|
16413
|
+
getNextWordBoundary() {
|
|
16414
|
+
this.guard();
|
|
16415
|
+
return this.lib.editorViewGetNextWordBoundary(this.viewPtr);
|
|
16416
|
+
}
|
|
16417
|
+
getPrevWordBoundary() {
|
|
16418
|
+
this.guard();
|
|
16419
|
+
return this.lib.editorViewGetPrevWordBoundary(this.viewPtr);
|
|
16420
|
+
}
|
|
16421
|
+
getEOL() {
|
|
16422
|
+
this.guard();
|
|
16423
|
+
return this.lib.editorViewGetEOL(this.viewPtr);
|
|
16424
|
+
}
|
|
16425
|
+
getVisualSOL() {
|
|
16426
|
+
this.guard();
|
|
16427
|
+
return this.lib.editorViewGetVisualSOL(this.viewPtr);
|
|
16428
|
+
}
|
|
16429
|
+
getVisualEOL() {
|
|
16430
|
+
this.guard();
|
|
16431
|
+
return this.lib.editorViewGetVisualEOL(this.viewPtr);
|
|
16432
|
+
}
|
|
16433
|
+
getLineInfo() {
|
|
16434
|
+
this.guard();
|
|
16435
|
+
return this.lib.editorViewGetLineInfo(this.viewPtr);
|
|
16436
|
+
}
|
|
16437
|
+
getLogicalLineInfo() {
|
|
16438
|
+
this.guard();
|
|
16439
|
+
return this.lib.editorViewGetLogicalLineInfo(this.viewPtr);
|
|
16440
|
+
}
|
|
16441
|
+
get extmarks() {
|
|
16442
|
+
if (!this._extmarksController) {
|
|
16443
|
+
this._extmarksController = createExtmarksController(this.editBuffer, this);
|
|
16444
|
+
}
|
|
16445
|
+
return this._extmarksController;
|
|
16446
|
+
}
|
|
16447
|
+
setPlaceholderStyledText(chunks) {
|
|
16448
|
+
this.guard();
|
|
16449
|
+
this.lib.editorViewSetPlaceholderStyledText(this.viewPtr, chunks);
|
|
16450
|
+
}
|
|
16451
|
+
setTabIndicator(indicator) {
|
|
16452
|
+
this.guard();
|
|
16453
|
+
const codePoint = typeof indicator === "string" ? indicator.codePointAt(0) ?? 0 : indicator;
|
|
16454
|
+
this.lib.editorViewSetTabIndicator(this.viewPtr, codePoint);
|
|
16455
|
+
}
|
|
16456
|
+
setTabIndicatorColor(color) {
|
|
16457
|
+
this.guard();
|
|
16458
|
+
this.lib.editorViewSetTabIndicatorColor(this.viewPtr, color);
|
|
16459
|
+
}
|
|
16460
|
+
measureForDimensions(width, height) {
|
|
16461
|
+
this.guard();
|
|
16462
|
+
if (!this._textBufferViewPtr) {
|
|
16463
|
+
this._textBufferViewPtr = this.lib.editorViewGetTextBufferView(this.viewPtr);
|
|
16464
|
+
}
|
|
16465
|
+
return this.lib.textBufferViewMeasureForDimensions(this._textBufferViewPtr, width, height);
|
|
16466
|
+
}
|
|
16467
|
+
destroy() {
|
|
16468
|
+
if (this._destroyed)
|
|
16469
|
+
return;
|
|
16470
|
+
if (this._extmarksController) {
|
|
16471
|
+
this._extmarksController.destroy();
|
|
16472
|
+
this._extmarksController = undefined;
|
|
16473
|
+
}
|
|
16474
|
+
this._destroyed = true;
|
|
16475
|
+
this.lib.destroyEditorView(this.viewPtr);
|
|
16476
|
+
}
|
|
16477
|
+
}
|
|
16478
|
+
|
|
16479
|
+
// src/console.ts
|
|
16480
|
+
import { EventEmitter as EventEmitter8 } from "events";
|
|
16481
|
+
import { Console } from "console";
|
|
16482
|
+
import fs from "fs";
|
|
16483
|
+
import path5 from "path";
|
|
16484
|
+
import util2 from "util";
|
|
16485
|
+
|
|
16486
|
+
// src/lib/output.capture.ts
|
|
16487
|
+
import { Writable } from "stream";
|
|
16488
|
+
import { EventEmitter as EventEmitter7 } from "events";
|
|
16489
|
+
|
|
16490
|
+
class Capture extends EventEmitter7 {
|
|
16491
|
+
output = [];
|
|
16492
|
+
constructor() {
|
|
16493
|
+
super();
|
|
16494
|
+
}
|
|
16495
|
+
get size() {
|
|
16496
|
+
return this.output.length;
|
|
16497
|
+
}
|
|
16498
|
+
write(stream, data) {
|
|
16499
|
+
this.output.push({ stream, output: data });
|
|
16500
|
+
this.emit("write", stream, data);
|
|
16501
|
+
}
|
|
16502
|
+
claimOutput() {
|
|
16503
|
+
const output = this.output.map((o) => o.output).join("");
|
|
16504
|
+
this.clear();
|
|
16505
|
+
return output;
|
|
16506
|
+
}
|
|
16507
|
+
clear() {
|
|
16508
|
+
this.output = [];
|
|
16509
|
+
}
|
|
16510
|
+
}
|
|
16511
|
+
|
|
16512
|
+
class CapturedWritableStream extends Writable {
|
|
16513
|
+
stream;
|
|
16514
|
+
capture;
|
|
16515
|
+
isTTY = true;
|
|
16516
|
+
columns = process.stdout.columns || 80;
|
|
16517
|
+
rows = process.stdout.rows || 24;
|
|
16518
|
+
constructor(stream, capture) {
|
|
16519
|
+
super();
|
|
16520
|
+
this.stream = stream;
|
|
16521
|
+
this.capture = capture;
|
|
16522
|
+
}
|
|
16523
|
+
_write(chunk, encoding, callback) {
|
|
16524
|
+
const data = chunk.toString();
|
|
16525
|
+
this.capture.write(this.stream, data);
|
|
16526
|
+
callback();
|
|
16527
|
+
}
|
|
16528
|
+
getColorDepth() {
|
|
16529
|
+
return process.stdout.getColorDepth?.() || 8;
|
|
16530
|
+
}
|
|
16531
|
+
}
|
|
16532
|
+
|
|
16533
|
+
// src/lib/keymapping.ts
|
|
16534
|
+
var defaultKeyAliases = {
|
|
16535
|
+
enter: "return",
|
|
16536
|
+
esc: "escape",
|
|
16537
|
+
kp0: "0",
|
|
16538
|
+
kp1: "1",
|
|
16539
|
+
kp2: "2",
|
|
16540
|
+
kp3: "3",
|
|
16541
|
+
kp4: "4",
|
|
16542
|
+
kp5: "5",
|
|
16543
|
+
kp6: "6",
|
|
16544
|
+
kp7: "7",
|
|
16545
|
+
kp8: "8",
|
|
16546
|
+
kp9: "9",
|
|
16547
|
+
kpdecimal: ".",
|
|
16548
|
+
kpdivide: "/",
|
|
16549
|
+
kpmultiply: "*",
|
|
16550
|
+
kpminus: "-",
|
|
16551
|
+
kpplus: "+",
|
|
16552
|
+
kpenter: "enter",
|
|
16553
|
+
kpequal: "=",
|
|
16554
|
+
kpseparator: ",",
|
|
16555
|
+
kpleft: "left",
|
|
16556
|
+
kpright: "right",
|
|
16557
|
+
kpup: "up",
|
|
16558
|
+
kpdown: "down",
|
|
16559
|
+
kppageup: "pageup",
|
|
16560
|
+
kppagedown: "pagedown",
|
|
16561
|
+
kphome: "home",
|
|
16562
|
+
kpend: "end",
|
|
16563
|
+
kpinsert: "insert",
|
|
16564
|
+
kpdelete: "delete"
|
|
16565
|
+
};
|
|
16566
|
+
function mergeKeyAliases(defaults, custom) {
|
|
16567
|
+
return { ...defaults, ...custom };
|
|
16568
|
+
}
|
|
16569
|
+
function mergeKeyBindings(defaults, custom) {
|
|
16570
|
+
const map = new Map;
|
|
16571
|
+
for (const binding of defaults) {
|
|
16572
|
+
const key = getKeyBindingKey(binding);
|
|
16573
|
+
map.set(key, binding);
|
|
16574
|
+
}
|
|
16575
|
+
for (const binding of custom) {
|
|
16576
|
+
const key = getKeyBindingKey(binding);
|
|
16577
|
+
map.set(key, binding);
|
|
16578
|
+
}
|
|
16579
|
+
return Array.from(map.values());
|
|
16580
|
+
}
|
|
16581
|
+
function getKeyBindingKey(binding) {
|
|
16582
|
+
return `${binding.name}:${binding.ctrl ? 1 : 0}:${binding.shift ? 1 : 0}:${binding.meta ? 1 : 0}:${binding.super ? 1 : 0}`;
|
|
16583
|
+
}
|
|
16584
|
+
function buildKeyBindingsMap(bindings, aliasMap) {
|
|
16585
|
+
const map = new Map;
|
|
16586
|
+
const aliases = aliasMap || {};
|
|
16587
|
+
for (const binding of bindings) {
|
|
16588
|
+
const key = getKeyBindingKey(binding);
|
|
16589
|
+
map.set(key, binding.action);
|
|
16590
|
+
}
|
|
16591
|
+
for (const binding of bindings) {
|
|
16592
|
+
const normalizedName = aliases[binding.name] || binding.name;
|
|
16593
|
+
if (normalizedName !== binding.name) {
|
|
16594
|
+
const aliasedKey = getKeyBindingKey({ ...binding, name: normalizedName });
|
|
16595
|
+
map.set(aliasedKey, binding.action);
|
|
16596
|
+
}
|
|
16597
|
+
}
|
|
16598
|
+
return map;
|
|
16599
|
+
}
|
|
16600
|
+
function keyBindingToString(binding) {
|
|
16601
|
+
const parts = [];
|
|
16602
|
+
if (binding.ctrl)
|
|
16603
|
+
parts.push("ctrl");
|
|
16604
|
+
if (binding.shift)
|
|
16605
|
+
parts.push("shift");
|
|
16606
|
+
if (binding.meta)
|
|
16607
|
+
parts.push("meta");
|
|
16608
|
+
if (binding.super)
|
|
16609
|
+
parts.push("super");
|
|
16610
|
+
parts.push(binding.name);
|
|
16611
|
+
return parts.join("+");
|
|
16612
|
+
}
|
|
16613
|
+
|
|
16614
|
+
// src/console.ts
|
|
16615
|
+
function getCallerInfo() {
|
|
16616
|
+
const err = new Error;
|
|
16617
|
+
const stackLines = err.stack?.split(`
|
|
16618
|
+
`).slice(5) || [];
|
|
16619
|
+
if (!stackLines.length)
|
|
16620
|
+
return null;
|
|
16621
|
+
const callerLine = stackLines[0].trim();
|
|
16622
|
+
const regex = /at\s+(?:([\w$.<>]+)\s+\()?((?:\/|[A-Za-z]:\\)[^:]+):(\d+):(\d+)\)?/;
|
|
16623
|
+
const match = callerLine.match(regex);
|
|
16624
|
+
if (!match)
|
|
16625
|
+
return null;
|
|
16626
|
+
const functionName = match[1] || "<anonymous>";
|
|
16627
|
+
const fullPath = match[2];
|
|
16628
|
+
const fileName = fullPath.split(/[\\/]/).pop() || "<unknown>";
|
|
16629
|
+
const lineNumber = parseInt(match[3], 10) || 0;
|
|
16630
|
+
const columnNumber = parseInt(match[4], 10) || 0;
|
|
16631
|
+
return { functionName, fullPath, fileName, lineNumber, columnNumber };
|
|
16632
|
+
}
|
|
16633
|
+
var capture = singleton("ConsoleCapture", () => new Capture);
|
|
16634
|
+
registerEnvVar({
|
|
16635
|
+
name: "OTUI_USE_CONSOLE",
|
|
16636
|
+
description: "Whether to use the console. Will not capture console output if set to false.",
|
|
16637
|
+
type: "boolean",
|
|
16638
|
+
default: true
|
|
16639
|
+
});
|
|
16640
|
+
registerEnvVar({
|
|
16641
|
+
name: "SHOW_CONSOLE",
|
|
16642
|
+
description: "Show the console at startup if set to true.",
|
|
16643
|
+
type: "boolean",
|
|
16644
|
+
default: false
|
|
16645
|
+
});
|
|
16646
|
+
|
|
16647
|
+
class TerminalConsoleCache extends EventEmitter8 {
|
|
16648
|
+
_cachedLogs = [];
|
|
16649
|
+
MAX_CACHE_SIZE = 1000;
|
|
16650
|
+
_collectCallerInfo = false;
|
|
16651
|
+
_cachingEnabled = true;
|
|
16652
|
+
_originalConsole = null;
|
|
16653
|
+
get cachedLogs() {
|
|
16654
|
+
return this._cachedLogs;
|
|
16655
|
+
}
|
|
16656
|
+
constructor() {
|
|
16657
|
+
super();
|
|
16658
|
+
}
|
|
16659
|
+
activate() {
|
|
16660
|
+
if (!this._originalConsole) {
|
|
16661
|
+
this._originalConsole = global.console;
|
|
16662
|
+
}
|
|
16663
|
+
this.setupConsoleCapture();
|
|
16664
|
+
this.overrideConsoleMethods();
|
|
16665
|
+
}
|
|
16666
|
+
setupConsoleCapture() {
|
|
16667
|
+
if (!env.OTUI_USE_CONSOLE)
|
|
16668
|
+
return;
|
|
16669
|
+
const mockStdout = new CapturedWritableStream("stdout", capture);
|
|
16670
|
+
const mockStderr = new CapturedWritableStream("stderr", capture);
|
|
16671
|
+
global.console = new Console({
|
|
16672
|
+
stdout: mockStdout,
|
|
16673
|
+
stderr: mockStderr,
|
|
16674
|
+
colorMode: true,
|
|
16675
|
+
inspectOptions: {
|
|
16676
|
+
compact: false,
|
|
16677
|
+
breakLength: 80,
|
|
16678
|
+
depth: 2
|
|
16679
|
+
}
|
|
16680
|
+
});
|
|
16681
|
+
}
|
|
16682
|
+
overrideConsoleMethods() {
|
|
16683
|
+
console.log = (...args) => {
|
|
16684
|
+
this.appendToConsole("LOG" /* LOG */, ...args);
|
|
16685
|
+
};
|
|
16686
|
+
console.info = (...args) => {
|
|
16687
|
+
this.appendToConsole("INFO" /* INFO */, ...args);
|
|
16688
|
+
};
|
|
16689
|
+
console.warn = (...args) => {
|
|
16690
|
+
this.appendToConsole("WARN" /* WARN */, ...args);
|
|
16691
|
+
};
|
|
16692
|
+
console.error = (...args) => {
|
|
16693
|
+
this.appendToConsole("ERROR" /* ERROR */, ...args);
|
|
16694
|
+
};
|
|
16695
|
+
console.debug = (...args) => {
|
|
16696
|
+
this.appendToConsole("DEBUG" /* DEBUG */, ...args);
|
|
16697
|
+
};
|
|
16698
|
+
}
|
|
16699
|
+
setCollectCallerInfo(enabled) {
|
|
16700
|
+
this._collectCallerInfo = enabled;
|
|
16701
|
+
}
|
|
16702
|
+
clearConsole() {
|
|
16703
|
+
this._cachedLogs = [];
|
|
16704
|
+
}
|
|
16705
|
+
setCachingEnabled(enabled) {
|
|
16706
|
+
this._cachingEnabled = enabled;
|
|
16707
|
+
}
|
|
16708
|
+
deactivate() {
|
|
16709
|
+
this.restoreOriginalConsole();
|
|
16710
|
+
}
|
|
16711
|
+
restoreOriginalConsole() {
|
|
16712
|
+
if (this._originalConsole) {
|
|
16713
|
+
global.console = this._originalConsole;
|
|
16714
|
+
}
|
|
16715
|
+
}
|
|
16716
|
+
addLogEntry(level, ...args) {
|
|
16717
|
+
const callerInfo = this._collectCallerInfo ? getCallerInfo() : null;
|
|
16157
16718
|
const logEntry = [new Date, level, args, callerInfo];
|
|
16158
16719
|
if (this._cachingEnabled) {
|
|
16159
16720
|
if (this._cachedLogs.length >= this.MAX_CACHE_SIZE) {
|
|
16160
16721
|
this._cachedLogs.shift();
|
|
16161
16722
|
}
|
|
16162
|
-
this._cachedLogs.push(logEntry);
|
|
16723
|
+
this._cachedLogs.push(logEntry);
|
|
16724
|
+
}
|
|
16725
|
+
return logEntry;
|
|
16726
|
+
}
|
|
16727
|
+
appendToConsole(level, ...args) {
|
|
16728
|
+
if (this._cachedLogs.length >= this.MAX_CACHE_SIZE) {
|
|
16729
|
+
this._cachedLogs.shift();
|
|
16730
|
+
}
|
|
16731
|
+
const entry = this.addLogEntry(level, ...args);
|
|
16732
|
+
this.emit("entry", entry);
|
|
16733
|
+
}
|
|
16734
|
+
destroy() {
|
|
16735
|
+
this.deactivate();
|
|
16736
|
+
}
|
|
16737
|
+
}
|
|
16738
|
+
var terminalConsoleCache = singleton("TerminalConsoleCache", () => {
|
|
16739
|
+
const terminalConsoleCache2 = new TerminalConsoleCache;
|
|
16740
|
+
process.on("exit", () => {
|
|
16741
|
+
terminalConsoleCache2.destroy();
|
|
16742
|
+
});
|
|
16743
|
+
return terminalConsoleCache2;
|
|
16744
|
+
});
|
|
16745
|
+
var ConsolePosition;
|
|
16746
|
+
((ConsolePosition2) => {
|
|
16747
|
+
ConsolePosition2["TOP"] = "top";
|
|
16748
|
+
ConsolePosition2["BOTTOM"] = "bottom";
|
|
16749
|
+
ConsolePosition2["LEFT"] = "left";
|
|
16750
|
+
ConsolePosition2["RIGHT"] = "right";
|
|
16751
|
+
})(ConsolePosition ||= {});
|
|
16752
|
+
var defaultConsoleKeybindings = [
|
|
16753
|
+
{ name: "up", action: "scroll-up" },
|
|
16754
|
+
{ name: "down", action: "scroll-down" },
|
|
16755
|
+
{ name: "up", shift: true, action: "scroll-to-top" },
|
|
16756
|
+
{ name: "down", shift: true, action: "scroll-to-bottom" },
|
|
16757
|
+
{ name: "p", ctrl: true, action: "position-previous" },
|
|
16758
|
+
{ name: "o", ctrl: true, action: "position-next" },
|
|
16759
|
+
{ name: "+", action: "size-increase" },
|
|
16760
|
+
{ name: "=", shift: true, action: "size-increase" },
|
|
16761
|
+
{ name: "-", action: "size-decrease" },
|
|
16762
|
+
{ name: "s", ctrl: true, action: "save-logs" },
|
|
16763
|
+
{ name: "c", ctrl: true, shift: true, action: "copy-selection" }
|
|
16764
|
+
];
|
|
16765
|
+
var DEFAULT_CONSOLE_OPTIONS = {
|
|
16766
|
+
position: "bottom" /* BOTTOM */,
|
|
16767
|
+
sizePercent: 30,
|
|
16768
|
+
zIndex: Infinity,
|
|
16769
|
+
colorInfo: "#00FFFF",
|
|
16770
|
+
colorWarn: "#FFFF00",
|
|
16771
|
+
colorError: "#FF0000",
|
|
16772
|
+
colorDebug: "#808080",
|
|
16773
|
+
colorDefault: "#FFFFFF",
|
|
16774
|
+
backgroundColor: RGBA.fromValues(0.1, 0.1, 0.1, 0.7),
|
|
16775
|
+
startInDebugMode: false,
|
|
16776
|
+
title: "Console",
|
|
16777
|
+
titleBarColor: RGBA.fromValues(0.05, 0.05, 0.05, 0.7),
|
|
16778
|
+
titleBarTextColor: "#FFFFFF",
|
|
16779
|
+
cursorColor: "#00A0FF",
|
|
16780
|
+
maxStoredLogs: 2000,
|
|
16781
|
+
maxDisplayLines: 3000,
|
|
16782
|
+
onCopySelection: undefined,
|
|
16783
|
+
keyBindings: undefined,
|
|
16784
|
+
keyAliasMap: undefined,
|
|
16785
|
+
selectionColor: RGBA.fromValues(0.3, 0.5, 0.8, 0.5),
|
|
16786
|
+
copyButtonColor: "#00A0FF"
|
|
16787
|
+
};
|
|
16788
|
+
var INDENT_WIDTH = 2;
|
|
16789
|
+
|
|
16790
|
+
class TerminalConsole extends EventEmitter8 {
|
|
16791
|
+
isVisible = false;
|
|
16792
|
+
isFocused = false;
|
|
16793
|
+
renderer;
|
|
16794
|
+
keyHandler;
|
|
16795
|
+
options;
|
|
16796
|
+
_debugModeEnabled = false;
|
|
16797
|
+
frameBuffer = null;
|
|
16798
|
+
consoleX = 0;
|
|
16799
|
+
consoleY = 0;
|
|
16800
|
+
consoleWidth = 0;
|
|
16801
|
+
consoleHeight = 0;
|
|
16802
|
+
scrollTopIndex = 0;
|
|
16803
|
+
isScrolledToBottom = true;
|
|
16804
|
+
currentLineIndex = 0;
|
|
16805
|
+
_displayLines = [];
|
|
16806
|
+
_allLogEntries = [];
|
|
16807
|
+
_needsFrameBufferUpdate = false;
|
|
16808
|
+
_entryListener;
|
|
16809
|
+
_selectionStart = null;
|
|
16810
|
+
_selectionEnd = null;
|
|
16811
|
+
_isDragging = false;
|
|
16812
|
+
_copyButtonBounds = {
|
|
16813
|
+
x: 0,
|
|
16814
|
+
y: 0,
|
|
16815
|
+
width: 0,
|
|
16816
|
+
height: 0
|
|
16817
|
+
};
|
|
16818
|
+
_autoScrollInterval = null;
|
|
16819
|
+
clock;
|
|
16820
|
+
_keyBindingsMap;
|
|
16821
|
+
_keyAliasMap;
|
|
16822
|
+
_keyBindings;
|
|
16823
|
+
_mergedKeyBindings;
|
|
16824
|
+
_actionHandlers;
|
|
16825
|
+
markNeedsRerender() {
|
|
16826
|
+
this._needsFrameBufferUpdate = true;
|
|
16827
|
+
this.renderer.requestRender();
|
|
16828
|
+
}
|
|
16829
|
+
getCopyButtonLabel() {
|
|
16830
|
+
const copyBindings = this._mergedKeyBindings.filter((b) => b.action === "copy-selection");
|
|
16831
|
+
const copyBinding = copyBindings[copyBindings.length - 1];
|
|
16832
|
+
if (copyBinding) {
|
|
16833
|
+
const shortcut = keyBindingToString(copyBinding);
|
|
16834
|
+
return `[Copy (${shortcut})]`;
|
|
16835
|
+
}
|
|
16836
|
+
return "[Copy]";
|
|
16837
|
+
}
|
|
16838
|
+
_rgbaInfo;
|
|
16839
|
+
_rgbaWarn;
|
|
16840
|
+
_rgbaError;
|
|
16841
|
+
_rgbaDebug;
|
|
16842
|
+
_rgbaDefault;
|
|
16843
|
+
backgroundColor;
|
|
16844
|
+
_rgbaTitleBar;
|
|
16845
|
+
_rgbaTitleBarText;
|
|
16846
|
+
_title;
|
|
16847
|
+
_rgbaCursor;
|
|
16848
|
+
_rgbaSelection;
|
|
16849
|
+
_rgbaCopyButton;
|
|
16850
|
+
_positions = [
|
|
16851
|
+
"top" /* TOP */,
|
|
16852
|
+
"right" /* RIGHT */,
|
|
16853
|
+
"bottom" /* BOTTOM */,
|
|
16854
|
+
"left" /* LEFT */
|
|
16855
|
+
];
|
|
16856
|
+
constructor(renderer, options = {}) {
|
|
16857
|
+
super();
|
|
16858
|
+
this.renderer = renderer;
|
|
16859
|
+
this.clock = options.clock ?? new SystemClock;
|
|
16860
|
+
this.options = { ...DEFAULT_CONSOLE_OPTIONS, ...options };
|
|
16861
|
+
this.keyHandler = this.handleKeyPress.bind(this);
|
|
16862
|
+
this._debugModeEnabled = this.options.startInDebugMode;
|
|
16863
|
+
terminalConsoleCache.setCollectCallerInfo(this._debugModeEnabled);
|
|
16864
|
+
this._rgbaInfo = parseColor(this.options.colorInfo);
|
|
16865
|
+
this._rgbaWarn = parseColor(this.options.colorWarn);
|
|
16866
|
+
this._rgbaError = parseColor(this.options.colorError);
|
|
16867
|
+
this._rgbaDebug = parseColor(this.options.colorDebug);
|
|
16868
|
+
this._rgbaDefault = parseColor(this.options.colorDefault);
|
|
16869
|
+
this.backgroundColor = parseColor(this.options.backgroundColor);
|
|
16870
|
+
this._rgbaTitleBar = parseColor(this.options.titleBarColor);
|
|
16871
|
+
this._rgbaTitleBarText = parseColor(this.options.titleBarTextColor || this.options.colorDefault);
|
|
16872
|
+
this._title = this.options.title;
|
|
16873
|
+
this._rgbaCursor = parseColor(this.options.cursorColor);
|
|
16874
|
+
this._rgbaSelection = parseColor(this.options.selectionColor);
|
|
16875
|
+
this._rgbaCopyButton = parseColor(this.options.copyButtonColor);
|
|
16876
|
+
this._keyAliasMap = mergeKeyAliases(defaultKeyAliases, options.keyAliasMap || {});
|
|
16877
|
+
this._keyBindings = options.keyBindings || [];
|
|
16878
|
+
this._mergedKeyBindings = mergeKeyBindings(defaultConsoleKeybindings, this._keyBindings);
|
|
16879
|
+
this._keyBindingsMap = buildKeyBindingsMap(this._mergedKeyBindings, this._keyAliasMap);
|
|
16880
|
+
this._actionHandlers = this.buildActionHandlers();
|
|
16881
|
+
this._updateConsoleDimensions();
|
|
16882
|
+
this._scrollToBottom(true);
|
|
16883
|
+
this._entryListener = (logEntry) => {
|
|
16884
|
+
this._handleNewLog(logEntry);
|
|
16885
|
+
};
|
|
16886
|
+
terminalConsoleCache.on("entry", this._entryListener);
|
|
16887
|
+
if (env.SHOW_CONSOLE) {
|
|
16888
|
+
this.show();
|
|
16889
|
+
}
|
|
16890
|
+
}
|
|
16891
|
+
buildActionHandlers() {
|
|
16892
|
+
return new Map([
|
|
16893
|
+
["scroll-up", () => this.scrollUp()],
|
|
16894
|
+
["scroll-down", () => this.scrollDown()],
|
|
16895
|
+
["scroll-to-top", () => this.scrollToTop()],
|
|
16896
|
+
["scroll-to-bottom", () => this.scrollToBottomAction()],
|
|
16897
|
+
["position-previous", () => this.positionPrevious()],
|
|
16898
|
+
["position-next", () => this.positionNext()],
|
|
16899
|
+
["size-increase", () => this.sizeIncrease()],
|
|
16900
|
+
["size-decrease", () => this.sizeDecrease()],
|
|
16901
|
+
["save-logs", () => this.saveLogsAction()],
|
|
16902
|
+
["copy-selection", () => this.triggerCopyAction()]
|
|
16903
|
+
]);
|
|
16904
|
+
}
|
|
16905
|
+
activate() {
|
|
16906
|
+
terminalConsoleCache.activate();
|
|
16907
|
+
}
|
|
16908
|
+
deactivate() {
|
|
16909
|
+
terminalConsoleCache.deactivate();
|
|
16910
|
+
}
|
|
16911
|
+
_handleNewLog(logEntry) {
|
|
16912
|
+
if (!this.isVisible)
|
|
16913
|
+
return;
|
|
16914
|
+
this._allLogEntries.push(logEntry);
|
|
16915
|
+
if (this._allLogEntries.length > this.options.maxStoredLogs) {
|
|
16916
|
+
this._allLogEntries.splice(0, this._allLogEntries.length - this.options.maxStoredLogs);
|
|
16917
|
+
}
|
|
16918
|
+
const newDisplayLines = this._processLogEntry(logEntry);
|
|
16919
|
+
this._displayLines.push(...newDisplayLines);
|
|
16920
|
+
if (this._displayLines.length > this.options.maxDisplayLines) {
|
|
16921
|
+
this._displayLines.splice(0, this._displayLines.length - this.options.maxDisplayLines);
|
|
16922
|
+
const linesRemoved = this._displayLines.length - this.options.maxDisplayLines;
|
|
16923
|
+
this.scrollTopIndex = Math.max(0, this.scrollTopIndex - linesRemoved);
|
|
16924
|
+
}
|
|
16925
|
+
if (this.isScrolledToBottom) {
|
|
16926
|
+
this._scrollToBottom();
|
|
16927
|
+
}
|
|
16928
|
+
this.markNeedsRerender();
|
|
16929
|
+
}
|
|
16930
|
+
_updateConsoleDimensions(termWidth, termHeight) {
|
|
16931
|
+
const width = termWidth ?? this.renderer.width;
|
|
16932
|
+
const height = termHeight ?? this.renderer.height;
|
|
16933
|
+
const sizePercent = this.options.sizePercent / 100;
|
|
16934
|
+
switch (this.options.position) {
|
|
16935
|
+
case "top" /* TOP */:
|
|
16936
|
+
this.consoleX = 0;
|
|
16937
|
+
this.consoleY = 0;
|
|
16938
|
+
this.consoleWidth = width;
|
|
16939
|
+
this.consoleHeight = Math.max(1, Math.floor(height * sizePercent));
|
|
16940
|
+
break;
|
|
16941
|
+
case "bottom" /* BOTTOM */:
|
|
16942
|
+
this.consoleHeight = Math.max(1, Math.floor(height * sizePercent));
|
|
16943
|
+
this.consoleWidth = width;
|
|
16944
|
+
this.consoleX = 0;
|
|
16945
|
+
this.consoleY = height - this.consoleHeight;
|
|
16946
|
+
break;
|
|
16947
|
+
case "left" /* LEFT */:
|
|
16948
|
+
this.consoleWidth = Math.max(1, Math.floor(width * sizePercent));
|
|
16949
|
+
this.consoleHeight = height;
|
|
16950
|
+
this.consoleX = 0;
|
|
16951
|
+
this.consoleY = 0;
|
|
16952
|
+
break;
|
|
16953
|
+
case "right" /* RIGHT */:
|
|
16954
|
+
this.consoleWidth = Math.max(1, Math.floor(width * sizePercent));
|
|
16955
|
+
this.consoleHeight = height;
|
|
16956
|
+
this.consoleY = 0;
|
|
16957
|
+
this.consoleX = width - this.consoleWidth;
|
|
16958
|
+
break;
|
|
16959
|
+
}
|
|
16960
|
+
this.currentLineIndex = Math.max(0, Math.min(this.currentLineIndex, this.consoleHeight - 1));
|
|
16961
|
+
}
|
|
16962
|
+
handleKeyPress(event) {
|
|
16963
|
+
if (event.name === "escape") {
|
|
16964
|
+
this.blur();
|
|
16965
|
+
return;
|
|
16966
|
+
}
|
|
16967
|
+
const bindingKey = getKeyBindingKey({
|
|
16968
|
+
name: event.name,
|
|
16969
|
+
ctrl: event.ctrl,
|
|
16970
|
+
shift: event.shift,
|
|
16971
|
+
meta: event.meta,
|
|
16972
|
+
super: event.super,
|
|
16973
|
+
action: "scroll-up"
|
|
16974
|
+
});
|
|
16975
|
+
const action = this._keyBindingsMap.get(bindingKey);
|
|
16976
|
+
if (action) {
|
|
16977
|
+
const handler = this._actionHandlers.get(action);
|
|
16978
|
+
if (handler) {
|
|
16979
|
+
handler();
|
|
16980
|
+
return;
|
|
16981
|
+
}
|
|
16982
|
+
}
|
|
16983
|
+
}
|
|
16984
|
+
scrollUp() {
|
|
16985
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
16986
|
+
if (this.currentLineIndex > 0) {
|
|
16987
|
+
this.currentLineIndex--;
|
|
16988
|
+
this.markNeedsRerender();
|
|
16989
|
+
} else if (this.scrollTopIndex > 0) {
|
|
16990
|
+
this.scrollTopIndex--;
|
|
16991
|
+
this.isScrolledToBottom = false;
|
|
16992
|
+
this.markNeedsRerender();
|
|
16993
|
+
}
|
|
16994
|
+
return true;
|
|
16995
|
+
}
|
|
16996
|
+
scrollDown() {
|
|
16997
|
+
const displayLineCount = this._displayLines.length;
|
|
16998
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
16999
|
+
const maxScrollTop = Math.max(0, displayLineCount - logAreaHeight);
|
|
17000
|
+
const canCursorMoveDown = this.currentLineIndex < logAreaHeight - 1 && this.scrollTopIndex + this.currentLineIndex < displayLineCount - 1;
|
|
17001
|
+
if (canCursorMoveDown) {
|
|
17002
|
+
this.currentLineIndex++;
|
|
17003
|
+
this.markNeedsRerender();
|
|
17004
|
+
} else if (this.scrollTopIndex < maxScrollTop) {
|
|
17005
|
+
this.scrollTopIndex++;
|
|
17006
|
+
this.isScrolledToBottom = this.scrollTopIndex === maxScrollTop;
|
|
17007
|
+
this.markNeedsRerender();
|
|
17008
|
+
}
|
|
17009
|
+
return true;
|
|
17010
|
+
}
|
|
17011
|
+
scrollToTop() {
|
|
17012
|
+
if (this.scrollTopIndex > 0 || this.currentLineIndex > 0) {
|
|
17013
|
+
this.scrollTopIndex = 0;
|
|
17014
|
+
this.currentLineIndex = 0;
|
|
17015
|
+
this.isScrolledToBottom = this._displayLines.length <= Math.max(1, this.consoleHeight - 1);
|
|
17016
|
+
this.markNeedsRerender();
|
|
17017
|
+
}
|
|
17018
|
+
return true;
|
|
17019
|
+
}
|
|
17020
|
+
scrollToBottomAction() {
|
|
17021
|
+
const logAreaHeightForScroll = Math.max(1, this.consoleHeight - 1);
|
|
17022
|
+
const maxScrollPossible = Math.max(0, this._displayLines.length - logAreaHeightForScroll);
|
|
17023
|
+
if (this.scrollTopIndex < maxScrollPossible || !this.isScrolledToBottom) {
|
|
17024
|
+
this._scrollToBottom(true);
|
|
17025
|
+
this.markNeedsRerender();
|
|
17026
|
+
}
|
|
17027
|
+
return true;
|
|
17028
|
+
}
|
|
17029
|
+
positionPrevious() {
|
|
17030
|
+
const currentPositionIndex = this._positions.indexOf(this.options.position);
|
|
17031
|
+
const prevIndex = (currentPositionIndex - 1 + this._positions.length) % this._positions.length;
|
|
17032
|
+
this.options.position = this._positions[prevIndex];
|
|
17033
|
+
this.resize(this.renderer.width, this.renderer.height);
|
|
17034
|
+
return true;
|
|
17035
|
+
}
|
|
17036
|
+
positionNext() {
|
|
17037
|
+
const currentPositionIndex = this._positions.indexOf(this.options.position);
|
|
17038
|
+
const nextIndex = (currentPositionIndex + 1) % this._positions.length;
|
|
17039
|
+
this.options.position = this._positions[nextIndex];
|
|
17040
|
+
this.resize(this.renderer.width, this.renderer.height);
|
|
17041
|
+
return true;
|
|
17042
|
+
}
|
|
17043
|
+
sizeIncrease() {
|
|
17044
|
+
this.options.sizePercent = Math.min(100, this.options.sizePercent + 5);
|
|
17045
|
+
this.resize(this.renderer.width, this.renderer.height);
|
|
17046
|
+
return true;
|
|
17047
|
+
}
|
|
17048
|
+
sizeDecrease() {
|
|
17049
|
+
this.options.sizePercent = Math.max(10, this.options.sizePercent - 5);
|
|
17050
|
+
this.resize(this.renderer.width, this.renderer.height);
|
|
17051
|
+
return true;
|
|
17052
|
+
}
|
|
17053
|
+
saveLogsAction() {
|
|
17054
|
+
this.saveLogsToFile();
|
|
17055
|
+
return true;
|
|
17056
|
+
}
|
|
17057
|
+
triggerCopyAction() {
|
|
17058
|
+
this.triggerCopy();
|
|
17059
|
+
return true;
|
|
17060
|
+
}
|
|
17061
|
+
attachStdin() {
|
|
17062
|
+
if (this.isFocused)
|
|
17063
|
+
return;
|
|
17064
|
+
this.renderer.keyInput.on("keypress", this.keyHandler);
|
|
17065
|
+
this.isFocused = true;
|
|
17066
|
+
}
|
|
17067
|
+
detachStdin() {
|
|
17068
|
+
if (!this.isFocused)
|
|
17069
|
+
return;
|
|
17070
|
+
this.renderer.keyInput.off("keypress", this.keyHandler);
|
|
17071
|
+
this.isFocused = false;
|
|
17072
|
+
}
|
|
17073
|
+
formatTimestamp(date) {
|
|
17074
|
+
return new Intl.DateTimeFormat("en-US", {
|
|
17075
|
+
hour: "2-digit",
|
|
17076
|
+
minute: "2-digit",
|
|
17077
|
+
second: "2-digit",
|
|
17078
|
+
hour12: false
|
|
17079
|
+
}).format(date);
|
|
17080
|
+
}
|
|
17081
|
+
formatArguments(args) {
|
|
17082
|
+
return args.map((arg) => {
|
|
17083
|
+
if (arg instanceof Error) {
|
|
17084
|
+
const errorProps = arg;
|
|
17085
|
+
return `Error: ${errorProps.message}
|
|
17086
|
+
` + (errorProps.stack ? `${errorProps.stack}
|
|
17087
|
+
` : "");
|
|
17088
|
+
}
|
|
17089
|
+
if (typeof arg === "object" && arg !== null) {
|
|
17090
|
+
try {
|
|
17091
|
+
return util2.inspect(arg, { depth: 2 });
|
|
17092
|
+
} catch (e) {
|
|
17093
|
+
return String(arg);
|
|
17094
|
+
}
|
|
17095
|
+
}
|
|
17096
|
+
try {
|
|
17097
|
+
return util2.inspect(arg, { depth: 2 });
|
|
17098
|
+
} catch (e) {
|
|
17099
|
+
return String(arg);
|
|
17100
|
+
}
|
|
17101
|
+
}).join(" ");
|
|
17102
|
+
}
|
|
17103
|
+
resize(width, height) {
|
|
17104
|
+
this._updateConsoleDimensions(width, height);
|
|
17105
|
+
if (this.frameBuffer) {
|
|
17106
|
+
this.frameBuffer.resize(this.consoleWidth, this.consoleHeight);
|
|
17107
|
+
const displayLineCount = this._displayLines.length;
|
|
17108
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
17109
|
+
const maxScrollTop = Math.max(0, displayLineCount - logAreaHeight);
|
|
17110
|
+
this.scrollTopIndex = Math.min(this.scrollTopIndex, maxScrollTop);
|
|
17111
|
+
this.isScrolledToBottom = this.scrollTopIndex === maxScrollTop;
|
|
17112
|
+
const visibleLineCount = Math.min(logAreaHeight, displayLineCount - this.scrollTopIndex);
|
|
17113
|
+
this.currentLineIndex = Math.max(0, Math.min(this.currentLineIndex, visibleLineCount - 1));
|
|
17114
|
+
if (this.isVisible) {
|
|
17115
|
+
this.markNeedsRerender();
|
|
17116
|
+
}
|
|
17117
|
+
}
|
|
17118
|
+
}
|
|
17119
|
+
clear() {
|
|
17120
|
+
terminalConsoleCache.clearConsole();
|
|
17121
|
+
this._allLogEntries = [];
|
|
17122
|
+
this._displayLines = [];
|
|
17123
|
+
this.markNeedsRerender();
|
|
17124
|
+
}
|
|
17125
|
+
toggle() {
|
|
17126
|
+
if (this.isVisible) {
|
|
17127
|
+
if (this.isFocused) {
|
|
17128
|
+
this.hide();
|
|
17129
|
+
} else {
|
|
17130
|
+
this.focus();
|
|
17131
|
+
}
|
|
17132
|
+
} else {
|
|
17133
|
+
this.show();
|
|
17134
|
+
}
|
|
17135
|
+
if (!this.renderer.isRunning) {
|
|
17136
|
+
this.renderer.requestRender();
|
|
17137
|
+
}
|
|
17138
|
+
}
|
|
17139
|
+
focus() {
|
|
17140
|
+
this.attachStdin();
|
|
17141
|
+
this._scrollToBottom(true);
|
|
17142
|
+
this.markNeedsRerender();
|
|
17143
|
+
}
|
|
17144
|
+
blur() {
|
|
17145
|
+
this.detachStdin();
|
|
17146
|
+
this.markNeedsRerender();
|
|
17147
|
+
}
|
|
17148
|
+
show() {
|
|
17149
|
+
if (!this.isVisible) {
|
|
17150
|
+
this.isVisible = true;
|
|
17151
|
+
this._processCachedLogs();
|
|
17152
|
+
terminalConsoleCache.setCachingEnabled(false);
|
|
17153
|
+
if (!this.frameBuffer) {
|
|
17154
|
+
this.frameBuffer = OptimizedBuffer.create(this.consoleWidth, this.consoleHeight, this.renderer.widthMethod, {
|
|
17155
|
+
respectAlpha: this.backgroundColor.a < 1,
|
|
17156
|
+
id: "console framebuffer"
|
|
17157
|
+
});
|
|
17158
|
+
}
|
|
17159
|
+
const logCount = terminalConsoleCache.cachedLogs.length;
|
|
17160
|
+
const visibleLogLines = Math.min(this.consoleHeight, logCount);
|
|
17161
|
+
this.currentLineIndex = Math.max(0, visibleLogLines - 1);
|
|
17162
|
+
this.scrollTopIndex = 0;
|
|
17163
|
+
this._scrollToBottom(true);
|
|
17164
|
+
this.focus();
|
|
17165
|
+
this.markNeedsRerender();
|
|
16163
17166
|
}
|
|
16164
|
-
return logEntry;
|
|
16165
17167
|
}
|
|
16166
|
-
|
|
16167
|
-
if (this.
|
|
16168
|
-
this.
|
|
17168
|
+
hide() {
|
|
17169
|
+
if (this.isVisible) {
|
|
17170
|
+
this.isVisible = false;
|
|
17171
|
+
this.blur();
|
|
17172
|
+
terminalConsoleCache.setCachingEnabled(true);
|
|
16169
17173
|
}
|
|
16170
|
-
const entry = this.addLogEntry(level, ...args);
|
|
16171
|
-
this.emit("entry", entry);
|
|
16172
17174
|
}
|
|
16173
17175
|
destroy() {
|
|
17176
|
+
this.stopAutoScroll();
|
|
17177
|
+
this.hide();
|
|
16174
17178
|
this.deactivate();
|
|
17179
|
+
terminalConsoleCache.off("entry", this._entryListener);
|
|
16175
17180
|
}
|
|
16176
|
-
|
|
16177
|
-
|
|
16178
|
-
|
|
16179
|
-
process.on("exit", () => {
|
|
16180
|
-
terminalConsoleCache2.destroy();
|
|
16181
|
-
});
|
|
16182
|
-
return terminalConsoleCache2;
|
|
16183
|
-
});
|
|
16184
|
-
var ConsolePosition;
|
|
16185
|
-
((ConsolePosition2) => {
|
|
16186
|
-
ConsolePosition2["TOP"] = "top";
|
|
16187
|
-
ConsolePosition2["BOTTOM"] = "bottom";
|
|
16188
|
-
ConsolePosition2["LEFT"] = "left";
|
|
16189
|
-
ConsolePosition2["RIGHT"] = "right";
|
|
16190
|
-
})(ConsolePosition ||= {});
|
|
16191
|
-
var defaultConsoleKeybindings = [
|
|
16192
|
-
{ name: "up", action: "scroll-up" },
|
|
16193
|
-
{ name: "down", action: "scroll-down" },
|
|
16194
|
-
{ name: "up", shift: true, action: "scroll-to-top" },
|
|
16195
|
-
{ name: "down", shift: true, action: "scroll-to-bottom" },
|
|
16196
|
-
{ name: "p", ctrl: true, action: "position-previous" },
|
|
16197
|
-
{ name: "o", ctrl: true, action: "position-next" },
|
|
16198
|
-
{ name: "+", action: "size-increase" },
|
|
16199
|
-
{ name: "=", shift: true, action: "size-increase" },
|
|
16200
|
-
{ name: "-", action: "size-decrease" },
|
|
16201
|
-
{ name: "s", ctrl: true, action: "save-logs" },
|
|
16202
|
-
{ name: "c", ctrl: true, shift: true, action: "copy-selection" }
|
|
16203
|
-
];
|
|
16204
|
-
var DEFAULT_CONSOLE_OPTIONS = {
|
|
16205
|
-
position: "bottom" /* BOTTOM */,
|
|
16206
|
-
sizePercent: 30,
|
|
16207
|
-
zIndex: Infinity,
|
|
16208
|
-
colorInfo: "#00FFFF",
|
|
16209
|
-
colorWarn: "#FFFF00",
|
|
16210
|
-
colorError: "#FF0000",
|
|
16211
|
-
colorDebug: "#808080",
|
|
16212
|
-
colorDefault: "#FFFFFF",
|
|
16213
|
-
backgroundColor: RGBA.fromValues(0.1, 0.1, 0.1, 0.7),
|
|
16214
|
-
startInDebugMode: false,
|
|
16215
|
-
title: "Console",
|
|
16216
|
-
titleBarColor: RGBA.fromValues(0.05, 0.05, 0.05, 0.7),
|
|
16217
|
-
titleBarTextColor: "#FFFFFF",
|
|
16218
|
-
cursorColor: "#00A0FF",
|
|
16219
|
-
maxStoredLogs: 2000,
|
|
16220
|
-
maxDisplayLines: 3000,
|
|
16221
|
-
onCopySelection: undefined,
|
|
16222
|
-
keyBindings: undefined,
|
|
16223
|
-
keyAliasMap: undefined,
|
|
16224
|
-
selectionColor: RGBA.fromValues(0.3, 0.5, 0.8, 0.5),
|
|
16225
|
-
copyButtonColor: "#00A0FF"
|
|
16226
|
-
};
|
|
16227
|
-
var INDENT_WIDTH = 2;
|
|
16228
|
-
|
|
16229
|
-
class TerminalConsole extends EventEmitter7 {
|
|
16230
|
-
isVisible = false;
|
|
16231
|
-
isFocused = false;
|
|
16232
|
-
renderer;
|
|
16233
|
-
keyHandler;
|
|
16234
|
-
options;
|
|
16235
|
-
_debugModeEnabled = false;
|
|
16236
|
-
frameBuffer = null;
|
|
16237
|
-
consoleX = 0;
|
|
16238
|
-
consoleY = 0;
|
|
16239
|
-
consoleWidth = 0;
|
|
16240
|
-
consoleHeight = 0;
|
|
16241
|
-
scrollTopIndex = 0;
|
|
16242
|
-
isScrolledToBottom = true;
|
|
16243
|
-
currentLineIndex = 0;
|
|
16244
|
-
_displayLines = [];
|
|
16245
|
-
_allLogEntries = [];
|
|
16246
|
-
_needsFrameBufferUpdate = false;
|
|
16247
|
-
_entryListener;
|
|
16248
|
-
_selectionStart = null;
|
|
16249
|
-
_selectionEnd = null;
|
|
16250
|
-
_isDragging = false;
|
|
16251
|
-
_copyButtonBounds = {
|
|
16252
|
-
x: 0,
|
|
16253
|
-
y: 0,
|
|
16254
|
-
width: 0,
|
|
16255
|
-
height: 0
|
|
16256
|
-
};
|
|
16257
|
-
_autoScrollInterval = null;
|
|
16258
|
-
clock;
|
|
16259
|
-
_keyBindingsMap;
|
|
16260
|
-
_keyAliasMap;
|
|
16261
|
-
_keyBindings;
|
|
16262
|
-
_mergedKeyBindings;
|
|
16263
|
-
_actionHandlers;
|
|
16264
|
-
markNeedsRerender() {
|
|
16265
|
-
this._needsFrameBufferUpdate = true;
|
|
16266
|
-
this.renderer.requestRender();
|
|
17181
|
+
getCachedLogs() {
|
|
17182
|
+
return terminalConsoleCache.cachedLogs.map((logEntry) => logEntry[0].toISOString() + " " + logEntry.slice(1).join(" ")).join(`
|
|
17183
|
+
`);
|
|
16267
17184
|
}
|
|
16268
|
-
|
|
16269
|
-
|
|
16270
|
-
|
|
16271
|
-
|
|
16272
|
-
|
|
16273
|
-
|
|
17185
|
+
updateFrameBuffer() {
|
|
17186
|
+
if (!this.frameBuffer)
|
|
17187
|
+
return;
|
|
17188
|
+
this.frameBuffer.clear(this.backgroundColor);
|
|
17189
|
+
const displayLines = this._displayLines;
|
|
17190
|
+
const displayLineCount = displayLines.length;
|
|
17191
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
17192
|
+
this.frameBuffer.fillRect(0, 0, this.consoleWidth, 1, this._rgbaTitleBar);
|
|
17193
|
+
const dynamicTitle = `${this._title}${this.isFocused ? " (Focused)" : ""}`;
|
|
17194
|
+
const titleX = Math.max(0, Math.floor((this.consoleWidth - dynamicTitle.length) / 2));
|
|
17195
|
+
this.frameBuffer.drawText(dynamicTitle, titleX, 0, this._rgbaTitleBarText, this._rgbaTitleBar);
|
|
17196
|
+
const copyLabel = this.getCopyButtonLabel();
|
|
17197
|
+
const copyButtonX = this.consoleWidth - copyLabel.length - 1;
|
|
17198
|
+
if (copyButtonX >= 0) {
|
|
17199
|
+
const copyButtonEnabled = this.hasSelection();
|
|
17200
|
+
const disabledColor = RGBA.fromInts(100, 100, 100, 255);
|
|
17201
|
+
const copyColor = copyButtonEnabled ? this._rgbaCopyButton : disabledColor;
|
|
17202
|
+
this.frameBuffer.drawText(copyLabel, copyButtonX, 0, copyColor, this._rgbaTitleBar);
|
|
17203
|
+
this._copyButtonBounds = { x: copyButtonX, y: 0, width: copyLabel.length, height: 1 };
|
|
17204
|
+
} else {
|
|
17205
|
+
this._copyButtonBounds = { x: -1, y: -1, width: 0, height: 0 };
|
|
16274
17206
|
}
|
|
16275
|
-
|
|
16276
|
-
|
|
16277
|
-
|
|
16278
|
-
|
|
16279
|
-
|
|
16280
|
-
|
|
16281
|
-
|
|
16282
|
-
|
|
16283
|
-
|
|
16284
|
-
|
|
16285
|
-
|
|
16286
|
-
|
|
16287
|
-
|
|
16288
|
-
|
|
16289
|
-
|
|
16290
|
-
|
|
16291
|
-
|
|
16292
|
-
|
|
16293
|
-
|
|
16294
|
-
|
|
16295
|
-
|
|
16296
|
-
|
|
16297
|
-
|
|
16298
|
-
|
|
16299
|
-
|
|
16300
|
-
|
|
16301
|
-
|
|
16302
|
-
|
|
16303
|
-
|
|
16304
|
-
|
|
16305
|
-
|
|
16306
|
-
|
|
16307
|
-
|
|
16308
|
-
|
|
16309
|
-
|
|
16310
|
-
|
|
16311
|
-
|
|
16312
|
-
|
|
16313
|
-
|
|
16314
|
-
|
|
16315
|
-
|
|
16316
|
-
|
|
17207
|
+
const startIndex = this.scrollTopIndex;
|
|
17208
|
+
const endIndex = Math.min(startIndex + logAreaHeight, displayLineCount);
|
|
17209
|
+
const visibleDisplayLines = displayLines.slice(startIndex, endIndex);
|
|
17210
|
+
let lineY = 1;
|
|
17211
|
+
for (let i = 0;i < visibleDisplayLines.length; i++) {
|
|
17212
|
+
if (lineY >= this.consoleHeight)
|
|
17213
|
+
break;
|
|
17214
|
+
const displayLine = visibleDisplayLines[i];
|
|
17215
|
+
const absoluteLineIndex = startIndex + i;
|
|
17216
|
+
let levelColor = this._rgbaDefault;
|
|
17217
|
+
switch (displayLine.level) {
|
|
17218
|
+
case "INFO" /* INFO */:
|
|
17219
|
+
levelColor = this._rgbaInfo;
|
|
17220
|
+
break;
|
|
17221
|
+
case "WARN" /* WARN */:
|
|
17222
|
+
levelColor = this._rgbaWarn;
|
|
17223
|
+
break;
|
|
17224
|
+
case "ERROR" /* ERROR */:
|
|
17225
|
+
levelColor = this._rgbaError;
|
|
17226
|
+
break;
|
|
17227
|
+
case "DEBUG" /* DEBUG */:
|
|
17228
|
+
levelColor = this._rgbaDebug;
|
|
17229
|
+
break;
|
|
17230
|
+
}
|
|
17231
|
+
const linePrefix = displayLine.indent ? " ".repeat(INDENT_WIDTH) : "";
|
|
17232
|
+
const textToDraw = displayLine.text;
|
|
17233
|
+
const textAvailableWidth = this.consoleWidth - 1 - (displayLine.indent ? INDENT_WIDTH : 0);
|
|
17234
|
+
const showCursor = this.isFocused && lineY - 1 === this.currentLineIndex;
|
|
17235
|
+
if (showCursor) {
|
|
17236
|
+
this.frameBuffer.drawText(">", 0, lineY, this._rgbaCursor, this.backgroundColor);
|
|
17237
|
+
} else {
|
|
17238
|
+
this.frameBuffer.drawText(" ", 0, lineY, this._rgbaDefault, this.backgroundColor);
|
|
17239
|
+
}
|
|
17240
|
+
const fullText = `${linePrefix}${textToDraw.substring(0, textAvailableWidth)}`;
|
|
17241
|
+
const selectionRange = this.getLineSelectionRange(absoluteLineIndex);
|
|
17242
|
+
if (selectionRange) {
|
|
17243
|
+
const adjustedStart = Math.max(0, selectionRange.start);
|
|
17244
|
+
const adjustedEnd = Math.min(fullText.length, selectionRange.end);
|
|
17245
|
+
if (adjustedStart > 0) {
|
|
17246
|
+
this.frameBuffer.drawText(fullText.substring(0, adjustedStart), 1, lineY, levelColor);
|
|
17247
|
+
}
|
|
17248
|
+
if (adjustedStart < adjustedEnd) {
|
|
17249
|
+
this.frameBuffer.fillRect(1 + adjustedStart, lineY, adjustedEnd - adjustedStart, 1, this._rgbaSelection);
|
|
17250
|
+
this.frameBuffer.drawText(fullText.substring(adjustedStart, adjustedEnd), 1 + adjustedStart, lineY, levelColor, this._rgbaSelection);
|
|
17251
|
+
}
|
|
17252
|
+
if (adjustedEnd < fullText.length) {
|
|
17253
|
+
this.frameBuffer.drawText(fullText.substring(adjustedEnd), 1 + adjustedEnd, lineY, levelColor);
|
|
17254
|
+
}
|
|
17255
|
+
} else {
|
|
17256
|
+
this.frameBuffer.drawText(fullText, 1, lineY, levelColor);
|
|
17257
|
+
}
|
|
17258
|
+
lineY++;
|
|
17259
|
+
}
|
|
17260
|
+
}
|
|
17261
|
+
renderToBuffer(buffer) {
|
|
17262
|
+
if (!this.isVisible || !this.frameBuffer)
|
|
17263
|
+
return;
|
|
17264
|
+
if (this._needsFrameBufferUpdate) {
|
|
17265
|
+
this.updateFrameBuffer();
|
|
17266
|
+
this._needsFrameBufferUpdate = false;
|
|
17267
|
+
}
|
|
17268
|
+
buffer.drawFrameBuffer(this.consoleX, this.consoleY, this.frameBuffer);
|
|
17269
|
+
}
|
|
17270
|
+
setDebugMode(enabled) {
|
|
17271
|
+
this._debugModeEnabled = enabled;
|
|
17272
|
+
terminalConsoleCache.setCollectCallerInfo(enabled);
|
|
17273
|
+
if (this.isVisible) {
|
|
17274
|
+
this.markNeedsRerender();
|
|
17275
|
+
}
|
|
17276
|
+
}
|
|
17277
|
+
toggleDebugMode() {
|
|
17278
|
+
this.setDebugMode(!this._debugModeEnabled);
|
|
17279
|
+
}
|
|
17280
|
+
set keyBindings(bindings) {
|
|
17281
|
+
this._keyBindings = bindings;
|
|
17282
|
+
this._mergedKeyBindings = mergeKeyBindings(defaultConsoleKeybindings, bindings);
|
|
17283
|
+
this._keyBindingsMap = buildKeyBindingsMap(this._mergedKeyBindings, this._keyAliasMap);
|
|
17284
|
+
this.markNeedsRerender();
|
|
17285
|
+
}
|
|
17286
|
+
set keyAliasMap(aliases) {
|
|
17287
|
+
this._keyAliasMap = mergeKeyAliases(defaultKeyAliases, aliases);
|
|
16317
17288
|
this._mergedKeyBindings = mergeKeyBindings(defaultConsoleKeybindings, this._keyBindings);
|
|
16318
17289
|
this._keyBindingsMap = buildKeyBindingsMap(this._mergedKeyBindings, this._keyAliasMap);
|
|
16319
|
-
this.
|
|
16320
|
-
this._updateConsoleDimensions();
|
|
16321
|
-
this._scrollToBottom(true);
|
|
16322
|
-
this._entryListener = (logEntry) => {
|
|
16323
|
-
this._handleNewLog(logEntry);
|
|
16324
|
-
};
|
|
16325
|
-
terminalConsoleCache.on("entry", this._entryListener);
|
|
16326
|
-
if (env.SHOW_CONSOLE) {
|
|
16327
|
-
this.show();
|
|
16328
|
-
}
|
|
17290
|
+
this.markNeedsRerender();
|
|
16329
17291
|
}
|
|
16330
|
-
|
|
16331
|
-
|
|
16332
|
-
["scroll-up", () => this.scrollUp()],
|
|
16333
|
-
["scroll-down", () => this.scrollDown()],
|
|
16334
|
-
["scroll-to-top", () => this.scrollToTop()],
|
|
16335
|
-
["scroll-to-bottom", () => this.scrollToBottomAction()],
|
|
16336
|
-
["position-previous", () => this.positionPrevious()],
|
|
16337
|
-
["position-next", () => this.positionNext()],
|
|
16338
|
-
["size-increase", () => this.sizeIncrease()],
|
|
16339
|
-
["size-decrease", () => this.sizeDecrease()],
|
|
16340
|
-
["save-logs", () => this.saveLogsAction()],
|
|
16341
|
-
["copy-selection", () => this.triggerCopyAction()]
|
|
16342
|
-
]);
|
|
17292
|
+
set onCopySelection(callback) {
|
|
17293
|
+
this.options.onCopySelection = callback;
|
|
16343
17294
|
}
|
|
16344
|
-
|
|
16345
|
-
|
|
17295
|
+
get onCopySelection() {
|
|
17296
|
+
return this.options.onCopySelection;
|
|
16346
17297
|
}
|
|
16347
|
-
|
|
16348
|
-
|
|
17298
|
+
_scrollToBottom(forceCursorToLastLine = false) {
|
|
17299
|
+
const displayLineCount = this._displayLines.length;
|
|
17300
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
17301
|
+
const maxScrollTop = Math.max(0, displayLineCount - logAreaHeight);
|
|
17302
|
+
this.scrollTopIndex = maxScrollTop;
|
|
17303
|
+
this.isScrolledToBottom = true;
|
|
17304
|
+
const visibleLineCount = Math.min(logAreaHeight, displayLineCount - this.scrollTopIndex);
|
|
17305
|
+
if (forceCursorToLastLine || this.currentLineIndex >= visibleLineCount) {
|
|
17306
|
+
this.currentLineIndex = Math.max(0, visibleLineCount - 1);
|
|
17307
|
+
}
|
|
16349
17308
|
}
|
|
16350
|
-
|
|
16351
|
-
|
|
16352
|
-
|
|
16353
|
-
this.
|
|
17309
|
+
_processLogEntry(logEntry) {
|
|
17310
|
+
const [date, level, args, callerInfo] = logEntry;
|
|
17311
|
+
const displayLines = [];
|
|
17312
|
+
const timestamp = this.formatTimestamp(date);
|
|
17313
|
+
const callerSource = callerInfo ? `${callerInfo.fileName}:${callerInfo.lineNumber}` : "unknown";
|
|
17314
|
+
const prefix = `[${timestamp}] [${level}]` + (this._debugModeEnabled ? ` [${callerSource}]` : "") + " ";
|
|
17315
|
+
const formattedArgs = this.formatArguments(args);
|
|
17316
|
+
const initialLines = formattedArgs.split(`
|
|
17317
|
+
`);
|
|
17318
|
+
for (let i = 0;i < initialLines.length; i++) {
|
|
17319
|
+
const lineText = initialLines[i];
|
|
17320
|
+
const isFirstLineOfEntry = i === 0;
|
|
17321
|
+
const availableWidth = this.consoleWidth - 1 - (isFirstLineOfEntry ? 0 : INDENT_WIDTH);
|
|
17322
|
+
const linePrefix = isFirstLineOfEntry ? prefix : " ".repeat(INDENT_WIDTH);
|
|
17323
|
+
const textToWrap = isFirstLineOfEntry ? linePrefix + lineText : lineText;
|
|
17324
|
+
let currentPos = 0;
|
|
17325
|
+
while (currentPos < textToWrap.length || isFirstLineOfEntry && currentPos === 0 && textToWrap.length === 0) {
|
|
17326
|
+
const segment = textToWrap.substring(currentPos, currentPos + availableWidth);
|
|
17327
|
+
const isFirstSegmentOfLine = currentPos === 0;
|
|
17328
|
+
displayLines.push({
|
|
17329
|
+
text: isFirstSegmentOfLine && !isFirstLineOfEntry ? linePrefix + segment : segment,
|
|
17330
|
+
level,
|
|
17331
|
+
indent: !isFirstLineOfEntry || !isFirstSegmentOfLine
|
|
17332
|
+
});
|
|
17333
|
+
currentPos += availableWidth;
|
|
17334
|
+
if (isFirstLineOfEntry && currentPos === 0 && textToWrap.length === 0)
|
|
17335
|
+
break;
|
|
17336
|
+
}
|
|
17337
|
+
}
|
|
17338
|
+
return displayLines;
|
|
17339
|
+
}
|
|
17340
|
+
_processCachedLogs() {
|
|
17341
|
+
const logsToProcess = [...terminalConsoleCache.cachedLogs];
|
|
17342
|
+
terminalConsoleCache.clearConsole();
|
|
17343
|
+
this._allLogEntries.push(...logsToProcess);
|
|
16354
17344
|
if (this._allLogEntries.length > this.options.maxStoredLogs) {
|
|
16355
17345
|
this._allLogEntries.splice(0, this._allLogEntries.length - this.options.maxStoredLogs);
|
|
16356
17346
|
}
|
|
16357
|
-
const
|
|
16358
|
-
|
|
17347
|
+
for (const logEntry of logsToProcess) {
|
|
17348
|
+
const processed = this._processLogEntry(logEntry);
|
|
17349
|
+
this._displayLines.push(...processed);
|
|
17350
|
+
}
|
|
16359
17351
|
if (this._displayLines.length > this.options.maxDisplayLines) {
|
|
16360
17352
|
this._displayLines.splice(0, this._displayLines.length - this.options.maxDisplayLines);
|
|
16361
|
-
const linesRemoved = this._displayLines.length - this.options.maxDisplayLines;
|
|
16362
|
-
this.scrollTopIndex = Math.max(0, this.scrollTopIndex - linesRemoved);
|
|
16363
17353
|
}
|
|
16364
|
-
|
|
16365
|
-
|
|
17354
|
+
}
|
|
17355
|
+
hasSelection() {
|
|
17356
|
+
if (this._selectionStart === null || this._selectionEnd === null)
|
|
17357
|
+
return false;
|
|
17358
|
+
return this._selectionStart.line !== this._selectionEnd.line || this._selectionStart.col !== this._selectionEnd.col;
|
|
17359
|
+
}
|
|
17360
|
+
normalizeSelection() {
|
|
17361
|
+
if (!this._selectionStart || !this._selectionEnd)
|
|
17362
|
+
return null;
|
|
17363
|
+
const start = this._selectionStart;
|
|
17364
|
+
const end = this._selectionEnd;
|
|
17365
|
+
const startBeforeEnd = start.line < end.line || start.line === end.line && start.col <= end.col;
|
|
17366
|
+
if (startBeforeEnd) {
|
|
17367
|
+
return {
|
|
17368
|
+
startLine: start.line,
|
|
17369
|
+
startCol: start.col,
|
|
17370
|
+
endLine: end.line,
|
|
17371
|
+
endCol: end.col
|
|
17372
|
+
};
|
|
17373
|
+
} else {
|
|
17374
|
+
return {
|
|
17375
|
+
startLine: end.line,
|
|
17376
|
+
startCol: end.col,
|
|
17377
|
+
endLine: start.line,
|
|
17378
|
+
endCol: start.col
|
|
17379
|
+
};
|
|
16366
17380
|
}
|
|
16367
|
-
this.markNeedsRerender();
|
|
16368
17381
|
}
|
|
16369
|
-
|
|
16370
|
-
const
|
|
16371
|
-
|
|
16372
|
-
|
|
16373
|
-
|
|
16374
|
-
|
|
16375
|
-
|
|
16376
|
-
|
|
16377
|
-
|
|
16378
|
-
|
|
16379
|
-
|
|
16380
|
-
|
|
16381
|
-
|
|
16382
|
-
|
|
16383
|
-
|
|
16384
|
-
|
|
16385
|
-
|
|
16386
|
-
|
|
16387
|
-
|
|
16388
|
-
|
|
16389
|
-
|
|
16390
|
-
this.consoleY = 0;
|
|
16391
|
-
break;
|
|
16392
|
-
case "right" /* RIGHT */:
|
|
16393
|
-
this.consoleWidth = Math.max(1, Math.floor(width * sizePercent));
|
|
16394
|
-
this.consoleHeight = height;
|
|
16395
|
-
this.consoleY = 0;
|
|
16396
|
-
this.consoleX = width - this.consoleWidth;
|
|
16397
|
-
break;
|
|
17382
|
+
getSelectedText() {
|
|
17383
|
+
const selection2 = this.normalizeSelection();
|
|
17384
|
+
if (!selection2)
|
|
17385
|
+
return "";
|
|
17386
|
+
const lines = [];
|
|
17387
|
+
for (let i = selection2.startLine;i <= selection2.endLine; i++) {
|
|
17388
|
+
if (i < 0 || i >= this._displayLines.length)
|
|
17389
|
+
continue;
|
|
17390
|
+
const line = this._displayLines[i];
|
|
17391
|
+
const linePrefix = line.indent ? " ".repeat(INDENT_WIDTH) : "";
|
|
17392
|
+
const textAvailableWidth = this.consoleWidth - 1 - (line.indent ? INDENT_WIDTH : 0);
|
|
17393
|
+
const fullText = linePrefix + line.text.substring(0, textAvailableWidth);
|
|
17394
|
+
let text = fullText;
|
|
17395
|
+
if (i === selection2.startLine && i === selection2.endLine) {
|
|
17396
|
+
text = fullText.substring(selection2.startCol, selection2.endCol);
|
|
17397
|
+
} else if (i === selection2.startLine) {
|
|
17398
|
+
text = fullText.substring(selection2.startCol);
|
|
17399
|
+
} else if (i === selection2.endLine) {
|
|
17400
|
+
text = fullText.substring(0, selection2.endCol);
|
|
17401
|
+
}
|
|
17402
|
+
lines.push(text);
|
|
16398
17403
|
}
|
|
16399
|
-
|
|
17404
|
+
return lines.join(`
|
|
17405
|
+
`);
|
|
16400
17406
|
}
|
|
16401
|
-
|
|
16402
|
-
|
|
16403
|
-
|
|
16404
|
-
|
|
17407
|
+
clearSelection() {
|
|
17408
|
+
this._selectionStart = null;
|
|
17409
|
+
this._selectionEnd = null;
|
|
17410
|
+
this._isDragging = false;
|
|
17411
|
+
this.stopAutoScroll();
|
|
17412
|
+
}
|
|
17413
|
+
stopAutoScroll() {
|
|
17414
|
+
if (this._autoScrollInterval !== null) {
|
|
17415
|
+
this.clock.clearInterval(this._autoScrollInterval);
|
|
17416
|
+
this._autoScrollInterval = null;
|
|
16405
17417
|
}
|
|
16406
|
-
|
|
16407
|
-
|
|
16408
|
-
|
|
16409
|
-
|
|
16410
|
-
|
|
16411
|
-
|
|
16412
|
-
|
|
16413
|
-
|
|
16414
|
-
|
|
16415
|
-
|
|
16416
|
-
|
|
16417
|
-
|
|
16418
|
-
|
|
16419
|
-
|
|
17418
|
+
}
|
|
17419
|
+
startAutoScroll(direction) {
|
|
17420
|
+
this.stopAutoScroll();
|
|
17421
|
+
this._autoScrollInterval = this.clock.setInterval(() => {
|
|
17422
|
+
if (direction === "up") {
|
|
17423
|
+
if (this.scrollTopIndex > 0) {
|
|
17424
|
+
this.scrollTopIndex--;
|
|
17425
|
+
this.isScrolledToBottom = false;
|
|
17426
|
+
if (this._selectionEnd) {
|
|
17427
|
+
this._selectionEnd = {
|
|
17428
|
+
line: this.scrollTopIndex,
|
|
17429
|
+
col: this._selectionEnd.col
|
|
17430
|
+
};
|
|
17431
|
+
}
|
|
17432
|
+
this.markNeedsRerender();
|
|
17433
|
+
} else {
|
|
17434
|
+
this.stopAutoScroll();
|
|
17435
|
+
}
|
|
17436
|
+
} else {
|
|
17437
|
+
const displayLineCount = this._displayLines.length;
|
|
17438
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
17439
|
+
const maxScrollTop = Math.max(0, displayLineCount - logAreaHeight);
|
|
17440
|
+
if (this.scrollTopIndex < maxScrollTop) {
|
|
17441
|
+
this.scrollTopIndex++;
|
|
17442
|
+
this.isScrolledToBottom = this.scrollTopIndex === maxScrollTop;
|
|
17443
|
+
if (this._selectionEnd) {
|
|
17444
|
+
const maxLine = this.scrollTopIndex + logAreaHeight - 1;
|
|
17445
|
+
this._selectionEnd = {
|
|
17446
|
+
line: Math.min(maxLine, displayLineCount - 1),
|
|
17447
|
+
col: this._selectionEnd.col
|
|
17448
|
+
};
|
|
17449
|
+
}
|
|
17450
|
+
this.markNeedsRerender();
|
|
17451
|
+
} else {
|
|
17452
|
+
this.stopAutoScroll();
|
|
17453
|
+
}
|
|
16420
17454
|
}
|
|
16421
|
-
}
|
|
17455
|
+
}, 50);
|
|
16422
17456
|
}
|
|
16423
|
-
|
|
16424
|
-
|
|
16425
|
-
|
|
16426
|
-
|
|
16427
|
-
|
|
16428
|
-
|
|
16429
|
-
|
|
16430
|
-
|
|
17457
|
+
triggerCopy() {
|
|
17458
|
+
if (!this.hasSelection())
|
|
17459
|
+
return;
|
|
17460
|
+
const text = this.getSelectedText();
|
|
17461
|
+
if (text && this.options.onCopySelection) {
|
|
17462
|
+
try {
|
|
17463
|
+
this.options.onCopySelection(text);
|
|
17464
|
+
} catch {}
|
|
17465
|
+
this.clearSelection();
|
|
16431
17466
|
this.markNeedsRerender();
|
|
16432
17467
|
}
|
|
16433
|
-
return true;
|
|
16434
17468
|
}
|
|
16435
|
-
|
|
16436
|
-
const
|
|
16437
|
-
|
|
16438
|
-
|
|
16439
|
-
|
|
16440
|
-
|
|
16441
|
-
this.currentLineIndex++;
|
|
16442
|
-
this.markNeedsRerender();
|
|
16443
|
-
} else if (this.scrollTopIndex < maxScrollTop) {
|
|
16444
|
-
this.scrollTopIndex++;
|
|
16445
|
-
this.isScrolledToBottom = this.scrollTopIndex === maxScrollTop;
|
|
16446
|
-
this.markNeedsRerender();
|
|
17469
|
+
getLineSelectionRange(lineIndex) {
|
|
17470
|
+
const selection2 = this.normalizeSelection();
|
|
17471
|
+
if (!selection2)
|
|
17472
|
+
return null;
|
|
17473
|
+
if (lineIndex < selection2.startLine || lineIndex > selection2.endLine) {
|
|
17474
|
+
return null;
|
|
16447
17475
|
}
|
|
16448
|
-
|
|
17476
|
+
const line = this._displayLines[lineIndex];
|
|
17477
|
+
if (!line)
|
|
17478
|
+
return null;
|
|
17479
|
+
const linePrefix = line.indent ? " ".repeat(INDENT_WIDTH) : "";
|
|
17480
|
+
const textAvailableWidth = this.consoleWidth - 1 - (line.indent ? INDENT_WIDTH : 0);
|
|
17481
|
+
const fullTextLength = linePrefix.length + Math.min(line.text.length, textAvailableWidth);
|
|
17482
|
+
let start = 0;
|
|
17483
|
+
let end = fullTextLength;
|
|
17484
|
+
if (lineIndex === selection2.startLine) {
|
|
17485
|
+
start = Math.max(0, selection2.startCol);
|
|
17486
|
+
}
|
|
17487
|
+
if (lineIndex === selection2.endLine) {
|
|
17488
|
+
end = Math.min(fullTextLength, selection2.endCol);
|
|
17489
|
+
}
|
|
17490
|
+
if (start >= end)
|
|
17491
|
+
return null;
|
|
17492
|
+
return { start, end };
|
|
16449
17493
|
}
|
|
16450
|
-
|
|
16451
|
-
if (this.
|
|
16452
|
-
|
|
16453
|
-
|
|
16454
|
-
|
|
17494
|
+
handleMouse(event) {
|
|
17495
|
+
if (!this.isVisible)
|
|
17496
|
+
return false;
|
|
17497
|
+
const localX = event.x - this.consoleX;
|
|
17498
|
+
const localY = event.y - this.consoleY;
|
|
17499
|
+
if (localX < 0 || localX >= this.consoleWidth || localY < 0 || localY >= this.consoleHeight) {
|
|
17500
|
+
return false;
|
|
17501
|
+
}
|
|
17502
|
+
if (event.type === "scroll" && event.scroll) {
|
|
17503
|
+
if (event.scroll.direction === "up") {
|
|
17504
|
+
this.scrollUp();
|
|
17505
|
+
} else if (event.scroll.direction === "down") {
|
|
17506
|
+
this.scrollDown();
|
|
17507
|
+
}
|
|
17508
|
+
return true;
|
|
17509
|
+
}
|
|
17510
|
+
if (localY === 0) {
|
|
17511
|
+
if (event.type === "down" && event.button === 0 && localX >= this._copyButtonBounds.x && localX < this._copyButtonBounds.x + this._copyButtonBounds.width) {
|
|
17512
|
+
this.triggerCopy();
|
|
17513
|
+
return true;
|
|
17514
|
+
}
|
|
17515
|
+
return true;
|
|
17516
|
+
}
|
|
17517
|
+
const lineIndex = this.scrollTopIndex + (localY - 1);
|
|
17518
|
+
const colIndex = Math.max(0, localX - 1);
|
|
17519
|
+
if (event.type === "down" && event.button === 0) {
|
|
17520
|
+
this.clearSelection();
|
|
17521
|
+
this._selectionStart = { line: lineIndex, col: colIndex };
|
|
17522
|
+
this._selectionEnd = { line: lineIndex, col: colIndex };
|
|
17523
|
+
this._isDragging = true;
|
|
16455
17524
|
this.markNeedsRerender();
|
|
17525
|
+
return true;
|
|
16456
17526
|
}
|
|
16457
|
-
|
|
16458
|
-
|
|
16459
|
-
|
|
16460
|
-
|
|
16461
|
-
|
|
16462
|
-
|
|
16463
|
-
|
|
17527
|
+
if (event.type === "drag" && this._isDragging) {
|
|
17528
|
+
this._selectionEnd = { line: lineIndex, col: colIndex };
|
|
17529
|
+
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
17530
|
+
const relativeY = localY - 1;
|
|
17531
|
+
if (relativeY <= 0) {
|
|
17532
|
+
this.startAutoScroll("up");
|
|
17533
|
+
} else if (relativeY >= logAreaHeight - 1) {
|
|
17534
|
+
this.startAutoScroll("down");
|
|
17535
|
+
} else {
|
|
17536
|
+
this.stopAutoScroll();
|
|
17537
|
+
}
|
|
16464
17538
|
this.markNeedsRerender();
|
|
17539
|
+
return true;
|
|
17540
|
+
}
|
|
17541
|
+
if (event.type === "up") {
|
|
17542
|
+
if (this._isDragging) {
|
|
17543
|
+
this._selectionEnd = { line: lineIndex, col: colIndex };
|
|
17544
|
+
this._isDragging = false;
|
|
17545
|
+
this.stopAutoScroll();
|
|
17546
|
+
this.markNeedsRerender();
|
|
17547
|
+
}
|
|
17548
|
+
return true;
|
|
16465
17549
|
}
|
|
16466
17550
|
return true;
|
|
16467
17551
|
}
|
|
16468
|
-
|
|
16469
|
-
|
|
16470
|
-
const prevIndex = (currentPositionIndex - 1 + this._positions.length) % this._positions.length;
|
|
16471
|
-
this.options.position = this._positions[prevIndex];
|
|
16472
|
-
this.resize(this.renderer.width, this.renderer.height);
|
|
16473
|
-
return true;
|
|
16474
|
-
}
|
|
16475
|
-
positionNext() {
|
|
16476
|
-
const currentPositionIndex = this._positions.indexOf(this.options.position);
|
|
16477
|
-
const nextIndex = (currentPositionIndex + 1) % this._positions.length;
|
|
16478
|
-
this.options.position = this._positions[nextIndex];
|
|
16479
|
-
this.resize(this.renderer.width, this.renderer.height);
|
|
16480
|
-
return true;
|
|
16481
|
-
}
|
|
16482
|
-
sizeIncrease() {
|
|
16483
|
-
this.options.sizePercent = Math.min(100, this.options.sizePercent + 5);
|
|
16484
|
-
this.resize(this.renderer.width, this.renderer.height);
|
|
16485
|
-
return true;
|
|
16486
|
-
}
|
|
16487
|
-
sizeDecrease() {
|
|
16488
|
-
this.options.sizePercent = Math.max(10, this.options.sizePercent - 5);
|
|
16489
|
-
this.resize(this.renderer.width, this.renderer.height);
|
|
16490
|
-
return true;
|
|
16491
|
-
}
|
|
16492
|
-
saveLogsAction() {
|
|
16493
|
-
this.saveLogsToFile();
|
|
16494
|
-
return true;
|
|
16495
|
-
}
|
|
16496
|
-
triggerCopyAction() {
|
|
16497
|
-
this.triggerCopy();
|
|
16498
|
-
return true;
|
|
16499
|
-
}
|
|
16500
|
-
attachStdin() {
|
|
16501
|
-
if (this.isFocused)
|
|
16502
|
-
return;
|
|
16503
|
-
this.renderer.keyInput.on("keypress", this.keyHandler);
|
|
16504
|
-
this.isFocused = true;
|
|
16505
|
-
}
|
|
16506
|
-
detachStdin() {
|
|
16507
|
-
if (!this.isFocused)
|
|
16508
|
-
return;
|
|
16509
|
-
this.renderer.keyInput.off("keypress", this.keyHandler);
|
|
16510
|
-
this.isFocused = false;
|
|
17552
|
+
get visible() {
|
|
17553
|
+
return this.isVisible;
|
|
16511
17554
|
}
|
|
16512
|
-
|
|
16513
|
-
return
|
|
16514
|
-
|
|
16515
|
-
|
|
16516
|
-
|
|
16517
|
-
|
|
16518
|
-
}
|
|
17555
|
+
get bounds() {
|
|
17556
|
+
return {
|
|
17557
|
+
x: this.consoleX,
|
|
17558
|
+
y: this.consoleY,
|
|
17559
|
+
width: this.consoleWidth,
|
|
17560
|
+
height: this.consoleHeight
|
|
17561
|
+
};
|
|
16519
17562
|
}
|
|
16520
|
-
|
|
16521
|
-
|
|
16522
|
-
|
|
16523
|
-
|
|
16524
|
-
|
|
16525
|
-
|
|
16526
|
-
|
|
16527
|
-
|
|
16528
|
-
|
|
16529
|
-
|
|
16530
|
-
|
|
16531
|
-
|
|
16532
|
-
|
|
16533
|
-
}
|
|
16534
|
-
}
|
|
16535
|
-
try {
|
|
16536
|
-
return util2.inspect(arg, { depth: 2 });
|
|
16537
|
-
} catch (e) {
|
|
16538
|
-
return String(arg);
|
|
17563
|
+
saveLogsToFile() {
|
|
17564
|
+
try {
|
|
17565
|
+
const timestamp = Date.now();
|
|
17566
|
+
const filename = `_console_${timestamp}.log`;
|
|
17567
|
+
const filepath = path5.join(process.cwd(), filename);
|
|
17568
|
+
const allLogEntries = [...this._allLogEntries, ...terminalConsoleCache.cachedLogs];
|
|
17569
|
+
const logLines = [];
|
|
17570
|
+
for (const [date, level, args, callerInfo] of allLogEntries) {
|
|
17571
|
+
const timestampStr = this.formatTimestamp(date);
|
|
17572
|
+
const callerSource = callerInfo ? `${callerInfo.fileName}:${callerInfo.lineNumber}` : "unknown";
|
|
17573
|
+
const prefix = `[${timestampStr}] [${level}]` + (this._debugModeEnabled ? ` [${callerSource}]` : "") + " ";
|
|
17574
|
+
const formattedArgs = this.formatArguments(args);
|
|
17575
|
+
logLines.push(prefix + formattedArgs);
|
|
16539
17576
|
}
|
|
16540
|
-
|
|
17577
|
+
const content = logLines.join(`
|
|
17578
|
+
`);
|
|
17579
|
+
fs.writeFileSync(filepath, content, "utf8");
|
|
17580
|
+
console.info(`Console logs saved to: ${filename}`);
|
|
17581
|
+
} catch (error) {
|
|
17582
|
+
console.error(`Failed to save console logs:`, error);
|
|
17583
|
+
}
|
|
16541
17584
|
}
|
|
16542
|
-
|
|
16543
|
-
|
|
16544
|
-
|
|
16545
|
-
|
|
16546
|
-
|
|
16547
|
-
|
|
16548
|
-
|
|
16549
|
-
|
|
16550
|
-
|
|
16551
|
-
|
|
16552
|
-
|
|
16553
|
-
|
|
16554
|
-
|
|
17585
|
+
}
|
|
17586
|
+
|
|
17587
|
+
// src/renderables/EditBufferRenderable.ts
|
|
17588
|
+
var BrandedEditBufferRenderable = Symbol.for("@opentui/core/EditBufferRenderable");
|
|
17589
|
+
var EditBufferRenderableEvents;
|
|
17590
|
+
((EditBufferRenderableEvents2) => {
|
|
17591
|
+
EditBufferRenderableEvents2["TRAITS_CHANGED"] = "traits-changed";
|
|
17592
|
+
})(EditBufferRenderableEvents ||= {});
|
|
17593
|
+
function sameCapture(a, b) {
|
|
17594
|
+
if (a === b)
|
|
17595
|
+
return true;
|
|
17596
|
+
if (!a || !b)
|
|
17597
|
+
return !a && !b;
|
|
17598
|
+
if (a.length !== b.length)
|
|
17599
|
+
return false;
|
|
17600
|
+
return a.every((item, i) => item === b[i]);
|
|
17601
|
+
}
|
|
17602
|
+
function sameTraits(a, b) {
|
|
17603
|
+
return a.suspend === b.suspend && a.status === b.status && sameCapture(a.capture, b.capture);
|
|
17604
|
+
}
|
|
17605
|
+
function isEditBufferRenderable(obj) {
|
|
17606
|
+
return !!(obj && typeof obj === "object" && (BrandedEditBufferRenderable in obj));
|
|
17607
|
+
}
|
|
17608
|
+
|
|
17609
|
+
class EditBufferRenderable extends Renderable {
|
|
17610
|
+
[BrandedEditBufferRenderable] = true;
|
|
17611
|
+
_focusable = true;
|
|
17612
|
+
selectable = true;
|
|
17613
|
+
_traits = {};
|
|
17614
|
+
_textColor;
|
|
17615
|
+
_backgroundColor;
|
|
17616
|
+
_defaultAttributes;
|
|
17617
|
+
_selectionBg;
|
|
17618
|
+
_selectionFg;
|
|
17619
|
+
_wrapMode = "word";
|
|
17620
|
+
_scrollMargin = 0.2;
|
|
17621
|
+
_showCursor = true;
|
|
17622
|
+
_cursorColor;
|
|
17623
|
+
_cursorStyle;
|
|
17624
|
+
lastLocalSelection = null;
|
|
17625
|
+
_tabIndicator;
|
|
17626
|
+
_tabIndicatorColor;
|
|
17627
|
+
_cursorChangeListener = undefined;
|
|
17628
|
+
_contentChangeListener = undefined;
|
|
17629
|
+
_autoScrollVelocity = 0;
|
|
17630
|
+
_autoScrollAccumulator = 0;
|
|
17631
|
+
_scrollSpeed = 16;
|
|
17632
|
+
_keyboardSelectionActive = false;
|
|
17633
|
+
editBuffer;
|
|
17634
|
+
editorView;
|
|
17635
|
+
_defaultOptions = {
|
|
17636
|
+
textColor: RGBA.fromValues(1, 1, 1, 1),
|
|
17637
|
+
backgroundColor: "transparent",
|
|
17638
|
+
selectionBg: undefined,
|
|
17639
|
+
selectionFg: undefined,
|
|
17640
|
+
selectable: true,
|
|
17641
|
+
attributes: 0,
|
|
17642
|
+
wrapMode: "word",
|
|
17643
|
+
scrollMargin: 0.2,
|
|
17644
|
+
scrollSpeed: 16,
|
|
17645
|
+
showCursor: true,
|
|
17646
|
+
cursorColor: RGBA.fromValues(1, 1, 1, 1),
|
|
17647
|
+
cursorStyle: {
|
|
17648
|
+
style: "block",
|
|
17649
|
+
blinking: true
|
|
17650
|
+
},
|
|
17651
|
+
tabIndicator: undefined,
|
|
17652
|
+
tabIndicatorColor: undefined
|
|
17653
|
+
};
|
|
17654
|
+
constructor(ctx, options) {
|
|
17655
|
+
super(ctx, options);
|
|
17656
|
+
this._textColor = parseColor(options.textColor ?? this._defaultOptions.textColor);
|
|
17657
|
+
this._backgroundColor = parseColor(options.backgroundColor ?? this._defaultOptions.backgroundColor);
|
|
17658
|
+
this._defaultAttributes = options.attributes ?? this._defaultOptions.attributes;
|
|
17659
|
+
this._selectionBg = options.selectionBg ? parseColor(options.selectionBg) : this._defaultOptions.selectionBg;
|
|
17660
|
+
this._selectionFg = options.selectionFg ? parseColor(options.selectionFg) : this._defaultOptions.selectionFg;
|
|
17661
|
+
this.selectable = options.selectable ?? this._defaultOptions.selectable;
|
|
17662
|
+
this._wrapMode = options.wrapMode ?? this._defaultOptions.wrapMode;
|
|
17663
|
+
this._scrollMargin = options.scrollMargin ?? this._defaultOptions.scrollMargin;
|
|
17664
|
+
this._scrollSpeed = options.scrollSpeed ?? this._defaultOptions.scrollSpeed;
|
|
17665
|
+
this._showCursor = options.showCursor ?? this._defaultOptions.showCursor;
|
|
17666
|
+
this._cursorColor = parseColor(options.cursorColor ?? this._defaultOptions.cursorColor);
|
|
17667
|
+
this._cursorStyle = options.cursorStyle ?? this._defaultOptions.cursorStyle;
|
|
17668
|
+
this._tabIndicator = options.tabIndicator ?? this._defaultOptions.tabIndicator;
|
|
17669
|
+
this._tabIndicatorColor = options.tabIndicatorColor ? parseColor(options.tabIndicatorColor) : this._defaultOptions.tabIndicatorColor;
|
|
17670
|
+
this.editBuffer = EditBuffer.create(this._ctx.widthMethod);
|
|
17671
|
+
this.editorView = EditorView.create(this.editBuffer, this.width || 80, this.height || 24);
|
|
17672
|
+
this.editorView.setWrapMode(this._wrapMode);
|
|
17673
|
+
this.editorView.setScrollMargin(this._scrollMargin);
|
|
17674
|
+
this.editBuffer.setDefaultFg(this._textColor);
|
|
17675
|
+
this.editBuffer.setDefaultBg(this._backgroundColor);
|
|
17676
|
+
this.editBuffer.setDefaultAttributes(this._defaultAttributes);
|
|
17677
|
+
if (options.syntaxStyle) {
|
|
17678
|
+
this.editBuffer.setSyntaxStyle(options.syntaxStyle);
|
|
17679
|
+
}
|
|
17680
|
+
if (this._tabIndicator !== undefined) {
|
|
17681
|
+
this.editorView.setTabIndicator(this._tabIndicator);
|
|
17682
|
+
}
|
|
17683
|
+
if (this._tabIndicatorColor !== undefined) {
|
|
17684
|
+
this.editorView.setTabIndicatorColor(this._tabIndicatorColor);
|
|
17685
|
+
}
|
|
17686
|
+
this.setupMeasureFunc();
|
|
17687
|
+
this.setupEventListeners(options);
|
|
17688
|
+
}
|
|
17689
|
+
get lineInfo() {
|
|
17690
|
+
return this.editorView.getLogicalLineInfo();
|
|
17691
|
+
}
|
|
17692
|
+
setupEventListeners(options) {
|
|
17693
|
+
this._cursorChangeListener = options.onCursorChange;
|
|
17694
|
+
this._contentChangeListener = options.onContentChange;
|
|
17695
|
+
this.editBuffer.on("cursor-changed", () => {
|
|
17696
|
+
if (this._cursorChangeListener) {
|
|
17697
|
+
const cursor = this.editBuffer.getCursorPosition();
|
|
17698
|
+
this._cursorChangeListener({
|
|
17699
|
+
line: cursor.row,
|
|
17700
|
+
visualColumn: cursor.col
|
|
17701
|
+
});
|
|
16555
17702
|
}
|
|
16556
|
-
}
|
|
17703
|
+
});
|
|
17704
|
+
this.editBuffer.on("content-changed", () => {
|
|
17705
|
+
this.yogaNode.markDirty();
|
|
17706
|
+
this.requestRender();
|
|
17707
|
+
this.emit("line-info-change");
|
|
17708
|
+
if (this._contentChangeListener) {
|
|
17709
|
+
this._contentChangeListener({});
|
|
17710
|
+
}
|
|
17711
|
+
});
|
|
16557
17712
|
}
|
|
16558
|
-
|
|
16559
|
-
|
|
16560
|
-
this._allLogEntries = [];
|
|
16561
|
-
this._displayLines = [];
|
|
16562
|
-
this.markNeedsRerender();
|
|
17713
|
+
get lineCount() {
|
|
17714
|
+
return this.editBuffer.getLineCount();
|
|
16563
17715
|
}
|
|
16564
|
-
|
|
16565
|
-
|
|
16566
|
-
if (this.isFocused) {
|
|
16567
|
-
this.hide();
|
|
16568
|
-
} else {
|
|
16569
|
-
this.focus();
|
|
16570
|
-
}
|
|
16571
|
-
} else {
|
|
16572
|
-
this.show();
|
|
16573
|
-
}
|
|
16574
|
-
if (!this.renderer.isRunning) {
|
|
16575
|
-
this.renderer.requestRender();
|
|
16576
|
-
}
|
|
17716
|
+
get virtualLineCount() {
|
|
17717
|
+
return this.editorView.getVirtualLineCount();
|
|
16577
17718
|
}
|
|
16578
|
-
|
|
16579
|
-
this.
|
|
16580
|
-
this._scrollToBottom(true);
|
|
16581
|
-
this.markNeedsRerender();
|
|
17719
|
+
get scrollY() {
|
|
17720
|
+
return this.editorView.getViewport().offsetY;
|
|
16582
17721
|
}
|
|
16583
|
-
|
|
16584
|
-
this.
|
|
16585
|
-
this.markNeedsRerender();
|
|
17722
|
+
get plainText() {
|
|
17723
|
+
return this.editBuffer.getText();
|
|
16586
17724
|
}
|
|
16587
|
-
|
|
16588
|
-
|
|
16589
|
-
|
|
16590
|
-
|
|
16591
|
-
|
|
16592
|
-
|
|
16593
|
-
|
|
16594
|
-
|
|
16595
|
-
|
|
16596
|
-
|
|
16597
|
-
|
|
16598
|
-
|
|
16599
|
-
|
|
16600
|
-
|
|
16601
|
-
|
|
16602
|
-
|
|
16603
|
-
|
|
16604
|
-
|
|
17725
|
+
get logicalCursor() {
|
|
17726
|
+
return this.editBuffer.getCursorPosition();
|
|
17727
|
+
}
|
|
17728
|
+
get visualCursor() {
|
|
17729
|
+
return this.editorView.getVisualCursor();
|
|
17730
|
+
}
|
|
17731
|
+
get cursorOffset() {
|
|
17732
|
+
return this.editorView.getVisualCursor().offset;
|
|
17733
|
+
}
|
|
17734
|
+
set cursorOffset(offset) {
|
|
17735
|
+
this.editorView.setCursorByOffset(offset);
|
|
17736
|
+
this.requestRender();
|
|
17737
|
+
}
|
|
17738
|
+
get cursorCharacterOffset() {
|
|
17739
|
+
const len = this.plainText.length;
|
|
17740
|
+
if (len <= 0)
|
|
17741
|
+
return;
|
|
17742
|
+
const cursor = this.logicalCursor;
|
|
17743
|
+
const offset = this.cursorOffset;
|
|
17744
|
+
if (offset >= len) {
|
|
17745
|
+
if (cursor.col > 0)
|
|
17746
|
+
return len - 1;
|
|
17747
|
+
return 0;
|
|
16605
17748
|
}
|
|
17749
|
+
if (this.plainText[offset] === `
|
|
17750
|
+
` && cursor.col > 0) {
|
|
17751
|
+
return offset - 1;
|
|
17752
|
+
}
|
|
17753
|
+
return offset;
|
|
16606
17754
|
}
|
|
16607
|
-
|
|
16608
|
-
|
|
16609
|
-
|
|
16610
|
-
|
|
16611
|
-
|
|
17755
|
+
get textColor() {
|
|
17756
|
+
return this._textColor;
|
|
17757
|
+
}
|
|
17758
|
+
set textColor(value) {
|
|
17759
|
+
const newColor = parseColor(value ?? this._defaultOptions.textColor);
|
|
17760
|
+
if (this._textColor !== newColor) {
|
|
17761
|
+
this._textColor = newColor;
|
|
17762
|
+
this.editBuffer.setDefaultFg(newColor);
|
|
17763
|
+
this.requestRender();
|
|
16612
17764
|
}
|
|
16613
17765
|
}
|
|
16614
|
-
|
|
16615
|
-
this.
|
|
16616
|
-
this.hide();
|
|
16617
|
-
this.deactivate();
|
|
16618
|
-
terminalConsoleCache.off("entry", this._entryListener);
|
|
17766
|
+
get selectionBg() {
|
|
17767
|
+
return this._selectionBg;
|
|
16619
17768
|
}
|
|
16620
|
-
|
|
16621
|
-
return
|
|
16622
|
-
`);
|
|
17769
|
+
get traits() {
|
|
17770
|
+
return this._traits;
|
|
16623
17771
|
}
|
|
16624
|
-
|
|
16625
|
-
if (
|
|
17772
|
+
set traits(value) {
|
|
17773
|
+
if (sameTraits(this._traits, value))
|
|
16626
17774
|
return;
|
|
16627
|
-
this.
|
|
16628
|
-
|
|
16629
|
-
|
|
16630
|
-
|
|
16631
|
-
|
|
16632
|
-
const
|
|
16633
|
-
|
|
16634
|
-
|
|
16635
|
-
|
|
16636
|
-
|
|
16637
|
-
if (copyButtonX >= 0) {
|
|
16638
|
-
const copyButtonEnabled = this.hasSelection();
|
|
16639
|
-
const disabledColor = RGBA.fromInts(100, 100, 100, 255);
|
|
16640
|
-
const copyColor = copyButtonEnabled ? this._rgbaCopyButton : disabledColor;
|
|
16641
|
-
this.frameBuffer.drawText(copyLabel, copyButtonX, 0, copyColor, this._rgbaTitleBar);
|
|
16642
|
-
this._copyButtonBounds = { x: copyButtonX, y: 0, width: copyLabel.length, height: 1 };
|
|
16643
|
-
} else {
|
|
16644
|
-
this._copyButtonBounds = { x: -1, y: -1, width: 0, height: 0 };
|
|
17775
|
+
const prev = this._traits;
|
|
17776
|
+
this._traits = value;
|
|
17777
|
+
this.emit("traits-changed" /* TRAITS_CHANGED */, value, prev);
|
|
17778
|
+
}
|
|
17779
|
+
set selectionBg(value) {
|
|
17780
|
+
const newColor = value ? parseColor(value) : this._defaultOptions.selectionBg;
|
|
17781
|
+
if (this._selectionBg !== newColor) {
|
|
17782
|
+
this._selectionBg = newColor;
|
|
17783
|
+
this.refreshSelectionStyle();
|
|
17784
|
+
this.requestRender();
|
|
16645
17785
|
}
|
|
16646
|
-
|
|
16647
|
-
|
|
16648
|
-
|
|
16649
|
-
|
|
16650
|
-
|
|
16651
|
-
|
|
16652
|
-
|
|
16653
|
-
|
|
16654
|
-
|
|
16655
|
-
|
|
16656
|
-
switch (displayLine.level) {
|
|
16657
|
-
case "INFO" /* INFO */:
|
|
16658
|
-
levelColor = this._rgbaInfo;
|
|
16659
|
-
break;
|
|
16660
|
-
case "WARN" /* WARN */:
|
|
16661
|
-
levelColor = this._rgbaWarn;
|
|
16662
|
-
break;
|
|
16663
|
-
case "ERROR" /* ERROR */:
|
|
16664
|
-
levelColor = this._rgbaError;
|
|
16665
|
-
break;
|
|
16666
|
-
case "DEBUG" /* DEBUG */:
|
|
16667
|
-
levelColor = this._rgbaDebug;
|
|
16668
|
-
break;
|
|
16669
|
-
}
|
|
16670
|
-
const linePrefix = displayLine.indent ? " ".repeat(INDENT_WIDTH) : "";
|
|
16671
|
-
const textToDraw = displayLine.text;
|
|
16672
|
-
const textAvailableWidth = this.consoleWidth - 1 - (displayLine.indent ? INDENT_WIDTH : 0);
|
|
16673
|
-
const showCursor = this.isFocused && lineY - 1 === this.currentLineIndex;
|
|
16674
|
-
if (showCursor) {
|
|
16675
|
-
this.frameBuffer.drawText(">", 0, lineY, this._rgbaCursor, this.backgroundColor);
|
|
16676
|
-
} else {
|
|
16677
|
-
this.frameBuffer.drawText(" ", 0, lineY, this._rgbaDefault, this.backgroundColor);
|
|
16678
|
-
}
|
|
16679
|
-
const fullText = `${linePrefix}${textToDraw.substring(0, textAvailableWidth)}`;
|
|
16680
|
-
const selectionRange = this.getLineSelectionRange(absoluteLineIndex);
|
|
16681
|
-
if (selectionRange) {
|
|
16682
|
-
const adjustedStart = Math.max(0, selectionRange.start);
|
|
16683
|
-
const adjustedEnd = Math.min(fullText.length, selectionRange.end);
|
|
16684
|
-
if (adjustedStart > 0) {
|
|
16685
|
-
this.frameBuffer.drawText(fullText.substring(0, adjustedStart), 1, lineY, levelColor);
|
|
16686
|
-
}
|
|
16687
|
-
if (adjustedStart < adjustedEnd) {
|
|
16688
|
-
this.frameBuffer.fillRect(1 + adjustedStart, lineY, adjustedEnd - adjustedStart, 1, this._rgbaSelection);
|
|
16689
|
-
this.frameBuffer.drawText(fullText.substring(adjustedStart, adjustedEnd), 1 + adjustedStart, lineY, levelColor, this._rgbaSelection);
|
|
16690
|
-
}
|
|
16691
|
-
if (adjustedEnd < fullText.length) {
|
|
16692
|
-
this.frameBuffer.drawText(fullText.substring(adjustedEnd), 1 + adjustedEnd, lineY, levelColor);
|
|
16693
|
-
}
|
|
16694
|
-
} else {
|
|
16695
|
-
this.frameBuffer.drawText(fullText, 1, lineY, levelColor);
|
|
16696
|
-
}
|
|
16697
|
-
lineY++;
|
|
17786
|
+
}
|
|
17787
|
+
get selectionFg() {
|
|
17788
|
+
return this._selectionFg;
|
|
17789
|
+
}
|
|
17790
|
+
set selectionFg(value) {
|
|
17791
|
+
const newColor = value ? parseColor(value) : this._defaultOptions.selectionFg;
|
|
17792
|
+
if (this._selectionFg !== newColor) {
|
|
17793
|
+
this._selectionFg = newColor;
|
|
17794
|
+
this.refreshSelectionStyle();
|
|
17795
|
+
this.requestRender();
|
|
16698
17796
|
}
|
|
16699
17797
|
}
|
|
16700
|
-
|
|
16701
|
-
|
|
16702
|
-
|
|
16703
|
-
|
|
16704
|
-
|
|
16705
|
-
|
|
17798
|
+
get backgroundColor() {
|
|
17799
|
+
return this._backgroundColor;
|
|
17800
|
+
}
|
|
17801
|
+
set backgroundColor(value) {
|
|
17802
|
+
const newColor = parseColor(value ?? this._defaultOptions.backgroundColor);
|
|
17803
|
+
if (this._backgroundColor !== newColor) {
|
|
17804
|
+
this._backgroundColor = newColor;
|
|
17805
|
+
this.editBuffer.setDefaultBg(newColor);
|
|
17806
|
+
this.requestRender();
|
|
16706
17807
|
}
|
|
16707
|
-
buffer.drawFrameBuffer(this.consoleX, this.consoleY, this.frameBuffer);
|
|
16708
17808
|
}
|
|
16709
|
-
|
|
16710
|
-
this.
|
|
16711
|
-
|
|
16712
|
-
|
|
16713
|
-
|
|
17809
|
+
get attributes() {
|
|
17810
|
+
return this._defaultAttributes;
|
|
17811
|
+
}
|
|
17812
|
+
set attributes(value) {
|
|
17813
|
+
if (this._defaultAttributes !== value) {
|
|
17814
|
+
this._defaultAttributes = value;
|
|
17815
|
+
this.editBuffer.setDefaultAttributes(value);
|
|
17816
|
+
this.requestRender();
|
|
16714
17817
|
}
|
|
16715
17818
|
}
|
|
16716
|
-
|
|
16717
|
-
this.
|
|
17819
|
+
get wrapMode() {
|
|
17820
|
+
return this._wrapMode;
|
|
16718
17821
|
}
|
|
16719
|
-
set
|
|
16720
|
-
this.
|
|
16721
|
-
|
|
16722
|
-
|
|
16723
|
-
|
|
17822
|
+
set wrapMode(value) {
|
|
17823
|
+
if (this._wrapMode !== value) {
|
|
17824
|
+
this._wrapMode = value;
|
|
17825
|
+
this.editorView.setWrapMode(value);
|
|
17826
|
+
this.yogaNode.markDirty();
|
|
17827
|
+
this.requestRender();
|
|
17828
|
+
}
|
|
16724
17829
|
}
|
|
16725
|
-
|
|
16726
|
-
this.
|
|
16727
|
-
this._mergedKeyBindings = mergeKeyBindings(defaultConsoleKeybindings, this._keyBindings);
|
|
16728
|
-
this._keyBindingsMap = buildKeyBindingsMap(this._mergedKeyBindings, this._keyAliasMap);
|
|
16729
|
-
this.markNeedsRerender();
|
|
17830
|
+
get showCursor() {
|
|
17831
|
+
return this._showCursor;
|
|
16730
17832
|
}
|
|
16731
|
-
set
|
|
16732
|
-
this.
|
|
17833
|
+
set showCursor(value) {
|
|
17834
|
+
if (this._showCursor !== value) {
|
|
17835
|
+
this._showCursor = value;
|
|
17836
|
+
if (!value && this._focused) {
|
|
17837
|
+
this._ctx.setCursorPosition(0, 0, false);
|
|
17838
|
+
}
|
|
17839
|
+
this.requestRender();
|
|
17840
|
+
}
|
|
16733
17841
|
}
|
|
16734
|
-
get
|
|
16735
|
-
return this.
|
|
17842
|
+
get cursorColor() {
|
|
17843
|
+
return this._cursorColor;
|
|
16736
17844
|
}
|
|
16737
|
-
|
|
16738
|
-
const
|
|
16739
|
-
|
|
16740
|
-
|
|
16741
|
-
|
|
16742
|
-
|
|
16743
|
-
|
|
16744
|
-
if (forceCursorToLastLine || this.currentLineIndex >= visibleLineCount) {
|
|
16745
|
-
this.currentLineIndex = Math.max(0, visibleLineCount - 1);
|
|
17845
|
+
set cursorColor(value) {
|
|
17846
|
+
const newColor = parseColor(value);
|
|
17847
|
+
if (this._cursorColor !== newColor) {
|
|
17848
|
+
this._cursorColor = newColor;
|
|
17849
|
+
if (this._focused) {
|
|
17850
|
+
this.requestRender();
|
|
17851
|
+
}
|
|
16746
17852
|
}
|
|
16747
17853
|
}
|
|
16748
|
-
|
|
16749
|
-
|
|
16750
|
-
|
|
16751
|
-
|
|
16752
|
-
const
|
|
16753
|
-
|
|
16754
|
-
|
|
16755
|
-
|
|
16756
|
-
|
|
16757
|
-
for (let i = 0;i < initialLines.length; i++) {
|
|
16758
|
-
const lineText = initialLines[i];
|
|
16759
|
-
const isFirstLineOfEntry = i === 0;
|
|
16760
|
-
const availableWidth = this.consoleWidth - 1 - (isFirstLineOfEntry ? 0 : INDENT_WIDTH);
|
|
16761
|
-
const linePrefix = isFirstLineOfEntry ? prefix : " ".repeat(INDENT_WIDTH);
|
|
16762
|
-
const textToWrap = isFirstLineOfEntry ? linePrefix + lineText : lineText;
|
|
16763
|
-
let currentPos = 0;
|
|
16764
|
-
while (currentPos < textToWrap.length || isFirstLineOfEntry && currentPos === 0 && textToWrap.length === 0) {
|
|
16765
|
-
const segment = textToWrap.substring(currentPos, currentPos + availableWidth);
|
|
16766
|
-
const isFirstSegmentOfLine = currentPos === 0;
|
|
16767
|
-
displayLines.push({
|
|
16768
|
-
text: isFirstSegmentOfLine && !isFirstLineOfEntry ? linePrefix + segment : segment,
|
|
16769
|
-
level,
|
|
16770
|
-
indent: !isFirstLineOfEntry || !isFirstSegmentOfLine
|
|
16771
|
-
});
|
|
16772
|
-
currentPos += availableWidth;
|
|
16773
|
-
if (isFirstLineOfEntry && currentPos === 0 && textToWrap.length === 0)
|
|
16774
|
-
break;
|
|
17854
|
+
get cursorStyle() {
|
|
17855
|
+
return this._cursorStyle;
|
|
17856
|
+
}
|
|
17857
|
+
set cursorStyle(style) {
|
|
17858
|
+
const newStyle = style;
|
|
17859
|
+
if (this.cursorStyle.style !== newStyle.style || this.cursorStyle.blinking !== newStyle.blinking) {
|
|
17860
|
+
this._cursorStyle = newStyle;
|
|
17861
|
+
if (this._focused) {
|
|
17862
|
+
this.requestRender();
|
|
16775
17863
|
}
|
|
16776
17864
|
}
|
|
16777
|
-
return displayLines;
|
|
16778
17865
|
}
|
|
16779
|
-
|
|
16780
|
-
|
|
16781
|
-
|
|
16782
|
-
|
|
16783
|
-
if (this.
|
|
16784
|
-
this.
|
|
17866
|
+
get tabIndicator() {
|
|
17867
|
+
return this._tabIndicator;
|
|
17868
|
+
}
|
|
17869
|
+
set tabIndicator(value) {
|
|
17870
|
+
if (this._tabIndicator !== value) {
|
|
17871
|
+
this._tabIndicator = value;
|
|
17872
|
+
if (value !== undefined) {
|
|
17873
|
+
this.editorView.setTabIndicator(value);
|
|
17874
|
+
}
|
|
17875
|
+
this.requestRender();
|
|
16785
17876
|
}
|
|
16786
|
-
|
|
16787
|
-
|
|
16788
|
-
|
|
17877
|
+
}
|
|
17878
|
+
get tabIndicatorColor() {
|
|
17879
|
+
return this._tabIndicatorColor;
|
|
17880
|
+
}
|
|
17881
|
+
set tabIndicatorColor(value) {
|
|
17882
|
+
const newColor = value ? parseColor(value) : undefined;
|
|
17883
|
+
if (this._tabIndicatorColor !== newColor) {
|
|
17884
|
+
this._tabIndicatorColor = newColor;
|
|
17885
|
+
if (newColor !== undefined) {
|
|
17886
|
+
this.editorView.setTabIndicatorColor(newColor);
|
|
17887
|
+
}
|
|
17888
|
+
this.requestRender();
|
|
17889
|
+
}
|
|
17890
|
+
}
|
|
17891
|
+
get scrollSpeed() {
|
|
17892
|
+
return this._scrollSpeed;
|
|
17893
|
+
}
|
|
17894
|
+
set scrollSpeed(value) {
|
|
17895
|
+
this._scrollSpeed = Math.max(0, value);
|
|
17896
|
+
}
|
|
17897
|
+
onMouseEvent(event) {
|
|
17898
|
+
if (event.type === "scroll") {
|
|
17899
|
+
this.handleScroll(event);
|
|
17900
|
+
}
|
|
17901
|
+
}
|
|
17902
|
+
handleScroll(event) {
|
|
17903
|
+
if (!event.scroll)
|
|
17904
|
+
return;
|
|
17905
|
+
const { direction, delta } = event.scroll;
|
|
17906
|
+
const viewport = this.editorView.getViewport();
|
|
17907
|
+
if (direction === "up") {
|
|
17908
|
+
const newOffsetY = Math.max(0, viewport.offsetY - delta);
|
|
17909
|
+
this.editorView.setViewport(viewport.offsetX, newOffsetY, viewport.width, viewport.height, true);
|
|
17910
|
+
this.requestRender();
|
|
17911
|
+
} else if (direction === "down") {
|
|
17912
|
+
const totalVirtualLines = this.editorView.getTotalVirtualLineCount();
|
|
17913
|
+
const maxOffsetY = Math.max(0, totalVirtualLines - viewport.height);
|
|
17914
|
+
const newOffsetY = Math.min(viewport.offsetY + delta, maxOffsetY);
|
|
17915
|
+
this.editorView.setViewport(viewport.offsetX, newOffsetY, viewport.width, viewport.height, true);
|
|
17916
|
+
this.requestRender();
|
|
17917
|
+
}
|
|
17918
|
+
if (this._wrapMode === "none") {
|
|
17919
|
+
if (direction === "left") {
|
|
17920
|
+
const newOffsetX = Math.max(0, viewport.offsetX - delta);
|
|
17921
|
+
this.editorView.setViewport(newOffsetX, viewport.offsetY, viewport.width, viewport.height, true);
|
|
17922
|
+
this.requestRender();
|
|
17923
|
+
} else if (direction === "right") {
|
|
17924
|
+
const newOffsetX = viewport.offsetX + delta;
|
|
17925
|
+
this.editorView.setViewport(newOffsetX, viewport.offsetY, viewport.width, viewport.height, true);
|
|
17926
|
+
this.requestRender();
|
|
17927
|
+
}
|
|
16789
17928
|
}
|
|
16790
|
-
|
|
16791
|
-
|
|
17929
|
+
}
|
|
17930
|
+
onResize(width, height) {
|
|
17931
|
+
this.editorView.setViewportSize(width, height);
|
|
17932
|
+
}
|
|
17933
|
+
refreshLocalSelection() {
|
|
17934
|
+
if (this.lastLocalSelection) {
|
|
17935
|
+
return this.updateLocalSelection(this.lastLocalSelection);
|
|
16792
17936
|
}
|
|
17937
|
+
return false;
|
|
16793
17938
|
}
|
|
16794
|
-
|
|
16795
|
-
if (
|
|
17939
|
+
updateLocalSelection(localSelection) {
|
|
17940
|
+
if (!localSelection?.isActive) {
|
|
17941
|
+
this.editorView.resetLocalSelection();
|
|
17942
|
+
return true;
|
|
17943
|
+
}
|
|
17944
|
+
return this.editorView.setLocalSelection(localSelection.anchorX, localSelection.anchorY, localSelection.focusX, localSelection.focusY, this._selectionBg, this._selectionFg, false);
|
|
17945
|
+
}
|
|
17946
|
+
shouldStartSelection(x, y) {
|
|
17947
|
+
if (!this.selectable)
|
|
16796
17948
|
return false;
|
|
16797
|
-
|
|
17949
|
+
const localX = x - this.x;
|
|
17950
|
+
const localY = y - this.y;
|
|
17951
|
+
return localX >= 0 && localX < this.width && localY >= 0 && localY < this.height;
|
|
16798
17952
|
}
|
|
16799
|
-
|
|
16800
|
-
|
|
16801
|
-
|
|
16802
|
-
const
|
|
16803
|
-
const
|
|
16804
|
-
|
|
16805
|
-
if (
|
|
16806
|
-
|
|
16807
|
-
|
|
16808
|
-
|
|
16809
|
-
|
|
16810
|
-
|
|
16811
|
-
};
|
|
17953
|
+
onSelectionChanged(selection2) {
|
|
17954
|
+
const localSelection = convertGlobalToLocalSelection(selection2, this.x, this.y);
|
|
17955
|
+
this.lastLocalSelection = localSelection;
|
|
17956
|
+
const updateCursor = true;
|
|
17957
|
+
const followCursor = this._keyboardSelectionActive;
|
|
17958
|
+
let changed;
|
|
17959
|
+
if (!localSelection?.isActive) {
|
|
17960
|
+
this._keyboardSelectionActive = false;
|
|
17961
|
+
this.editorView.resetLocalSelection();
|
|
17962
|
+
changed = true;
|
|
17963
|
+
} else if (selection2?.isStart) {
|
|
17964
|
+
changed = this.editorView.setLocalSelection(localSelection.anchorX, localSelection.anchorY, localSelection.focusX, localSelection.focusY, this._selectionBg, this._selectionFg, updateCursor, followCursor);
|
|
16812
17965
|
} else {
|
|
16813
|
-
|
|
16814
|
-
|
|
16815
|
-
|
|
16816
|
-
|
|
16817
|
-
|
|
16818
|
-
|
|
17966
|
+
changed = this.editorView.updateLocalSelection(localSelection.anchorX, localSelection.anchorY, localSelection.focusX, localSelection.focusY, this._selectionBg, this._selectionFg, updateCursor, followCursor);
|
|
17967
|
+
}
|
|
17968
|
+
if (changed && localSelection?.isActive && selection2?.isDragging) {
|
|
17969
|
+
const viewport = this.editorView.getViewport();
|
|
17970
|
+
const focusY = localSelection.focusY;
|
|
17971
|
+
const scrollMargin = Math.max(1, Math.floor(viewport.height * this._scrollMargin));
|
|
17972
|
+
if (focusY < scrollMargin) {
|
|
17973
|
+
this._autoScrollVelocity = -this._scrollSpeed;
|
|
17974
|
+
} else if (focusY >= viewport.height - scrollMargin) {
|
|
17975
|
+
this._autoScrollVelocity = this._scrollSpeed;
|
|
17976
|
+
} else {
|
|
17977
|
+
this._autoScrollVelocity = 0;
|
|
17978
|
+
}
|
|
17979
|
+
} else {
|
|
17980
|
+
this._keyboardSelectionActive = false;
|
|
17981
|
+
this._autoScrollVelocity = 0;
|
|
17982
|
+
this._autoScrollAccumulator = 0;
|
|
16819
17983
|
}
|
|
16820
|
-
|
|
16821
|
-
|
|
16822
|
-
|
|
16823
|
-
|
|
16824
|
-
|
|
16825
|
-
|
|
16826
|
-
|
|
16827
|
-
|
|
16828
|
-
|
|
16829
|
-
|
|
16830
|
-
const
|
|
16831
|
-
|
|
16832
|
-
|
|
16833
|
-
|
|
16834
|
-
|
|
16835
|
-
|
|
16836
|
-
|
|
16837
|
-
|
|
16838
|
-
|
|
16839
|
-
|
|
17984
|
+
if (changed) {
|
|
17985
|
+
this.requestRender();
|
|
17986
|
+
}
|
|
17987
|
+
return this.hasSelection();
|
|
17988
|
+
}
|
|
17989
|
+
onUpdate(deltaTime) {
|
|
17990
|
+
super.onUpdate(deltaTime);
|
|
17991
|
+
if (this._autoScrollVelocity !== 0 && this.hasSelection()) {
|
|
17992
|
+
const deltaSeconds = deltaTime / 1000;
|
|
17993
|
+
this._autoScrollAccumulator += this._autoScrollVelocity * deltaSeconds;
|
|
17994
|
+
const linesToScroll = Math.floor(Math.abs(this._autoScrollAccumulator));
|
|
17995
|
+
if (linesToScroll > 0) {
|
|
17996
|
+
const direction = this._autoScrollVelocity > 0 ? 1 : -1;
|
|
17997
|
+
const viewport = this.editorView.getViewport();
|
|
17998
|
+
const totalVirtualLines = this.editorView.getTotalVirtualLineCount();
|
|
17999
|
+
const maxOffsetY = Math.max(0, totalVirtualLines - viewport.height);
|
|
18000
|
+
const newOffsetY = Math.max(0, Math.min(viewport.offsetY + direction * linesToScroll, maxOffsetY));
|
|
18001
|
+
if (newOffsetY !== viewport.offsetY) {
|
|
18002
|
+
this.editorView.setViewport(viewport.offsetX, newOffsetY, viewport.width, viewport.height, false);
|
|
18003
|
+
this._ctx.requestSelectionUpdate();
|
|
18004
|
+
}
|
|
18005
|
+
this._autoScrollAccumulator -= direction * linesToScroll;
|
|
16840
18006
|
}
|
|
16841
|
-
lines.push(text);
|
|
16842
18007
|
}
|
|
16843
|
-
return lines.join(`
|
|
16844
|
-
`);
|
|
16845
18008
|
}
|
|
16846
|
-
|
|
16847
|
-
this.
|
|
16848
|
-
this._selectionEnd = null;
|
|
16849
|
-
this._isDragging = false;
|
|
16850
|
-
this.stopAutoScroll();
|
|
18009
|
+
getSelectedText() {
|
|
18010
|
+
return this.editorView.getSelectedText();
|
|
16851
18011
|
}
|
|
16852
|
-
|
|
16853
|
-
|
|
16854
|
-
|
|
16855
|
-
|
|
18012
|
+
hasSelection() {
|
|
18013
|
+
return this.editorView.hasSelection();
|
|
18014
|
+
}
|
|
18015
|
+
getSelection() {
|
|
18016
|
+
return this.editorView.getSelection();
|
|
18017
|
+
}
|
|
18018
|
+
refreshSelectionStyle() {
|
|
18019
|
+
if (this.lastLocalSelection) {
|
|
18020
|
+
this.updateLocalSelection(this.lastLocalSelection);
|
|
18021
|
+
return;
|
|
16856
18022
|
}
|
|
18023
|
+
const selection2 = this.getSelection();
|
|
18024
|
+
if (!selection2)
|
|
18025
|
+
return;
|
|
18026
|
+
this.editorView.setSelection(selection2.start, selection2.end, this._selectionBg, this._selectionFg);
|
|
16857
18027
|
}
|
|
16858
|
-
|
|
16859
|
-
this.
|
|
16860
|
-
this.
|
|
16861
|
-
|
|
16862
|
-
if (this.scrollTopIndex > 0) {
|
|
16863
|
-
this.scrollTopIndex--;
|
|
16864
|
-
this.isScrolledToBottom = false;
|
|
16865
|
-
if (this._selectionEnd) {
|
|
16866
|
-
this._selectionEnd = {
|
|
16867
|
-
line: this.scrollTopIndex,
|
|
16868
|
-
col: this._selectionEnd.col
|
|
16869
|
-
};
|
|
16870
|
-
}
|
|
16871
|
-
this.markNeedsRerender();
|
|
16872
|
-
} else {
|
|
16873
|
-
this.stopAutoScroll();
|
|
16874
|
-
}
|
|
16875
|
-
} else {
|
|
16876
|
-
const displayLineCount = this._displayLines.length;
|
|
16877
|
-
const logAreaHeight = Math.max(1, this.consoleHeight - 1);
|
|
16878
|
-
const maxScrollTop = Math.max(0, displayLineCount - logAreaHeight);
|
|
16879
|
-
if (this.scrollTopIndex < maxScrollTop) {
|
|
16880
|
-
this.scrollTopIndex++;
|
|
16881
|
-
this.isScrolledToBottom = this.scrollTopIndex === maxScrollTop;
|
|
16882
|
-
if (this._selectionEnd) {
|
|
16883
|
-
const maxLine = this.scrollTopIndex + logAreaHeight - 1;
|
|
16884
|
-
this._selectionEnd = {
|
|
16885
|
-
line: Math.min(maxLine, displayLineCount - 1),
|
|
16886
|
-
col: this._selectionEnd.col
|
|
16887
|
-
};
|
|
16888
|
-
}
|
|
16889
|
-
this.markNeedsRerender();
|
|
16890
|
-
} else {
|
|
16891
|
-
this.stopAutoScroll();
|
|
16892
|
-
}
|
|
16893
|
-
}
|
|
16894
|
-
}, 50);
|
|
18028
|
+
deleteSelectedText() {
|
|
18029
|
+
this.editorView.deleteSelectedText();
|
|
18030
|
+
this._ctx.clearSelection();
|
|
18031
|
+
this.requestRender();
|
|
16895
18032
|
}
|
|
16896
|
-
|
|
18033
|
+
setSelection(start, end) {
|
|
18034
|
+
this.lastLocalSelection = null;
|
|
18035
|
+
this.editorView.resetLocalSelection();
|
|
18036
|
+
this._ctx.clearSelection();
|
|
18037
|
+
this.editorView.setSelection(start, end, this._selectionBg, this._selectionFg);
|
|
18038
|
+
this.requestRender();
|
|
18039
|
+
}
|
|
18040
|
+
setSelectionInclusive(start, end) {
|
|
18041
|
+
this.setSelection(Math.min(start, end), Math.max(start, end) + 1);
|
|
18042
|
+
}
|
|
18043
|
+
clearSelection() {
|
|
18044
|
+
const had = this.hasSelection();
|
|
18045
|
+
this.lastLocalSelection = null;
|
|
18046
|
+
this.editorView.resetSelection();
|
|
18047
|
+
this.editorView.resetLocalSelection();
|
|
18048
|
+
this._ctx.clearSelection();
|
|
18049
|
+
if (had) {
|
|
18050
|
+
this.requestRender();
|
|
18051
|
+
}
|
|
18052
|
+
return had;
|
|
18053
|
+
}
|
|
18054
|
+
deleteSelection() {
|
|
16897
18055
|
if (!this.hasSelection())
|
|
16898
|
-
return;
|
|
16899
|
-
|
|
16900
|
-
|
|
16901
|
-
|
|
16902
|
-
|
|
16903
|
-
|
|
16904
|
-
|
|
16905
|
-
|
|
18056
|
+
return false;
|
|
18057
|
+
this.lastLocalSelection = null;
|
|
18058
|
+
this.deleteSelectedText();
|
|
18059
|
+
return true;
|
|
18060
|
+
}
|
|
18061
|
+
setCursor(row, col) {
|
|
18062
|
+
this.editBuffer.setCursor(row, col);
|
|
18063
|
+
this.requestRender();
|
|
18064
|
+
}
|
|
18065
|
+
insertChar(char) {
|
|
18066
|
+
if (this.hasSelection()) {
|
|
18067
|
+
this.deleteSelectedText();
|
|
16906
18068
|
}
|
|
18069
|
+
this.editBuffer.insertChar(char);
|
|
18070
|
+
this.requestRender();
|
|
16907
18071
|
}
|
|
16908
|
-
|
|
16909
|
-
|
|
16910
|
-
|
|
16911
|
-
return null;
|
|
16912
|
-
if (lineIndex < selection2.startLine || lineIndex > selection2.endLine) {
|
|
16913
|
-
return null;
|
|
18072
|
+
insertText(text) {
|
|
18073
|
+
if (this.hasSelection()) {
|
|
18074
|
+
this.deleteSelectedText();
|
|
16914
18075
|
}
|
|
16915
|
-
|
|
16916
|
-
|
|
16917
|
-
|
|
16918
|
-
|
|
16919
|
-
|
|
16920
|
-
|
|
16921
|
-
|
|
16922
|
-
let end = fullTextLength;
|
|
16923
|
-
if (lineIndex === selection2.startLine) {
|
|
16924
|
-
start = Math.max(0, selection2.startCol);
|
|
18076
|
+
this.editBuffer.insertText(text);
|
|
18077
|
+
this.requestRender();
|
|
18078
|
+
}
|
|
18079
|
+
deleteChar() {
|
|
18080
|
+
if (this.hasSelection()) {
|
|
18081
|
+
this.deleteSelectedText();
|
|
18082
|
+
return true;
|
|
16925
18083
|
}
|
|
16926
|
-
|
|
16927
|
-
|
|
18084
|
+
this._ctx.clearSelection();
|
|
18085
|
+
this.editBuffer.deleteChar();
|
|
18086
|
+
this.requestRender();
|
|
18087
|
+
return true;
|
|
18088
|
+
}
|
|
18089
|
+
deleteCharBackward() {
|
|
18090
|
+
if (this.hasSelection()) {
|
|
18091
|
+
this.deleteSelectedText();
|
|
18092
|
+
return true;
|
|
16928
18093
|
}
|
|
16929
|
-
|
|
16930
|
-
|
|
16931
|
-
|
|
18094
|
+
this._ctx.clearSelection();
|
|
18095
|
+
this.editBuffer.deleteCharBackward();
|
|
18096
|
+
this.requestRender();
|
|
18097
|
+
return true;
|
|
16932
18098
|
}
|
|
16933
|
-
|
|
16934
|
-
|
|
16935
|
-
|
|
16936
|
-
|
|
16937
|
-
|
|
16938
|
-
|
|
16939
|
-
|
|
18099
|
+
newLine() {
|
|
18100
|
+
this._ctx.clearSelection();
|
|
18101
|
+
this.editBuffer.newLine();
|
|
18102
|
+
this.requestRender();
|
|
18103
|
+
return true;
|
|
18104
|
+
}
|
|
18105
|
+
deleteLine() {
|
|
18106
|
+
this._ctx.clearSelection();
|
|
18107
|
+
this.editBuffer.deleteLine();
|
|
18108
|
+
this.requestRender();
|
|
18109
|
+
return true;
|
|
18110
|
+
}
|
|
18111
|
+
moveCursorLeft(options) {
|
|
18112
|
+
const select = options?.select ?? false;
|
|
18113
|
+
if (!select && this.hasSelection()) {
|
|
18114
|
+
const selection2 = this.getSelection();
|
|
18115
|
+
this.editBuffer.setCursorByOffset(selection2.start);
|
|
18116
|
+
this._ctx.clearSelection();
|
|
18117
|
+
this.requestRender();
|
|
18118
|
+
return true;
|
|
16940
18119
|
}
|
|
16941
|
-
|
|
16942
|
-
|
|
16943
|
-
|
|
16944
|
-
|
|
16945
|
-
|
|
16946
|
-
|
|
18120
|
+
this.updateSelectionForMovement(select, true);
|
|
18121
|
+
this.editBuffer.moveCursorLeft();
|
|
18122
|
+
this.updateSelectionForMovement(select, false);
|
|
18123
|
+
this.requestRender();
|
|
18124
|
+
return true;
|
|
18125
|
+
}
|
|
18126
|
+
moveCursorRight(options) {
|
|
18127
|
+
const select = options?.select ?? false;
|
|
18128
|
+
if (!select && this.hasSelection()) {
|
|
18129
|
+
const selection2 = this.getSelection();
|
|
18130
|
+
const targetOffset = this.cursorOffset === selection2.start ? selection2.end - 1 : selection2.end;
|
|
18131
|
+
this.editBuffer.setCursorByOffset(targetOffset);
|
|
18132
|
+
this._ctx.clearSelection();
|
|
18133
|
+
this.requestRender();
|
|
16947
18134
|
return true;
|
|
16948
18135
|
}
|
|
16949
|
-
|
|
16950
|
-
|
|
16951
|
-
|
|
16952
|
-
|
|
16953
|
-
|
|
18136
|
+
this.updateSelectionForMovement(select, true);
|
|
18137
|
+
this.editBuffer.moveCursorRight();
|
|
18138
|
+
this.updateSelectionForMovement(select, false);
|
|
18139
|
+
this.requestRender();
|
|
18140
|
+
return true;
|
|
18141
|
+
}
|
|
18142
|
+
moveCursorUp(options) {
|
|
18143
|
+
const select = options?.select ?? false;
|
|
18144
|
+
this.updateSelectionForMovement(select, true);
|
|
18145
|
+
this.editorView.moveUpVisual();
|
|
18146
|
+
this.updateSelectionForMovement(select, false);
|
|
18147
|
+
this.requestRender();
|
|
18148
|
+
return true;
|
|
18149
|
+
}
|
|
18150
|
+
moveCursorDown(options) {
|
|
18151
|
+
const select = options?.select ?? false;
|
|
18152
|
+
this.updateSelectionForMovement(select, true);
|
|
18153
|
+
this.editorView.moveDownVisual();
|
|
18154
|
+
this.updateSelectionForMovement(select, false);
|
|
18155
|
+
this.requestRender();
|
|
18156
|
+
return true;
|
|
18157
|
+
}
|
|
18158
|
+
gotoLine(line) {
|
|
18159
|
+
this.editBuffer.gotoLine(line);
|
|
18160
|
+
this.requestRender();
|
|
18161
|
+
}
|
|
18162
|
+
gotoLineStart() {
|
|
18163
|
+
this.setCursor(this.logicalCursor.row, 0);
|
|
18164
|
+
}
|
|
18165
|
+
gotoLineTextEnd() {
|
|
18166
|
+
const eol = this.editBuffer.getEOL();
|
|
18167
|
+
this.setCursor(eol.row, eol.col);
|
|
18168
|
+
}
|
|
18169
|
+
gotoLineHome(options) {
|
|
18170
|
+
const select = options?.select ?? false;
|
|
18171
|
+
this.updateSelectionForMovement(select, true);
|
|
18172
|
+
const cursor = this.editorView.getCursor();
|
|
18173
|
+
if (cursor.col === 0 && cursor.row > 0) {
|
|
18174
|
+
this.editBuffer.setCursor(cursor.row - 1, 0);
|
|
18175
|
+
const prevLineEol = this.editBuffer.getEOL();
|
|
18176
|
+
this.editBuffer.setCursor(prevLineEol.row, prevLineEol.col);
|
|
18177
|
+
} else {
|
|
18178
|
+
this.editBuffer.setCursor(cursor.row, 0);
|
|
18179
|
+
}
|
|
18180
|
+
this.updateSelectionForMovement(select, false);
|
|
18181
|
+
this.requestRender();
|
|
18182
|
+
return true;
|
|
18183
|
+
}
|
|
18184
|
+
gotoLineEnd(options) {
|
|
18185
|
+
const select = options?.select ?? false;
|
|
18186
|
+
this.updateSelectionForMovement(select, true);
|
|
18187
|
+
const cursor = this.editorView.getCursor();
|
|
18188
|
+
const eol = this.editBuffer.getEOL();
|
|
18189
|
+
const lineCount = this.editBuffer.getLineCount();
|
|
18190
|
+
if (cursor.col === eol.col && cursor.row < lineCount - 1) {
|
|
18191
|
+
this.editBuffer.setCursor(cursor.row + 1, 0);
|
|
18192
|
+
} else {
|
|
18193
|
+
this.editBuffer.setCursor(eol.row, eol.col);
|
|
18194
|
+
}
|
|
18195
|
+
this.updateSelectionForMovement(select, false);
|
|
18196
|
+
this.requestRender();
|
|
18197
|
+
return true;
|
|
18198
|
+
}
|
|
18199
|
+
gotoVisualLineHome(options) {
|
|
18200
|
+
const select = options?.select ?? false;
|
|
18201
|
+
this.updateSelectionForMovement(select, true);
|
|
18202
|
+
const sol = this.editorView.getVisualSOL();
|
|
18203
|
+
this.editBuffer.setCursor(sol.logicalRow, sol.logicalCol);
|
|
18204
|
+
this.updateSelectionForMovement(select, false);
|
|
18205
|
+
this.requestRender();
|
|
18206
|
+
return true;
|
|
18207
|
+
}
|
|
18208
|
+
gotoVisualLineEnd(options) {
|
|
18209
|
+
const select = options?.select ?? false;
|
|
18210
|
+
this.updateSelectionForMovement(select, true);
|
|
18211
|
+
const eol = this.editorView.getVisualEOL();
|
|
18212
|
+
this.editBuffer.setCursor(eol.logicalRow, eol.logicalCol);
|
|
18213
|
+
this.updateSelectionForMovement(select, false);
|
|
18214
|
+
this.requestRender();
|
|
18215
|
+
return true;
|
|
18216
|
+
}
|
|
18217
|
+
gotoBufferHome(options) {
|
|
18218
|
+
const select = options?.select ?? false;
|
|
18219
|
+
this.updateSelectionForMovement(select, true);
|
|
18220
|
+
this.editBuffer.setCursor(0, 0);
|
|
18221
|
+
this.updateSelectionForMovement(select, false);
|
|
18222
|
+
this.requestRender();
|
|
18223
|
+
return true;
|
|
18224
|
+
}
|
|
18225
|
+
gotoBufferEnd(options) {
|
|
18226
|
+
const select = options?.select ?? false;
|
|
18227
|
+
this.updateSelectionForMovement(select, true);
|
|
18228
|
+
this.editBuffer.gotoLine(999999);
|
|
18229
|
+
this.updateSelectionForMovement(select, false);
|
|
18230
|
+
this.requestRender();
|
|
18231
|
+
return true;
|
|
18232
|
+
}
|
|
18233
|
+
selectAll() {
|
|
18234
|
+
this.updateSelectionForMovement(false, true);
|
|
18235
|
+
this.editBuffer.setCursor(0, 0);
|
|
18236
|
+
return this.gotoBufferEnd({ select: true });
|
|
18237
|
+
}
|
|
18238
|
+
deleteToLineEnd() {
|
|
18239
|
+
const cursor = this.editorView.getCursor();
|
|
18240
|
+
const eol = this.editBuffer.getEOL();
|
|
18241
|
+
if (eol.col > cursor.col) {
|
|
18242
|
+
this.editBuffer.deleteRange(cursor.row, cursor.col, eol.row, eol.col);
|
|
18243
|
+
}
|
|
18244
|
+
this.requestRender();
|
|
18245
|
+
return true;
|
|
18246
|
+
}
|
|
18247
|
+
deleteToLineStart() {
|
|
18248
|
+
const cursor = this.editorView.getCursor();
|
|
18249
|
+
if (cursor.col > 0) {
|
|
18250
|
+
this.editBuffer.deleteRange(cursor.row, 0, cursor.row, cursor.col);
|
|
18251
|
+
}
|
|
18252
|
+
this.requestRender();
|
|
18253
|
+
return true;
|
|
18254
|
+
}
|
|
18255
|
+
undo() {
|
|
18256
|
+
this._ctx.clearSelection();
|
|
18257
|
+
this.editBuffer.undo();
|
|
18258
|
+
this.requestRender();
|
|
18259
|
+
return true;
|
|
18260
|
+
}
|
|
18261
|
+
redo() {
|
|
18262
|
+
this._ctx.clearSelection();
|
|
18263
|
+
this.editBuffer.redo();
|
|
18264
|
+
this.requestRender();
|
|
18265
|
+
return true;
|
|
18266
|
+
}
|
|
18267
|
+
moveWordForward(options) {
|
|
18268
|
+
const select = options?.select ?? false;
|
|
18269
|
+
this.updateSelectionForMovement(select, true);
|
|
18270
|
+
const nextWord = this.editBuffer.getNextWordBoundary();
|
|
18271
|
+
this.editBuffer.setCursorByOffset(nextWord.offset);
|
|
18272
|
+
this.updateSelectionForMovement(select, false);
|
|
18273
|
+
this.requestRender();
|
|
18274
|
+
return true;
|
|
18275
|
+
}
|
|
18276
|
+
moveWordBackward(options) {
|
|
18277
|
+
const select = options?.select ?? false;
|
|
18278
|
+
this.updateSelectionForMovement(select, true);
|
|
18279
|
+
const prevWord = this.editBuffer.getPrevWordBoundary();
|
|
18280
|
+
this.editBuffer.setCursorByOffset(prevWord.offset);
|
|
18281
|
+
this.updateSelectionForMovement(select, false);
|
|
18282
|
+
this.requestRender();
|
|
18283
|
+
return true;
|
|
18284
|
+
}
|
|
18285
|
+
deleteWordForward() {
|
|
18286
|
+
if (this.hasSelection()) {
|
|
18287
|
+
this.deleteSelectedText();
|
|
16954
18288
|
return true;
|
|
16955
18289
|
}
|
|
16956
|
-
const
|
|
16957
|
-
const
|
|
16958
|
-
if (
|
|
16959
|
-
this.
|
|
16960
|
-
|
|
16961
|
-
|
|
16962
|
-
|
|
16963
|
-
|
|
18290
|
+
const currentCursor = this.editBuffer.getCursorPosition();
|
|
18291
|
+
const nextWord = this.editBuffer.getNextWordBoundary();
|
|
18292
|
+
if (nextWord.offset > currentCursor.offset) {
|
|
18293
|
+
this.editBuffer.deleteRange(currentCursor.row, currentCursor.col, nextWord.row, nextWord.col);
|
|
18294
|
+
}
|
|
18295
|
+
this._ctx.clearSelection();
|
|
18296
|
+
this.requestRender();
|
|
18297
|
+
return true;
|
|
18298
|
+
}
|
|
18299
|
+
deleteWordBackward() {
|
|
18300
|
+
if (this.hasSelection()) {
|
|
18301
|
+
this.deleteSelectedText();
|
|
16964
18302
|
return true;
|
|
16965
18303
|
}
|
|
16966
|
-
|
|
16967
|
-
|
|
16968
|
-
|
|
16969
|
-
|
|
16970
|
-
|
|
16971
|
-
|
|
16972
|
-
|
|
16973
|
-
|
|
18304
|
+
const currentCursor = this.editBuffer.getCursorPosition();
|
|
18305
|
+
const prevWord = this.editBuffer.getPrevWordBoundary();
|
|
18306
|
+
if (prevWord.offset < currentCursor.offset) {
|
|
18307
|
+
this.editBuffer.deleteRange(prevWord.row, prevWord.col, currentCursor.row, currentCursor.col);
|
|
18308
|
+
}
|
|
18309
|
+
this._ctx.clearSelection();
|
|
18310
|
+
this.requestRender();
|
|
18311
|
+
return true;
|
|
18312
|
+
}
|
|
18313
|
+
setupMeasureFunc() {
|
|
18314
|
+
const measureFunc = (width, widthMode, height, heightMode) => {
|
|
18315
|
+
let effectiveWidth;
|
|
18316
|
+
if (widthMode === MeasureMode.Undefined || isNaN(width)) {
|
|
18317
|
+
effectiveWidth = 0;
|
|
16974
18318
|
} else {
|
|
16975
|
-
|
|
18319
|
+
effectiveWidth = width;
|
|
16976
18320
|
}
|
|
16977
|
-
|
|
16978
|
-
|
|
16979
|
-
|
|
16980
|
-
|
|
16981
|
-
if (this.
|
|
16982
|
-
|
|
16983
|
-
|
|
16984
|
-
|
|
16985
|
-
|
|
18321
|
+
const effectiveHeight = isNaN(height) ? 1 : height;
|
|
18322
|
+
const measureResult = this.editorView.measureForDimensions(Math.floor(effectiveWidth), Math.floor(effectiveHeight));
|
|
18323
|
+
const measuredWidth = measureResult ? Math.max(1, measureResult.widthColsMax) : 1;
|
|
18324
|
+
const measuredHeight = measureResult ? Math.max(1, measureResult.lineCount) : 1;
|
|
18325
|
+
if (widthMode === MeasureMode.AtMost && this._positionType !== "absolute") {
|
|
18326
|
+
return {
|
|
18327
|
+
width: Math.min(effectiveWidth, measuredWidth),
|
|
18328
|
+
height: Math.min(effectiveHeight, measuredHeight)
|
|
18329
|
+
};
|
|
16986
18330
|
}
|
|
16987
|
-
return
|
|
18331
|
+
return {
|
|
18332
|
+
width: measuredWidth,
|
|
18333
|
+
height: measuredHeight
|
|
18334
|
+
};
|
|
18335
|
+
};
|
|
18336
|
+
this.yogaNode.setMeasureFunc(measureFunc);
|
|
18337
|
+
}
|
|
18338
|
+
render(buffer, deltaTime) {
|
|
18339
|
+
if (!this.visible)
|
|
18340
|
+
return;
|
|
18341
|
+
if (this.isDestroyed)
|
|
18342
|
+
return;
|
|
18343
|
+
this.markClean();
|
|
18344
|
+
this._ctx.addToHitGrid(this.x, this.y, this.width, this.height, this.num);
|
|
18345
|
+
this.renderSelf(buffer);
|
|
18346
|
+
this.renderCursor(buffer);
|
|
18347
|
+
}
|
|
18348
|
+
renderSelf(buffer) {
|
|
18349
|
+
buffer.drawEditorView(this.editorView, this.x, this.y);
|
|
18350
|
+
}
|
|
18351
|
+
renderCursor(buffer) {
|
|
18352
|
+
if (!this._showCursor || !this._focused)
|
|
18353
|
+
return;
|
|
18354
|
+
const visualCursor = this.editorView.getVisualCursor();
|
|
18355
|
+
const cursorX = this.x + visualCursor.visualCol + 1;
|
|
18356
|
+
const cursorY = this.y + visualCursor.visualRow + 1;
|
|
18357
|
+
this._ctx.setCursorPosition(cursorX, cursorY, true);
|
|
18358
|
+
this._ctx.setCursorStyle({ ...this._cursorStyle, color: this._cursorColor });
|
|
18359
|
+
}
|
|
18360
|
+
focus() {
|
|
18361
|
+
super.focus();
|
|
18362
|
+
this._ctx.setCursorStyle({ ...this._cursorStyle, color: this._cursorColor });
|
|
18363
|
+
this.requestRender();
|
|
18364
|
+
}
|
|
18365
|
+
blur() {
|
|
18366
|
+
super.blur();
|
|
18367
|
+
this._ctx.setCursorPosition(0, 0, false);
|
|
18368
|
+
this.requestRender();
|
|
18369
|
+
}
|
|
18370
|
+
onRemove() {
|
|
18371
|
+
if (this._focused) {
|
|
18372
|
+
this._ctx.setCursorPosition(0, 0, false);
|
|
16988
18373
|
}
|
|
16989
|
-
return true;
|
|
16990
18374
|
}
|
|
16991
|
-
|
|
16992
|
-
|
|
18375
|
+
destroy() {
|
|
18376
|
+
if (this.isDestroyed)
|
|
18377
|
+
return;
|
|
18378
|
+
this.traits = {};
|
|
18379
|
+
if (this._focused) {
|
|
18380
|
+
this._ctx.setCursorPosition(0, 0, false);
|
|
18381
|
+
this.blur();
|
|
18382
|
+
}
|
|
18383
|
+
this.editorView.destroy();
|
|
18384
|
+
this.editBuffer.destroy();
|
|
18385
|
+
super.destroy();
|
|
16993
18386
|
}
|
|
16994
|
-
|
|
16995
|
-
|
|
16996
|
-
x: this.consoleX,
|
|
16997
|
-
y: this.consoleY,
|
|
16998
|
-
width: this.consoleWidth,
|
|
16999
|
-
height: this.consoleHeight
|
|
17000
|
-
};
|
|
18387
|
+
set onCursorChange(handler) {
|
|
18388
|
+
this._cursorChangeListener = handler;
|
|
17001
18389
|
}
|
|
17002
|
-
|
|
17003
|
-
|
|
17004
|
-
|
|
17005
|
-
|
|
17006
|
-
|
|
17007
|
-
|
|
17008
|
-
|
|
17009
|
-
|
|
17010
|
-
|
|
17011
|
-
|
|
17012
|
-
|
|
17013
|
-
|
|
17014
|
-
|
|
18390
|
+
get onCursorChange() {
|
|
18391
|
+
return this._cursorChangeListener;
|
|
18392
|
+
}
|
|
18393
|
+
set onContentChange(handler) {
|
|
18394
|
+
this._contentChangeListener = handler;
|
|
18395
|
+
}
|
|
18396
|
+
get onContentChange() {
|
|
18397
|
+
return this._contentChangeListener;
|
|
18398
|
+
}
|
|
18399
|
+
get syntaxStyle() {
|
|
18400
|
+
return this.editBuffer.getSyntaxStyle();
|
|
18401
|
+
}
|
|
18402
|
+
set syntaxStyle(style) {
|
|
18403
|
+
this.editBuffer.setSyntaxStyle(style);
|
|
18404
|
+
this.requestRender();
|
|
18405
|
+
}
|
|
18406
|
+
addHighlight(lineIdx, highlight) {
|
|
18407
|
+
this.editBuffer.addHighlight(lineIdx, highlight);
|
|
18408
|
+
this.requestRender();
|
|
18409
|
+
}
|
|
18410
|
+
addHighlightByCharRange(highlight) {
|
|
18411
|
+
this.editBuffer.addHighlightByCharRange(highlight);
|
|
18412
|
+
this.requestRender();
|
|
18413
|
+
}
|
|
18414
|
+
removeHighlightsByRef(hlRef) {
|
|
18415
|
+
this.editBuffer.removeHighlightsByRef(hlRef);
|
|
18416
|
+
this.requestRender();
|
|
18417
|
+
}
|
|
18418
|
+
clearLineHighlights(lineIdx) {
|
|
18419
|
+
this.editBuffer.clearLineHighlights(lineIdx);
|
|
18420
|
+
this.requestRender();
|
|
18421
|
+
}
|
|
18422
|
+
clearAllHighlights() {
|
|
18423
|
+
this.editBuffer.clearAllHighlights();
|
|
18424
|
+
this.requestRender();
|
|
18425
|
+
}
|
|
18426
|
+
getLineHighlights(lineIdx) {
|
|
18427
|
+
return this.editBuffer.getLineHighlights(lineIdx);
|
|
18428
|
+
}
|
|
18429
|
+
setText(text) {
|
|
18430
|
+
this.editBuffer.setText(text);
|
|
18431
|
+
this.yogaNode.markDirty();
|
|
18432
|
+
this.requestRender();
|
|
18433
|
+
}
|
|
18434
|
+
replaceText(text) {
|
|
18435
|
+
this.editBuffer.replaceText(text);
|
|
18436
|
+
this.yogaNode.markDirty();
|
|
18437
|
+
this.requestRender();
|
|
18438
|
+
}
|
|
18439
|
+
clear() {
|
|
18440
|
+
this.editBuffer.clear();
|
|
18441
|
+
this.editBuffer.clearAllHighlights();
|
|
18442
|
+
this.yogaNode.markDirty();
|
|
18443
|
+
this.requestRender();
|
|
18444
|
+
}
|
|
18445
|
+
deleteRange(startLine, startCol, endLine, endCol) {
|
|
18446
|
+
this.editBuffer.deleteRange(startLine, startCol, endLine, endCol);
|
|
18447
|
+
this.yogaNode.markDirty();
|
|
18448
|
+
this.requestRender();
|
|
18449
|
+
}
|
|
18450
|
+
getTextRange(startOffset, endOffset) {
|
|
18451
|
+
return this.editBuffer.getTextRange(startOffset, endOffset);
|
|
18452
|
+
}
|
|
18453
|
+
getTextRangeByCoords(startRow, startCol, endRow, endCol) {
|
|
18454
|
+
return this.editBuffer.getTextRangeByCoords(startRow, startCol, endRow, endCol);
|
|
18455
|
+
}
|
|
18456
|
+
updateSelectionForMovement(shiftPressed, isBeforeMovement) {
|
|
18457
|
+
if (!this.selectable)
|
|
18458
|
+
return;
|
|
18459
|
+
if (!shiftPressed) {
|
|
18460
|
+
this._keyboardSelectionActive = false;
|
|
18461
|
+
this._ctx.clearSelection();
|
|
18462
|
+
return;
|
|
18463
|
+
}
|
|
18464
|
+
this._keyboardSelectionActive = true;
|
|
18465
|
+
const visualCursor = this.editorView.getVisualCursor();
|
|
18466
|
+
const cursorX = this.x + visualCursor.visualCol;
|
|
18467
|
+
const cursorY = this.y + visualCursor.visualRow;
|
|
18468
|
+
if (isBeforeMovement) {
|
|
18469
|
+
if (!this._ctx.hasSelection) {
|
|
18470
|
+
this._ctx.startSelection(this, cursorX, cursorY);
|
|
17015
18471
|
}
|
|
17016
|
-
|
|
17017
|
-
`);
|
|
17018
|
-
fs.writeFileSync(filepath, content, "utf8");
|
|
17019
|
-
console.info(`Console logs saved to: ${filename}`);
|
|
17020
|
-
} catch (error) {
|
|
17021
|
-
console.error(`Failed to save console logs:`, error);
|
|
18472
|
+
return;
|
|
17022
18473
|
}
|
|
18474
|
+
this._ctx.updateSelection(this, cursorX, cursorY, { finishDragging: true });
|
|
17023
18475
|
}
|
|
17024
18476
|
}
|
|
17025
18477
|
|
|
@@ -17071,7 +18523,7 @@ class Clipboard {
|
|
|
17071
18523
|
}
|
|
17072
18524
|
|
|
17073
18525
|
// src/renderer.ts
|
|
17074
|
-
import { EventEmitter as
|
|
18526
|
+
import { EventEmitter as EventEmitter9 } from "events";
|
|
17075
18527
|
|
|
17076
18528
|
// src/lib/objects-in-viewport.ts
|
|
17077
18529
|
function getObjectsInViewport(viewport, objects, direction = "column", padding = 10, minTriggerSize = 16) {
|
|
@@ -17209,25 +18661,25 @@ function parsePixelResolution(sequence) {
|
|
|
17209
18661
|
// src/renderer.ts
|
|
17210
18662
|
registerEnvVar({
|
|
17211
18663
|
name: "OTUI_DUMP_CAPTURES",
|
|
17212
|
-
description: "Dump captured
|
|
18664
|
+
description: "Dump captured stdout and console caches when the renderer exit handler runs.",
|
|
17213
18665
|
type: "boolean",
|
|
17214
18666
|
default: false
|
|
17215
18667
|
});
|
|
17216
18668
|
registerEnvVar({
|
|
17217
18669
|
name: "OTUI_NO_NATIVE_RENDER",
|
|
17218
|
-
description: "
|
|
18670
|
+
description: "Skip the Zig/native frame renderer. Useful for debugging the render loop; split-footer stdout flushing may still write ANSI.",
|
|
17219
18671
|
type: "boolean",
|
|
17220
18672
|
default: false
|
|
17221
18673
|
});
|
|
17222
18674
|
registerEnvVar({
|
|
17223
18675
|
name: "OTUI_USE_ALTERNATE_SCREEN",
|
|
17224
|
-
description: "
|
|
18676
|
+
description: "When explicitly set, force screen mode selection: true=alternate-screen, false=main-screen.",
|
|
17225
18677
|
type: "boolean",
|
|
17226
18678
|
default: true
|
|
17227
18679
|
});
|
|
17228
18680
|
registerEnvVar({
|
|
17229
18681
|
name: "OTUI_OVERRIDE_STDOUT",
|
|
17230
|
-
description: "
|
|
18682
|
+
description: "When explicitly set, force stdout routing: false=passthrough, true=capture in split-footer mode.",
|
|
17231
18683
|
type: "boolean",
|
|
17232
18684
|
default: true
|
|
17233
18685
|
});
|
|
@@ -17243,6 +18695,39 @@ registerEnvVar({
|
|
|
17243
18695
|
type: "boolean",
|
|
17244
18696
|
default: false
|
|
17245
18697
|
});
|
|
18698
|
+
var DEFAULT_FOOTER_HEIGHT = 12;
|
|
18699
|
+
function normalizeFooterHeight(footerHeight) {
|
|
18700
|
+
if (footerHeight === undefined) {
|
|
18701
|
+
return DEFAULT_FOOTER_HEIGHT;
|
|
18702
|
+
}
|
|
18703
|
+
if (!Number.isFinite(footerHeight)) {
|
|
18704
|
+
throw new Error("footerHeight must be a finite number");
|
|
18705
|
+
}
|
|
18706
|
+
const normalizedFooterHeight = Math.trunc(footerHeight);
|
|
18707
|
+
if (normalizedFooterHeight <= 0) {
|
|
18708
|
+
throw new Error("footerHeight must be greater than 0");
|
|
18709
|
+
}
|
|
18710
|
+
return normalizedFooterHeight;
|
|
18711
|
+
}
|
|
18712
|
+
function resolveModes(config) {
|
|
18713
|
+
let screenMode = config.screenMode ?? "alternate-screen";
|
|
18714
|
+
if (process.env.OTUI_USE_ALTERNATE_SCREEN !== undefined) {
|
|
18715
|
+
screenMode = env.OTUI_USE_ALTERNATE_SCREEN ? "alternate-screen" : "main-screen";
|
|
18716
|
+
}
|
|
18717
|
+
const footerHeight = screenMode === "split-footer" ? normalizeFooterHeight(config.footerHeight) : DEFAULT_FOOTER_HEIGHT;
|
|
18718
|
+
let externalOutputMode = config.externalOutputMode ?? (screenMode === "split-footer" ? "capture-stdout" : "passthrough");
|
|
18719
|
+
if (process.env.OTUI_OVERRIDE_STDOUT !== undefined) {
|
|
18720
|
+
externalOutputMode = env.OTUI_OVERRIDE_STDOUT && screenMode === "split-footer" ? "capture-stdout" : "passthrough";
|
|
18721
|
+
}
|
|
18722
|
+
if (externalOutputMode === "capture-stdout" && screenMode !== "split-footer") {
|
|
18723
|
+
throw new Error('externalOutputMode "capture-stdout" requires screenMode "split-footer"');
|
|
18724
|
+
}
|
|
18725
|
+
return {
|
|
18726
|
+
screenMode,
|
|
18727
|
+
footerHeight,
|
|
18728
|
+
externalOutputMode
|
|
18729
|
+
};
|
|
18730
|
+
}
|
|
17246
18731
|
var DEFAULT_FORWARDED_ENV_KEYS = [
|
|
17247
18732
|
"TMUX",
|
|
17248
18733
|
"TERM",
|
|
@@ -17360,9 +18845,10 @@ async function createCliRenderer(config = {}) {
|
|
|
17360
18845
|
}
|
|
17361
18846
|
const stdin = config.stdin || process.stdin;
|
|
17362
18847
|
const stdout = config.stdout || process.stdout;
|
|
18848
|
+
const { screenMode, footerHeight } = resolveModes(config);
|
|
17363
18849
|
const width = stdout.columns || 80;
|
|
17364
18850
|
const height = stdout.rows || 24;
|
|
17365
|
-
const renderHeight =
|
|
18851
|
+
const renderHeight = screenMode === "split-footer" ? footerHeight : height;
|
|
17366
18852
|
const ziglib = resolveRenderLib();
|
|
17367
18853
|
const rendererPtr = ziglib.createRenderer(width, renderHeight, {
|
|
17368
18854
|
remote: config.remote ?? false,
|
|
@@ -17392,6 +18878,7 @@ var CliRenderEvents;
|
|
|
17392
18878
|
CliRenderEvents2["RESIZE"] = "resize";
|
|
17393
18879
|
CliRenderEvents2["FOCUS"] = "focus";
|
|
17394
18880
|
CliRenderEvents2["BLUR"] = "blur";
|
|
18881
|
+
CliRenderEvents2["FOCUSED_EDITOR"] = "focused_editor";
|
|
17395
18882
|
CliRenderEvents2["THEME_MODE"] = "theme_mode";
|
|
17396
18883
|
CliRenderEvents2["CAPABILITIES"] = "capabilities";
|
|
17397
18884
|
CliRenderEvents2["SELECTION"] = "selection";
|
|
@@ -17409,7 +18896,7 @@ var RendererControlState;
|
|
|
17409
18896
|
RendererControlState2["EXPLICIT_STOPPED"] = "explicit_stopped";
|
|
17410
18897
|
})(RendererControlState ||= {});
|
|
17411
18898
|
|
|
17412
|
-
class CliRenderer extends
|
|
18899
|
+
class CliRenderer extends EventEmitter9 {
|
|
17413
18900
|
static animationFrameId = 0;
|
|
17414
18901
|
lib;
|
|
17415
18902
|
rendererPtr;
|
|
@@ -17421,11 +18908,12 @@ class CliRenderer extends EventEmitter8 {
|
|
|
17421
18908
|
_isDestroyed = false;
|
|
17422
18909
|
_destroyPending = false;
|
|
17423
18910
|
_destroyFinalized = false;
|
|
18911
|
+
_destroyCleanupPrepared = false;
|
|
17424
18912
|
nextRenderBuffer;
|
|
17425
18913
|
currentRenderBuffer;
|
|
17426
18914
|
_isRunning = false;
|
|
17427
|
-
|
|
17428
|
-
|
|
18915
|
+
_targetFps = 30;
|
|
18916
|
+
_maxFps = 60;
|
|
17429
18917
|
automaticMemorySnapshot = false;
|
|
17430
18918
|
memorySnapshotInterval;
|
|
17431
18919
|
memorySnapshotTimer = null;
|
|
@@ -17452,8 +18940,8 @@ class CliRenderer extends EventEmitter8 {
|
|
|
17452
18940
|
frameCount = 0;
|
|
17453
18941
|
lastFpsTime = 0;
|
|
17454
18942
|
currentFps = 0;
|
|
17455
|
-
targetFrameTime = 1000 / this.
|
|
17456
|
-
minTargetFrameTime = 1000 / this.
|
|
18943
|
+
targetFrameTime = 1000 / this._targetFps;
|
|
18944
|
+
minTargetFrameTime = 1000 / this._maxFps;
|
|
17457
18945
|
immediateRerenderRequested = false;
|
|
17458
18946
|
updateScheduled = false;
|
|
17459
18947
|
liveRequestCounter = 0;
|
|
@@ -17482,7 +18970,9 @@ class CliRenderer extends EventEmitter8 {
|
|
|
17482
18970
|
enableMouseMovement = false;
|
|
17483
18971
|
_useMouse = true;
|
|
17484
18972
|
autoFocus = true;
|
|
17485
|
-
|
|
18973
|
+
_screenMode = "alternate-screen";
|
|
18974
|
+
_footerHeight = DEFAULT_FOOTER_HEIGHT;
|
|
18975
|
+
_externalOutputMode = "passthrough";
|
|
17486
18976
|
_suspendedMouseEnabled = false;
|
|
17487
18977
|
_previousControlState = "idle" /* IDLE */;
|
|
17488
18978
|
capturedRenderable;
|
|
@@ -17581,13 +19071,9 @@ Captured output:
|
|
|
17581
19071
|
this.width = width;
|
|
17582
19072
|
this.height = height;
|
|
17583
19073
|
this._useThread = config.useThread === undefined ? false : config.useThread;
|
|
17584
|
-
|
|
17585
|
-
|
|
17586
|
-
|
|
17587
|
-
this.renderOffset = height - this._splitHeight;
|
|
17588
|
-
this.height = this._splitHeight;
|
|
17589
|
-
lib.setRenderOffset(rendererPtr, this.renderOffset);
|
|
17590
|
-
}
|
|
19074
|
+
const { screenMode, footerHeight, externalOutputMode } = resolveModes(config);
|
|
19075
|
+
this._footerHeight = footerHeight;
|
|
19076
|
+
this._screenMode = screenMode;
|
|
17591
19077
|
this.rendererPtr = rendererPtr;
|
|
17592
19078
|
const forwardEnvKeys = config.forwardEnvKeys ?? [...DEFAULT_FORWARDED_ENV_KEYS];
|
|
17593
19079
|
for (const key of forwardEnvKeys) {
|
|
@@ -17605,15 +19091,12 @@ Captured output:
|
|
|
17605
19091
|
"SIGHUP",
|
|
17606
19092
|
"SIGBREAK",
|
|
17607
19093
|
"SIGPIPE",
|
|
17608
|
-
"SIGBUS"
|
|
17609
|
-
"SIGFPE"
|
|
19094
|
+
"SIGBUS"
|
|
17610
19095
|
];
|
|
17611
19096
|
this.clipboard = new Clipboard(this.lib, this.rendererPtr);
|
|
17612
19097
|
this.resizeDebounceDelay = config.debounceDelay || 100;
|
|
17613
19098
|
this.targetFps = config.targetFps || 30;
|
|
17614
19099
|
this.maxFps = config.maxFps || 60;
|
|
17615
|
-
this.targetFrameTime = 1000 / this.targetFps;
|
|
17616
|
-
this.minTargetFrameTime = 1000 / this.maxFps;
|
|
17617
19100
|
this.clock = config.clock ?? new SystemClock;
|
|
17618
19101
|
this.memorySnapshotInterval = config.memorySnapshotInterval ?? 0;
|
|
17619
19102
|
this.gatherStats = config.gatherStats || false;
|
|
@@ -17621,7 +19104,6 @@ Captured output:
|
|
|
17621
19104
|
this.enableMouseMovement = config.enableMouseMovement ?? true;
|
|
17622
19105
|
this._useMouse = config.useMouse ?? true;
|
|
17623
19106
|
this.autoFocus = config.autoFocus ?? true;
|
|
17624
|
-
this._useAlternateScreen = config.useAlternateScreen ?? env.OTUI_USE_ALTERNATE_SCREEN;
|
|
17625
19107
|
this.nextRenderBuffer = this.lib.getNextBuffer(this.rendererPtr);
|
|
17626
19108
|
this.currentRenderBuffer = this.lib.getCurrentBuffer(this.rendererPtr);
|
|
17627
19109
|
this.postProcessFns = config.postProcessFns || [];
|
|
@@ -17630,9 +19112,6 @@ Captured output:
|
|
|
17630
19112
|
if (this.memorySnapshotInterval > 0) {
|
|
17631
19113
|
this.startMemorySnapshotTimer();
|
|
17632
19114
|
}
|
|
17633
|
-
if (env.OTUI_OVERRIDE_STDOUT) {
|
|
17634
|
-
this.stdout.write = this.interceptStdoutWrite.bind(this);
|
|
17635
|
-
}
|
|
17636
19115
|
process.on("SIGWINCH", this.sigwinchHandler);
|
|
17637
19116
|
process.on("warning", this.warningHandler);
|
|
17638
19117
|
process.on("uncaughtException", this.handleError);
|
|
@@ -17652,7 +19131,7 @@ Captured output:
|
|
|
17652
19131
|
this.addExitListeners();
|
|
17653
19132
|
const stdinParserMaxBufferBytes = config.stdinParserMaxBufferBytes ?? DEFAULT_STDIN_PARSER_MAX_BUFFER_BYTES;
|
|
17654
19133
|
this.stdinParser = new StdinParser({
|
|
17655
|
-
timeoutMs:
|
|
19134
|
+
timeoutMs: 20,
|
|
17656
19135
|
maxPendingBytes: stdinParserMaxBufferBytes,
|
|
17657
19136
|
armTimeouts: true,
|
|
17658
19137
|
onTimeoutFlush: () => {
|
|
@@ -17671,7 +19150,9 @@ Captured output:
|
|
|
17671
19150
|
...config.consoleOptions ?? {},
|
|
17672
19151
|
clock: this.clock
|
|
17673
19152
|
});
|
|
17674
|
-
this.
|
|
19153
|
+
this.consoleMode = config.consoleMode ?? "console-overlay";
|
|
19154
|
+
this.applyScreenMode(screenMode, false, false);
|
|
19155
|
+
this.externalOutputMode = externalOutputMode;
|
|
17675
19156
|
this._openConsoleOnError = config.openConsoleOnError ?? true;
|
|
17676
19157
|
this._onDestroy = config.onDestroy;
|
|
17677
19158
|
global.requestAnimationFrame = (callback) => {
|
|
@@ -17728,6 +19209,13 @@ Captured output:
|
|
|
17728
19209
|
get currentFocusedRenderable() {
|
|
17729
19210
|
return this._currentFocusedRenderable;
|
|
17730
19211
|
}
|
|
19212
|
+
get currentFocusedEditor() {
|
|
19213
|
+
if (!this._currentFocusedRenderable)
|
|
19214
|
+
return null;
|
|
19215
|
+
if (!isEditBufferRenderable(this._currentFocusedRenderable))
|
|
19216
|
+
return null;
|
|
19217
|
+
return this._currentFocusedRenderable;
|
|
19218
|
+
}
|
|
17731
19219
|
normalizeClockTime(now, fallback) {
|
|
17732
19220
|
if (Number.isFinite(now)) {
|
|
17733
19221
|
return now;
|
|
@@ -17743,10 +19231,15 @@ Captured output:
|
|
|
17743
19231
|
focusRenderable(renderable) {
|
|
17744
19232
|
if (this._currentFocusedRenderable === renderable)
|
|
17745
19233
|
return;
|
|
19234
|
+
const prev = this.currentFocusedEditor;
|
|
17746
19235
|
if (this._currentFocusedRenderable) {
|
|
17747
19236
|
this._currentFocusedRenderable.blur();
|
|
17748
19237
|
}
|
|
17749
19238
|
this._currentFocusedRenderable = renderable;
|
|
19239
|
+
const next = this.currentFocusedEditor;
|
|
19240
|
+
if (prev !== next) {
|
|
19241
|
+
this.emit("focused_editor" /* FOCUSED_EDITOR */, next, prev);
|
|
19242
|
+
}
|
|
17750
19243
|
}
|
|
17751
19244
|
setCapturedRenderable(renderable) {
|
|
17752
19245
|
if (this.capturedRenderable === renderable) {
|
|
@@ -17807,16 +19300,23 @@ Captured output:
|
|
|
17807
19300
|
}
|
|
17808
19301
|
}
|
|
17809
19302
|
async activateFrame() {
|
|
17810
|
-
|
|
17811
|
-
|
|
17812
|
-
|
|
19303
|
+
if (!this.updateScheduled) {
|
|
19304
|
+
this.resolveIdleIfNeeded();
|
|
19305
|
+
return;
|
|
19306
|
+
}
|
|
19307
|
+
try {
|
|
19308
|
+
await this.loop();
|
|
19309
|
+
} finally {
|
|
19310
|
+
this.updateScheduled = false;
|
|
19311
|
+
this.resolveIdleIfNeeded();
|
|
19312
|
+
}
|
|
17813
19313
|
}
|
|
17814
|
-
get
|
|
17815
|
-
return this._useConsole;
|
|
19314
|
+
get consoleMode() {
|
|
19315
|
+
return this._useConsole ? "console-overlay" : "disabled";
|
|
17816
19316
|
}
|
|
17817
|
-
set
|
|
17818
|
-
this._useConsole =
|
|
17819
|
-
if (
|
|
19317
|
+
set consoleMode(mode) {
|
|
19318
|
+
this._useConsole = mode === "console-overlay";
|
|
19319
|
+
if (this._useConsole) {
|
|
17820
19320
|
this.console.activate();
|
|
17821
19321
|
} else {
|
|
17822
19322
|
this.console.deactivate();
|
|
@@ -17866,6 +19366,20 @@ Captured output:
|
|
|
17866
19366
|
get useThread() {
|
|
17867
19367
|
return this._useThread;
|
|
17868
19368
|
}
|
|
19369
|
+
get targetFps() {
|
|
19370
|
+
return this._targetFps;
|
|
19371
|
+
}
|
|
19372
|
+
set targetFps(targetFps) {
|
|
19373
|
+
this._targetFps = targetFps;
|
|
19374
|
+
this.targetFrameTime = 1000 / this._targetFps;
|
|
19375
|
+
}
|
|
19376
|
+
get maxFps() {
|
|
19377
|
+
return this._maxFps;
|
|
19378
|
+
}
|
|
19379
|
+
set maxFps(maxFps) {
|
|
19380
|
+
this._maxFps = maxFps;
|
|
19381
|
+
this.minTargetFrameTime = 1000 / this._maxFps;
|
|
19382
|
+
}
|
|
17869
19383
|
get useMouse() {
|
|
17870
19384
|
return this._useMouse;
|
|
17871
19385
|
}
|
|
@@ -17879,8 +19393,37 @@ Captured output:
|
|
|
17879
19393
|
this.disableMouse();
|
|
17880
19394
|
}
|
|
17881
19395
|
}
|
|
17882
|
-
get
|
|
17883
|
-
return this.
|
|
19396
|
+
get screenMode() {
|
|
19397
|
+
return this._screenMode;
|
|
19398
|
+
}
|
|
19399
|
+
set screenMode(mode) {
|
|
19400
|
+
if (this.externalOutputMode === "capture-stdout" && mode !== "split-footer") {
|
|
19401
|
+
throw new Error('externalOutputMode "capture-stdout" requires screenMode "split-footer"');
|
|
19402
|
+
}
|
|
19403
|
+
this.applyScreenMode(mode);
|
|
19404
|
+
}
|
|
19405
|
+
get footerHeight() {
|
|
19406
|
+
return this._footerHeight;
|
|
19407
|
+
}
|
|
19408
|
+
set footerHeight(footerHeight) {
|
|
19409
|
+
const normalizedFooterHeight = normalizeFooterHeight(footerHeight);
|
|
19410
|
+
if (normalizedFooterHeight === this._footerHeight) {
|
|
19411
|
+
return;
|
|
19412
|
+
}
|
|
19413
|
+
this._footerHeight = normalizedFooterHeight;
|
|
19414
|
+
if (this.screenMode === "split-footer") {
|
|
19415
|
+
this.applyScreenMode("split-footer");
|
|
19416
|
+
}
|
|
19417
|
+
}
|
|
19418
|
+
get externalOutputMode() {
|
|
19419
|
+
return this._externalOutputMode;
|
|
19420
|
+
}
|
|
19421
|
+
set externalOutputMode(mode) {
|
|
19422
|
+
if (mode === "capture-stdout" && this.screenMode !== "split-footer") {
|
|
19423
|
+
throw new Error('externalOutputMode "capture-stdout" requires screenMode "split-footer"');
|
|
19424
|
+
}
|
|
19425
|
+
this._externalOutputMode = mode;
|
|
19426
|
+
this.stdout.write = mode === "capture-stdout" ? this.interceptStdoutWrite : this.realStdoutWrite;
|
|
17884
19427
|
}
|
|
17885
19428
|
get liveRequestCount() {
|
|
17886
19429
|
return this.liveRequestCounter;
|
|
@@ -17904,61 +19447,75 @@ Captured output:
|
|
|
17904
19447
|
const flags = use ? KITTY_FLAG_DISAMBIGUATE | KITTY_FLAG_ALTERNATE_KEYS : 0;
|
|
17905
19448
|
this.lib.setKittyKeyboardFlags(this.rendererPtr, flags);
|
|
17906
19449
|
}
|
|
17907
|
-
|
|
17908
|
-
|
|
17909
|
-
|
|
19450
|
+
interceptStdoutWrite = (chunk, encoding, callback) => {
|
|
19451
|
+
const text = chunk.toString();
|
|
19452
|
+
capture.write("stdout", text);
|
|
19453
|
+
if (this._splitHeight > 0) {
|
|
19454
|
+
this.requestRender();
|
|
19455
|
+
}
|
|
19456
|
+
if (typeof callback === "function") {
|
|
19457
|
+
process.nextTick(callback);
|
|
19458
|
+
}
|
|
19459
|
+
return true;
|
|
19460
|
+
};
|
|
19461
|
+
applyScreenMode(screenMode, emitResize = true, requestRender = true) {
|
|
19462
|
+
const prevScreenMode = this._screenMode;
|
|
17910
19463
|
const prevSplitHeight = this._splitHeight;
|
|
17911
|
-
|
|
17912
|
-
|
|
17913
|
-
|
|
17914
|
-
|
|
17915
|
-
|
|
17916
|
-
|
|
17917
|
-
|
|
17918
|
-
|
|
19464
|
+
const nextSplitHeight = screenMode === "split-footer" ? this._footerHeight : 0;
|
|
19465
|
+
if (prevScreenMode === screenMode && prevSplitHeight === nextSplitHeight) {
|
|
19466
|
+
return;
|
|
19467
|
+
}
|
|
19468
|
+
const prevUseAlternateScreen = prevScreenMode === "alternate-screen";
|
|
19469
|
+
const nextUseAlternateScreen = screenMode === "alternate-screen";
|
|
19470
|
+
const terminalScreenModeChanged = this._terminalIsSetup && prevUseAlternateScreen !== nextUseAlternateScreen;
|
|
19471
|
+
const leavingSplitFooter = prevSplitHeight > 0 && nextSplitHeight === 0;
|
|
19472
|
+
if (this._terminalIsSetup && leavingSplitFooter) {
|
|
19473
|
+
this.flushStdoutCache(this._terminalHeight, true);
|
|
19474
|
+
}
|
|
19475
|
+
if (this._terminalIsSetup && !terminalScreenModeChanged) {
|
|
19476
|
+
if (prevSplitHeight === 0 && nextSplitHeight > 0) {
|
|
19477
|
+
const freedLines = this._terminalHeight - nextSplitHeight;
|
|
17919
19478
|
const scrollDown = ANSI.scrollDown(freedLines);
|
|
17920
19479
|
this.writeOut(scrollDown);
|
|
17921
|
-
} else if (prevSplitHeight >
|
|
17922
|
-
const freedLines = prevSplitHeight -
|
|
19480
|
+
} else if (prevSplitHeight > nextSplitHeight && nextSplitHeight > 0) {
|
|
19481
|
+
const freedLines = prevSplitHeight - nextSplitHeight;
|
|
17923
19482
|
const scrollDown = ANSI.scrollDown(freedLines);
|
|
17924
19483
|
this.writeOut(scrollDown);
|
|
17925
|
-
} else if (prevSplitHeight <
|
|
17926
|
-
const additionalLines =
|
|
19484
|
+
} else if (prevSplitHeight < nextSplitHeight && prevSplitHeight > 0) {
|
|
19485
|
+
const additionalLines = nextSplitHeight - prevSplitHeight;
|
|
17927
19486
|
const scrollUp = ANSI.scrollUp(additionalLines);
|
|
17928
19487
|
this.writeOut(scrollUp);
|
|
17929
19488
|
}
|
|
17930
|
-
} else {
|
|
17931
|
-
if (prevSplitHeight > 0) {
|
|
17932
|
-
this.flushStdoutCache(this._terminalHeight, true);
|
|
17933
|
-
capture.off("write", this.captureCallback);
|
|
17934
|
-
this.useConsole = true;
|
|
17935
|
-
}
|
|
17936
|
-
this._splitHeight = 0;
|
|
17937
|
-
this.renderOffset = 0;
|
|
17938
|
-
this.height = this._terminalHeight;
|
|
17939
19489
|
}
|
|
19490
|
+
if (prevSplitHeight === 0 && nextSplitHeight > 0) {
|
|
19491
|
+
capture.on("write", this.captureCallback);
|
|
19492
|
+
} else if (prevSplitHeight > 0 && nextSplitHeight === 0) {
|
|
19493
|
+
capture.off("write", this.captureCallback);
|
|
19494
|
+
}
|
|
19495
|
+
this._screenMode = screenMode;
|
|
19496
|
+
this._splitHeight = nextSplitHeight;
|
|
19497
|
+
this.renderOffset = nextSplitHeight > 0 ? this._terminalHeight - nextSplitHeight : 0;
|
|
17940
19498
|
this.width = this._terminalWidth;
|
|
19499
|
+
this.height = nextSplitHeight > 0 ? nextSplitHeight : this._terminalHeight;
|
|
17941
19500
|
this.lib.setRenderOffset(this.rendererPtr, this.renderOffset);
|
|
17942
19501
|
this.lib.resizeRenderer(this.rendererPtr, this.width, this.height);
|
|
17943
19502
|
this.nextRenderBuffer = this.lib.getNextBuffer(this.rendererPtr);
|
|
19503
|
+
this.currentRenderBuffer = this.lib.getCurrentBuffer(this.rendererPtr);
|
|
17944
19504
|
this._console.resize(this.width, this.height);
|
|
17945
19505
|
this.root.resize(this.width, this.height);
|
|
17946
|
-
|
|
17947
|
-
|
|
17948
|
-
|
|
17949
|
-
|
|
17950
|
-
|
|
17951
|
-
|
|
17952
|
-
if (this._splitHeight > 0) {
|
|
17953
|
-
this.requestRender();
|
|
19506
|
+
if (terminalScreenModeChanged) {
|
|
19507
|
+
this.lib.suspendRenderer(this.rendererPtr);
|
|
19508
|
+
this.lib.setupTerminal(this.rendererPtr, nextUseAlternateScreen);
|
|
19509
|
+
if (this._useMouse) {
|
|
19510
|
+
this.enableMouse();
|
|
19511
|
+
}
|
|
17954
19512
|
}
|
|
17955
|
-
if (
|
|
17956
|
-
|
|
19513
|
+
if (emitResize) {
|
|
19514
|
+
this.emit("resize" /* RESIZE */, this.width, this.height);
|
|
19515
|
+
}
|
|
19516
|
+
if (requestRender) {
|
|
19517
|
+
this.requestRender();
|
|
17957
19518
|
}
|
|
17958
|
-
return true;
|
|
17959
|
-
};
|
|
17960
|
-
disableStdoutInterception() {
|
|
17961
|
-
this.stdout.write = this.realStdoutWrite;
|
|
17962
19519
|
}
|
|
17963
19520
|
flushStdoutCache(space, force = false) {
|
|
17964
19521
|
if (capture.size === 0 && !force)
|
|
@@ -18012,7 +19569,7 @@ Captured output:
|
|
|
18012
19569
|
privateCapabilityRepliesActive: true,
|
|
18013
19570
|
explicitWidthCprActive: true
|
|
18014
19571
|
});
|
|
18015
|
-
this.lib.setupTerminal(this.rendererPtr, this.
|
|
19572
|
+
this.lib.setupTerminal(this.rendererPtr, this._screenMode === "alternate-screen");
|
|
18016
19573
|
this._capabilities = this.lib.getTerminalCapabilities(this.rendererPtr);
|
|
18017
19574
|
if (this.debugOverlay.enabled) {
|
|
18018
19575
|
this.lib.setDebugOverlay(this.rendererPtr, true, this.debugOverlay.corner);
|
|
@@ -18585,6 +20142,7 @@ Captured output:
|
|
|
18585
20142
|
internalStart() {
|
|
18586
20143
|
if (!this._isRunning && !this._isDestroyed) {
|
|
18587
20144
|
this._isRunning = true;
|
|
20145
|
+
this.updateScheduled = false;
|
|
18588
20146
|
if (this.memorySnapshotInterval > 0) {
|
|
18589
20147
|
this.startMemorySnapshotTimer();
|
|
18590
20148
|
}
|
|
@@ -18672,15 +20230,15 @@ Captured output:
|
|
|
18672
20230
|
this._isDestroyed = true;
|
|
18673
20231
|
this._destroyPending = true;
|
|
18674
20232
|
if (this.rendering) {
|
|
20233
|
+
this.prepareDestroyDuringRender();
|
|
18675
20234
|
return;
|
|
18676
20235
|
}
|
|
18677
20236
|
this.finalizeDestroy();
|
|
18678
20237
|
}
|
|
18679
|
-
|
|
18680
|
-
if (this.
|
|
20238
|
+
cleanupBeforeDestroy() {
|
|
20239
|
+
if (this._destroyCleanupPrepared)
|
|
18681
20240
|
return;
|
|
18682
|
-
this.
|
|
18683
|
-
this._destroyPending = false;
|
|
20241
|
+
this._destroyCleanupPrepared = true;
|
|
18684
20242
|
process.removeListener("SIGWINCH", this.sigwinchHandler);
|
|
18685
20243
|
process.removeListener("uncaughtException", this.handleError);
|
|
18686
20244
|
process.removeListener("unhandledRejection", this.handleError);
|
|
@@ -18698,14 +20256,8 @@ Captured output:
|
|
|
18698
20256
|
}
|
|
18699
20257
|
if (this.memorySnapshotTimer) {
|
|
18700
20258
|
this.clock.clearInterval(this.memorySnapshotTimer);
|
|
20259
|
+
this.memorySnapshotTimer = null;
|
|
18701
20260
|
}
|
|
18702
|
-
if (this._paletteDetector) {
|
|
18703
|
-
this._paletteDetector.cleanup();
|
|
18704
|
-
this._paletteDetector = null;
|
|
18705
|
-
}
|
|
18706
|
-
this._paletteDetectionPromise = null;
|
|
18707
|
-
this._cachedPalette = null;
|
|
18708
|
-
this.emit("destroy" /* DESTROY */);
|
|
18709
20261
|
if (this.renderTimeout) {
|
|
18710
20262
|
this.clock.clearTimeout(this.renderTimeout);
|
|
18711
20263
|
this.renderTimeout = null;
|
|
@@ -18718,23 +20270,41 @@ Captured output:
|
|
|
18718
20270
|
explicitWidthCprActive: false
|
|
18719
20271
|
}, true);
|
|
18720
20272
|
this.setCapturedRenderable(undefined);
|
|
20273
|
+
this.stdin.removeListener("data", this.stdinListener);
|
|
20274
|
+
if (this.stdin.setRawMode) {
|
|
20275
|
+
this.stdin.setRawMode(false);
|
|
20276
|
+
}
|
|
20277
|
+
this.externalOutputMode = "passthrough";
|
|
20278
|
+
if (this._splitHeight > 0) {
|
|
20279
|
+
this.flushStdoutCache(this._splitHeight, true);
|
|
20280
|
+
}
|
|
20281
|
+
}
|
|
20282
|
+
prepareDestroyDuringRender() {
|
|
20283
|
+
this.cleanupBeforeDestroy();
|
|
20284
|
+
this.lib.suspendRenderer(this.rendererPtr);
|
|
20285
|
+
}
|
|
20286
|
+
finalizeDestroy() {
|
|
20287
|
+
if (this._destroyFinalized)
|
|
20288
|
+
return;
|
|
20289
|
+
this._destroyFinalized = true;
|
|
20290
|
+
this._destroyPending = false;
|
|
20291
|
+
this.cleanupBeforeDestroy();
|
|
20292
|
+
if (this._paletteDetector) {
|
|
20293
|
+
this._paletteDetector.cleanup();
|
|
20294
|
+
this._paletteDetector = null;
|
|
20295
|
+
}
|
|
20296
|
+
this._paletteDetectionPromise = null;
|
|
20297
|
+
this._cachedPalette = null;
|
|
20298
|
+
this.emit("destroy" /* DESTROY */);
|
|
18721
20299
|
try {
|
|
18722
20300
|
this.root.destroyRecursively();
|
|
18723
20301
|
} catch (e) {
|
|
18724
20302
|
console.error("Error destroying root renderable:", e instanceof Error ? e.stack : String(e));
|
|
18725
20303
|
}
|
|
18726
|
-
this.stdin.removeListener("data", this.stdinListener);
|
|
18727
|
-
if (this.stdin.setRawMode) {
|
|
18728
|
-
this.stdin.setRawMode(false);
|
|
18729
|
-
}
|
|
18730
20304
|
this.stdinParser?.destroy();
|
|
18731
20305
|
this.stdinParser = null;
|
|
18732
20306
|
this.oscSubscribers.clear();
|
|
18733
20307
|
this._console.destroy();
|
|
18734
|
-
this.disableStdoutInterception();
|
|
18735
|
-
if (this._splitHeight > 0) {
|
|
18736
|
-
this.flushStdoutCache(this._splitHeight, true);
|
|
18737
|
-
}
|
|
18738
20308
|
this.lib.destroyRenderer(this.rendererPtr);
|
|
18739
20309
|
rendererTracker.removeRenderer(this);
|
|
18740
20310
|
if (this._onDestroy) {
|
|
@@ -19029,7 +20599,7 @@ Captured output:
|
|
|
19029
20599
|
}
|
|
19030
20600
|
}
|
|
19031
20601
|
|
|
19032
|
-
export { __toESM, __commonJS, __export, __require, Edge, Gutter, MeasureMode, exports_src, isValidBorderStyle, parseBorderStyle, BorderChars, getBorderFromSides, getBorderSides, borderCharsToArray, BorderCharArrays, KeyEvent, PasteEvent, KeyHandler, InternalKeyHandler, RGBA, hexToRgb, rgbToHex, hsvToRgb, parseColor, fonts, measureText, getCharacterPositions, coordinateToCharacterIndex, renderFontToFrameBuffer, TextAttributes, ATTRIBUTE_BASE_BITS, ATTRIBUTE_BASE_MASK, getBaseAttributes, DebugOverlayCorner, TargetChannel, createTextAttributes, attributesWithLink, getLinkId, visualizeRenderableTree, isStyledText, StyledText, stringToStyledText, black, red, green, yellow, blue, magenta, cyan, white, brightBlack, brightRed, brightGreen, brightYellow, brightBlue, brightMagenta, brightCyan, brightWhite, bgBlack, bgRed, bgGreen, bgYellow, bgBlue, bgMagenta, bgCyan, bgWhite, bold, italic, underline, strikethrough, dim, reverse, blink, fg, bg, link, t, hastToStyledText, SystemClock, nonAlphanumericKeys, parseKeypress, LinearScrollAccel, MacOSScrollAccel, parseAlign, parseAlignItems, parseBoxSizing, parseDimension, parseDirection, parseDisplay, parseEdge, parseFlexDirection, parseGutter, parseJustify, parseLogLevel, parseMeasureMode, parseOverflow, parsePositionType, parseUnit, parseWrap, MouseParser, Selection, convertGlobalToLocalSelection, ASCIIFontSelectionHelper, envRegistry, registerEnvVar, clearEnvCache, generateEnvMarkdown, generateEnvColored, env, StdinParser, treeSitterToTextChunks, treeSitterToStyledText, addDefaultParsers, TreeSitterClient, DataPathsManager, getDataPaths, extensionToFiletype, basenameToFiletype, extToFiletype, pathToFiletype, infoStringToFiletype, main, getTreeSitterClient, ExtmarksController, createExtmarksController, TerminalPalette, createTerminalPalette, decodePasteBytes, stripAnsiSequences, detectLinks, TextBuffer, SpanInfoStruct, LogLevel2 as LogLevel, setRenderLibPath, resolveRenderLib, OptimizedBuffer, h, isVNode, maybeMakeRenderable, wrapWithDelegates, instantiate, delegate, isValidPercentage, LayoutEvents, RenderableEvents, isRenderable, BaseRenderable, Renderable, RootRenderable, ANSI, defaultKeyAliases, mergeKeyAliases, mergeKeyBindings, getKeyBindingKey, buildKeyBindingsMap, capture, ConsolePosition, TerminalConsole, getObjectsInViewport, buildKittyKeyboardFlags, MouseEvent, MouseButton, createCliRenderer, CliRenderEvents, RendererControlState, CliRenderer };
|
|
20602
|
+
export { __toESM, __commonJS, __export, __require, Edge, Gutter, MeasureMode, exports_src, isValidBorderStyle, parseBorderStyle, BorderChars, getBorderFromSides, getBorderSides, borderCharsToArray, BorderCharArrays, KeyEvent, PasteEvent, KeyHandler, InternalKeyHandler, RGBA, hexToRgb, rgbToHex, hsvToRgb, parseColor, fonts, measureText, getCharacterPositions, coordinateToCharacterIndex, renderFontToFrameBuffer, TextAttributes, ATTRIBUTE_BASE_BITS, ATTRIBUTE_BASE_MASK, getBaseAttributes, DebugOverlayCorner, TargetChannel, createTextAttributes, attributesWithLink, getLinkId, visualizeRenderableTree, isStyledText, StyledText, stringToStyledText, black, red, green, yellow, blue, magenta, cyan, white, brightBlack, brightRed, brightGreen, brightYellow, brightBlue, brightMagenta, brightCyan, brightWhite, bgBlack, bgRed, bgGreen, bgYellow, bgBlue, bgMagenta, bgCyan, bgWhite, bold, italic, underline, strikethrough, dim, reverse, blink, fg, bg, link, t, hastToStyledText, SystemClock, nonAlphanumericKeys, parseKeypress, LinearScrollAccel, MacOSScrollAccel, parseAlign, parseAlignItems, parseBoxSizing, parseDimension, parseDirection, parseDisplay, parseEdge, parseFlexDirection, parseGutter, parseJustify, parseLogLevel, parseMeasureMode, parseOverflow, parsePositionType, parseUnit, parseWrap, MouseParser, Selection, convertGlobalToLocalSelection, ASCIIFontSelectionHelper, envRegistry, registerEnvVar, clearEnvCache, generateEnvMarkdown, generateEnvColored, env, StdinParser, treeSitterToTextChunks, treeSitterToStyledText, addDefaultParsers, TreeSitterClient, DataPathsManager, getDataPaths, extensionToFiletype, basenameToFiletype, extToFiletype, pathToFiletype, infoStringToFiletype, main, getTreeSitterClient, ExtmarksController, createExtmarksController, TerminalPalette, createTerminalPalette, decodePasteBytes, stripAnsiSequences, detectLinks, TextBuffer, SpanInfoStruct, LogLevel2 as LogLevel, setRenderLibPath, resolveRenderLib, OptimizedBuffer, h, isVNode, maybeMakeRenderable, wrapWithDelegates, instantiate, delegate, isValidPercentage, LayoutEvents, RenderableEvents, isRenderable, BaseRenderable, Renderable, RootRenderable, EditBuffer, EditorView, ANSI, defaultKeyAliases, mergeKeyAliases, mergeKeyBindings, getKeyBindingKey, buildKeyBindingsMap, capture, ConsolePosition, TerminalConsole, getObjectsInViewport, EditBufferRenderableEvents, isEditBufferRenderable, EditBufferRenderable, buildKittyKeyboardFlags, MouseEvent, MouseButton, createCliRenderer, CliRenderEvents, RendererControlState, CliRenderer };
|
|
19033
20603
|
|
|
19034
|
-
//# debugId=
|
|
19035
|
-
//# sourceMappingURL=index-
|
|
20604
|
+
//# debugId=8662AB2ADD41165D64756E2164756E21
|
|
20605
|
+
//# sourceMappingURL=index-8z2zcznw.js.map
|