Skeleton screens
A spinner says "nothing is here yet." A grey ghost of the layout says "it's already arriving, this is its shape." Same 1,400ms wait, different verdict.
Modern interface craft is mostly a set of small, borrowed-from-physics lies. A grey box that pretends content is coming. A heart that turns red before the server has agreed. A list of ten thousand rows that only ever draws twenty. Every specimen below has a switch. Turn it off, watch the same interaction happen with the trick removed, and feel the difference in your gut rather than read about it.
The user's clock and the machine's clock are different clocks. These nine specimens all cheat the first one.
A spinner says "nothing is here yet." A grey ghost of the layout says "it's already arriving, this is its shape." Same 1,400ms wait, different verdict.
Paint the success before the server confirms it, then quietly reconcile. If the request fails, roll the interface back and say so. Every like button you have ever pressed works this way.
Ship a thumbnail so small it fits in the HTML — roughly a kilobyte — blur it hard, then cross-fade the real file over the top. The reader sees the colour and composition immediately and never faces an empty rectangle.
The gap between your cursor arriving on a link and your finger completing the click is roughly 200–300ms of free time. Spend it fetching the page. The click then resolves against something already in memory.
Rather than holding the whole response until the slowest query finishes, the server flushes the shell first and fills the holes as each part resolves. The page becomes readable and clickable long before it is complete.
Ten thousand rows exist in your data. About twenty exist on screen. Draw those twenty, keep a tall empty spacer so the scrollbar still tells the truth, and recycle as the user scrolls. Gmail, Slack and every feed you use do this.
Firing a request on every keystroke means eleven requests for the word "interfaces", ten of which are already stale by the time they land. Wait for a 300ms pause instead and send one.
Only ship the JavaScript this screen needs, then use the idle moments to pull down what the user is statistically about to open. The first load stays small and the second navigation costs nothing.
The strongest move is to delete the loading state entirely. Hold the data client-side, render from that instantly, and sync to the server in the background. This is why Linear and Figma feel structurally unlike a website.
Good motion is not decoration. It is the interface explaining what just happened to what.
An easing curve arrives and stops dead. A spring overshoots slightly, settles back, and reads as an object with mass. Your hand has held ten thousand objects with mass and knows the difference immediately.
When a thumbnail opens, the thumbnail should become the detail view rather than being replaced by it. The eye tracks one continuous object and never has to re-find its place.
Everything animating in at once is one event. The same items offset by 40ms each is a sequence, and a sequence reads as composed rather than dumped.
Four patterns the web borrowed back from phones, plus the one power users would riot over.
A sheet you can throw away with your thumb, with resistance when you pull the wrong way and a velocity threshold that lets a flick close it early. Closing stops being a target you have to hit.
Hide destructive and frequent actions under the row itself. The list stays clean for reading and stays fast for operating, which are usually two conflicting demands.
A secondary menu that costs nothing visually because it isn't drawn until you ask. Hold for half a second, feel the progress fill confirm that the interface understood, then choose.
One keystroke that reaches every action in the product without a mouse. Linear made it table stakes; for people who use an app daily it is the difference between a tool and a website.
Five ways to stop a screen from looking like a screen.
A blurred, slightly saturated sample of whatever sits behind the panel. It creates depth without a heavy shadow, and it tells you the thing underneath is still there rather than gone.
Real light does not cast one shadow at one blur radius. Stack three — tight and dark, medium, wide and faint — and the card stops looking like a rectangle with a grey smudge under it.
A faint noise layer over a gradient breaks up the banding that betrays a flat digital surface. It is the cheapest way to make a screen feel like a printed object.
Four or five colour points bleeding into each other from different corners, rather than a straight line between two hex values. Organic instead of ruled.
Pure black is a hole. Real dark mode sits on a dark grey around #121212, raises cards by getting lighter rather than by adding shadow, and desaturates accents so they stop vibrating against the ground.
Where a page gets its posture.
Oversized, tightly tracked, mixed weights inside a single line so hierarchy happens within the sentence instead of between elements. Gradient fill last, and sparingly.
Cells of deliberately different sizes locked into one grid. Size becomes a way of saying which thing matters, without a single heading.
Layers that scroll at different speeds read as layers at different distances. Restraint is the whole game — a few percent of differential is atmosphere, a lot of it is nausea.
Elements fade and rise as they cross into view, so a long page reads as a guided walk rather than a wall. You have been experiencing this specimen since you started scrolling.
Four one-second details, each of which someone argued about for a week.
A press that compresses two or three percent and brightens slightly confirms the action landed before any result exists. The ripple carries the same message outward from the exact point you touched.
The label lifts and shrinks into a caption, the border takes the accent, a soft ring appears. Three simultaneous signals that the system is listening to this field and no other.
A preview on hover removes a whole navigation for information-dense screens. A figure that counts up as it enters view turns a static number into an event worth reading.
"Saved" is information, not a decision. Information gets a toast that leaves on its own. A modal demands the user dismiss your success on your behalf, which breaks the flow they were in.
Your document was saved successfully.
Click anywhere to close and watch it travel home.