GitHub

Page Header

The standard prototype page top: optional breadcrumbs OR an eyebrow (with a leading icon), a title (page-title role, or the oversized display role for a hero), an optional lede, and a right-aligned actions slot.

Stable .astro import EsaPageHeader from '@esa/ecology/esa-page-header.astro';

Preview

The default form: a page-title-scale heading with a lede and an actions slot. The container is neutral and transparent — color is the consumer’s job.

Requirements

Track and triage every requirement across the program.

<PageHeader title="Requirements" lede="Track and triage every requirement across the program.">
  <Button slot="actions" color="primary" icon="plus">New requirement</Button>
</PageHeader>

Eyebrow + display prominence (hero)

For a landing or hero, add an eyebrow (with an optional leading icon) and bump the title to the display role with prominence="display". The actions here are link-buttons — esa-button with an href.

Annual Report

2026 in Review

A year of monitoring, mitigation, and measurable outcomes across the program.

<PageHeader
  eyebrow="Annual Report"
  icon="award"
  prominence="display"
  title="2026 in Review"
  lede="A year of monitoring, mitigation, and measurable outcomes across the program.">
  <Button slot="actions" color="primary" href="/report">Read the report</Button>
  <Button slot="actions" color="ghost" appearance="outline" href="/data">View the data</Button>
</PageHeader>

Host an esa-breadcrumbs in the breadcrumbs slot for a record or nested page.

Permit #4471

Filed 12 days ago · awaiting review.

<PageHeader title="Permit #4471" lede="Filed 12 days ago · awaiting review.">
  <nav slot="breadcrumbs">Permits / Active / #4471</nav>
  <Button slot="actions" color="ghost" appearance="outline" icon="pencil">Edit</Button>
</PageHeader>

API

PropTypeDefaultDescription
title string The page title (required). Rendered as the <h1>.
lede string Optional supporting sentence below the title, at the body-large role in secondary text.
eyebrow string Small kicker above the title — e.g. a section or award name.
icon string esa-icon registry name for the eyebrow’s leading glyph, e.g. "award" (eyebrow only).
prominence 'page-title' | 'display' 'page-title' Title scale: the page-title role (default) or the oversized display role for a hero.
as 'header' | 'div' | 'section' 'header' The host element tag.

Slots

PropTypeDefaultDescription
breadcrumbs slot Above the title — host an esa-breadcrumbs here. Mutually exclusive in spirit with eyebrow.
actions slot Right-aligned, top-aligned with the title block — buttons or links.

Accessibility

  • The title is the page <h1> — there should be exactly one per page; keep heading order sensible below it.
  • The host defaults to a <header> landmark; use as="div" when the header is nested inside another landmark.
  • The eyebrow icon is decorative (rendered via esa-icon, aria-hidden) — the eyebrow text carries the meaning.

Theming surface

Every public token this component reads, extracted from its source at build time. The Resolves to column walks each token's real lineage — component → semantic → primitive → raw value — so you can see exactly where re-pointing it lands. A spoke re-skins by overriding these in its theme-<slug>.css; component internals are never edited. No hook for what you need? File it with /request-lego.

TokenTierResolves to
--page-header-bar-gap ad-hoc 1.5rem via --spacing-500
--page-header-breadcrumbs-gap ad-hoc 0.75rem via --spacing-300
--page-header-eyebrow-color ad-hoc #646464 via --color-text-secondary--color-gray-11
--page-header-eyebrow-size ad-hoc clamp(0.75rem, 0.66rem + 0.44vw, 0.9375rem) via --type-size-200
--page-header-gap ad-hoc 0.5rem via --spacing-200
--page-header-lede-color ad-hoc #646464 via --color-text-secondary--color-gray-11
--page-header-lede-size ad-hoc clamp(0.875rem, 0.77rem + 0.52vw, 1.125rem) via --type-size-300
--page-header-title-color ad-hoc #202020 via --color-text-primary--color-gray-12
--page-header-title-size ad-hoc clamp(1.375rem, 1.2rem + 0.88vw, 1.875rem) via --type-size-600
--page-header-title-size-display ad-hoc clamp(2rem, 1.73rem + 1.35vw, 2.75rem) via --type-size-800
--page-header-title-weight ad-hoc 550 via --font-weight-semibold
--page-header-title-weight-display ad-hoc 650 via --font-weight-bold
--font-display semantic 'DM Sans', sans-serif via --font-sans
--letter-spacing-tight semantic -0.01em
--line-height-normal semantic 1.6
--line-height-relaxed semantic 1.8
--line-height-tight semantic 1.3
--font-weight-medium primitive 500
--font-weight-regular primitive 350
--spacing-100 primitive 0.25rem
--spacing-200 primitive 0.5rem