A mismatch with real content causes a jump
Aliases: placeholder mismatch · loading jump · skeleton shift
What it is
A skeleton promises the structure about to arrive. If row heights, block counts, or image-and-type positions disagree when content lands, the picture reflows in an instant. That jump turns rehearsal into a broken promise: gaze was already on “where the title should be,” the real title sits at another height, three skeleton rows become ten real ones, and modules below are shoved. A skeleton’s value is a stable spatial forecast. A mismatch spends that forecast and the orientation at the moment of arrival; a blank start would have been cheaper.
Why it happens
Vision prepares to receive objects in the regions the skeleton drew. An object landing outside those regions forces a new partition and a new anchor; every orientation saving is paid back, plus a correction that “the previous picture is void.” The jump also moves content that already arrived: a first-screen button is pushed out of the viewport by a late image, and the coordinates a finger was aiming at have a new owner. Mismatch often comes from drawing the skeleton in an ideal tense (always a cover image, always three lines of summary) while real data has no image, half a line, or a whole module hidden by permission. Drawing the average still jumps on extremes; drawing the maximum leaves a hole that collapses when the content is short. The issue is not polish. It is whether the promised geometry is cashed.
Where it stops holding
Secondary jumps from font fallback or late image decode are not only the skeleton’s fault, but a skeleton that reserves the height of an already-present image at least blocks the first jump. An infinite list that skeletons only the first viewport will grow later rows; that is not mismatch if first-viewport geometry holds. Ads or recommendations injected into the live stream cannot be predicted; better not to draw that slot in the skeleton than to guess wrong. Switching from a skeleton into an empty state (there was no data) is also a broken structural promise; swap to the empty template quickly rather than popping fake cards and then collapsing them.
Applying it
- Screenshot several real shapes of the data: image / no image, short copy / long copy, few modules / many, and check whether the skeleton’s geometry can take them.
- If a block is optional (no cover), do not draw a cover slot in the skeleton; fewer blocks beat an extra block that later falls away.
- Reserve stable height for images and variable modules, and fade them in when decoded, so already-rendered type is not shoved again.
- Verify by overlaying skeleton and first frame, or by stepping the recording. If title, primary button, or first list row changed cells, mismatch already happened.
Related
- Within the group: E6.07.1 A skeleton screen expresses the structure of content about to arrive · E6.07.3 A long skeleton confuses more than a spinner
- Adjacent: E6.03 Inline validation · E6.08 Loading indicators · E4.19 Dialog size and responsiveness
- Search terms:
skeleton mismatch·layout jump·content shift