{% comment %} LISTING / media list: a vertical list of entries, each pairing a thumbnail with its copy. WHEN TO USE THIS INSTEAD OF THE CARD GRID. When the summary matters more than the browse. A grid optimises for scanning many titles at once; this optimises for reading a few. Use it for a search-results page, a news index where recency beats breadth, or any list where entries differ in importance rather than sitting as equals. A grid of three implies "pick one of these"; a list implies "here they are, in order". WHAT YOUR VIEW MUST SUPPLY. Same entry shape as the card grid: entries = [ {"title": "Chasing without the awkwardness", "summary": "How to write a reminder that gets paid without costing " "you the relationship.", "url": "/blog/chasing-without-the-awkwardness/", "meta": "14 July 2026", "image": "/static/blog/chasing.jpg", "image_alt": "A printed invoice on a desk beside a phone"}, ... ] THE THUMBNAIL IS A PLACEHOLDER SVG, NOT AN , for the same reason hero/split-media.html uses one: an example shipping a path to an image the package does not contain renders as a broken-image box in the consumer's project the moment they copy it. Swap it for your own markup: {% if entry.image %} {{ entry.image_alt }} {% endif %} If you make that swap, `image_alt` is NOT optional. These thumbnails are content, not decoration, so an empty alt would hide the entry from a screen reader scanning the list by its images. Keep the width and height attributes: they reserve the space before the image loads, so the list does not jump. Wrapping it in the {% templatetag openblock %} if {% templatetag closeblock %} above also keeps an entry with no image rendering copy at full width rather than a gap where a picture should be. WHY THIS OWNS ITS MARKUP RATHER THAN REUSING THE CARD GRID. It is a different arrangement of the same data, not the same arrangement at a different size: the media list is a single column of horizontal rows, and the grid is multiple columns of vertical stacks. The two share no layout declaration. That is the answer to the "should a grid be a component" question this pair was written to settle: the shared thing between the two listing variants turned out to be the ENTRY CONTRACT, not the grid, so promoting a grid component would abstract the half they do not have in common. Each row collapses to a stack on a phone, image first, which keeps the reading order identical to the visual order at every width. States: the title link takes the accent colour plus an underline on hover and focus-visible; otherwise static. Accessibility: each entry's heading is a real

; only the title is the link (not the whole row, deliberately, since the row is wide enough that a full-row target would swallow the surrounding whitespace); the placeholder thumbnail SVG is aria-hidden and focusable="false", with the swap note above making clear a real image needs a genuine, non-empty alt (these thumbnails are content, not decoration). Covered by axe.spec.mjs against sections-*.html, which renders this exact file, both themes. Responsive: single named breakpoint. Below --bw-breakpoint-sm (40rem) each entry stacks in one column, image first; from sm upward each entry becomes a fixed 12rem-image-plus-flexible-body row, so reading order matches visual order at every width. {% endcomment %}

Latest posts