The Waiting State Is Not Empty: How to Design for Suspense, Not Just Speed

‎

Hatched by

May 11, 2026

9 min read

37%

0

The most important part of an answer is the moment before it arrives

Most digital experiences are judged by a simple metric: how fast do they feel? But that question hides a deeper one: what is the user supposed to feel while they are waiting? A blank pause can feel like negligence. A clear pause can feel like momentum. The difference is not technical, it is psychological.

That is why a tiny pattern like an await block carries a surprisingly large idea. In a few lines, it makes waiting legible:

{#await promise}
  <p>...waiting</p>
{:then number}
  <p>The number is {number}</p>
{:catch error}
  <p style="color: red">{error.message}</p>
{/await}

This is more than a syntax convenience. It is a design philosophy: do not treat uncertainty as a bug in the interface, treat it as a state of the interface. The user is not bouncing between success and failure. They are moving through a sequence of expectations, each with its own emotional needs.

The most thoughtful systems do not erase waiting. They shape it.


Waiting is not a void, it is a narrative

When people say they want something to be “fast,” they often mean something more specific. They want the system to feel predictable, intelligible, and under control. A loading state that simply spins can technically be correct and emotionally bankrupt. It says, in effect, “Something is happening, but you are not invited to understand it.”

The await pattern gives waiting a plot structure. There is a beginning, a middle, and an end. The user starts in suspense, moves into resolution, and if needed, receives a failure message that is not hidden inside the machinery. That structure matters because the mind does not experience time as a stopwatch. It experiences time as a sequence of expectations.

Think of ordering coffee in a café. If the barista says nothing, the delay feels longer and more annoying. If the barista says, “It will be three minutes, and I will call your name,” the exact same delay becomes easier to bear. The duration did not change, but the meaning of the duration did.

This is the central insight: good interfaces do not merely minimize waiting time, they minimize waiting uncertainty.

A pause becomes tolerable when it has shape.

That shape can be small. Even a plain “...waiting” message is better than silence, because it confirms the system is alive and the user is still inside a coherent process. The human brain is remarkably sensitive to these cues. It would rather endure an honest delay than an ambiguous one.


The hidden cost of pretending everything is instant

Modern products often chase the illusion of immediacy. They prefetch aggressively, animate transitions to mask latency, and try to make each interaction feel frictionless. None of that is wrong. The problem begins when design treats latency as something to conceal at all costs rather than something to design around.

Concealment creates a familiar trap. When the loading experience is invisible, the eventual failure feels abrupt and confusing. When the system is slow but gives no indication why, the user assumes the worst: maybe it broke, maybe they clicked wrong, maybe the network is bad, maybe the product is unreliable. In other words, ambiguity taxes trust.

This is where the await pattern reveals a broader principle about product design, software architecture, and even communication more generally. Any system with asynchronous parts has at least three truths:

  1. Delay is inevitable.
  2. Outcome is uncertain.
  3. Interpretation is what users pay for during the gap.

That last point is easy to miss. Users are not only waiting for data or computation. They are also waiting for a story about what is happening. The interface either supplies that story or leaves them to invent one. Human beings are excellent at inventing stories, and usually not in the product’s favor.

A blank screen says, “We have nothing to tell you.” A clear pending state says, “Here is exactly where we are.” A thoughtful error state says, “This path ended, but not incoherently.” These are not cosmetic differences. They are trust building mechanisms.

The deeper issue is that many systems optimize for the final state and neglect the intermediate state. Yet for the user, the intermediate state is not intermediate at all. It is the lived experience.


A better mental model: every interaction has three emotional contracts

A useful way to think about async experiences is through three emotional contracts:

1. The contract of anticipation

The system promises that something is happening and that the wait is meaningful. This is where the pending state matters. It reassures the user that silence is not abandonment.

2. The contract of resolution

The system delivers the expected result clearly, without making the user re-parse what happened. Success should feel like closure, not just data appearing on screen.

3. The contract of recovery

The system acknowledges failure without shame or opacity. Errors are not only technical outcomes. They are social moments. The system is effectively saying, “Here is what went wrong, and here is what you can do next.”

The await block makes all three contracts visible in one compact structure. That is why it is more philosophically important than it looks. It treats uncertainty as first-class, not incidental.

Now extend that idea beyond code.

A team announcement has these same three contracts. First, anticipation: “We are working on it.” Second, resolution: “Here is the decision.” Third, recovery: “Here is what happens if we cannot do this.” A classroom lecture has them too. First, set the question. Then, resolve it. Then, address what happens if the answer does not fit the initial model.

The ability to frame these states explicitly is one of the most underrated forms of clarity.


Why explicit states create calmer systems

The strongest interfaces are not the ones that feel magically instantaneous. They are the ones that feel calm. Calmness is different from speed. Calmness means the user never has to guess what state the system is in, what their next move should be, or whether they have been ignored.

That is why explicit state handling is so powerful. It reduces cognitive load by externalizing uncertainty. Instead of forcing the user to hold a suspended question in their head, the interface holds it for them.

Consider three examples:

  • Bank transfer: A spinner with no explanation can make a user worry the money vanished. A pending state with a message such as “Transfer in progress, usually completes in under 2 minutes” reduces anxiety.
  • Data dashboard: Empty widgets can look broken. A loading state that names the source, such as “Fetching latest sales figures,” turns absence into expectation.
  • Search results: An error that simply says “Failed” is emotionally blunt. A clear catch state, with a human explanation and next step, turns disappointment into recoverable friction.

The formula is simple: the less visible the process, the more emotionally expensive the delay.

There is a subtle design tradeoff here. If every tiny request gets a dramatic loading message, the interface becomes noisy. If nothing is ever acknowledged, it becomes opaque. The goal is not to overexplain every microsecond. The goal is to make the important waits legible.

Think of it like conversation. You do not narrate every pause. But when the pause matters, you say, “I am thinking,” or “I need a moment,” because that changes how the silence is experienced. The same is true in software.


The real lesson: uncertainty is a feature of the world, not a defect in the product

The most interesting thing about async design is that it mirrors life. We are always waiting for something we cannot fully control: an email reply, medical test results, feedback from a client, a decision from a partner, a job application status. In each case, the pain is rarely only the delay. It is the lack of structure around the delay.

This is why the await pattern resonates beyond programming. It is a miniature ethics of responsiveness. It says that when outcomes are not yet available, the proper response is not to disappear. It is to make the gap intelligible.

That principle scales.

A good leader does not leave a team in suspense without context. A good teacher does not spring final answers without scaffolding. A good product does not hide its internal uncertainty behind decorative motion. In all cases, the question is the same: how do we carry people through uncertainty without making them feel excluded from the process?

The answer is not always to shorten the wait. Sometimes the answer is to clarify the wait.

Clarity is often more valuable than immediacy.

This reframing is powerful because it shifts the design goal from speed to comprehension. A system can be fast and still feel chaotic. A system can be slower and still feel respectful. Users remember not just how long they waited, but whether the wait felt organized.

That is why the best asynchronous experiences often have three qualities:

  • They are truthful about state.
  • They are specific about progress.
  • They are kind about failure.

These are human virtues, translated into interface form.


Key Takeaways

  1. Do not treat waiting as a blank gap. Give it a state, a message, or a shape so the user knows what is happening.
  2. Optimize for certainty, not just speed. A slightly slower but clearer experience often feels better than a faster but ambiguous one.
  3. Design all three phases: pending, success, and error. Users need a coherent story, not just a final result.
  4. Use explicit states to reduce anxiety. The interface should hold uncertainty so the user does not have to.
  5. Apply the same principle outside software. Meetings, feedback, and announcements all become better when they acknowledge the waiting phase honestly.

The best interfaces do not eliminate suspense, they make it bearable

The instinct behind many modern products is to erase friction. But not all friction is bad, and not all delay is waste. Sometimes delay is simply the cost of reality. Data has to travel. Servers have to compute. Decisions have to settle. People have to think.

The deeper design challenge is not to pretend these things are instant. It is to build systems that respect the user while they are not. That respect begins with naming the state the user is in.

An await block is a small thing. Yet it points to a large truth: the quality of an experience is determined not only by its endpoints, but by how honestly it handles the interval between them.

If you remember only one thing, remember this: users do not hate waiting as much as they hate not knowing. When you design the waiting state well, you are not decorating a delay. You are turning uncertainty into comprehension, and comprehension into trust.

Sources

← Back to Library

Hatch New Ideas with Glasp AI 🐣

Glasp AI allows you to hatch new ideas based on your curated content. Let's curate and create with Glasp AI :)

Start Hatching 🐣
The Waiting State Is Not Empty: How to Design for Suspense, Not Just Speed | Glasp