Navigation

v0.0.4
Site pages

Centered

One task in the middle of the viewport, alone or beside a panel.

A centered layout puts one task in the middle of the viewport and nothing else: signing in, confirming an address, an error page. The frame is a page, so it is as tall as the viewport in dvh; two utilities center what is in it.

Centered

<main class="page items-center justify-center p-lg bg-surface-tray fg-text-body text-sm">  <form class="sheet form w-full max-w(380) p-xl">    <header class="flex flex-col gap-3xs">      <h1 class="heading heading-lg">Sign in to Atlas</h1>      <p class="m(0) fg-text-muted">Welcome back.</p>    </header>    <label class="field">Email      <input class="input" type="email" name="email" autocomplete="email" placeholder="you@example.com">    </label>    <label class="field">Password      <input class="input" type="password" name="password" autocomplete="current-password">    </label>    <button class="btn btn-primary">Sign in</button>    <p class="m(0) text-center fg-text-muted">New here?      <a class="link" href="#">Create an account</a>    </p>  </form></main>

#How it is built

  • page items-center justify-center. The page is a column at least as tall as the viewport, on the <main> itself since the task is the whole page; the two utilities center its content on both axes. p-lg keeps the card off the edges of a phone.
  • w-full max-w(380) on the card. It fills a phone and stops at a comfortable width for one column of fields.
  • The tray under the sheet. bg-surface-tray on the frame and a sheet for the card: the card is the one raised thing on the page.
  • When the card is taller than the viewport, the page scrolls. A minimum height, not a fixed one, is what makes that work. A phone with its keyboard open is this case.

The card is also a form, which sets the distance between its fields.

#Beside a panel

From the md breakpoint the frame becomes two equal columns: the task in one, and a panel in the other for the brand, a quotation or a picture. Below it the panel leaves, and the task is alone again.

Beside a panel

<div class="page bg-surface-base fg-text-body text-sm">  <div class="grow(1) grid grid-cols(2)@md">    <main class="flex items-center justify-center p-lg">      <form class="form w-full max-w(340)">        <header class="flex flex-col gap-3xs">          <h1 class="heading heading-lg">Sign in to Atlas</h1>          <p class="m(0) fg-text-muted">Welcome back.</p>        </header>        <label class="field">Email          <input class="input" type="email" name="email" autocomplete="email" placeholder="you@example.com">        </label>        <label class="field">Password          <input class="input" type="password" name="password" autocomplete="current-password">        </label>        <button class="btn btn-primary">Sign in</button>        <p class="m(0) text-center fg-text-muted">New here?          <a class="link" href="#">Create an account</a>        </p>      </form>    </main>    <aside class="hidden flex@md flex-col justify-between p-2xl bg-surface-inverse fg-text-inverse">      <p class="m(0) flex items-center gap-xs text-md font-medium">        <svg class="icon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">          <path d="M12 3a9 9 0 1 0 0 18a9 9 0 0 0 0-18M12 3a9 9 0 0 0 0 18" />        </svg>Atlas</p>      <blockquote class="m(0) flex flex-col gap-md max-w(440)">        <p class="m(0) text-2xl">We replaced four libraries with a stylesheet, and the interface got quieter.</p>        <footer class="text-sm">Katherine Johnson, Engineering at Orbit</footer>      </blockquote>    </aside>  </div></div>
At Tablet and Phone the panel leaves and the form keeps the page.

grid grid-cols(2)@md splits the frame; the panel is hidden flex@md. This one measures the viewport, with @md, not a container: the frame is the viewport.

The panel is ink, bg-surface-inverse with fg-text-inverse. Keep it to a few words: it is the first thing that leaves, so nothing a reader needs may live there.

#Accessibility

  • The page has one <h1>, in the card.
  • The panel is an <aside>. When it holds only decoration, hide it from assistive technology with aria-hidden="true"; when it holds a quotation, it is content and stays.
  • Fields carry autocomplete values, so a password manager can fill them.