2024-04-27 23:09:12 -04:00
|
|
|
export type ProgressCallback = (progress: number) => any;
|
|
|
|
|
|
|
|
export class PromiseProgress<T> extends Promise<T> {
|
|
|
|
private listeners: ProgressCallback[] = [];
|
|
|
|
|
|
|
|
private _progress = 0;
|
|
|
|
get progress() { return this._progress; }
|
|
|
|
set progress(p: number) {
|
|
|
|
if(p == this._progress) return;
|
|
|
|
this._progress = p;
|
|
|
|
this.listeners.forEach(l => l(p));
|
|
|
|
}
|
|
|
|
|
|
|
|
constructor(executor: (resolve: (value: T) => any, reject: (reason: any) => void, progress: (progress: number) => any) => void) {
|
|
|
|
super((resolve, reject) => executor(
|
|
|
|
(value: T) => resolve(value),
|
|
|
|
(reason: any) => reject(reason),
|
2024-07-18 23:59:12 -04:00
|
|
|
(progress: number) => this.progress = progress,
|
2024-04-27 23:09:12 -04:00
|
|
|
));
|
|
|
|
}
|
|
|
|
|
2024-07-18 23:59:12 -04:00
|
|
|
static from<T>(promise: Promise<T>): PromiseProgress<T> {
|
|
|
|
if(promise instanceof PromiseProgress) return promise;
|
|
|
|
return new PromiseProgress<T>((res, rej) => promise
|
|
|
|
.then((...args) => res(...args))
|
|
|
|
.catch((...args) => rej(...args)));
|
|
|
|
}
|
|
|
|
|
|
|
|
private from(promise: Promise<T>): PromiseProgress<T> {
|
|
|
|
const newPromise = PromiseProgress.from(promise);
|
|
|
|
this.onProgress(p => newPromise.progress = p);
|
|
|
|
return newPromise;
|
|
|
|
}
|
|
|
|
|
2024-04-27 23:09:12 -04:00
|
|
|
onProgress(callback: ProgressCallback) {
|
|
|
|
this.listeners.push(callback);
|
|
|
|
return this;
|
|
|
|
}
|
2024-07-18 23:59:12 -04:00
|
|
|
|
|
|
|
then(res?: (v: T) => any, rej?: (err: any) => any): PromiseProgress<any> {
|
|
|
|
const resp = super.then(res, rej);
|
|
|
|
return this.from(resp);
|
|
|
|
}
|
|
|
|
|
|
|
|
catch(rej?: (err: any) => any): PromiseProgress<any> {
|
|
|
|
return this.from(super.catch(rej));
|
|
|
|
}
|
|
|
|
|
|
|
|
finally(res?: () => any): PromiseProgress<any> {
|
|
|
|
return this.from(super.finally(res));
|
|
|
|
}
|
2024-04-27 23:09:12 -04:00
|
|
|
}
|