From f41273cd7852866dc72dd9430dd289ef62d97b4b Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 15 Dec 2021 10:42:36 +0100 Subject: [PATCH] add `Event.debouncedListener` as replacement for `debounce`, https://github.com/microsoft/vscode/issues/123487 --- src/vs/base/common/event.ts | 35 +++++++++++++++++-- .../notebook/browser/notebook.contribution.ts | 5 +-- 2 files changed, 35 insertions(+), 5 deletions(-) diff --git a/src/vs/base/common/event.ts b/src/vs/base/common/event.ts index 52631be0620..ecbac6597a7 100644 --- a/src/vs/base/common/event.ts +++ b/src/vs/base/common/event.ts @@ -119,16 +119,45 @@ export namespace Event { return emitter.event; } + export function debouncedListener(event: Event, listener: (data: O) => any, merge: (last: O | undefined, event: T) => O, delay: number = 100, leading: boolean = false): IDisposable { + + let output: O | undefined = undefined; + let handle: any = undefined; + let numDebouncedCalls = 0; + + return event(cur => { + numDebouncedCalls++; + output = merge(output, cur); + + if (leading && !handle) { + listener(output); + output = undefined; + } + + clearTimeout(handle); + handle = setTimeout(() => { + const _output = output; + output = undefined; + handle = undefined; + if (!leading || numDebouncedCalls > 1) { + listener(_output!); + } + + numDebouncedCalls = 0; + }, delay); + }); + } + /** - * @deprecated DO NOT use, this leaks memory + * @deprecated this leaks memory, {@link debouncedListener} or {@link DebounceEmitter} instead */ export function debounce(event: Event, merge: (last: T | undefined, event: T) => T, delay?: number, leading?: boolean, leakWarningThreshold?: number): Event; /** - * @deprecated DO NOT use, this leaks memory + * @deprecated this leaks memory, {@link debouncedListener} or {@link DebounceEmitter} instead */ export function debounce(event: Event, merge: (last: O | undefined, event: I) => O, delay?: number, leading?: boolean, leakWarningThreshold?: number): Event; /** - * @deprecated DO NOT use, this leaks memory + * @deprecated this leaks memory, {@link debouncedListener} or {@link DebounceEmitter} instead */ export function debounce(event: Event, merge: (last: O | undefined, event: I) => O, delay: number = 100, leading = false, leakWarningThreshold?: number): Event { diff --git a/src/vs/workbench/contrib/notebook/browser/notebook.contribution.ts b/src/vs/workbench/contrib/notebook/browser/notebook.contribution.ts index 7a5ea0f7d4f..635ead87134 100644 --- a/src/vs/workbench/contrib/notebook/browser/notebook.contribution.ts +++ b/src/vs/workbench/contrib/notebook/browser/notebook.contribution.ts @@ -504,11 +504,12 @@ class NotebookEditorManager implements IWorkbenchContribution { // OPEN notebook editor for models that have turned dirty without being visible in an editor type E = IResolvedNotebookEditorModel; - this._disposables.add(Event.debounce( + this._disposables.add(Event.debouncedListener( this._notebookEditorModelService.onDidChangeDirty, + this._openMissingDirtyNotebookEditors.bind(this), (last, current) => !last ? [current] : [...last, current], 100 - )(this._openMissingDirtyNotebookEditors, this)); + )); // CLOSE notebook editor for models that have no more serializer this._disposables.add(notebookService.onWillRemoveViewType(e => {