Stack

Stack setzt Abstand zwischen Dinge. Es ist ein Flex-Container mit einer einzigen Aufgabe und die Antwort auf die meisten „wie kriege ich hier Abstand hin“-Fragen — senkrecht als Standard, waagerecht mit direction: 'row'.

Die Lücken stammen aus der Abstandsskala, sodass der Rhythmus einer Seite stimmig bleibt, ohne dass jemand Pixelwerte aussucht.

Einfacher Stack

Erstes
Zweites
Drittes
stack({ gap: 'md' },
  card(cardBody('Erstes')),
  card(cardBody('Zweites')),
  card(cardBody('Drittes')),
)

Richtung

stack({ direction: 'row', gap: 'md' },
  button('Eins'),
  button({ variant: 'outline' }, 'Zwei'),
  button({ variant: 'outline' }, 'Drei'),
)

Lücke

Ein Token-Name ('xs' … '3xl'), eine Anzahl Abstandseinheiten oder eine rohe CSS-Länge.

xsxsxs
mdmdmd
6 Einheiten6 Einheiten
3rem3rem
stack({ gap: 'lg' },
  stack({ direction: 'row', gap: 'xs' }, chip('xs'), chip('xs'), chip('xs')),
  stack({ direction: 'row', gap: 'md' }, chip('md'), chip('md'), chip('md')),
  stack({ direction: 'row', gap: 6 }, chip('6 Einheiten'), chip('6 Einheiten')),
  stack({ direction: 'row', gap: '3rem' }, chip('3rem'), chip('3rem')),
)

Ausrichtung

align und justify nehmen rohe Flexbox-Werte, es funktioniert also alles, was CSS versteht.

AnfangEnde
und ausgerichtet
stack({ gap: 'md' },
  stack({ direction: 'row', gap: 'sm', justify: 'space-between', style: 'background: var(--su-surface-2); padding: 0.6rem; border-radius: 0.5rem' },
    chip('Anfang'),
    chip('Ende'),
  ),
  stack({ direction: 'row', gap: 'sm', justify: 'center', align: 'center', style: 'background: var(--su-surface-2); padding: 0.6rem; border-radius: 0.5rem' },
    button({ size: 'sm' }, 'Zentriert'),
    chip('und ausgerichtet'),
  ),
)

Umbruch

Eine Reihe von Chips oder Buttons, die vielleicht nicht passt, braucht wrap — ohne ihn quetschen sie sich, statt in die nächste Zeile zu rutschen.

routingdataislandsimagespagefindlighthousesitemaprss
stack({ direction: 'row', gap: 'sm', wrap: true },
  ...['routing', 'data', 'islands', 'images', 'pagefind', 'lighthouse', 'sitemap', 'rss'].map(
    (name) => chip({ color: 'neutral' }, name),
  ),
)

Inline

inline macht aus dem Stack ein inline-flex, sodass er in einer Textzeile sitzt, statt die volle Breite zu nehmen.

Gebaut mit

sitelovite
und sonst nichts.

text(
  'Gebaut mit ',
  stack({ direction: 'row', gap: 'xs', inline: true, align: 'center' },
    chip({ color: 'primary', size: 'sm' }, 'sitelo'),
    chip({ color: 'neutral', size: 'sm' }, 'vite'),
  ),
  ' und sonst nichts.',
)

Als anderes Element

stack({ as: 'nav', direction: 'row', gap: 'sm' },
  navLink({ href: '/de/docs' }, 'Doku'),
  navLink({ href: '/de/ui', current: true }, 'UI'),
  navLink({ href: '/de/examples' }, 'Beispiele'),
)

Props

PropTypStandardBeschreibung
direction'row' | 'column''column'Hauptachse.
gapSpace'md'Abstand zwischen den Kindern.
alignstring'stretch'Jeder align-items-Wert.
justifystring'flex-start'Jeder justify-content-Wert.
wrapboolean | stringfalsetrue heißt umbrechen; ein String wird als flex-wrap durchgereicht.
inlinebooleanfalseWird als inline-flex gerendert.
asstring'div'Element, das gerendert wird, z. B. nav oder ul.