UI Card: document the spacing custom properties as a supported contract
[Type] EnhancementDesign System[Package] UI
## Problem
`Card`'s spacing is driven by three custom properties declared on `Card.Root` in `packages/ui/src/card/style.module.css`:
- `--wp-ui-card-padding`, default `var(--wpds-dimension-padding-2xl)` (24px)
- `--wp-ui-card-header-content-gap`, default `var(--wpds-dimension-gap-xl)` (24px)
- `--wp-ui-card-header-content-margin`, derived as `calc(gap - padding)`
They are the only density controls Card has, and consumers already need them: dashboard widget tiles are a denser surface than a settings page, and at small tile sizes the default padding takes space that self-sizing widgets need for content.
Using the properties safely requires three facts that nothing documents today:
1. They only take effect on the `Card.Root` element itself. The root re-declares them, so a value set on an ancestor never reaches the component, and consumers fall back to structural selectors that target the root from outside.
2. The padding and the gap must move together. Lowering only `--wp-ui-card-padding` leaves the derived margin positive, and the space between header and content becomes the header's block-end padding plus a leftover `margin-block-start` on the content: two stacked spaces where the design intends one. With the current defaults (24px and 24px) the margin resolves to 0, so the trap only opens when overriding.
3. `CollapsibleCard` consumes the derived margin too (`packages/ui/src/collapsible-card/style.module.css`), so the contract spans both components.
## Proposed solution
Make the two input properties the documented spacing contract, and remove the override trap. This intentionally stops short of a `size`/density prop: documenting the variables keeps density decisions with consumers while the design system explores a broader density story.
1. Document `--wp-ui-card-padding` and `--wp-ui-card-header-content-gap` in the component docs and Storybook, marking the derived margin as internal.
2. Default the header gap to the padding: `--wp-ui-card-header-content-gap: var(--wp-ui-card-padding)`. Both default to 24px today, so nothing changes visually, and overriding just the padding keeps the header/content space a single space.
3. Evaluate resolving both from inheritable public properties, for example `var(--wp-card-padding, <default>)`, so a subtree can be themed from an ancestor without targeting the root element.
## Tasks
- [ ] Document the two spacing properties as the supported contract
- [ ] Default `--wp-ui-card-header-content-gap` to `--wp-ui-card-padding`
- [ ] Evaluate ancestor-inheritable public properties
- [ ] Add a story exercising an overridden density so the contract stays covered
## Location
- `packages/ui/src/card/style.module.css` (property declarations and the header/content rules)
- `packages/ui/src/collapsible-card/style.module.css` (shared derived margin)
## Related
- #77616: widget tiles are the first consumer needing a denser Card; the widget dashboard chrome resolves these properties on its `Card.Root` elements to expose host-level spacing controls (PR to follow).
- #79231: tile density feeds the responsive work tracked for the dashboard's graduation.
0 条评论