Performance complaints rarely start in your profiler.
Users don’t say:
“Your main thread is blocked for 300ms.”
They say:
“This app feels slow.”
And most of the time? They’re reacting to UX latency, not actual performance.
Let’s break down why — and how to fix it.
⚡ Perceived Performance > Actual Performance
Humans don’t experience time objectively. We experience feedback.
A 500ms delay with feedback feels faster than a 100ms delay with silence.
That’s why:
- A loading spinner can feel fast
- A frozen screen feels broken
Your app may be technically fast — but emotionally unresponsive.
🧠 The UX Latency Trifecta
1. No Immediate Feedback
User taps a button.
Nothing happens.
Even if your API responds in 200ms, the brain already decided:
“This didn’t work.”
Fix it:
- Button press states
- Instant visual changes
- Optimistic UI
button.addEventListener("click", () => {
button.classList.add("loading")
})
2. Blocking Transitions
Hard cuts feel slow.
Abrupt layout shifts feel broken.
Smooth transitions buy you time.
Fix it:
- Fade
- Slide
- Skeleton screens
.card {
transition: opacity 150ms ease, transform 150ms ease;
}
3. Unpredictable Waiting
The worst UX sin:
“I don’t know how long this will take.”
Spinners without context increase anxiety.
Fix it:
- Progress indicators
- Step-based loaders
- Honest microcopy
<p>Uploading image (2 of 5)…</p>
🦴 Skeleton Screens Beat Spinners
Spinners say:
“Wait.”
Skeletons say:
“Content is coming.”
Users perceive skeletons as **faste
Top comments (0)