Turn the phone in one step, not through every shape
A turn is not one shape change: the viewport passes through every shape between the one it left and the one it lands in, and each of them re-letterboxes the picture somewhere else. Painted, that run of hard jumps is the stutter. So for the length of a turn the slides are held at the size they already had, and the moment the viewport stops moving they take the size it ended at -- measured, not guessed. The picture moves exactly once, straight into the position and size it then keeps. The device's own `orientationchange` starts the hold, which is the earliest anything can know a turn is coming and the one signal that separates it from a window being dragged wider; failing that, the viewport swapping its long side for its short one does. A viewport that only changes height is the browser's chrome sliding away, and is never held. Underneath: snapping is off while the slides are held, so the container cannot re-anchor on the old height at the same time; a scroll arriving during the window is put back in the event rather than a frame later, so the stale position is never painted; and the per-frame realign only writes what actually differs instead of costing a layout sixty times a second. Measured over a recorded turn: the picture moves 12 times -> 2, once per turn; the worst of those was a 660px jump between two intermediate shapes and is now the one step into the final size; the reel is never off its step (was 660px out); and the clip never pauses. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MPZFnNdHbPGDTqQUNiE4ZN
This commit is contained in:
@@ -2236,6 +2236,27 @@ body.feed-mode-open .mode-toggle-btn .icon-svg {
|
||||
height: 1px;
|
||||
}
|
||||
|
||||
/* A turn goes through every shape between the one it left and the one it
|
||||
lands in, and each of those re-letterboxes the picture somewhere else --
|
||||
a run of jumps where there should be one. So for the length of the turn
|
||||
the slides are held at the size it is heading for (feed.js sets the two
|
||||
numbers): the picture moves once, straight into its final position and
|
||||
size, and stays there while the viewport catches up to it. */
|
||||
.feed-view.is-turning .feed-slide {
|
||||
width: var(--turn-w);
|
||||
height: var(--turn-h);
|
||||
}
|
||||
|
||||
.feed-view.is-turning .feed-scroll {
|
||||
/* The pinned slides are a different shape from the viewport until the turn
|
||||
finishes, and none of that overflow is for scrolling through. Snapping
|
||||
is off with it: the container would otherwise be re-anchoring on the old
|
||||
height at the same time as the feed is pinning itself to the new one. */
|
||||
overflow: hidden;
|
||||
scroll-snap-type: none;
|
||||
scroll-behavior: auto;
|
||||
}
|
||||
|
||||
/* Stands in for the slides above the rendered window so scroll position and
|
||||
snap points stay stable while slides are virtualized in and out. */
|
||||
.feed-top-spacer {
|
||||
|
||||
Reference in New Issue
Block a user