{%- comment -%} MIT License · (c) 2026 Lintel · https://lintelagency.com/resources/shopify-sections {%- endcomment -%} {%- comment -%} Timeline: dated milestones for a brand's story or a process, as an ordered list on a line. On desktop the milestones alternate either side of the line or sit on one side; on mobile they always stack on one side. Each milestone has a date label, title, text, optional image (separate mobile image, focal points) and an optional link. Pure Liquid and CSS; no JavaScript. Depends on: snippets/lib-image.liquid, snippets/lib-button.liquid {%- endcomment -%} {%- liquid assign s = section.settings assign heading_tag = s.heading_tag | default: 'h2' assign item_tag = 'h3' if heading_tag == 'h3' or heading_tag == 'p' assign item_tag = 'h4' endif -%}
{%- if s.heading != blank or s.text != blank -%}
{%- if s.heading != blank -%} <{{ heading_tag }} class="lib-timeline__heading lib-timeline__heading--{{ s.heading_size }}"> {{- s.heading -}} {%- endif -%} {%- if s.text != blank -%}
{{ s.text }}
{%- endif -%}
{%- endif -%} {%- if section.blocks.size > 0 -%}
    {%- for block in section.blocks -%} {%- assign b = block.settings -%}
  1. {%- if b.date != blank -%}

    {{ b.date | escape }}

    {%- endif -%} {%- if b.title != blank -%} <{{ item_tag }} class="lib-timeline__title">{{ b.title | escape }} {%- endif -%} {%- if b.image != blank or b.image_mobile != blank -%}
    {%- render 'lib-image', image: b.image, image_mobile: b.image_mobile, class: 'lib-timeline__img', sizes: '(min-width: 990px) 480px, 90vw' -%}
    {%- endif -%} {%- if b.text != blank -%}
    {{ b.text }}
    {%- endif -%} {%- if b.link_label != blank -%} {%- endif -%}
  2. {%- endfor -%}
{%- endif -%}
{% stylesheet %} .lib-timeline { background-color: var(--lib-bg); background-image: var(--lib-bg-image, none); color: var(--lib-text); padding: var(--lib-pt) 1rem var(--lib-pb); } .lib-timeline__inner { max-width: 1100px; margin: 0 auto; } .lib-timeline--full .lib-timeline__inner { max-width: none; } @media (max-width: 749px) { .lib-timeline { padding-top: var(--lib-pt-m); padding-bottom: var(--lib-pb-m); } .lib-timeline[data-show='desktop'] { display: none; } } @media (min-width: 750px) { .lib-timeline[data-show='mobile'] { display: none; } } .lib-timeline__header { max-width: 42rem; margin-bottom: clamp(2rem, 5vw, 3.5rem); } .lib-timeline__heading { margin: 0; font-size: clamp(1.75rem, 3vw, 2.5rem); line-height: 1.15; letter-spacing: -0.02em; text-wrap: balance; } .lib-timeline__heading--small { font-size: clamp(1.25rem, 1.8vw, 1.5rem); } .lib-timeline__heading--large { font-size: clamp(2rem, 4vw, 3.25rem); } .lib-timeline__text { margin-top: 0.75rem; font-size: 1rem; line-height: 1.6; opacity: 0.85; } .lib-timeline__text > :first-child { margin-top: 0; } .lib-timeline__text > :last-child { margin-bottom: 0; } .lib-timeline__header[data-align='center'] { margin-inline: auto; text-align: center; } @media (max-width: 749px) { .lib-timeline__header[data-align-m='left'] { margin-inline: 0; text-align: left; } .lib-timeline__header[data-align-m='center'] { margin-inline: auto; text-align: center; } } /* One side: line on the left. Mobile always uses this. */ .lib-timeline__list { --lib-gutter: 2.25rem; position: relative; display: grid; gap: clamp(1.75rem, 4vw, 2.75rem); margin: 0; padding: 0 0 0 var(--lib-gutter); list-style: none; } .lib-timeline__list::before { content: ''; position: absolute; top: 0.5rem; bottom: 0.5rem; left: calc(0.5rem - 1px); width: 2px; background: var(--lib-line); } .lib-timeline__item { position: relative; min-width: 0; } .lib-timeline__marker { position: absolute; top: 0.3rem; left: calc(var(--lib-gutter) * -1); width: 1rem; height: 1rem; border: 3px solid var(--lib-bg); border-radius: 50%; background: var(--lib-accent); box-shadow: 0 0 0 2px var(--lib-accent); } .lib-timeline__card { max-width: 34rem; } .lib-timeline[data-style='card'] .lib-timeline__card { padding: clamp(1.125rem, 2.5vw, 1.75rem); border-radius: 14px; background: var(--lib-card); } .lib-timeline__date { display: inline-block; margin: 0 0 0.5rem; padding: 0.2rem 0.65rem; border-radius: 999px; background: var(--lib-accent); color: var(--lib-accent-text); font-size: 0.8125rem; font-weight: 700; letter-spacing: 0.02em; } .lib-timeline__title { margin: 0; font-size: clamp(1.125rem, 1.6vw, 1.3125rem); line-height: 1.3; } .lib-timeline__media { overflow: hidden; margin-top: 0.875rem; border-radius: 10px; aspect-ratio: 4 / 3; background: color-mix(in srgb, var(--lib-text) 6%, transparent); } .lib-timeline__media[data-ratio='landscape'] { aspect-ratio: 16 / 9; } .lib-timeline__media[data-ratio='square'] { aspect-ratio: 1; } .lib-timeline__img { display: block; width: 100%; height: 100%; object-fit: cover; } .lib-timeline__body { margin-top: 0.625rem; font-size: 0.9375rem; line-height: 1.6; opacity: 0.85; } .lib-timeline__body > :first-child { margin-top: 0; } .lib-timeline__body > :last-child { margin-bottom: 0; } .lib-timeline__link { margin-top: 0.625rem; font-size: 0.9375rem; } /* Alternating: the line runs down the middle; milestones take turns on either side, the right column a little lower, so each pair overlaps instead of leaving a gap the height of a card. */ @media (min-width: 750px) { .lib-timeline[data-layout='alternate'] .lib-timeline__list { grid-template-columns: repeat(2, minmax(0, 1fr)); column-gap: calc(var(--lib-gutter) * 2); padding-left: 0; } .lib-timeline[data-layout='alternate'] .lib-timeline__list::before { left: calc(50% - 1px); } .lib-timeline[data-layout='alternate'] .lib-timeline__item { grid-column: 1; } .lib-timeline[data-layout='alternate'] .lib-timeline__card { margin-left: auto; text-align: right; } .lib-timeline[data-layout='alternate'] .lib-timeline__marker { left: auto; right: calc(var(--lib-gutter) * -1 - 0.5rem); } .lib-timeline[data-layout='alternate'] .lib-timeline__item:nth-child(even) { grid-column: 2; margin-top: clamp(3rem, 9vw, 8rem); } .lib-timeline[data-layout='alternate'] .lib-timeline__item:nth-child(even) .lib-timeline__card { margin-left: 0; text-align: left; } .lib-timeline[data-layout='alternate'] .lib-timeline__item:nth-child(even) .lib-timeline__marker { right: auto; left: calc(var(--lib-gutter) * -1 - 0.5rem); } } @supports (animation-timeline: view()) { @media (prefers-reduced-motion: no-preference) { .lib-timeline[data-animate] .lib-timeline__card { animation: lib-timeline-rise linear both; animation-timeline: view(); animation-range: entry 0% entry 55%; } } } @keyframes lib-timeline-rise { from { opacity: 0; transform: translateY(20px); } } {% endstylesheet %} {% schema %} { "name": "Lib · Timeline", "tag": "section", "class": "lib-section", "max_blocks": 16, "settings": [ { "type": "header", "content": "Content" }, { "type": "inline_richtext", "id": "heading", "label": "Heading", "default": "Our story so far" }, { "type": "select", "id": "heading_tag", "label": "Heading tag", "info": "Use H1 only when this is the page's main heading.", "options": [ { "value": "h1", "label": "H1" }, { "value": "h2", "label": "H2" }, { "value": "h3", "label": "H3" }, { "value": "p", "label": "Paragraph" } ], "default": "h2" }, { "type": "select", "id": "heading_size", "label": "Heading size", "options": [ { "value": "small", "label": "Small" }, { "value": "medium", "label": "Medium" }, { "value": "large", "label": "Large" } ], "default": "medium" }, { "type": "richtext", "id": "text", "label": "Intro text" }, { "type": "header", "content": "Layout" }, { "type": "select", "id": "layout", "label": "Layout on desktop", "info": "Mobile always shows one side.", "options": [ { "value": "alternate", "label": "Alternating sides" }, { "value": "single", "label": "One side" } ], "default": "alternate" }, { "type": "select", "id": "item_style", "label": "Milestone style", "options": [ { "value": "plain", "label": "Plain" }, { "value": "card", "label": "Card" } ], "default": "card" }, { "type": "select", "id": "image_ratio", "label": "Image shape", "options": [ { "value": "standard", "label": "4:3" }, { "value": "landscape", "label": "16:9" }, { "value": "square", "label": "Square" } ], "default": "standard" }, { "type": "select", "id": "section_width", "label": "Width", "options": [ { "value": "page", "label": "Page width" }, { "value": "full", "label": "Full width" } ], "default": "page" }, { "type": "select", "id": "text_alignment", "label": "Heading alignment on desktop", "options": [ { "value": "left", "label": "Left" }, { "value": "center", "label": "Center" } ], "default": "center" }, { "type": "select", "id": "text_alignment_mobile", "label": "Heading alignment on mobile", "options": [ { "value": "left", "label": "Left" }, { "value": "center", "label": "Center" } ], "default": "left" }, { "type": "header", "content": "Colors" }, { "type": "color", "id": "color_bg", "label": "Background", "default": "#FAF6F1" }, { "type": "color_background", "id": "color_bg_gradient", "label": "Background gradient", "info": "Optional. Covers the background color." }, { "type": "color", "id": "color_text", "label": "Text", "default": "#1F1B17" }, { "type": "color", "id": "color_accent", "label": "Accent (markers, dates)", "default": "#7A5A3A" }, { "type": "color", "id": "color_accent_text", "label": "Text on accent", "default": "#FFFFFF" }, { "type": "color", "id": "color_line", "label": "Line", "default": "#DCCFBF" }, { "type": "color", "id": "color_card", "label": "Card background", "default": "#FFFFFF" }, { "type": "header", "content": "Spacing and visibility" }, { "type": "range", "id": "padding_top", "label": "Top padding on desktop", "min": 0, "max": 200, "step": 4, "unit": "px", "default": 80 }, { "type": "range", "id": "padding_bottom", "label": "Bottom padding on desktop", "min": 0, "max": 200, "step": 4, "unit": "px", "default": 80 }, { "type": "range", "id": "padding_top_mobile", "label": "Top padding on mobile", "min": 0, "max": 160, "step": 4, "unit": "px", "default": 48 }, { "type": "range", "id": "padding_bottom_mobile", "label": "Bottom padding on mobile", "min": 0, "max": 160, "step": 4, "unit": "px", "default": 48 }, { "type": "select", "id": "show_on", "label": "Show on", "options": [ { "value": "all", "label": "All devices" }, { "value": "desktop", "label": "Desktop only" }, { "value": "mobile", "label": "Mobile only" } ], "default": "all" }, { "type": "text", "id": "anchor_id", "label": "Anchor ID", "info": "Optional. Link to this section with #your-id." }, { "type": "header", "content": "Motion" }, { "type": "checkbox", "id": "animate", "label": "Fade milestones in on scroll", "info": "Only in browsers that support scroll-driven animations; never when reduced motion is on.", "default": true } ], "blocks": [ { "type": "milestone", "name": "Milestone", "settings": [ { "type": "text", "id": "date", "label": "Date", "info": "Any label: 2019, Spring 2021, Step 1…", "default": "2019" }, { "type": "text", "id": "title", "label": "Title", "default": "Milestone title" }, { "type": "richtext", "id": "text", "label": "Text", "default": "

A sentence or two about what happened and why it mattered.

" }, { "type": "image_picker", "id": "image", "label": "Image" }, { "type": "image_picker", "id": "image_mobile", "label": "Mobile image", "info": "Optional. Below 750px." }, { "type": "text", "id": "link_label", "label": "Link text" }, { "type": "url", "id": "link_url", "label": "Link" }, { "type": "checkbox", "id": "link_new_tab", "label": "Open link in a new tab", "default": false } ] } ], "presets": [ { "name": "Lib · Timeline", "blocks": [ { "type": "milestone", "settings": { "date": "2019", "title": "The first wheel" } }, { "type": "milestone", "settings": { "date": "2021", "title": "Our own kiln" } }, { "type": "milestone", "settings": { "date": "2024", "title": "The studio shop opens" } } ] } ] } {% endschema %}