- Accordion
- Alert
- Alert Dialog
- Aspect Ratio
- Attachment
- Avatar
- Badge
- Breadcrumb
- Bubble
- Button
- Button Group
- Calendar
- Card
- Carousel
- Chart
- Checkbox
- Collapsible
- Combobox
- Command
- Context Menu
- Date Picker
- Desktop Window
- Dialog
- Drawer
- Dropdown Menu
- Empty
- Field
- Frame
- Heading
- Hover Card
- Input
- Input Group
- Input OTP
- Item
- Kbd
- Label
- Live Waveform
- Marker
- Menubar
- Message
- Message Scroller
- Meter
- Meter Ring
- Native Select
- Navigation Menu
- NumberCount
- Pagination
- Paragraph
- Popover
- Progress
- Progress Ring
- Questionnaire
- Radio Group
- Resizable
- Scroll Area
- Select
- Separator
- Sheet
- Sidebar
- Skeleton
- Slider
- Spinner
- Stepper
- Switch
- Table
- Tabs
- Textarea
- Timeline
- Toast
- Toggle
- Toggle Group
- Tooltip
Build faster with ondo
Components you own, styled with your own theme tokens.
import { Heading } from "@/components/ui/heading"
export default function HeadingDemo() {Heading is for application UI. Rendered markdown and MDX already get their
heading styles from the typeset layer, so you do not need this component
inside prose.
Installation#
bunx --bun shadcn@latest add @ondo-ui/heading
Usage#
import { Heading } from "@/components/ui/heading"<Heading
level={1 | 2 | 3 | 4 | 5 | 6}
size="1 | 2 | 3 | 4 | 5 | 6"
wrap="normal | nowrap | balance | pretty"
>
Heading
</Heading>level sets the rendered tag. size sets the visual scale and defaults to
level, so most of the time you only pass level.
Examples#
Levels#
level renders the matching h1–h6 tag and picks the matching size.
Heading level 1
Heading level 2
Heading level 3
Heading level 4
Heading level 5
Heading level 6
import { Heading } from "@/components/ui/heading"
export default function HeadingLevels() {Sizes#
Use size to pick a scale step directly. 1 is the largest and 6 the
smallest.
Size 1
Size 2
Size 3
Size 4
Size 5
Size 6
import { Heading } from "@/components/ui/heading"
export default function HeadingSizes() {Pairing with a paragraph#
The two scales are numbered together. Passing the same size to Heading and
Paragraph keeps the title and its copy in proportion at every step.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
Ship a design system
Every heading size has a paragraph size with the same number, so a heading and the copy beneath it stay in proportion.
import { Heading } from "@/components/ui/heading"
import { Paragraph } from "@/components/ui/paragraph"
Level and size apart#
Document outlines and visual hierarchy do not always agree. Set size to keep
the heading rank the page needs while showing the size the design needs.
Ship faster
Recent activity
import { Heading } from "@/components/ui/heading"
export default function HeadingLevelAndSize() {Wrap#
wrap controls how the text breaks across lines. It defaults to normal, the
browser's own wrapping. nowrap keeps the heading on a single line. balance
evens out the length of every line, which suits short headings. pretty
instead fills lines normally and only tidies the last one, so it does little
more than avoid an orphaned final word.
On a short two-line heading balance and pretty land on the same result — the
difference only shows once the text runs to three or more lines, as below.
Build a design system your whole team enjoys using
Build a design system your whole team enjoys using
Build a design system your whole team enjoys using
Build a design system your whole team enjoys using
import { Heading } from "@/components/ui/heading"
export default function HeadingWrap() {For per-breakpoint wrapping, reach for className instead — text-* wrap
utilities merge cleanly, so <Heading wrap="pretty" className="md:text-balance" />
is pretty on small screens and balance from md up.
Each value maps to the matching Tailwind utility. See the
text-wrap documentation for the
details behind each one.
Custom element#
Use the render prop when the markup needs a different element — a legend
inside a fieldset, for example — but you still want heading styles.
import { Heading } from "@/components/ui/heading"
export default function HeadingRender() {API reference#
Heading#
Renders an h1–h6 element styled from the heading scale.
| Prop | Type | Default |
|---|---|---|
level | 1 | 2 | 3 | 4 | 5 | 6 | 1 |
size | 1 | 2 | 3 | 4 | 5 | 6 | level |
wrap | "normal" | "nowrap" | "balance" | "pretty" | normal |
render | ReactElement | (props, state) => ReactElement | - |
className | string | - |
Scale#
| Size | Classes | Pairs with paragraph |
|---|---|---|
1 | text-[2.25rem]/[1.25] font-bold tracking-[-0.02em] | 1.25rem |
2 | text-[1.75rem]/[1.3] font-bold tracking-[-0.017em] | 1.125rem |
3 | text-[1.5rem]/[1.35] font-bold tracking-[-0.014em] | 1.0625rem |
4 | text-[1.375rem]/[1.4] font-bold tracking-[-0.011em] | 1rem |
5 | text-[1.25rem]/[1.4] font-bold tracking-[-0.008em] | 0.9375rem |
6 | text-[1.125rem]/[1.45] font-bold tracking-[-0.005em] | 0.875rem |
Every size also gets font-heading text-foreground, plus a wrap utility from
wrap (text-wrap by default). Pass the same size to Paragraph to pair the
heading with its matching body copy.