fix(reader): gate route View Transitions on API support (READEST-9) (#4989)
* fix(reader): gate route View Transitions on the API, turns on groups (READEST-9) Reverts #4949, which opened books through the plain router to dodge the "Transition was aborted because of timeout in DOM update" TimeoutError (Sentry READEST-9). Rather than carve the transition out of one flow, gate it at the router: useAppRouter routes through the View Transition router only where the engine has the View Transitions API, and every into-reader path (including the reverted ones) goes back through useAppRouter. The base View Transitions API and nested view-transition groups reach very different browsers, so they become two separate appService capability flags, each backed by a probe in utils/viewTransition: * supportsViewTransitionsAPI (document.startViewTransition): the baseline a route crossfade needs, landing on Chrome 111+, Safari 18+, recent WebView. Gates the router. * supportsViewTransitionGroup (view-transition-group: nearest, Chrome/WebView 140+): the far narrower target the paginator's layered turns require. Gates the turn-style options and the captured-turn fallback. Both flags fold in the Linux WebKitGTK carve-out because it crashes on the snapshot, matching the supportsCanvasContext2DFilter precedent. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix(tts): enlarge the Now Playing bar and scale its controls responsively Grow the collapsed bar to h-14 with a 10x10 cover and symmetric px-2 padding, drive the play/pause and close icons through useResponsiveSize instead of fixed pixel sizes, and cut the bottom safe-area contribution to a third so the bar sits closer to the screen edge. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -5,6 +5,7 @@ import { useBookDataStore } from '@/store/bookDataStore';
|
||||
import { useReaderStore } from '@/store/readerStore';
|
||||
import { captureWebviewRegion } from '@/utils/bridge';
|
||||
import { isTauriAppPlatform } from '@/services/environment';
|
||||
import { detectViewTransitionGroup } from '@/utils/viewTransition';
|
||||
import { CapturedPageTurn, CapturedTurnStyle } from '../utils/capturedTurn';
|
||||
import { useTouchInterceptor } from './useTouchInterceptor';
|
||||
|
||||
@@ -13,21 +14,6 @@ import { useTouchInterceptor } from './useTouchInterceptor';
|
||||
// take over where the engine supports them, push everywhere else.
|
||||
let captureBroken = false;
|
||||
|
||||
/**
|
||||
* Whether the engine runs the paginator's layered View Transition turns
|
||||
* reliably. iOS 18 WebKit ships `document.startViewTransition` but crashes
|
||||
* the WebContent process when a turn transition snapshots the reader, so
|
||||
* the presence of the API is not enough; nested view-transition groups
|
||||
* (Chrome/WebView 140+) mark the mature engines where the layered turns
|
||||
* are known to work.
|
||||
*/
|
||||
export const supportsViewTransitionTurns = (): boolean =>
|
||||
typeof document !== 'undefined' &&
|
||||
'startViewTransition' in document &&
|
||||
typeof CSS !== 'undefined' &&
|
||||
typeof CSS.supports === 'function' &&
|
||||
CSS.supports('view-transition-group', 'nearest');
|
||||
|
||||
/**
|
||||
* The turn style the captured-page pipeline should drive for this view, or
|
||||
* null when the paginator's own turns apply. The pipeline needs a native
|
||||
@@ -46,7 +32,7 @@ export const getCapturedTurnStyle = (
|
||||
return null;
|
||||
}
|
||||
if (viewSettings.pageTurnStyle === 'curl') return 'curl';
|
||||
if (viewSettings.pageTurnStyle === 'slide' && !supportsViewTransitionTurns()) return 'slide';
|
||||
if (viewSettings.pageTurnStyle === 'slide' && !detectViewTransitionGroup()) return 'slide';
|
||||
return null;
|
||||
};
|
||||
|
||||
@@ -66,7 +52,7 @@ export const applyPageTurnAttributes = (
|
||||
) => {
|
||||
const captured = getCapturedTurnStyle(viewSettings, isFixedLayout);
|
||||
const style = viewSettings.pageTurnStyle;
|
||||
if (style && style !== 'push' && !captured && supportsViewTransitionTurns()) {
|
||||
if (style && style !== 'push' && !captured && detectViewTransitionGroup()) {
|
||||
view.renderer.setAttribute('turn-style', style);
|
||||
} else {
|
||||
view.renderer.removeAttribute('turn-style');
|
||||
|
||||
Reference in New Issue
Block a user