RoadieRoadie
  • Home
  • Brand
  • Foundations
  • Content
  • Tokens
  • Components
  • Charts
  • Widgets
  • Appearance
HomeBrandFoundations
Appearance

Foundations

  • Visual

    • Colors
    • Elevation
    • Iconography
    • Shape
    • Theming
  • Content

    • Date and time
    • Layout
    • Prose styles
    • Typography
  • Behaviour

    • Accessibility
    • Interactions
    • Motion
    • View transitions
  • Building apps

    • Forms
    • Linking
    • Navigation
    • Performance
    • Records modelAlpha
    • Tables

Typography

Docs updated
19 Oct 2026

ReferenceTypography tokens

Use pre-composed text styles. Let fluid type handle responsiveness. Pair semantic colours with semantic HTML.

Roadie has two font families: Intermission, a sans-serif set with font-sans, and IBM Plex Mono, a monospace set with font-mono.

Type scale

Sizes from text-lg up use clamp() to scale fluidly between viewport widths, so they need no breakpoint overrides. On the docs site, each step is set in its own size, with its size in pixels or its fluid range.

  1. xs

    The quick brown fox

    12px
  2. sm

    The quick brown fox

    14px
  3. base

    The quick brown fox

    16px
  4. lg

    The quick brown fox

    18 to 20px
  5. xl

    The quick brown fox

    20 to 24px
  6. 2xl

    The quick brown fox

    24 to 32px
  7. 3xl

    The quick brown fox

    28 to 40px
  8. 4xl

    The quick brown fox

    32 to 48px
  9. 5xl

    The quick brown fox

    36 to 64px
  10. 6xl

    The quick brown fox

    40 to 76px
  11. 7xl

    The quick brown fox

    44 to 96px

Text style utilities

Pre-composed utilities combine font size, weight, line height, and letter spacing. They come in two contexts: UI for app interfaces, and prose for long-form content.

Display styles

UI display styles are compact headings for dashboards, settings, and navigation, with tighter line height and tracking. Prose display styles are larger, heavier headings for articles, marketing pages, and rich content, designed for reading. On the docs site, each style is set in its own style, UI first, then prose.

UI

  1. ui-1

    text-display-ui-1
  2. ui-2

    text-display-ui-2
  3. ui-3

    text-display-ui-3
  4. ui-4

    text-display-ui-4
  5. ui-5

    text-display-ui-5
  6. ui-6

    text-display-ui-6

Prose

  1. prose-1

    text-display-prose-1
  2. prose-2

    text-display-prose-2
  3. prose-3

    text-display-prose-3
  4. prose-4

    text-display-prose-4
  5. prose-5

    text-display-prose-5
  6. prose-6

    text-display-prose-6
UtilitySizeWeight
text-display-ui-14xlBold (700)
text-display-ui-23xlBold (700)
text-display-ui-32xlBold (700)
text-display-ui-4xlBold (700)
text-display-ui-5lgSemibold (600)
text-display-ui-6baseSemibold (600)
text-display-prose-15xlBlack (900)
text-display-prose-24xlBold (700)
text-display-prose-33xlBold (700)
text-display-prose-42xlBold (700)
text-display-prose-5xlBold (700)
text-display-prose-6lgBold (700)

Body text styles

body already sets text-ui, so standard UI text needs no class. Each style takes the line height and letter spacing of its context.

{/* text-ui */}
<p className='text-ui'>App interface text with a tighter line height.</p>
{/* text-prose */}
<p className='text-prose'>
Long-form content with a more generous line height, better for extended
reading such as articles and documentation.
UtilityUse forSizeContext
text-uiApp interface text, and the default on bodybaseui
text-proseLong-form content, such as articles and documentationbaseprose
text-ui-metaSecondary UI text, such as timestamps, counts, and hintssmui
text-codeMonospaced codesmcode

Line height and tracking

Semantic tokens keep rhythm consistent. Text style utilities set them by themselves, so use the tokens on their own only for custom compositions. On the docs site, each context is listed with its line height and letter spacing.

ContextLine heightLetter spacing
display1.2-0.02em
ui1.35-0.01em
prose1.5-0.01em
code1.6250em

Semantic text colours

Use semantic colour utilities instead of raw colour values. They adapt to intents, themes, and dark mode by themselves.

<p className='text-strong'>text-strong for headings, emphasis, and high contrast</p>
<p className='text-normal'>text-normal for body text, inherited from the body reset</p>
<p className='text-subtle'>text-subtle for secondary text and descriptions</p>
<p className='text-subtler'>text-subtler for meta text, timestamps, and hints</p>

Usage

Headings

Roadie has no Text or Heading component. Use raw heading elements with a display style utility and text-strong. Match the semantic level, h1 to h6, to the document structure, and the visual style to the context.

<h1 className='text-display-ui-1 text-strong'>Page title</h1>
<h2 className='text-display-ui-3 text-strong'>Section</h2>
<h3 className='text-display-ui-5 text-strong'>Subsection</h3>

Body text

Body inherits text-ui from the reset. Use <p> elements with semantic colour classes.

<p>Default body text. No class needed.</p>
<p className='text-subtle'>Secondary text</p>
<p className='text-ui-meta text-subtler'>Meta or hint text</p>
<p className='text-strong'>Emphasised text</p>

Prose content

Wrap CMS output, markdown, or user-generated content in <Prose> for automatic typography and spacing. See Prose styles.

<Prose>
<h2>Article heading</h2>
<p>
Body paragraph with <strong>bold</strong> and <a href='#'>links</a>.
The Prose component handles spacing, list styles, and element
typography.

Numerals

Intermission has two sets of figures. Proportional is the default, and each digit takes the width its shape wants. Tabular gives every digit the same width, so values line up in a column.

Tabular figures where numbers stack, proportional where they do not

Equal-width digits are for columns and ticks. On a large standalone figure they read as gappy, because the 1s carry the same width as the 0s with nothing to line up against.

table column tabular-nums
axis ticks tabular-nums
ticking clock tabular-nums
hero figure proportional

Do

Tabular where values sit above one another, or where a digit changes under the eye. Proportional everywhere else.

hero figure tabular-nums

Don’t

A large static number with gaps where the narrow digits are.

A ticking countdown is the exception that proves the rule. Its digits don't align with anything, but they change while somebody is watching, so tabular figures stop the row shifting on every tick.

Guidelines

Use text style utilities

Text style utilities combine size, weight, line height, and letter spacing into a single class. Raw Tailwind size classes miss the other properties.

Section title

Body text inherits defaults

Secondary text

<h2 className='text-display-ui-3 text-strong'>Section title</h2>
<p>Body text inherits defaults</p>
<p className='text-ui-meta text-subtle'>Secondary text</p>

Do

Use pre-composed utilities. They set all typographic properties at once.

Section title

Body text

Secondary text

<h2 className='text-2xl font-bold'>Section title</h2>
<p>Body text</p>
<p className='text-sm text-subtle'>Secondary text</p>

Don’t

Don't use raw size and weight classes. They miss line height and letter spacing.

Use semantic text colours

Semantic colours like text-subtle adapt to intents, themes, and dark mode. Raw colour values break when the context changes.

Strong text

Default text

Subtle text

Subtler text

<p className='text-strong'>Strong text</p>
<p className='text-normal'>Default text</p>
<p className='text-subtle'>Subtle text</p>
<p className='text-subtler'>Subtler text</p>

Do

Semantic colours adapt to the current intent and theme by themselves.

<p className='font-bold text-[#111827]'>Strong text</p>
<p className='text-[#374151]'>Default text</p>
<p className='text-[#6b7280]'>Subtle text</p>
<p className='text-[#9ca3af]'>Subtler text</p>

Don’t

Don't hardcode colour values. They won't respond to intent or dark mode.

Match context to content type

UI styles are compact for app interfaces. Prose styles are larger for long-form reading. Mixing them creates visual inconsistency.

Dashboard

Recent orders

3 orders in the last 24 hours

<h3 className='text-display-ui-4 text-strong'>Recent orders</h3>
<p className='text-sm text-subtle'>3 orders in the last 24 hours</p>

Do

UI headings for dashboards, prose headings for articles.

Dashboard

Recent orders

3 orders in the last 24 hours

<h3 className='text-display-prose-4 text-strong'>Recent orders</h3>
<p className='text-sm text-subtle'>3 orders in the last 24 hours</p>

Don’t

Don't use prose display styles in app UI. They're too large and heavy.

Use semantic HTML elements

Use the right element for the content type. Heading elements establish document structure for accessibility and SEO.

<h2 className='text-display-ui-3 text-strong'>
Section title
</h2>
<p className='text-subtle'>
Description text
</p>

Do

Use headings for headings, paragraphs for text, and spans for inline fragments.

<div className='text-display-ui-3 text-strong'>
Section title
</div>
<div className='text-subtle'>
Description text
</div>

Don’t

Don't use divs for text content. Screen readers can't identify the structure.

Let fluid type handle responsiveness

Sizes from text-lg up already use clamp() to scale fluidly. Adding breakpoint overrides for font size fights the system.

{/* Automatically fluid */}
<h1 className='text-display-ui-1 text-strong'>
Dashboard
</h1>

Do

Fluid type scales smoothly across all viewport widths.

{/* Fighting the fluid scale */}
<h1 className='text-xl md:text-2xl lg:text-4xl'>
Dashboard
</h1>

Don’t

Don't add manual breakpoints for font size. It creates jarring jumps.

Maintain heading hierarchy

Heading levels follow document structure, h1 then h2 then h3. The display utility sets the visual weight, not the heading level.

<h1 className='text-display-ui-1 ...'>Page</h1>
<h2 className='text-display-ui-3 ...'>Section</h2>
<h3 className='text-display-ui-5 ...'>Sub</h3>

Do

Semantic levels follow structure. Visual style is independent.

<h1 className='text-display-ui-1 ...'>Page</h1>
{/* Skipped h2 */}
<h4 className='text-display-ui-5 ...'>Sub</h4>

Don’t

Don't skip heading levels for visual effect.

Use Prose for rich content

The Prose component styles nested HTML for CMS output, markdown, or user-generated content. It handles spacing, list markers, and element typography.

<Prose>
<h2>Title</h2>
<p>Paragraph with <a href='#'>link</a></p>
<ul><li>Item</li></ul>
</Prose>

Do

Prose handles all child element styling by itself.

<div>
<h2 className='text-2xl mb-4'>Title</h2>
<p className='mb-2 leading-6'>Text</p>
<ul className='list-disc pl-4'>...</ul>
</div>

Don’t

Don't manually style every element in user content.

Semantic elements

ElementWhen to useExample
<h1> to <h6>Section headingstext-display-ui-3 text-strong
<p>Body text and descriptionstext-subtle
<span>Inline text fragmentstext-sm text-subtler
<strong>Important texttext-strong
<em>Emphasis or stressItalic inside <Prose>
<Code>Inline code, tokens, and commands<Code>bg-normal</Code>
<Prose>CMS or markdown content<Prose size='md'>...</Prose>
Previous page← Prose stylesNext pageAccessibility →