Skip to the page
TACTILE UI

Kit part · Navigation · Paginations

Pagination

Pages for tables and lists: numbered keys in a tray with the current page latched down, seven slots so the row never changes width. Compact, it is a transport with a track counter.

Element
<nav>
Needs
kit.css + kit.mjs
Rules
pagination.rules.md · 5
Finishes
Aluminium · Graphite · Porcelain · Black
Volumes
Tactile · Quiet
On this page
  1. Variants
  2. Every state, at once
  3. API
  4. Markup
  5. Accessibility
  6. How it’s built
  7. Rules
  8. Related parts
01

Variants

Few pages · no gaps
Many pages · start
Compact · transport and counter
Links · the server pages
02

Every state, at once

Both finishes, side by side. Hover, pressed and focus are forced with .is-hover, .is-down and .is-focus; checked and disabled are real.

Aluminium

PartRestHoverCurrent · at the endFocus
Key
Counter

Graphite

PartRestHoverCurrent · at the endFocus
Key
Counter
03

API

NameKindValuesWhat it does
.tui-paginationclasson <nav>The row: the keys, then the range and the rows-per-page, wrapping when narrow.
aria-labelattributeon the navName what is paged: “Circuits, pages”.
data-page · data-pagesattributenumbersThe page you are on and how many there are. The part keeps data-page current.
data-count · data-sizeattributenumbersRows in all and rows per page, for the range and the size select.
.tui-pagination__keysclasson <div>The tray: the two arrows and the numbered keys, 30px keys, 3px apart.
.tui-pagination__pagesclasson <ol>Seven slots at most: first, last, the page and its neighbours, and “…” gaps.
data-pageattributeon a <button>A number key. Links (<a href>) are left to the server.
aria-current="page"attributeon the current keyLatched below the plate, its printing at full ink.
data-page-step · aria-disabledattribute"-1" · "1"The arrows. At the ends they are aria-disabled, so focus is not lost.
.tui-pagination__rangeclasson <p>Rewritten as “51–75 of 287”.
select[data-pagination-size] · .tui-pagination__sizeattribute · classin a labelRows per page. Changing it keeps the first row you were reading on screen.
.tui-pagination--compact · .tui-pagination__lcdclasswith .tui-lcdThe transport: arrows round a counter, “03/12”, its ghost the same width.
.tui-pagination__saidclassaria-liveThe words behind the counter, for screen readers: “Page 3 of 12”.
paginationItems · paginationKeysHTML · paginationRangefunctionkit.mjs, pureThe slots, their markup, and the rows a page shows; for server rendering and tests.
setPaginationPage(nav, page)functionkit.mjsGo to a page from a script: clamps, redraws, fires tui-page.
tui-pageeventdetail: page, pages, sizeFired on the nav after every change.
Tab · Enter · Spacekeyboard—Every key is a real button. After a redraw, focus stays on the arrow or moves to the new page’s key.
04

Markup

<nav class="tui-pagination" aria-label="Circuits, pages" data-page="3" data-pages="12" data-count="287" data-size="25">
  <div class="tui-pagination__keys">
    <button class="tui-key tui-key--icon tui-pagination__step" data-page-step="-1" aria-label="Previous page">…</button>
    <ol class="tui-pagination__pages">
      <li><button class="tui-key" data-page="1" aria-label="Page 1">1</button></li>
      <li><button class="tui-key" data-page="2" aria-label="Page 2">2</button></li>
      <li><button class="tui-key" data-page="3" aria-label="Page 3" aria-current="page">3</button></li>
      <li><button class="tui-key" data-page="4" aria-label="Page 4">4</button></li>
      <li><button class="tui-key" data-page="5" aria-label="Page 5">5</button></li>
      <li class="tui-pagination__gap" aria-hidden="true">…</li>
      <li><button class="tui-key" data-page="12" aria-label="Page 12">12</button></li>
    </ol>
    <button class="tui-key tui-key--icon tui-pagination__step" data-page-step="1" aria-label="Next page">…</button>
  </div>
  <p class="tui-pagination__range" aria-live="polite">51–75 of 287</p>
  <label class="tui-pagination__size"><span class="tui-label">Rows</span>
    <select class="tui-select" data-pagination-size><option>10</option><option selected>25</option><option>50</option></select>
  </label>
</nav>
import { paginationKeysHTML } from '/kit/kit.mjs';

// Server-side, or first render: the same keys the part draws.
list.innerHTML = paginationKeysHTML(3, 12);

nav.addEventListener('tui-page', (e) => loadRows(e.detail.page, e.detail.size));
// Or go somewhere from a script:
import { setPaginationPage } from '/kit/kit.mjs';
setPaginationPage(nav, 1);

Needs kit.css and kit.mjs. How to install the kit.

05

Accessibility

  • A <nav> with its own name, a list of keys each named “Page 4”, and the current one marked aria-current="page".
  • At the first or last page the arrow is aria-disabled, not disabled, so the key you just pressed keeps focus.
  • The gaps are aria-hidden; the range sits in a polite live region.
  • The compact counter is a picture of the page number; the words “Page 3 of 12” are said beside it.
06

How it’s built

The numbers come from one pure function (seven slots: the first page, the last, the current one and its neighbours, and a gap on each side that needs one), so the row is the same width on page 1 and page 40. pagination.mjs redraws the list from it on each press, delegated from the document, and keeps focus where your hand was. The keys are the kit’s at 30px in a tray; the current one takes the latched shadow. The compact counter is the kit’s LCD, with a ghost the same width as the digits.

07

Rules

pagination.rules.mdIn the brain

The row keeps its width while you page; the first and last pages are always one press away.

5 rules in this file, with the foundations they rest on and the anti-patterns that break them. Full rules ship in the brain with the Pass.

08
Reel 342:10
Mixed0:30

Table

Rows of data with printed column labels, figures right-aligned in columns, and status in lamps with words.

Selector

One mode of two to five: latching keys in a tray, one down at a time, each with a lamp that lights when chosen.

02:52min

LCD

A value that changes, on grey-green liquid crystal, with a ghost of the unlit segments behind it: clocks, battery, counters.

Docs
Finish
Volume