fix: defer viewport DOM sync during synchronized output
Defer Viewport DOM scroll updates while DEC 2026 synchronized output is active, then flush once rendering resumes so DOM and canvas update atomically. Also update demo sizing to avoid relying on removed internal viewport scrollBarWidth.
This commit is contained in:
@@ -617,8 +617,12 @@ function addDomListener(element: HTMLElement, type: string, handler: (...args: a
|
||||
}
|
||||
|
||||
function updateTerminalSize(): void {
|
||||
const showScrollbar = term!.options.scrollbar?.showScrollbar ?? true;
|
||||
const scrollBarWidth = (term!.options.scrollback === 0 || !showScrollbar)
|
||||
? 0
|
||||
: (term!.options.scrollbar?.width ?? 14);
|
||||
const width = optionsWindow.autoResize ? '100%'
|
||||
: ((term as any).dimensions.css.canvas.width + (term as any)._core.viewport.scrollBarWidth).toString() + 'px';
|
||||
: ((term as any).dimensions.css.canvas.width + scrollBarWidth).toString() + 'px';
|
||||
const height = optionsWindow.autoResize ? '100%'
|
||||
: ((term as any).dimensions.css.canvas.height).toString() + 'px';
|
||||
terminalContainer!.style.width = width;
|
||||
|
||||
+17
-2
@@ -27,6 +27,7 @@ export class Viewport extends Disposable {
|
||||
private _isSyncing: boolean = false;
|
||||
private _isHandlingScroll: boolean = false;
|
||||
private _suppressOnScrollHandler: boolean = false;
|
||||
private _needsSyncOnRender: boolean = false;
|
||||
|
||||
constructor(
|
||||
element: HTMLElement,
|
||||
@@ -105,6 +106,16 @@ export class Viewport extends Disposable {
|
||||
}));
|
||||
this._register(this._bufferService.onScroll(() => this._sync()));
|
||||
|
||||
// Flush deferred viewport sync after a render completes (e.g. after ESU ends
|
||||
// synchronized output mode). This ensures DOM scroll position updates atomically
|
||||
// with the canvas render.
|
||||
this._register(this._renderService.onRender(() => {
|
||||
if (this._needsSyncOnRender) {
|
||||
this._needsSyncOnRender = false;
|
||||
this._sync();
|
||||
}
|
||||
}));
|
||||
|
||||
this._register(this._scrollableElement.onScroll(e => this._handleScroll(e)));
|
||||
|
||||
}
|
||||
@@ -162,8 +173,12 @@ export class Viewport extends Disposable {
|
||||
if (!this._renderService || this._isSyncing) {
|
||||
return;
|
||||
}
|
||||
// Plumb synchronized output state into Viewport for follow-up behavior changes.
|
||||
void this._coreService.decPrivateModes.synchronizedOutput;
|
||||
// Defer DOM scroll updates during synchronized output to prevent visible
|
||||
// scroll position flickering while the canvas content is frozen.
|
||||
if (this._coreService.decPrivateModes.synchronizedOutput) {
|
||||
this._needsSyncOnRender = true;
|
||||
return;
|
||||
}
|
||||
this._isSyncing = true;
|
||||
|
||||
// Ignore any onScroll event that happens as a result of dimensions changing as this should
|
||||
|
||||
Reference in New Issue
Block a user