@swiftbrowser/web 0.10.0 → 0.10.1
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/package.json +1 -1
- package/src/browserHistory.ts +34 -12
package/package.json
CHANGED
package/src/browserHistory.ts
CHANGED
|
@@ -54,10 +54,19 @@ function shown(win: Window, el: HTMLElement): boolean {
|
|
|
54
54
|
return win.getComputedStyle(el).visibility !== 'hidden';
|
|
55
55
|
}
|
|
56
56
|
|
|
57
|
+
/** How long a back the browser made waits for the app to pop a level before what it shows is recorded as it is. */
|
|
58
|
+
const DISMISS_WAIT_MS = 1000;
|
|
59
|
+
|
|
57
60
|
export class BrowserHistory {
|
|
58
61
|
private readonly win: Window;
|
|
59
|
-
/**
|
|
60
|
-
|
|
62
|
+
/**
|
|
63
|
+
* A back the browser made, while the app pops to it: the depth the entry
|
|
64
|
+
* names, the depth the latest dismissal started from, and until when the
|
|
65
|
+
* app's pop is waited for. A pop can take more than one commit (a compact
|
|
66
|
+
* split view clears its sidebar selection first, and the detail goes on
|
|
67
|
+
* the next), so a commit that still shows the level is not a new one.
|
|
68
|
+
*/
|
|
69
|
+
private dismissing: { target: number; from: number; until: number } | null = null;
|
|
61
70
|
/** `popstate` events to ignore: the ones our own `history.go` causes. */
|
|
62
71
|
private ignorePops = 0;
|
|
63
72
|
/**
|
|
@@ -205,6 +214,15 @@ export class BrowserHistory {
|
|
|
205
214
|
return top ? Number(top.dataset['sbDepth'] ?? '0') || 0 : 0;
|
|
206
215
|
}
|
|
207
216
|
|
|
217
|
+
/** Dismisses the level above `depth` for the back in progress, and waits for the app's pop. */
|
|
218
|
+
private dismissFrom(depth: number): void {
|
|
219
|
+
const dismissing = this.dismissing;
|
|
220
|
+
if (!dismissing) return;
|
|
221
|
+
dismissing.from = depth;
|
|
222
|
+
dismissing.until = performance.now() + DISMISS_WAIT_MS;
|
|
223
|
+
if (!this.dismissOne()) this.dismissing = null;
|
|
224
|
+
}
|
|
225
|
+
|
|
208
226
|
/** Asks the app to dismiss one level: the top sheet when nothing is pushed inside it, else the deepest visible stack's top screen. */
|
|
209
227
|
private dismissOne(): boolean {
|
|
210
228
|
const sheets = this.sheets();
|
|
@@ -282,13 +300,16 @@ export class BrowserHistory {
|
|
|
282
300
|
const depth = this.depth();
|
|
283
301
|
const recorded = this.recorded();
|
|
284
302
|
const selection = this.selection();
|
|
285
|
-
|
|
303
|
+
const dismissing = this.dismissing;
|
|
304
|
+
if (dismissing) {
|
|
286
305
|
// Dismissing for a `popstate`: the entry already names the target depth.
|
|
287
|
-
if (depth >
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
306
|
+
if (depth > dismissing.target && performance.now() < dismissing.until) {
|
|
307
|
+
// The latest dismissal landed: the next level. Otherwise the app has not popped yet.
|
|
308
|
+
if (depth < dismissing.from) this.dismissFrom(depth);
|
|
309
|
+
return;
|
|
310
|
+
}
|
|
311
|
+
// Arrived, or the app kept the level (it is then recorded as any other).
|
|
312
|
+
this.dismissing = null;
|
|
292
313
|
}
|
|
293
314
|
if (depth > recorded) {
|
|
294
315
|
// Under our own pending `go`, a push would land relative to wherever the browser is when it runs (and
|
|
@@ -326,11 +347,12 @@ export class BrowserHistory {
|
|
|
326
347
|
// The browser moved on its own (a swipe, a button): keep painting past its transition.
|
|
327
348
|
this.renderer.keepRepainting();
|
|
328
349
|
const depth = this.depth();
|
|
350
|
+
// A move the browser makes replaces any back still in progress.
|
|
351
|
+
this.dismissing = null;
|
|
329
352
|
if (target.sbDepth < depth) {
|
|
330
|
-
// Back: dismiss one level now, the rest as each
|
|
331
|
-
this.
|
|
332
|
-
|
|
333
|
-
else this.pendingPops -= 1;
|
|
353
|
+
// Back: dismiss one level now, the rest as each pop lands.
|
|
354
|
+
this.dismissing = { target: target.sbDepth, from: depth, until: 0 };
|
|
355
|
+
this.dismissFrom(depth);
|
|
334
356
|
} else if (target.sbDepth > depth) {
|
|
335
357
|
// Forward: a screen cannot be re-pushed; return to the entry that matches.
|
|
336
358
|
this.go(depth - target.sbDepth, depth);
|