---
title: "PostCard and HighlightCard"
description: "Listing cards and highlight cards for the Posts module."
requested_language: nl
language: en
translation_notice: "This page isn't translated yet"
url: https://docs.systhema.app/nl/components/post-card
version: unreleased (main)
docs_index: https://docs.systhema.app/nl/llms.txt
---
> This page isn't translated yet. Showing English.


`PostCard` is the default card for one post in a grid or row list, and `HighlightCard` is the full-bleed card for a lead post. [`PostsList`](https://docs.systhema.app/nl/components/posts-list.md) renders both for you; use them directly when you lay posts out yourself, for example a single featured post in a sidebar.

```tsx preview title="PostCard"
import { PostCard, type PostView } from '@systhemaui/next'

const post: PostView = {
  id: 1,
  title: 'Designing with tokens from day one',
  label: 'Design',
  href: '#',
  excerpt: 'How a small team keeps a large site consistent without slowing its editors down.',
  tags: [],
  postType: 'article',
  author: { name: 'Mira Kovač', avatar: { url: '/demo-assets/avatar-1.webp' } },
  publishedAt: '2026-09-14T09:00:00.000Z',
  media: { url: '/demo-assets/mountains.webp', alt: '', width: 1920, height: 1080 },
  layout: 'grid3',
  doc: null,
}

export default function Demo() {
  return (
    <div className="w-full max-w-sm">
      <PostCard post={post} />
    </div>
  )
}
```

## Import

```tsx
import { HighlightCard, PostCard } from '@systhemaui/next'
```

In a React app without Next.js, import them from `@systhemaui/react`. Both take a [`PostView`](https://docs.systhema.app/nl/components/posts-helpers.md#postview) as `post`.

## `PostCard`

A vertical stack of media, label, title, byline (author and date) and excerpt, with an optional "read more". The React card is presentational: it renders no link and fetches nothing. The Next.js card links the whole card to `post.href` (see [Next.js](#nextjs)).

### Default parts per layout

`post.layout` (`grid2`, `grid3`, `grid4` or `row`) decides the media aspect ratio and which parts show by default. `PostsList` sets it from its `view`; set it yourself when you render a card on its own.

| Layout          | Media aspect ratio                  | Excerpt | Read more |
| --------------- | ----------------------------------- | ------- | --------- |
| `grid2`         | 4:3, 16:9 from `md`                 | on      | off       |
| `grid3` or none | 4:3                                 | on      | off       |
| `grid4`         | 4:3                                 | off     | off       |
| `row`           | 4:3, 3:2 from `md`, beside the text | off     | on        |

Media, label, title, author and date are on in every layout. On small screens every layout is stacked, media first. From `md` the `row` card becomes a two-column grid (`1fr 2fr`) with the text top-aligned.

```tsx preview iframe height=420 title="A row card"
import { PostCard, type PostView } from '@systhemaui/next'

const post: PostView = {
  id: 1,
  title: 'Shipping a multilingual site in a week',
  label: 'Engineering',
  href: '#',
  tags: [],
  postType: 'article',
  author: { name: 'Jonas Weber' },
  publishedAt: '2026-09-02T09:00:00.000Z',
  media: { url: '/demo-assets/city.webp', alt: '', width: 1920, height: 1080 },
  layout: 'row',
  doc: null,
}

export default function Demo() {
  return (
    <div className="w-full">
      <PostCard post={post} />
    </div>
  )
}
```

### Parts

`config.show` turns parts on or off and `config.classNames` overrides a part's classes. An override is merged with tailwind-merge, so `aspect-square` replaces the default `aspect-[4/3]` while non-conflicting classes are added.

| Card            | `show` parts                                                                  | `classNames` parts    |
| --------------- | ----------------------------------------------------------------------------- | --------------------- |
| `PostCard`      | `media`, `label`, `title`, `author`, `date`, `excerpt`, `readMore`            | the same, plus `root` |
| `HighlightCard` | `media`, `overlay`, `label`, `title`, `author`, `date`, `excerpt`, `readMore` | the same, plus `root` |

`PostCard`'s `config` also takes four presentation values, applied as inline styles so any value works without a Tailwind build: `aspectRatio` (CSS `aspect-ratio` of the media, such as `'1/1'`), `mediaGap` (the gap between media and text, such as `'var(--gap-md)'`), and for the `row` layout from `md` up `mediaWidth` (`grid-template-columns`, default `'1fr 2fr'`) and `bodyAlign` (`align-self` of the text).

```tsx preview title="Square media, no excerpt, a read-more link"
import { PostCard, type PostView } from '@systhemaui/next'

const post: PostView = {
  id: 1,
  title: 'A field guide to spacing',
  label: 'Design',
  href: '#',
  excerpt: 'Why the rich-text rhythm beats hand-tuned margins.',
  tags: [],
  postType: 'article',
  author: { name: 'Mira Kovač' },
  publishedAt: '2026-08-28T09:00:00.000Z',
  media: { url: '/demo-assets/coast.webp', alt: '', width: 1800, height: 1200 },
  layout: 'grid3',
  doc: null,
}

export default function Demo() {
  return (
    <div className="w-full max-w-xs">
      <PostCard
        post={post}
        config={{ show: { excerpt: false, readMore: true }, aspectRatio: '1/1' }}
        readMoreLabel="Read the guide"
      />
    </div>
  )
}
```

A post without media renders an empty placeholder box of the same aspect ratio, so a grid stays aligned.

## `HighlightCard`

A full-bleed card: the media fills the card, a dark scrim covers it, and the label, title, byline and excerpt sit bottom left in white, at most half the card's width from `md`. It is 4:5 on small screens and 16:9 from `md`. Every part is on by default except `readMore`; turn the scrim off with `config.show.overlay: false`.

```tsx preview iframe height=640 title="HighlightCard"
import { HighlightCard, type PostView } from '@systhemaui/next'

const post: PostView = {
  id: 1,
  title: 'Designing with tokens from day one',
  label: 'Design',
  href: '#',
  excerpt: 'How a small team keeps a large site consistent without slowing its editors down.',
  tags: [],
  postType: 'article',
  author: { name: 'Mira Kovač', avatar: { url: '/demo-assets/avatar-1.webp' } },
  publishedAt: '2026-09-14T09:00:00.000Z',
  media: { url: '/demo-assets/city.webp', alt: '', width: 1920, height: 1080 },
  doc: null,
}

export default function Demo() {
  return (
    <div className="w-full">
      <HighlightCard post={post} />
    </div>
  )
}
```

## Color

`PostCard` follows the active color system like [`Heading`](https://docs.systhema.app/nl/components/heading.md) and [`Paragraph`](https://docs.systhema.app/nl/components/paragraph.md): the title carries `color-heading`, the excerpt `color-body`, and the card root sets its color from `--color-typography-body` so the label and byline mute against the right base. Put a card on a themed `Section` and its text follows that theme, or pass `theme` to set `data-theme` on the card itself. A text color in `classNames.title` or `classNames.excerpt` still wins, because utilities beat the component layer. `HighlightCard` is always white on its scrim.

## Props

### `PostCard` props

<!-- generated:props @systhemaui/react PostCardProps -->

| Prop               | Type                                                                                                                                                                                                 | Default       | Description                                                                                                                                                                                                                    |
| ------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `post` (required)  | `PostView`                                                                                                                                                                                           | -             | The resolved, serializable view-model for this post.                                                                                                                                                                           |
| `config`           | `ResolvedCardConfig`                                                                                                                                                                                 | -             | The resolved show/classNames for this card layout. Defaults to the Figma defaults when omitted (media/label/title/author/date/excerpt ON, readMore OFF). Pulled from the per-layout `listing.cards.<layout>` plugin config.    |
| `className`        | `string`                                                                                                                                                                                             | -             |                                                                                                                                                                                                                                |
| `theme`            | `ColorSystem` (`dark`, `default`)                                                                                                                                                                    | -             |                                                                                                                                                                                                                                |
| `renderImage`      | `((media: { url: string; alt?: string \| undefined; width?: number \| undefined; height?: number \| undefined; srcset?: string \| undefined; isPlaceholder?: boolean \| undefined; }) => ReactNode)` | -             | Render-prop for the media region. The next package passes an optimized `next/image` here; react renders a plain `<img>` by default.                                                                                            |
| `headingLevel`     | `2 \| 3 \| 4`                                                                                                                                                                                        | `3`           | Heading level for the card title (default 3).                                                                                                                                                                                  |
| `readMoreLabel`    | `string`                                                                                                                                                                                             | `'Read more'` | Label for the optional "read more" affordance (default "Read more").                                                                                                                                                           |
| `disableAnimation` | `boolean`                                                                                                                                                                                            | `false`       | Disable this card's scroll-reveal animation. By default each card carries the config `animationClasses` so posts reveal **individually** as they enter the viewport (rather than the whole listing/Section fading in at once). |

<!-- /generated -->

`renderImage(media)` replaces the default `<img>` (the Next.js card passes `next/image`). `disableAnimation` turns off the card's scroll reveal; by default it carries `packages.react.animationClasses` from your config.

### `HighlightCard` props

<!-- generated:props @systhemaui/react HighlightCardProps -->

| Prop               | Type                                                                                                                                                                                                 | Default       | Description                                                                                                                                            |
| ------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `post` (required)  | `PostView`                                                                                                                                                                                           | -             | The resolved, serializable view-model for the highlighted post.                                                                                        |
| `config`           | `ResolvedHighlightCardConfig`                                                                                                                                                                        | -             | The resolved show/classNames for the highlight card. Defaults to the Figma defaults when omitted (all parts ON). Pulled from `listing.highlightCard`.  |
| `className`        | `string`                                                                                                                                                                                             | -             |                                                                                                                                                        |
| `theme`            | `ColorSystem` (`dark`, `default`)                                                                                                                                                                    | -             |                                                                                                                                                        |
| `renderImage`      | `((media: { url: string; alt?: string \| undefined; width?: number \| undefined; height?: number \| undefined; srcset?: string \| undefined; isPlaceholder?: boolean \| undefined; }) => ReactNode)` | -             | Render-prop for the full-bleed background media. The next package passes an optimized `next/image` (`fill`); react renders a plain `<img>` by default. |
| `headingLevel`     | `1 \| 2 \| 3`                                                                                                                                                                                        | `2`           | Heading level for the title (default 2 — it's the listing's lead card).                                                                                |
| `readMoreLabel`    | `string`                                                                                                                                                                                             | `'Read more'` | Label for the optional "read more" affordance (default "Read more").                                                                                   |
| `disableAnimation` | `boolean`                                                                                                                                                                                            | `false`       | Disable this card's scroll-reveal animation (default reveals on scroll).                                                                               |

<!-- /generated -->

## HTML and CSS

The `.post-card*` and `.post-highlight*` hooks come from the `posts` CSS layer. A grid card's markup is on [PostsList](https://docs.systhema.app/nl/components/posts-list.md#html-and-css); a highlight card looks like this:

```html
<article class="post-highlight relative aspect-[4/5] overflow-hidden rounded-xl md:aspect-video">
  <div class="post-highlight-media absolute inset-0">
    <img src="/media/mountains.webp" alt="" class="size-full object-cover" />
  </div>
  <div class="post-highlight-scrim absolute inset-0" aria-hidden="true"></div>
  <div
    class="post-highlight-overlay absolute inset-0 flex flex-col justify-end gap-4 p-7 text-white md:max-w-[50%]"
  >
    <span class="post-highlight-label text-label">Design</span>
    <h2 class="post-highlight-title text-h4">Designing with tokens from day one</h2>
    <div class="post-meta post-highlight-meta text-small flex flex-wrap items-center gap-x-2">
      <span class="post-meta-author">Mira Kovač</span>
      <span class="post-meta-separator" aria-hidden="true">•</span>
      <time class="post-meta-date" datetime="2026-09-14">September 14, 2026</time>
    </div>
    <p class="post-highlight-excerpt text-body">How a small team…</p>
  </div>
</article>
```

The scrim gradient is `.post-highlight-scrim` in the `posts` layer.

<!-- generated:utilities posts -->

| Class                               | Styles                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| ----------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `posts-list`                        | `width: 100%;`<br>`max-width: var(--container-width);`<br>`margin-inline: auto;`                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| `posts-list-grid`                   | `& { display: grid; grid-template-columns: minmax(0, 1fr); column-gap: var(--gap-sm, 1.25rem); row-gap: var(--gap-md, 2.5rem); }`<br>`& > .post-card { animation-delay: var(--post-card-stagger-delay, 0ms); }`<br>`& > * > .post-card { animation-delay: var(--post-card-stagger-delay, 0ms); }`                                                                                                                                                                                                                   |
| `posts-list-row`                    | `display: flex;`<br>`flex-direction: column;`<br>`row-gap: var(--gap-md, 2.5rem);`                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `posts-list-grid-2`                 | `@media (width >= 640px) { & { grid-template-columns: repeat(2, minmax(0, 1fr)); } }`<br>`@media (width >= 640px) { & > :nth-child(2n - 1) { --post-card-stagger-delay: 0ms; } }`<br>`@media (width >= 640px) { & > :nth-child(2n) { --post-card-stagger-delay: calc(var(--tw-stagger-delay, 120ms) * 1); } }`                                                                                                                                                                                                      |
| `posts-list-grid-3`                 | `@media (width >= 640px) { & { grid-template-columns: repeat(2, minmax(0, 1fr)); } }`<br>`@media (width >= 1192px) { & { grid-template-columns: repeat(3, minmax(0, 1fr)); } }`<br>`@media (width >= 640px) and (width < 1192px) { & > :nth-child(2n - 1) { --post-card-stagger-delay: 0ms; } }`<br>`@media (width >= 640px) and (width < 1192px) { & > :nth-child(2n) { --post-card-stagger-delay: calc(var(--tw-stagger-delay, 120ms) * 1); } }`<br>+ 3 more rules                                                |
| `posts-list-grid-4`                 | `@media (width >= 640px) { & { grid-template-columns: repeat(2, minmax(0, 1fr)); } }`<br>`@media (width >= 1192px) { & { grid-template-columns: repeat(4, minmax(0, 1fr)); } }`<br>`@media (width >= 640px) and (width < 1192px) { & > :nth-child(2n - 1) { --post-card-stagger-delay: 0ms; } }`<br>`@media (width >= 640px) and (width < 1192px) { & > :nth-child(2n) { --post-card-stagger-delay: calc(var(--tw-stagger-delay, 120ms) * 1); } }`<br>+ 4 more rules                                                |
| `posts-list-interspace`             | `width: 100%;`                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| `posts-list-empty`                  | `color: color-mix(in srgb, currentColor 60%, transparent);`<br>`text-align: center;`<br>`padding-block: var(--gap-md, 2.5rem);`                                                                                                                                                                                                                                                                                                                                                                                     |
| `posts-list-actions`                | `display: flex;`<br>`align-items: center;`<br>`justify-content: center;`<br>`gap: var(--gap-sm, 1.25rem);`                                                                                                                                                                                                                                                                                                                                                                                                          |
| `posts-list-load-more`              | `&:disabled, .posts-list-load-more[disabled] { opacity: 0.4; cursor: not-allowed; }`                                                                                                                                                                                                                                                                                                                                                                                                                                |
| `posts-list-pagination`             | `& { display: flex; justify-content: center; align-items: center; gap: var(--gallery-navigation-gap-x, 10px); }`<br>+ 13 more rules                                                                                                                                                                                                                                                                                                                                                                                 |
| `post-card`                         | `& { color: var(--color-typography-body); }`<br>`.posts-list-grid > .post-card { animation-delay: var(--post-card-stagger-delay, 0ms); }`<br>`.posts-list-grid > * > .post-card { animation-delay: var(--post-card-stagger-delay, 0ms); }`                                                                                                                                                                                                                                                                          |
| `post-card-label`                   | `& { color: color-mix(in srgb, currentColor 60%, transparent); }`<br>`&.text-label { color: color-mix(in srgb, currentColor 60%, transparent); }`                                                                                                                                                                                                                                                                                                                                                                   |
| `post-highlight-label`              | `& { color: color-mix(in srgb, currentColor 60%, transparent); }`<br>`&.text-label { color: color-mix(in srgb, currentColor 60%, transparent); }`                                                                                                                                                                                                                                                                                                                                                                   |
| `post-type`                         | `color: color-mix(in srgb, currentColor 60%, transparent);`                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| `text-label`                        | `& { font-family: var(--font-label-font-family); font-size: var(--typography-label-font-size); font-weight: var(--font-label-font-weight); letter-spacing: var(--typography-label-letter-spacing); line-height: var(--typography-label-line-height); text-transform: uppercase; text-decoration: none; font-style: var(--font-label-font-style); }`<br>`.post-card-label.text-label { color: color-mix(in srgb, currentColor 60%, transparent); }`<br>+ 1 more rule                                                 |
| `post-card-title`                   | `text-wrap: balance;`                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| `post-card-read-more`               | `color: var(--color-link-text-default, currentColor);`<br>`font-weight: 600;`<br>`text-decoration-line: underline;`                                                                                                                                                                                                                                                                                                                                                                                                 |
| `post-highlight-read-more`          | `color: var(--color-link-text-default, currentColor);`<br>`font-weight: 600;`<br>`text-decoration-line: underline;`                                                                                                                                                                                                                                                                                                                                                                                                 |
| `post-card-media-placeholder`       | `width: 100%;`<br>`height: 100%;`<br>`background-color: color-mix(in srgb, currentColor 6%, transparent);`                                                                                                                                                                                                                                                                                                                                                                                                          |
| `post-card-row`                     | `@media (width >= 640px) { & .post-card-body { align-self: start; justify-content: flex-start; } }`                                                                                                                                                                                                                                                                                                                                                                                                                 |
| `post-card-body`                    | `@media (width >= 640px) { .post-card-row .post-card-body { align-self: start; justify-content: flex-start; } }`                                                                                                                                                                                                                                                                                                                                                                                                    |
| `post-highlight`                    | `position: relative;`<br>`overflow: hidden;`<br>`border-radius: var(--card-default-border-radius, 12px);`                                                                                                                                                                                                                                                                                                                                                                                                           |
| `highlight-card`                    | `position: relative;`<br>`overflow: hidden;`<br>`border-radius: var(--card-default-border-radius, 12px);`                                                                                                                                                                                                                                                                                                                                                                                                           |
| `post-highlight-scrim`              | `position: absolute;`<br>`inset: 0;`<br>`background: linear-gradient(to top, rgba(0,0,0,0.75) 0%, rgba(0,0,0,0.35) 35%, rgba(0,0,0,0) 70%);`<br>`pointer-events: none;`                                                                                                                                                                                                                                                                                                                                             |
| `post-highlight-overlay`            | `position: relative;`<br>`z-index: 1;`                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| `post-highlight-excerpt`            | `color: color-mix(in srgb, #ffffff 85%, transparent);`                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| `post-meta`                         | `display: flex;`<br>`align-items: center;`<br>`flex-wrap: wrap;`<br>`gap: 0.5em;`<br>`color: color-mix(in srgb, currentColor 60%, transparent);`                                                                                                                                                                                                                                                                                                                                                                    |
| `post-byline-meta`                  | `display: flex;`<br>`align-items: center;`<br>`flex-wrap: wrap;`<br>`gap: 0.5em;`<br>`color: color-mix(in srgb, currentColor 60%, transparent);`                                                                                                                                                                                                                                                                                                                                                                    |
| `post-meta-avatar`                  | `width: var(--post-byline-avatar-size, 1.75em);`<br>`height: var(--post-byline-avatar-size, 1.75em);`<br>`border-radius: 9999px;`<br>`object-fit: cover;`<br>`flex-shrink: 0;`                                                                                                                                                                                                                                                                                                                                      |
| `post-meta-separator`               | `opacity: 0.5;`                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| `post-meta-author-role`             | `& { opacity: 0.7; }`<br>`&::before { content: ", "; }`                                                                                                                                                                                                                                                                                                                                                                                                                                                             |
| `archive-filter`                    | `display: flex;`<br>`flex-direction: column;`<br>`gap: var(--gap-sm, 1.25rem);`                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| `archive-filter-bar`                | `display: flex;`<br>`flex-wrap: wrap;`<br>`align-items: center;`<br>`gap: var(--gap-sm, 1.25rem);`                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `archive-filter-label`              | `flex: 0 0 auto;`<br>`color: color-mix(in srgb, currentColor 60%, transparent);`                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| `archive-filter-search`             | `flex: 1 1 16rem;`<br>`min-width: 0;`<br>`margin: 0;`                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| `archive-filter-select`             | `flex: 1 1 16rem;`<br>`min-width: 0;`<br>`margin: 0;`                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| `archive-filter-chips`              | `display: flex;`<br>`flex-wrap: wrap;`<br>`align-items: center;`<br>`gap: var(--chip-gap, 0.5rem);`<br>`flex: 1 1 16rem;`<br>`min-width: 0;`                                                                                                                                                                                                                                                                                                                                                                        |
| `archive-filter-chip-toggle`        | `cursor: pointer;`<br>`appearance: none;`                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |
| `archive-filter-chip-toggle-active` | `background-color: var(--color-chip-hover-background);`<br>`border-color: var(--color-chip-hover-border);`<br>`color: var(--color-chip-hover-text);`                                                                                                                                                                                                                                                                                                                                                                |
| `archive-filter-active`             | `display: flex;`<br>`flex-wrap: wrap;`<br>`align-items: center;`<br>`gap: var(--chip-gap, 0.5rem);`                                                                                                                                                                                                                                                                                                                                                                                                                 |
| `archive-filter-chip`               | `& { appearance: none; cursor: pointer; display: inline-flex; align-items: center; gap: var(--chip-gap); font-size: var(--chip-font-size); line-height: var(--chip-line-height); letter-spacing: calc(var(--chip-letter-spacing, 0) * 1px); padding-inline: var(--chip-padding-x); padding-block: var(--chip-padding-y); border-radius: var(--chip-border-radius); border-style: solid; border-width: var(--chip-border-width); background-color: var(--color-chip-normal-background); border-co…`<br>+ 1 more rule |
| `archive-filter-chip-remove`        | `font-size: 1.2em;`<br>`line-height: 1;`<br>`opacity: 0.7;`                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| `post-related-title`                | `margin-bottom: var(--gap-sm, 1.25rem);`                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| `post-single`                       | `& .article > :not(section, .figure-w-full, .figure-w-screen, .figure-w-container, a:not([class*="card"]), div:not(.columns, .stack, [class*="card"], [class*="accordion"])) { max-width: var(--post-reading-width, calc(var(--container-width) - (var(--article-padding-x) * 2))); }`                                                                                                                                                                                                                              |
| `post-share-button-label`           | `font-size: var(--text-small-font-size, 0.875rem);`<br>`line-height: 1;`                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| `post-share-icon-label`             | `& .post-share-list > a { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>`& .post-share-list > button { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`                                                                                                                                                                                                                                                                           |
| `post-share-list`                   | `.post-share-icon-label .post-share-list > a { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>`.post-share-icon-label .post-share-list > button { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>`.post-share-pills .post-share-list > a { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>+ 3 more rules                                                                           |
| `post-share-pills`                  | `& .post-share-list > a { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>`& .post-share-list > button { display: inline-flex; align-items: center; gap: var(--gap-xs, 0.5rem); width: auto; }`<br>`& .post-share-list > a { padding: var(--gap-xs, 0.5rem) var(--gap-sm, 1.25rem); border-radius: 9999px; border: 1px solid var(--color-separator-line, currentColor); }`<br>+ 1 more rule                                                                               |
| `post-share-sticky-bottom`          | `position: fixed;`<br>`left: 0;`<br>`right: 0;`<br>`bottom: 0;`<br>`z-index: 40;`<br>`justify-content: center;`<br>`background-color: var(--color-foundations-surface-bg);`<br>`border-top: 1px solid var(--color-separator-line, currentColor);`<br>`padding-block: var(--gap-sm, 1.25rem);`                                                                                                                                                                                                                       |
| `post-share-floating-sidebar`       | `@media (width >= 1192px) { & { position: fixed; left: var(--gap-lg, 1.5rem); top: 50%; transform: translateY(-50%); flex-direction: column; align-items: center; z-index: 40; } }`                                                                                                                                                                                                                                                                                                                                 |

<!-- /generated -->

## Next.js

### `PostCard` in Next.js

When `linked` (default `true`) is on and the post has an `href`, the whole card is wrapped in `next/link`, and the media renders through `next/image` (`fill`, `objectFit="cover"`) with a `sizes` hint from [`sizesForLayout(post.layout)`](https://docs.systhema.app/nl/components/posts-helpers.md#sizesforlayout). With no `href`, or `linked={false}`, it renders the React card. It takes the React props except `renderImage`, plus `linked`.

```tsx
import { PostCard } from '@systhemaui/next'

;<PostCard post={postView} linked={false} />
```

<!-- generated:props @systhemaui/next PostCardProps -->

| Prop               | Type                              | Default | Description                                                                                                                                                                                                                    |
| ------------------ | --------------------------------- | ------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `linked`           | `boolean`                         | `true`  | Wrap the whole card in a `next/link` to the post's `href` (prefetching + client navigation). When false (or the post has no href), renders the bare presentational card.                                                       |
| `className`        | `string`                          | -       |                                                                                                                                                                                                                                |
| `disableAnimation` | `boolean`                         | -       | Disable this card's scroll-reveal animation. By default each card carries the config `animationClasses` so posts reveal **individually** as they enter the viewport (rather than the whole listing/Section fading in at once). |
| `theme`            | `ColorSystem` (`dark`, `default`) | -       |                                                                                                                                                                                                                                |
| `post` (required)  | `PostView`                        | -       | The resolved, serializable view-model for this post.                                                                                                                                                                           |
| `config`           | `ResolvedCardConfig`              | -       | The resolved show/classNames for this card layout. Defaults to the Figma defaults when omitted (media/label/title/author/date/excerpt ON, readMore OFF). Pulled from the per-layout `listing.cards.<layout>` plugin config.    |
| `headingLevel`     | `2 \| 3 \| 4`                     | -       | Heading level for the card title (default 3).                                                                                                                                                                                  |
| `readMoreLabel`    | `string`                          | -       | Label for the optional "read more" affordance (default "Read more").                                                                                                                                                           |

<!-- /generated -->

### `HighlightCard` in Next.js

The media renders through `next/image` with `fill`, `sizes="100vw"` and `priority`, so it loads eagerly as the likely LCP image, and the card links through `next/link`. Use one highlight card per page, above the fold. It takes the React props except `renderImage`, plus `linked`.

<!-- generated:props @systhemaui/next HighlightCardProps -->

| Prop               | Type                              | Default | Description                                                                                                                                           |
| ------------------ | --------------------------------- | ------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- |
| `linked`           | `boolean`                         | `true`  | Wrap the whole card in a `next/link` to the post's `href`. When false (or the post has no href), renders the bare presentational highlight card.      |
| `className`        | `string`                          | -       |                                                                                                                                                       |
| `disableAnimation` | `boolean`                         | -       | Disable this card's scroll-reveal animation (default reveals on scroll).                                                                              |
| `theme`            | `ColorSystem` (`dark`, `default`) | -       |                                                                                                                                                       |
| `post` (required)  | `PostView`                        | -       | The resolved, serializable view-model for the highlighted post.                                                                                       |
| `config`           | `ResolvedHighlightCardConfig`     | -       | The resolved show/classNames for the highlight card. Defaults to the Figma defaults when omitted (all parts ON). Pulled from `listing.highlightCard`. |
| `headingLevel`     | `1 \| 2 \| 3`                     | -       | Heading level for the title (default 2 — it's the listing's lead card).                                                                               |
| `readMoreLabel`    | `string`                          | -       | Label for the optional "read more" affordance (default "Read more").                                                                                  |

<!-- /generated -->

## Accessibility

- The card is an `<article>` with a real heading: `<h3>` for `PostCard` (`headingLevel` 2 to 4) and `<h2>` for `HighlightCard` (`headingLevel` 1 to 3).
- The date is a `<time datetime>` with the ISO date.
- The "read more" text is `aria-hidden`, because the whole card is the link; it does not repeat in the link's name.
- The scrim is `aria-hidden`. Featured media is usually decorative next to the title, so an empty `alt` is fine; give `media.alt` a value when the image carries information the title does not.

## Related

- [PostsList](https://docs.systhema.app/nl/components/posts-list.md)
- [PostMeta](https://docs.systhema.app/nl/components/post-meta.md)
- [Posts view model and helpers](https://docs.systhema.app/nl/components/posts-helpers.md)
- [Customizing the presentation](https://docs.systhema.app/nl/payload/posts/presentation.md)
