@react-x11/components 0.3.0 → 0.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +131 -4
- package/dist/charts/components.d.ts +3 -1
- package/dist/charts/components.d.ts.map +1 -1
- package/dist/charts/components.js +8 -4
- package/dist/charts/components.js.map +1 -1
- package/dist/charts/node.d.ts +13 -6
- package/dist/charts/node.d.ts.map +1 -1
- package/dist/charts/node.js +75 -24
- package/dist/charts/node.js.map +1 -1
- package/dist/charts/render.d.ts +4 -0
- package/dist/charts/render.d.ts.map +1 -1
- package/dist/charts/render.js +11 -6
- package/dist/charts/render.js.map +1 -1
- package/dist/code-editor/node.d.ts +47 -16
- package/dist/code-editor/node.d.ts.map +1 -1
- package/dist/code-editor/node.js +121 -51
- package/dist/code-editor/node.js.map +1 -1
- package/dist/flow/draw.d.ts +19 -1
- package/dist/flow/draw.d.ts.map +1 -1
- package/dist/flow/draw.js +64 -35
- package/dist/flow/draw.js.map +1 -1
- package/dist/flow/index.d.ts.map +1 -1
- package/dist/flow/index.js +24 -8
- package/dist/flow/index.js.map +1 -1
- package/dist/flow/model.d.ts +4 -2
- package/dist/flow/model.d.ts.map +1 -1
- package/dist/flow/model.js +4 -2
- package/dist/flow/model.js.map +1 -1
- package/dist/flow/node.d.ts +40 -9
- package/dist/flow/node.d.ts.map +1 -1
- package/dist/flow/node.js +142 -53
- package/dist/flow/node.js.map +1 -1
- package/dist/flow/types.d.ts +46 -21
- package/dist/flow/types.d.ts.map +1 -1
- package/dist/formula/index.d.ts +4 -2
- package/dist/formula/index.d.ts.map +1 -1
- package/dist/formula/index.js.map +1 -1
- package/dist/formula/node.d.ts +5 -1
- package/dist/formula/node.d.ts.map +1 -1
- package/dist/formula/node.js +19 -3
- package/dist/formula/node.js.map +1 -1
- package/dist/html/controls.d.ts +4 -1
- package/dist/html/controls.d.ts.map +1 -1
- package/dist/html/controls.js.map +1 -1
- package/dist/html/css/cascade.d.ts +11 -5
- package/dist/html/css/cascade.d.ts.map +1 -1
- package/dist/html/css/cascade.js +18 -8
- package/dist/html/css/cascade.js.map +1 -1
- package/dist/html/css/parse.d.ts +15 -10
- package/dist/html/css/parse.d.ts.map +1 -1
- package/dist/html/css/parse.js +41 -16
- package/dist/html/css/parse.js.map +1 -1
- package/dist/html/css/style.d.ts +3 -0
- package/dist/html/css/style.d.ts.map +1 -1
- package/dist/html/css/style.js +3 -1
- package/dist/html/css/style.js.map +1 -1
- package/dist/html/css/values.d.ts +14 -1
- package/dist/html/css/values.d.ts.map +1 -1
- package/dist/html/css/values.js +11 -8
- package/dist/html/css/values.js.map +1 -1
- package/dist/html/index.d.ts.map +1 -1
- package/dist/html/index.js +1 -0
- package/dist/html/index.js.map +1 -1
- package/dist/html/layout/boxes.d.ts +12 -5
- package/dist/html/layout/boxes.d.ts.map +1 -1
- package/dist/html/layout/boxes.js +7 -4
- package/dist/html/layout/boxes.js.map +1 -1
- package/dist/html/layout/inline.d.ts.map +1 -1
- package/dist/html/layout/inline.js +22 -1
- package/dist/html/layout/inline.js.map +1 -1
- package/dist/html/node.d.ts +22 -8
- package/dist/html/node.d.ts.map +1 -1
- package/dist/html/node.js +97 -15
- package/dist/html/node.js.map +1 -1
- package/dist/html/paint.d.ts +3 -0
- package/dist/html/paint.d.ts.map +1 -1
- package/dist/html/paint.js +2 -2
- package/dist/html/paint.js.map +1 -1
- package/dist/index.d.ts +11 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +26 -0
- package/dist/index.js.map +1 -1
- package/dist/maps/clip.d.ts +43 -0
- package/dist/maps/clip.d.ts.map +1 -0
- package/dist/maps/clip.js +171 -0
- package/dist/maps/clip.js.map +1 -0
- package/dist/maps/gzip.d.ts +15 -0
- package/dist/maps/gzip.d.ts.map +1 -0
- package/dist/maps/gzip.js +56 -0
- package/dist/maps/gzip.js.map +1 -0
- package/dist/maps/index.d.ts +55 -0
- package/dist/maps/index.d.ts.map +1 -0
- package/dist/maps/index.js +141 -0
- package/dist/maps/index.js.map +1 -0
- package/dist/maps/labels.d.ts +123 -0
- package/dist/maps/labels.d.ts.map +1 -0
- package/dist/maps/labels.js +323 -0
- package/dist/maps/labels.js.map +1 -0
- package/dist/maps/mvt.d.ts +244 -0
- package/dist/maps/mvt.d.ts.map +1 -0
- package/dist/maps/mvt.js +820 -0
- package/dist/maps/mvt.js.map +1 -0
- package/dist/maps/node.d.ts +278 -0
- package/dist/maps/node.d.ts.map +1 -0
- package/dist/maps/node.js +1459 -0
- package/dist/maps/node.js.map +1 -0
- package/dist/maps/overlay.d.ts +157 -0
- package/dist/maps/overlay.d.ts.map +1 -0
- package/dist/maps/overlay.js +472 -0
- package/dist/maps/overlay.js.map +1 -0
- package/dist/maps/paint.d.ts +226 -0
- package/dist/maps/paint.d.ts.map +1 -0
- package/dist/maps/paint.js +705 -0
- package/dist/maps/paint.js.map +1 -0
- package/dist/maps/proj.d.ts +281 -0
- package/dist/maps/proj.d.ts.map +1 -0
- package/dist/maps/proj.js +451 -0
- package/dist/maps/proj.js.map +1 -0
- package/dist/maps/sources.d.ts +256 -0
- package/dist/maps/sources.d.ts.map +1 -0
- package/dist/maps/sources.js +210 -0
- package/dist/maps/sources.js.map +1 -0
- package/dist/maps/style.d.ts +141 -0
- package/dist/maps/style.d.ts.map +1 -0
- package/dist/maps/style.js +147 -0
- package/dist/maps/style.js.map +1 -0
- package/dist/maps/styles.d.ts +82 -0
- package/dist/maps/styles.d.ts.map +1 -0
- package/dist/maps/styles.js +898 -0
- package/dist/maps/styles.js.map +1 -0
- package/dist/maps/tiles.d.ts +283 -0
- package/dist/maps/tiles.d.ts.map +1 -0
- package/dist/maps/tiles.js +469 -0
- package/dist/maps/tiles.js.map +1 -0
- package/dist/maps/types.d.ts +244 -0
- package/dist/maps/types.d.ts.map +1 -0
- package/dist/maps/types.js +2 -0
- package/dist/maps/types.js.map +1 -0
- package/dist/qml/containers.d.ts +3 -0
- package/dist/qml/containers.d.ts.map +1 -0
- package/dist/qml/containers.js +331 -0
- package/dist/qml/containers.js.map +1 -0
- package/dist/qml/controls.d.ts +12 -0
- package/dist/qml/controls.d.ts.map +1 -0
- package/dist/qml/controls.js +21 -0
- package/dist/qml/controls.js.map +1 -0
- package/dist/qml/globals.d.ts +6 -0
- package/dist/qml/globals.d.ts.map +1 -0
- package/dist/qml/globals.js +25 -0
- package/dist/qml/globals.js.map +1 -0
- package/dist/qml/index.d.ts +15 -0
- package/dist/qml/index.d.ts.map +1 -0
- package/dist/qml/index.js +25 -0
- package/dist/qml/index.js.map +1 -0
- package/dist/qml/interaction.d.ts +12 -0
- package/dist/qml/interaction.d.ts.map +1 -0
- package/dist/qml/interaction.js +246 -0
- package/dist/qml/interaction.js.map +1 -0
- package/dist/qml/ir.d.ts +106 -0
- package/dist/qml/ir.d.ts.map +1 -0
- package/dist/qml/ir.js +7 -0
- package/dist/qml/ir.js.map +1 -0
- package/dist/qml/layouts.d.ts +3 -0
- package/dist/qml/layouts.d.ts.map +1 -0
- package/dist/qml/layouts.js +122 -0
- package/dist/qml/layouts.js.map +1 -0
- package/dist/qml/models.d.ts +14 -0
- package/dist/qml/models.d.ts.map +1 -0
- package/dist/qml/models.js +80 -0
- package/dist/qml/models.js.map +1 -0
- package/dist/qml/objects.d.ts +228 -0
- package/dist/qml/objects.d.ts.map +1 -0
- package/dist/qml/objects.js +1103 -0
- package/dist/qml/objects.js.map +1 -0
- package/dist/qml/parse.d.ts +10 -0
- package/dist/qml/parse.d.ts.map +1 -0
- package/dist/qml/parse.js +607 -0
- package/dist/qml/parse.js.map +1 -0
- package/dist/qml/qtquick.d.ts +7 -0
- package/dist/qml/qtquick.d.ts.map +1 -0
- package/dist/qml/qtquick.js +347 -0
- package/dist/qml/qtquick.js.map +1 -0
- package/dist/qml/react.d.ts +83 -0
- package/dist/qml/react.d.ts.map +1 -0
- package/dist/qml/react.js +323 -0
- package/dist/qml/react.js.map +1 -0
- package/dist/qml/resolver.d.ts +38 -0
- package/dist/qml/resolver.d.ts.map +1 -0
- package/dist/qml/resolver.js +64 -0
- package/dist/qml/resolver.js.map +1 -0
- package/dist/qml/slots.d.ts +65 -0
- package/dist/qml/slots.d.ts.map +1 -0
- package/dist/qml/slots.js +230 -0
- package/dist/qml/slots.js.map +1 -0
- package/dist/qml/states.d.ts +5 -0
- package/dist/qml/states.d.ts.map +1 -0
- package/dist/qml/states.js +276 -0
- package/dist/qml/states.js.map +1 -0
- package/dist/qml/view-utils.d.ts +42 -0
- package/dist/qml/view-utils.d.ts.map +1 -0
- package/dist/qml/view-utils.js +121 -0
- package/dist/qml/view-utils.js.map +1 -0
- package/dist/reorder/hx.d.ts +18 -0
- package/dist/reorder/hx.d.ts.map +1 -0
- package/dist/reorder/hx.js +10 -0
- package/dist/reorder/hx.js.map +1 -0
- package/dist/reorder/index.d.ts +314 -0
- package/dist/reorder/index.d.ts.map +1 -0
- package/dist/reorder/index.js +1539 -0
- package/dist/reorder/index.js.map +1 -0
- package/dist/reorder/model.d.ts +107 -0
- package/dist/reorder/model.d.ts.map +1 -0
- package/dist/reorder/model.js +162 -0
- package/dist/reorder/model.js.map +1 -0
- package/dist/richtext/node.d.ts +15 -5
- package/dist/richtext/node.d.ts.map +1 -1
- package/dist/richtext/node.js +40 -11
- package/dist/richtext/node.js.map +1 -1
- package/dist/richtext/runs.d.ts +35 -13
- package/dist/richtext/runs.d.ts.map +1 -1
- package/dist/richtext/runs.js +83 -27
- package/dist/richtext/runs.js.map +1 -1
- package/dist/tabs/hx.d.ts +18 -0
- package/dist/tabs/hx.d.ts.map +1 -0
- package/dist/tabs/hx.js +10 -0
- package/dist/tabs/hx.js.map +1 -0
- package/dist/tabs/index.d.ts +160 -0
- package/dist/tabs/index.d.ts.map +1 -0
- package/dist/tabs/index.js +1265 -0
- package/dist/tabs/index.js.map +1 -0
- package/dist/terminal/vt/fonts.d.ts +45 -15
- package/dist/terminal/vt/fonts.d.ts.map +1 -1
- package/dist/terminal/vt/fonts.js +89 -19
- package/dist/terminal/vt/fonts.js.map +1 -1
- package/dist/terminal/vt/index.d.ts +1 -1
- package/dist/terminal/vt/index.d.ts.map +1 -1
- package/dist/terminal/vt/index.js +3 -3
- package/dist/terminal/vt/index.js.map +1 -1
- package/dist/terminal/vt/node.d.ts +42 -0
- package/dist/terminal/vt/node.d.ts.map +1 -1
- package/dist/terminal/vt/node.js +95 -11
- package/dist/terminal/vt/node.js.map +1 -1
- package/dist/terminal/vt/pty.d.ts +16 -0
- package/dist/terminal/vt/pty.d.ts.map +1 -1
- package/dist/terminal/vt/pty.js +186 -0
- package/dist/terminal/vt/pty.js.map +1 -1
- package/dist/terminal/vt/renderer.d.ts.map +1 -1
- package/dist/terminal/vt/renderer.js +13 -3
- package/dist/terminal/vt/renderer.js.map +1 -1
- package/package.json +23 -3
- package/src/charts/components.ts +14 -7
- package/src/charts/node.ts +81 -26
- package/src/charts/render.ts +16 -6
- package/src/code-editor/node.ts +147 -53
- package/src/flow/draw.ts +104 -35
- package/src/flow/index.ts +33 -13
- package/src/flow/model.ts +4 -2
- package/src/flow/node.ts +158 -59
- package/src/flow/types.ts +46 -21
- package/src/formula/index.ts +4 -2
- package/src/formula/node.ts +24 -5
- package/src/html/controls.ts +4 -1
- package/src/html/css/cascade.ts +18 -7
- package/src/html/css/parse.ts +46 -21
- package/src/html/css/style.ts +6 -1
- package/src/html/css/values.ts +25 -9
- package/src/html/index.ts +1 -0
- package/src/html/layout/boxes.ts +19 -9
- package/src/html/layout/inline.ts +23 -1
- package/src/html/node.ts +110 -17
- package/src/html/paint.ts +17 -2
- package/src/index.ts +142 -0
- package/src/maps/clip.ts +184 -0
- package/src/maps/gzip.ts +66 -0
- package/src/maps/index.ts +316 -0
- package/src/maps/labels.ts +442 -0
- package/src/maps/mvt.ts +857 -0
- package/src/maps/node.ts +1819 -0
- package/src/maps/overlay.ts +639 -0
- package/src/maps/paint.ts +978 -0
- package/src/maps/proj.ts +641 -0
- package/src/maps/sources.ts +425 -0
- package/src/maps/style.ts +309 -0
- package/src/maps/styles.ts +1040 -0
- package/src/maps/tiles.ts +676 -0
- package/src/maps/types.ts +260 -0
- package/src/qml/containers.tsx +380 -0
- package/src/qml/controls.tsx +47 -0
- package/src/qml/globals.ts +33 -0
- package/src/qml/index.ts +67 -0
- package/src/qml/interaction.tsx +317 -0
- package/src/qml/ir.ts +80 -0
- package/src/qml/layouts.tsx +141 -0
- package/src/qml/models.ts +101 -0
- package/src/qml/objects.ts +1431 -0
- package/src/qml/parse.ts +624 -0
- package/src/qml/qtquick.tsx +413 -0
- package/src/qml/react.tsx +454 -0
- package/src/qml/resolver.ts +99 -0
- package/src/qml/slots.ts +249 -0
- package/src/qml/states.ts +318 -0
- package/src/qml/view-utils.ts +140 -0
- package/src/reorder/hx.ts +31 -0
- package/src/reorder/index.ts +2223 -0
- package/src/reorder/model.ts +232 -0
- package/src/richtext/node.ts +49 -14
- package/src/richtext/runs.ts +115 -30
- package/src/tabs/hx.ts +31 -0
- package/src/tabs/index.ts +1686 -0
- package/src/terminal/vt/fonts.ts +128 -36
- package/src/terminal/vt/index.ts +4 -2
- package/src/terminal/vt/node.ts +105 -12
- package/src/terminal/vt/pty.ts +243 -0
- package/src/terminal/vt/renderer.ts +13 -3
package/src/terminal/vt/pty.ts
CHANGED
|
@@ -332,3 +332,246 @@ export function nodePtyHost(): PtyHost {
|
|
|
332
332
|
sharedHost = host;
|
|
333
333
|
return host;
|
|
334
334
|
}
|
|
335
|
+
|
|
336
|
+
// --- the Bun implementation ------------------------------------------------
|
|
337
|
+
|
|
338
|
+
/**
|
|
339
|
+
* Bun's built-in pty, as of Bun 1.4: `Bun.spawn(argv, { terminal })` hands
|
|
340
|
+
* back a `Terminal` on the subprocess.
|
|
341
|
+
*
|
|
342
|
+
* This exists for the reason the whole file exists in the first place — a pty
|
|
343
|
+
* should not cost 64 MB and a native build. Under Bun it costs nothing: the
|
|
344
|
+
* pty is the runtime's, so `node-pty` is not installed, not probed, and not
|
|
345
|
+
* loaded, and the vt backend works out of the box on a machine with no C
|
|
346
|
+
* toolchain. Same argument as `@xterm/headless` being lazy: an app should not
|
|
347
|
+
* pay for what its runtime already provides.
|
|
348
|
+
*
|
|
349
|
+
* Written structurally, like `NodePty` above and for the same two reasons:
|
|
350
|
+
* `src/` may not name another runtime's types, and `@types/bun` is not
|
|
351
|
+
* installed here (nor in a Node app that merely imports this package).
|
|
352
|
+
*/
|
|
353
|
+
interface BunTerminalHandle {
|
|
354
|
+
write(data: string | Uint8Array): void;
|
|
355
|
+
resize(cols: number, rows: number): void;
|
|
356
|
+
close(): void;
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
interface BunSubprocess {
|
|
360
|
+
readonly pid: number;
|
|
361
|
+
readonly exitCode: number | null;
|
|
362
|
+
readonly signalCode: string | null;
|
|
363
|
+
readonly exited: Promise<number>;
|
|
364
|
+
readonly terminal?: BunTerminalHandle | null;
|
|
365
|
+
kill(signal?: string | number): void;
|
|
366
|
+
}
|
|
367
|
+
|
|
368
|
+
interface BunRuntime {
|
|
369
|
+
/** The pty class. Present from 1.4 — this is the feature detector. */
|
|
370
|
+
Terminal?: unknown;
|
|
371
|
+
spawn(
|
|
372
|
+
argv: readonly string[],
|
|
373
|
+
options: {
|
|
374
|
+
cwd?: string;
|
|
375
|
+
env?: Record<string, string | undefined>;
|
|
376
|
+
terminal?: {
|
|
377
|
+
cols?: number;
|
|
378
|
+
rows?: number;
|
|
379
|
+
data?(terminal: BunTerminalHandle, chunk: Uint8Array): void;
|
|
380
|
+
};
|
|
381
|
+
},
|
|
382
|
+
): BunSubprocess;
|
|
383
|
+
}
|
|
384
|
+
|
|
385
|
+
/**
|
|
386
|
+
* The Bun runtime, if this is Bun *and* its Bun is new enough to have a pty.
|
|
387
|
+
*
|
|
388
|
+
* `Bun.Terminal` rather than a parse of `Bun.version`: the `terminal` option
|
|
389
|
+
* is ignored rather than rejected by a Bun that predates it, so a version
|
|
390
|
+
* comparison is the difference between falling through to node-pty and
|
|
391
|
+
* spawning a child whose output goes nowhere.
|
|
392
|
+
*/
|
|
393
|
+
function bunRuntime(): BunRuntime | null {
|
|
394
|
+
const bun = (globalThis as { Bun?: BunRuntime }).Bun;
|
|
395
|
+
if (!bun || typeof bun.spawn !== 'function') return null;
|
|
396
|
+
return typeof bun.Terminal === 'function' ? bun : null;
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
class BunPtySession implements PtySession {
|
|
400
|
+
#proc: BunSubprocess;
|
|
401
|
+
#term: BunTerminalHandle;
|
|
402
|
+
#alive = true;
|
|
403
|
+
// Bun takes the output callback as a *spawn option*, so bytes can land
|
|
404
|
+
// before `openPty` has even returned — let alone before the caller has
|
|
405
|
+
// called `onData`. Anything that arrives in that window is held here and
|
|
406
|
+
// flushed on attach; without it the shell's first prompt is a coin flip.
|
|
407
|
+
#backlog: Uint8Array[] = [];
|
|
408
|
+
#data: ((chunk: Uint8Array) => void) | null = null;
|
|
409
|
+
// Same race, one step later: a program that exits immediately settles
|
|
410
|
+
// `exited` before `onExit` is attached.
|
|
411
|
+
#exit: ExitInfo | null = null;
|
|
412
|
+
#onExit: ((info: ExitInfo) => void) | null = null;
|
|
413
|
+
|
|
414
|
+
constructor(proc: BunSubprocess, term: BunTerminalHandle) {
|
|
415
|
+
this.#proc = proc;
|
|
416
|
+
this.#term = term;
|
|
417
|
+
void proc.exited.then(() => {
|
|
418
|
+
this.#alive = false;
|
|
419
|
+
// Bun reports the signal by *name* (`'SIGTERM'`) and nulls `exitCode`
|
|
420
|
+
// when one ended the child — which is `ExitInfo` exactly, so unlike the
|
|
421
|
+
// node-pty path there is no number to stringify and no name table to
|
|
422
|
+
// get wrong per platform.
|
|
423
|
+
const info: ExitInfo = {
|
|
424
|
+
code: proc.signalCode ? null : (proc.exitCode ?? 0),
|
|
425
|
+
signal: proc.signalCode ?? null,
|
|
426
|
+
};
|
|
427
|
+
if (this.#onExit) this.#onExit(info);
|
|
428
|
+
else this.#exit = info;
|
|
429
|
+
});
|
|
430
|
+
}
|
|
431
|
+
|
|
432
|
+
/** Called from the spawn-time `data` callback. */
|
|
433
|
+
receive(chunk: Uint8Array): void {
|
|
434
|
+
if (this.#data) this.#data(chunk);
|
|
435
|
+
else this.#backlog.push(chunk);
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
get pid(): number | null {
|
|
439
|
+
return this.#alive ? this.#proc.pid : null;
|
|
440
|
+
}
|
|
441
|
+
|
|
442
|
+
write(data: string): void {
|
|
443
|
+
if (!this.#alive) return;
|
|
444
|
+
try {
|
|
445
|
+
this.#term.write(data);
|
|
446
|
+
} catch {
|
|
447
|
+
// the child exited between the keystroke and this write
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
resize(cols: number, rows: number): void {
|
|
452
|
+
if (!this.#alive || cols <= 0 || rows <= 0) return;
|
|
453
|
+
try {
|
|
454
|
+
this.#term.resize(cols, rows);
|
|
455
|
+
} catch {
|
|
456
|
+
// same race as write
|
|
457
|
+
}
|
|
458
|
+
}
|
|
459
|
+
|
|
460
|
+
kill(signal = 'SIGTERM'): boolean {
|
|
461
|
+
if (!this.#alive) return false;
|
|
462
|
+
try {
|
|
463
|
+
this.#proc.kill(signal);
|
|
464
|
+
return true;
|
|
465
|
+
} catch {
|
|
466
|
+
return false;
|
|
467
|
+
}
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
onData(listener: (chunk: Uint8Array) => void): void {
|
|
471
|
+
this.#data = listener;
|
|
472
|
+
// Bytes, not a string: Bun hands over a `Buffer`, and the emulator's
|
|
473
|
+
// decoder is stateful across chunks. Decoding here would split a
|
|
474
|
+
// multi-byte character on whatever boundary the pty read returned.
|
|
475
|
+
const held = this.#backlog;
|
|
476
|
+
this.#backlog = [];
|
|
477
|
+
for (const chunk of held) listener(chunk);
|
|
478
|
+
}
|
|
479
|
+
|
|
480
|
+
onExit(listener: (info: ExitInfo) => void): void {
|
|
481
|
+
this.#onExit = listener;
|
|
482
|
+
if (this.#exit) {
|
|
483
|
+
const info = this.#exit;
|
|
484
|
+
this.#exit = null;
|
|
485
|
+
listener(info);
|
|
486
|
+
}
|
|
487
|
+
}
|
|
488
|
+
|
|
489
|
+
// No `pause`/`resume`: Bun's terminal has no flow control to expose, and
|
|
490
|
+
// the interface makes them optional for exactly this case. The emulator's
|
|
491
|
+
// own write queue still bounds parse work per tick; only the pipe's
|
|
492
|
+
// buffered bytes grow.
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
let sharedBunHost: PtyHost | null = null;
|
|
496
|
+
|
|
497
|
+
/**
|
|
498
|
+
* The runtime's own pty. Null-free: callers reach it through
|
|
499
|
+
* `defaultPtyHost()`, and `available()` answers honestly under Node.
|
|
500
|
+
*/
|
|
501
|
+
export function bunPtyHost(): PtyHost {
|
|
502
|
+
if (sharedBunHost) return sharedBunHost;
|
|
503
|
+
|
|
504
|
+
const host: PtyHost = {
|
|
505
|
+
environment() {
|
|
506
|
+
return nodeProcess()?.env ?? {};
|
|
507
|
+
},
|
|
508
|
+
|
|
509
|
+
async available() {
|
|
510
|
+
return bunRuntime() !== null;
|
|
511
|
+
},
|
|
512
|
+
|
|
513
|
+
async openPty(argv, options) {
|
|
514
|
+
const bun = bunRuntime();
|
|
515
|
+
if (!bun) throw new PtyUnavailableError();
|
|
516
|
+
const ambient = host.environment?.() ?? {};
|
|
517
|
+
const merged: Record<string, string> = {};
|
|
518
|
+
for (const [key, value] of Object.entries({
|
|
519
|
+
...ambient,
|
|
520
|
+
...options.env,
|
|
521
|
+
})) {
|
|
522
|
+
// An explicit `undefined` removes a variable, as `SpawnOptions` says
|
|
523
|
+
if (value !== undefined) merged[key] = String(value);
|
|
524
|
+
}
|
|
525
|
+
// Bun sets no `TERM` of its own — the pty is a device, not a profile —
|
|
526
|
+
// so the honest advertisement is made here, as the node-pty path makes
|
|
527
|
+
// it through node-pty's `name`.
|
|
528
|
+
merged.TERM ??= 'xterm-256color';
|
|
529
|
+
const file = argv[0] ?? defaultShell(ambient);
|
|
530
|
+
let session: BunPtySession | null = null;
|
|
531
|
+
const proc = bun.spawn([file, ...argv.slice(1)], {
|
|
532
|
+
cwd: options.cwd,
|
|
533
|
+
env: merged,
|
|
534
|
+
terminal: {
|
|
535
|
+
cols: options.cols,
|
|
536
|
+
rows: options.rows,
|
|
537
|
+
data(_terminal, chunk) {
|
|
538
|
+
session?.receive(chunk);
|
|
539
|
+
},
|
|
540
|
+
},
|
|
541
|
+
});
|
|
542
|
+
const term = proc.terminal;
|
|
543
|
+
if (!term) {
|
|
544
|
+
// A Bun that has `Terminal` but did not give us one back: kill the
|
|
545
|
+
// child rather than leak it, and report it as a load failure so the
|
|
546
|
+
// caller renders `fallback` instead of an empty terminal.
|
|
547
|
+
try {
|
|
548
|
+
proc.kill();
|
|
549
|
+
} catch {
|
|
550
|
+
// already gone
|
|
551
|
+
}
|
|
552
|
+
throw new PtyUnavailableError(
|
|
553
|
+
new Error('Bun.spawn returned no terminal for a pty request'),
|
|
554
|
+
);
|
|
555
|
+
}
|
|
556
|
+
session = new BunPtySession(proc, term);
|
|
557
|
+
return session;
|
|
558
|
+
},
|
|
559
|
+
};
|
|
560
|
+
|
|
561
|
+
sharedBunHost = host;
|
|
562
|
+
return host;
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
/**
|
|
566
|
+
* The pty the current runtime should use: Bun's own where there is one,
|
|
567
|
+
* `node-pty` otherwise.
|
|
568
|
+
*
|
|
569
|
+
* Bun wins on purpose even when node-pty is installed and would load (Bun's
|
|
570
|
+
* N-API support is good enough that it does). The built-in needs no native
|
|
571
|
+
* build, no ABI match and no 64 MB, and "use what the runtime provides" is
|
|
572
|
+
* the same call this package makes everywhere else. An app that wants the
|
|
573
|
+
* other one back passes `pty={nodePtyHost()}`, which is what the seam is for.
|
|
574
|
+
*/
|
|
575
|
+
export function defaultPtyHost(): PtyHost {
|
|
576
|
+
return bunRuntime() ? bunPtyHost() : nodePtyHost();
|
|
577
|
+
}
|
|
@@ -425,15 +425,25 @@ export class RetainedRenderer extends BatchingRenderer {
|
|
|
425
425
|
const metrics = this._metrics;
|
|
426
426
|
if (!surface || !metrics || count <= 0 || srcRow === dstRow) return false;
|
|
427
427
|
const h = metrics.cellHeight;
|
|
428
|
+
const delta = dstRow - srcRow;
|
|
429
|
+
// `copyWithin(rect, dx, dy)` is `scrollRegion` for a surface: it shifts
|
|
430
|
+
// the pixels *within* `rect` and writes nothing outside it — the band
|
|
431
|
+
// that survives is `rect ∩ (rect + delta)`. So the rect is the union of
|
|
432
|
+
// the source rows and the destination rows, not the source alone. Handed
|
|
433
|
+
// only the source, a scroll up by one moved rows 2… into rows 1… and
|
|
434
|
+
// never wrote row 0, while the mirror — shifted as a block — believed
|
|
435
|
+
// the old row 1 had landed there, so the top line stayed stale after
|
|
436
|
+
// every scroll (issue #60). With the union, the surviving band is exactly
|
|
437
|
+
// `dstRow…dstRow+count`, sourced from exactly `srcRow…srcRow+count`.
|
|
428
438
|
const ok = surface.copyWithin(
|
|
429
439
|
{
|
|
430
440
|
x: 0,
|
|
431
|
-
y: srcRow * h,
|
|
441
|
+
y: Math.min(srcRow, dstRow) * h,
|
|
432
442
|
width: this._cols * metrics.cellWidth,
|
|
433
|
-
height: count * h,
|
|
443
|
+
height: (count + Math.abs(delta)) * h,
|
|
434
444
|
},
|
|
435
445
|
0,
|
|
436
|
-
|
|
446
|
+
delta * h,
|
|
437
447
|
);
|
|
438
448
|
if (ok) this.count('copies');
|
|
439
449
|
return ok;
|