Something went wrong. Try again.
[READ-ONLY] Mirror of https://github.com/lukebennett88/luke-ui. ui.lukebennett.dev
Something went wrong. Try again.
4.4 kB · 153 lines
TypeScript
at main
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154import { vars } from '@luke-ui/react/theme';import { globalStyle, style } from '@vanilla-extract/css';import { docsTocMinInlineSize } from '../../lib/docs-container-queries.js';import { SITE_HEADER_BLOCK_SIZE } from '../site-header-size.js';import { TOC_BAR_BLOCK_SIZE } from './docs-article.css.js';
// WCAG 2.5.8 minimum target size: 24 CSS pixels, whatever the root font size.const MIN_TARGET_SIZE = 'max(1.5rem, 24px)';
// Prose spaces a block from the block before it with an element selector at `:where()` strength.// Wrappers that stand in for a prose element repeat that spacing here. The `h2 + &` style selectors// out-rank Prose's `h2 + *` rule, so the heading gap stays the same however the cascade orders them.
export const heading = style({ '@layer': { components: { // Clears the sticky header, and below the table of contents breakpoint the sticky bar too. scrollMarginBlockStart: `calc(${SITE_HEADER_BLOCK_SIZE} + ${TOC_BAR_BLOCK_SIZE} + ${vars.space.sp24})`, '@container': { [docsTocMinInlineSize]: { scrollMarginBlockStart: `calc(${SITE_HEADER_BLOCK_SIZE} + ${vars.space.sp24})`, }, }, }, },});
// The end margin reserves the button's inline space. Inline margin has no break opportunity before// it, so the last word wraps together with the button instead of leaving the button alone on a new// line.export const headingAnchor = style({ '@layer': { components: { color: 'inherit', marginInlineEnd: `calc(${vars.space.sp4} + ${MIN_TARGET_SIZE})`, textDecoration: 'none', }, },});
// A zero-size inline box on the baseline, at the end of the reserved space. It adds nothing to the// line box, so the Prose gaps around the heading and the Text cap-height trim stay intact. It moves// up half the cap height, in the heading's own font, to the centre of the cap-height band, and the// button is centred on it.export const headingCopyWrapper = style({ '@layer': { components: { blockSize: 0, display: 'inline-block', inlineSize: 0, position: 'relative', translate: '0 -0.5cap', verticalAlign: 'baseline', }, },});
// The control size token is 32px. A 24px target keeps the button quiet beside the heading text and// still meets the minimum target size. Hidden until the heading is hovered or keyboard focus is// inside it. A mouse click leaves `:focus-visible` unset, so it does not pin the button open.export const headingCopyButton = style({ '@layer': { components: { blockSize: MIN_TARGET_SIZE, color: vars.color.text.secondary, fontSize: 'inherit', inlineSize: MIN_TARGET_SIZE, insetBlockStart: 0, insetInlineEnd: 0, minBlockSize: 0, opacity: 0, position: 'absolute', translate: '0 -50%', transition: `opacity ${vars.motion.feedback.duration} ${vars.motion.feedback.easing}`, selectors: { '&:hover': { color: vars.color.text.primary, }, [`${heading}:hover &, ${heading}:has(:focus-visible) &`]: { opacity: 1, }, }, '@media': { '(prefers-reduced-motion: reduce)': { transition: 'none', }, }, }, },});
export const image = style({ '@layer': { components: { blockSize: 'auto', borderRadius: vars.radius.surface, maxInlineSize: '100%', }, },});
export const tableScroll = style({ '@layer': { components: { border: `1px solid ${vars.color.border.decorative}`, borderRadius: vars.radius.surface, marginBlockStart: vars.space.sp40, selectors: { 'h2 + &': { marginBlockStart: vars.space.sp32 }, 'h3 + &': { marginBlockStart: vars.space.sp24 }, 'h4 + &, h5 + &, h6 + &': { marginBlockStart: vars.space.sp16 }, }, }, },});
export const table = style({ '@layer': { components: { // Prose makes plain tables scroll themselves. This one scrolls inside its ScrollFade. display: 'table', inlineSize: '100%', maxInlineSize: 'none', overflowX: 'visible', }, },});
globalStyle(`${table} th, ${table} td`, { '@layer': { components: { borderBlockEnd: `1px solid ${vars.color.border.decorative}`, verticalAlign: 'top', }, },});
globalStyle(`${table} th`, { '@layer': { components: { backgroundColor: vars.color.surface.subdued, fontWeight: vars.font.weight.label, }, },});
globalStyle(`${table} tbody tr:last-child td`, { '@layer': { components: { borderBlockEnd: 0, }, },});