Skip to content
Facade UI
Colour mode
GitHub (opens in a new tab)
uiatom

Eyebrow

The small label above a section heading. A paragraph, never a heading.

Preview

Open full width (opens in a new tab)
Preview width

Installation

Package manager
pnpm dlx shadcn@latest add https://facadeui.dev/r/eyebrow.json

Pulls in utils. The CLI installs them for you.

Usage

The exact source of the preview above.

demos/eyebrow.tsx
import { Eyebrow } from "@registry/ui/eyebrow"
import { Heading } from "@registry/ui/heading"

export function Demo() {
  return (
    <div className="flex flex-col gap-8">
      <div className="flex flex-col gap-2">
        <Eyebrow>Platform</Eyebrow>
        <Heading level={2} className="text-display-sm font-semibold">
          One place for everything
        </Heading>
      </div>
      <div className="flex flex-col gap-2">
        <Eyebrow tone="primary">Changelog</Eyebrow>
        <Heading level={2} className="text-display-sm font-semibold">
          Shipped this week
        </Heading>
      </div>
    </div>
  )
}

Source

What the CLI copies into your project, byte for byte.

components/ui/eyebrow.tsx
/**
 * Eyebrow — the small label that sits above a section heading.
 *
 * a11y: never a heading. An eyebrow reads as a category, not as an outline
 * level, and promoting it to `<h3>` above an `<h2>` would invert the document
 * structure for screen-reader users navigating by heading. It renders a `<p>`
 * by default, or a `<span>` when it is already inside flow text.
 *
 * Dependencies: react, @/lib/utils.
 */

import type { ComponentPropsWithoutRef, ElementType, ReactNode } from "react"

import { cn } from "@/lib/utils"

export interface EyebrowProps extends Omit<ComponentPropsWithoutRef<"p">, "children"> {
  as?: "p" | "span" | "div"
  /** `muted` is the default; `primary` tints it with the brand colour. */
  tone?: "muted" | "primary" | "foreground"
  children?: ReactNode
}

const tones: Record<NonNullable<EyebrowProps["tone"]>, string> = {
  muted: "text-muted-foreground",
  primary: "text-primary",
  foreground: "text-foreground",
}

export function Eyebrow({
  as = "p",
  tone = "muted",
  className,
  children,
  ...props
}: EyebrowProps) {
  const Component = as as ElementType

  return (
    <Component
      className={cn(
        "text-sm font-semibold uppercase tracking-[0.12em]",
        tones[tone],
        className,
      )}
      {...props}
    >
      {children}
    </Component>
  )
}

Props

EyebrowProps

Extends Omit<ComponentPropsWithoutRef<"p">, "children">.

Props for EyebrowProps
PropTypeDefault
as"p" | "span" | "div""p"
tone`muted` is the default; `primary` tints it with the brand colour."muted" | "primary" | "foreground""muted"
childrenReactNode