Timeline

  1. Spruce CSS v3

    Design styles, a built-in dark mode, the block library and AI skills.

  2. Spruce UI

    A component library built with Spruce CSS: forms, cards, navigation and more.

  3. The first release

    A small Sass framework that uses CSS custom properties and logical properties from day one.

@use 'sprucecss/scss/spruce' as *;

.l-timeline {
  --size: 1.25em;
  --line-size: 0.15em;
  --offset: calc(#{config('line-height-base', $typography, false) + 0em} / 6);
  @include clear-list;
  @include layout-stack('l');
  position: relative;

  // The line connects the markers; logical insets keep it at the start in RTL.
  &::before {
    background-color: color('border');
    content: '';
    inline-size: var(--line-size);
    inset-block: var(--offset);
    inset-inline-start: calc(var(--size) / 2 - var(--line-size) / 2);
    position: absolute;
  }

  &__item {
    display: flex;
    gap: spacer('s');
    position: relative;

    &::before {
      background-color: color('primary');
      block-size: var(--size);
      border: 0.25em solid color('background');
      border-radius: 50%;
      box-shadow: 0 0 0 var(--line-size) color('primary');
      box-sizing: border-box;
      content: '';
      flex-shrink: 0;
      inline-size: var(--size);
      margin-block-start: var(--offset);
    }
  }

  &__content {
    @include layout-stack('xxs');
  }

  &__date {
    color: color('primary');
    font-size: config('font-size-sm', $typography);
    font-weight: 700;
  }

  &__title {
    font-size: font-size('h4');
  }
}
<ol class="l-timeline">
    <li class="l-timeline__item">
        <div class="l-timeline__content">
            <p class="l-timeline__date"><time datetime="2026">2026</time></p>
            <h3 class="l-timeline__title">Spruce CSS v3</h3>
            <p>Design styles, a built-in dark mode, the block library and AI skills.</p>
        </div>
    </li>
    <li class="l-timeline__item">
        <div class="l-timeline__content">
            <p class="l-timeline__date"><time datetime="2024">2024</time></p>
            <h3 class="l-timeline__title">Spruce UI</h3>
            <p>A component library built with Spruce CSS: forms, cards, navigation and more.</p>
        </div>
    </li>
    <li class="l-timeline__item">
        <div class="l-timeline__content">
            <p class="l-timeline__date"><time datetime="2022">2022</time></p>
            <h3 class="l-timeline__title">The first release</h3>
            <p>A small Sass framework that uses CSS custom properties and logical properties from day one.</p>
        </div>
    </li>
</ol>

Timeline

A vertical timeline for histories, roadmaps and processes: markers on a connecting line, with a date, a title and a description for each step.

Anatomy

  • .l-timeline is an ordered list (ol), because the order matters.
  • .l-timeline__item draws its marker with ::before; the list's ::before is the line.
  • .l-timeline__content holds the date (__date with a time element), the title (__title) and any content.

Customization

  • --size: the size of the markers.
  • --line-size: the width of the line and the marker ring.
  • --offset: aligns the marker with the first line of text; it's calculated from the base line height.

Everything is in em, so the timeline scales with its font size.

Technical Details

  • The line and the markers are positioned with logical properties (inset-inline-start, inset-block), so the timeline mirrors in RTL.
  • The marker ring uses the background color as a gap, so it works on any background color in the dark mode and every style.
  • The decorative parts are pseudo-elements; screen readers read the list as a plain ordered list.

Documentation

Learn about Spruce CSS through our extensive documentation.

Components

Explore our UI library of accessible components built with Spruce CSS.

Blocks and Pages

Full-width page blocks and complete page templates, ready to copy.

Find us on GitHub

Did you find a bug? Have an idea or a question? Please open an issue to help us develop the project.