Skip to content

Refactor form control sizing #1005

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 33 commits into from
Jun 3, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
33 commits
Select commit Hold shift + click to select a range
3f9fd46
visual test setup
lindsaym-fa May 29, 2025
e964a7b
fix improper class placement in visual tests
lindsaym-fa May 30, 2025
f5f07e5
add `wa-form-control-*-font-size` and `-wa-form-control-hint-*` custo…
lindsaym-fa May 30, 2025
943d7b1
use new custom properties
lindsaym-fa May 30, 2025
2a9483f
dump of component sizing improvements
lindsaym-fa May 30, 2025
ed7309f
fix native color picker styles
lindsaym-fa May 30, 2025
ced5e46
Merge branch 'next' into lm/form-control-sizing
lindsaym-fa May 30, 2025
572ce03
Merge branch 'next' into lm/form-control-sizing
lindsaym-fa Jun 2, 2025
736e315
update menu with relative sizes
lindsaym-fa Jun 2, 2025
1ace67d
tidy up menu, select, and tag sizing
lindsaym-fa Jun 2, 2025
b7c16d8
use relative sizing across components
lindsaym-fa Jun 2, 2025
d45b91e
touch up custom properties
lindsaym-fa Jun 3, 2025
5369fdb
update docs and comments
lindsaym-fa Jun 3, 2025
c86adb0
update changelog
lindsaym-fa Jun 3, 2025
3c4507f
Merge branch 'next' into lm/form-control-sizing
lindsaym-fa Jun 3, 2025
8a28970
revert changes to visual tests to simplify PR
lindsaym-fa Jun 3, 2025
fa685ec
revert leftover change to visual tests
lindsaym-fa Jun 3, 2025
e944626
tidy up space doc markdown
lindsaym-fa Jun 3, 2025
d8a90e7
fix default card spacing
lindsaym-fa Jun 3, 2025
1f552d1
fix card docs
lindsaym-fa Jun 3, 2025
dbdddb8
wrap up new `--tag-max-size` for `<wa-select>`
lindsaym-fa Jun 3, 2025
05d738f
change default `--tag-max-size`
lindsaym-fa Jun 3, 2025
2461375
prettier
lindsaym-fa Jun 3, 2025
1eaeeba
touch up
lindsaym-fa Jun 3, 2025
c619eb5
clean up leftovers
lindsaym-fa Jun 3, 2025
f8ba906
fix native form control margins
lindsaym-fa Jun 3, 2025
2923a55
set default toggle size relative to font size
lindsaym-fa Jun 3, 2025
cc513d2
correct toggle size in docs
lindsaym-fa Jun 3, 2025
ffd856d
Merge branch 'next' into lm/form-control-sizing
lindsaym-fa Jun 3, 2025
9da4ce4
Konnorrogers/lm form control sizing (#1025)
KonnorRogers Jun 3, 2025
ddf3b54
Merge branch 'next' into lm/form-control-sizing
lindsaym-fa Jun 3, 2025
abbfe14
add workflow dispatch for client tests
KonnorRogers Jun 3, 2025
f681434
Merge branch 'lm/form-control-sizing' of https://github.com/shoelace-…
KonnorRogers Jun 3, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .github/workflows/client_tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
name: Client Tests

on:
workflow_dispatch:
push:
branches: [next]
pull_request:
Expand Down
23 changes: 23 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion packages/webawesome/docs/assets/styles/ui.css
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@

> input {
font: inherit;
margin-block: calc(-1 * var(--wa-space-smaller));
margin-block: 0.75em;
field-sizing: content;
}

Expand Down
9 changes: 9 additions & 0 deletions packages/webawesome/docs/docs/resources/changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,14 +31,23 @@ During the alpha period, things might break! We take breaking changes very serio
- `<wa-tab-group no-scroll-controls>` => `<wa-tab-group without-scroll-controls>`
- `<wa-tag removable>` => `<wa-tag with-remove>`
- 🚨 BREAKING: removed the `size` attribute from `<wa-card>`; please set the size of child elements on the children directly
- 🚨 BREAKING: Greatly simplified the sizing strategy across components and utilities
- Removed `--wa-size`, `--wa-size-smaller`, `--wa-size-larger`, `--wa-space`, `--wa-space-smaller`, and `--wa-space-larger`
- Added tokens for `--wa-form-control-padding-inline`, `--wa-form-control-padding-block`, and `--wa-form-control-toggle-size`
- Refactored default `--wa-font-size-*` values to use an apparent 1.125 ratio and round rendered values to the nearest whole pixel
- Added convenience tokens for `--wa-font-size-smaller` and `--wa-font-size-larger`
- Updated components to use relative `em` values for internal padding and margin wherever appropriate
- 🚨 BREAKING: removed the `hint` property and slot from `<wa-radio>`; please apply hints directly to `<wa-radio-group>` instead
- Added a new free component: `<wa-popover>` (#2 of 14 per stretch goals)
- Added a `min-block-size` to `<wa-divider orientation="vertical">` to ensure the divider is visible regardless of container height [issue:675]
- Added support for `name` in `<wa-details>` for exclusively opening one in a group
- Added `--checked-icon-scale` to `<wa-checkbox>`
- Added `--tag-max-size` to `<wa-select>` when using `multiple`
- Fixed a bug in `<wa-radio-group>` that caused radios to uncheck when assigning a numeric value [issue:924]
- Fixed `<wa-button-group>` so dividers properly show between buttons
- Fixed the tooltip position in `<wa-slider>` when using RTL
- Fixed a bug in `<wa-details>` and native `<details>` styles that made the summary hard to click [issue:684]
- Fixed a handful of bugs unify form control height across components and native elements
- Improved CSS utilities and Native Styles to use [CSS layers](https://developer.mozilla.org/en-US/docs/Web/CSS/@layer) for easier end user customization (no more specificity conflicts — your CSS wins!)
- Improved native `<button>` styles to properly space icons
- Improved button appearances in `<wa-color-picker>`
Expand Down
69 changes: 28 additions & 41 deletions packages/webawesome/docs/docs/tokens/component-groups.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,31 +8,38 @@ For components that share similar qualities, Web Awesome includes custom propert

## Form Controls

Components such as [input](/docs/components/input), [select](/docs/components/select), [textarea](/docs/components/textarea), [checkbox](/docs/components/checkbox), etc. share a number of styles to give your forms a cohesive appearance. Web Awesome defines custom properties for these styles using the format `--wa-form-control-{style}`.
Components such as [input](/docs/components/input), [select](/docs/components/select), [textarea](/docs/components/textarea), [checkbox](/docs/components/checkbox), and others share a number of styles to give your forms a cohesive appearance. Web Awesome defines custom properties for these styles using the format `--wa-form-control-{style}`.

Not every form control uses all of these custom properties. For example, `<wa-radio>` defines its own height and border radius to achieve its familiar shape but shares many other styles with other components for a cohesive look and feel. Similarly, `<wa-button>` defines many of its own styles but matches the height and border width of other form controls.

| Custom Property | Default Value |
| ------------------------------------------- | ------------------------------------------------------------------------------------------------- |
| `--wa-form-control-background-color` | `var(--wa-color-surface-default)` |
| `--wa-form-control-border-color` | `var(--wa-color-neutral-border-loud)` |
| `--wa-form-control-border-style` | `var(--wa-border-style)` |
| `--wa-form-control-border-width` | `var(--wa-border-width-s)` |
| `--wa-form-control-border-radius` | `var(--wa-border-radius-m)` |
| `--wa-form-control-activated-color` | `var(--wa-color-brand-fill-loud)` |
| `--wa-form-control-label-color` | `var(--wa-color-neutral-border-loud)` |
| `--wa-form-control-label-font-weight` | `var(--wa-font-weight-normal)` |
| `--wa-form-control-label-line-height` | `var(--wa-line-height-normal)` |
| `--wa-form-control-value-color` | `var(--wa-color-text-normal)` |
| `--wa-form-control-value-font-weight` | `var(--wa-font-weight-body)` |
| `--wa-form-control-value-line-height` | `var(--wa-line-height-condensed)` |
| `--wa-form-control-placeholder-color` | `var(--wa-color-gray-60)` |
| `--wa-form-control-required-content` | `'*'` |
| `--wa-form-control-required-content-color` | `inherit` |
| `--wa-form-control-required-content-offset` | `-0.1em` |
| Custom Property | Default Value |
| ------------------------------------------- | ------------------------------------- |
| `--wa-form-control-background-color` | `var(--wa-color-surface-default)` |
| `--wa-form-control-border-color` | `var(--wa-color-neutral-border-loud)` |
| `--wa-form-control-border-style` | `var(--wa-border-style)` |
| `--wa-form-control-border-width` | `var(--wa-border-width-s)` |
| `--wa-form-control-border-radius` | `var(--wa-border-radius-m)` |
| `--wa-form-control-activated-color` | `var(--wa-color-brand-fill-loud)` |
| `--wa-form-control-label-color` | `var(--wa-color-neutral-border-loud)` |
| `--wa-form-control-label-font-weight` | `var(--wa-font-weight-normal)` |
| `--wa-form-control-label-line-height` | `var(--wa-line-height-normal)` |
| `--wa-form-control-value-color` | `var(--wa-color-text-normal)` |
| `--wa-form-control-value-font-weight` | `var(--wa-font-weight-body)` |
| `--wa-form-control-value-line-height` | `var(--wa-line-height-condensed)` |
| `--wa-form-control-hint-color` | `var(--wa-color-text-quiet)` |
| `--wa-form-control-hint-font-weight` | `var(--wa-font-weight-body)` |
| `--wa-form-control-hint-line-height` | `var(--wa-line-height-normal)` |
| `--wa-form-control-placeholder-color` | `var(--wa-color-gray-60)` |
| `--wa-form-control-required-content` | `'*'` |
| `--wa-form-control-required-content-color` | `inherit` |
| `--wa-form-control-required-content-offset` | `-0.1em` |
| `--wa-form-control-padding-block` | `0.75em` |
| `--wa-form-control-padding-inline` | `1em` |
| `--wa-form-control-height` | `round(calc(2 * var(--wa-form-control-padding-block) + 1em * var(--wa-form-control-value-line-height)), 1px)` |
| `--wa-form-control-toggle-size` | `round(1.25em, 1px)` |

```html {.example}
<form class="wa-block-spacing-l">
<form class="wa-stack">
<wa-input label="Input" placeholder="Placeholder"></wa-input>
<wa-select label="Select" value="option-1">
<wa-option value="option-1">Option 1</wa-option>
Expand All @@ -50,19 +57,6 @@ Not every form control uses all of these custom properties. For example, `<wa-ra
<wa-slider label="Range"></wa-slider>
<wa-button>Button</wa-button>
</form>

<style>
.wa-block-spacing-l > * + *, wa-radio {
display: block;
margin-block-start: var(--wa-space-l);
}
wa-radio {
margin-block-start: var(--wa-space-2xs);
}
wa-radio, wa-checkbox, wa-switch, wa-button {
width: fit-content;
}
</style>
```

## Panels
Expand All @@ -76,7 +70,7 @@ Panels consist of components with larger, contained surface areas like [callout]
| `--wa-panel-border-radius` | `var(--wa-border-radius-l)` |

```html {.example}
<div class="wa-block-spacing-l">
<div class="wa-stack">
<wa-callout>
<wa-icon slot="icon" name="circle-info" variant="regular"></wa-icon>
This is a simple callout with an icon.
Expand All @@ -86,13 +80,6 @@ Panels consist of components with larger, contained surface areas like [callout]
<code>wa-details</code>, at your service.
</wa-details>
</div>

<style>
.wa-block-spacing-l > * + * {
display: block;
margin-block-start: var(--wa-space-l);
}
</style>
```

## Tooltips
Expand Down
30 changes: 14 additions & 16 deletions packages/webawesome/docs/docs/tokens/space.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,21 +35,19 @@ description: Lock down consistent spacing Web Awesome's space properties.

Space properties are used intentionally throughout Web Awesome to create predictable rhythm and meaningful proximity. These properties use `rem` units in order to scale proportionately with the root font size.

Each space property uses a `calc()` function with `--wa-space-scale` to scale all spacing at once. By default, this multiplier is `1`. The table below lists the result of the calculation.
You can use `--wa-space-scale` to increase or decrease all spacing at once. By default, this multiplier is `1`.

| Custom Property | Default Value | Preview |
| ---------------- | ------------------------------- | --------------------------------------------------------------------- |
| `--wa-space-3xs` | `0.125rem` <small>(2px)</small> | <div class="spacing-example" style="width: var(--wa-space-3xs)"></div> |
| `--wa-space-2xs` | `0.25rem` <small>(4px)</small> | <div class="spacing-example" style="width: var(--wa-space-2xs)"></div> |
| `--wa-space-xs` | `0.5rem` <small>(8px)</small> | <div class="spacing-example" style="width: var(--wa-space-xs)"></div> |
| `--wa-space-s` | `0.75rem` <small>(12px)</small> | <div class="spacing-example" style="width: var(--wa-space-s)"></div> |
| `--wa-space-m` | `1rem` <small>(16px)</small> | <div class="spacing-example" style="width: var(--wa-space-m)"></div> |
| `--wa-space-l` | `1.25rem` <small>(20px)</small> | <div class="spacing-example" style="width: var(--wa-space-l)"></div> |
| `--wa-space-xl` | `1.5rem` <small>(24px)</small> | <div class="spacing-example" style="width: var(--wa-space-xl)"></div> |
| `--wa-space-2xl` | `2rem` <small>(32px)</small> | <div class="spacing-example" style="width: var(--wa-space-2xl)"></div> |
| `--wa-space-3xl` | `3rem` <small>(48px)</small> | <div class="spacing-example" style="width: var(--wa-space-3xl)"></div> |
The calculations for each size and the resulting pixel value (assuming a 16px root font size) are listed below.

When using space properties, it may be helpful to consider three distinct groups:
- Small-scale space (`3xs`, `2xs`, and `xs`) can be used for gaps between cooperating elements, such as a dropdown button and its menu, and padding within small components, such as badges and tooltips
- Normal space (`s`, `m`, and `l`) can be used for gaps between related elements with distinct touch targets and padding within typical interface elements, such as buttons and inputs
- Large-scale space (`xl`, `2xl`, and `3xl`) can be used for gaps between unrelated elements and padding within larger components, such as cards and dialogs
| Custom Property | Default Value | Preview - |
| ---------------- | ------------------------------------------------------------- | ---------------------------------------------------------------------- |
| `--wa-space-3xs` | `calc(var(--wa-space-scale) * 0.125rem)` <small>(2px)</small> | <div class="spacing-example" style="width: var(--wa-space-3xs)"></div> |
| `--wa-space-2xs` | `calc(var(--wa-space-scale) * 0.25rem)` <small>(4px)</small> | <div class="spacing-example" style="width: var(--wa-space-2xs)"></div> |
| `--wa-space-xs` | `calc(var(--wa-space-scale) * 0.5rem)` <small>(8px)</small> | <div class="spacing-example" style="width: var(--wa-space-xs)"></div> |
| `--wa-space-s` | `calc(var(--wa-space-scale) * 0.75rem)` <small>(12px)</small> | <div class="spacing-example" style="width: var(--wa-space-s)"></div> |
| `--wa-space-m` | `calc(var(--wa-space-scale) * 1rem)` <small>(16px)</small> | <div class="spacing-example" style="width: var(--wa-space-m)"></div> |
| `--wa-space-l` | `calc(var(--wa-space-scale) * 1.5rem)` <small>(24px)</small> | <div class="spacing-example" style="width: var(--wa-space-l)"></div> |
| `--wa-space-xl` | `calc(var(--wa-space-scale) * 2rem)` <small>(32px)</small> | <div class="spacing-example" style="width: var(--wa-space-xl)"></div> |
| `--wa-space-2xl` | `calc(var(--wa-space-scale) * 2.5rem)` <small>(40px)</small> | <div class="spacing-example" style="width: var(--wa-space-2xl)"></div> |
| `--wa-space-3xl` | `calc(var(--wa-space-scale) * 3rem)` <small>(48px)</small> | <div class="spacing-example" style="width: var(--wa-space-3xl)"></div> |
| `--wa-space-4xl` | `calc(var(--wa-space-scale) * 4rem)` <small>(64px)</small> | <div class="spacing-example" style="width: var(--wa-space-4xl)"></div> |
33 changes: 22 additions & 11 deletions packages/webawesome/docs/docs/tokens/typography.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,21 +17,32 @@ Font families are assigned specific roles &mdash; like heading or code &mdash; t

## Font Size

Font sizes use the Major Second type scale, rounded to the nearest whole pixel assuming a 16px root font size. To maximize variation in larger font sizes, every other step on the scale is skipped.
Font sizes use a ratio of 1.125 to scale sizes proportionally. Starting with the medium (`m`) font size, smaller sizes (`s` through `2xs`) are 1.125x smaller as the sizes decrease, and larger sizes (`l` through `4xl`) are _twice_ 1.125x larger as sizes increase — here, the ratio is doubled to maximize impact between sizes.

Each font size uses a `calc()` function with `--wa-font-size-scale` to scale all font sizes at once. By default, this multiplier is `1`. The table below lists the result of the calculation.
Each value uses `rem` units and is rounded to the nearest whole pixel when rendered with [`round()`](https://developer.mozilla.org/en-US/docs/Web/CSS/round).

You can use `--wa-font-size-scale` to increase or decrease all font sizes at once. By default, this multiplier is `1`.

The calculations for each size and the resulting pixel value (assuming a 16px root font size) are listed below.

| Custom Property | Default Value | Preview |
| -------------------- | --------------------------------- | ---------------------------------------------------------- |
| `--wa-font-size-2xs` | `0.6875rem` <small>(11px)</small> | <div style="font-size: var(--wa-font-size-2xs)">AaBb</div> |
| `--wa-font-size-xs` | `0.75rem` <small>(12px)</small> | <div style="font-size: var(--wa-font-size-xs)">AaBb</div> |
| `--wa-font-size-s` | `0.875rem` <small>(14px)</small> | <div style="font-size: var(--wa-font-size-s)">AaBb</div> |
| `--wa-font-size-m` | `1rem` <small>(16px)</small> | <div style="font-size: var(--wa-font-size-m)">AaBb</div> |
| `--wa-font-size-l` | `1.25rem` <small>(20px)</small> | <div style="font-size: var(--wa-font-size-l)">AaBb</div> |
| `--wa-font-size-xl` | `1.625rem` <small>(26px)</small> | <div style="font-size: var(--wa-font-size-xl)">AaBb</div> |
| `--wa-font-size-2xl` | `2rem` <small>(32px)</small> | <div style="font-size: var(--wa-font-size-2xl)">AaBb</div> |
| `--wa-font-size-3xl` | `2.5625rem` <small>(41px)</small> | <div style="font-size: var(--wa-font-size-3xl)">AaBb</div> |
| `--wa-font-size-4xl` | `3.25rem` <small>(52px)</small> | <div style="font-size: var(--wa-font-size-4xl)">AaBb</div> |
| `--wa-font-size-2xs` | `round(calc(var(--wa-font-size-xs) / 1.125), 1px)` <small>(11px)</small> | <div style="font-size: var(--wa-font-size-2xs)">AaBb</div> |
| `--wa-font-size-xs` | `round(calc(var(--wa-font-size-s) / 1.125), 1px)` <small>(12px)</small> | <div style="font-size: var(--wa-font-size-xs)">AaBb</div> |
| `--wa-font-size-s` | `round(calc(var(--wa-font-size-m) / 1.125), 1px)` <small>(14px)</small> | <div style="font-size: var(--wa-font-size-s)">AaBb</div> |
| `--wa-font-size-m` | `calc(1rem * var(--wa-font-size-scale))` <small>(16px)</small> | <div style="font-size: var(--wa-font-size-m)">AaBb</div> |
| `--wa-font-size-l` | `round(calc(var(--wa-font-size-m) * 1.125 * 1.125), 1px)` <small>(20px)</small> | <div style="font-size: var(--wa-font-size-l)">AaBb</div> |
| `--wa-font-size-xl` | `round(calc(var(--wa-font-size-l) * 1.125 * 1.125), 1px)` <small>(25px)</small> | <div style="font-size: var(--wa-font-size-xl)">AaBb</div> |
| `--wa-font-size-2xl` | `round(calc(var(--wa-font-size-xl) * 1.125 * 1.125), 1px)` <small>(32px)</small> | <div style="font-size: var(--wa-font-size-2xl)">AaBb</div> |
| `--wa-font-size-3xl` | `round(calc(var(--wa-font-size-2xl) * 1.125 * 1.125), 1px)` <small>(41px)</small> | <div style="font-size: var(--wa-font-size-3xl)">AaBb</div> |
| `--wa-font-size-4xl` | `round(calc(var(--wa-font-size-3xl) * 1.125 * 1.125)` <small>(52px)</small> | <div style="font-size: var(--wa-font-size-4xl)">AaBb</div> |

You can also use these two custom properties make any font size proportionally smaller or larger to its parent.

| Custom Property | Default Value |
| ------------------------ | --------------------------------------- |
| `--wa-font-size-smaller` | `round(calc(1em / 1.125), 1px)` |
| `--wa-font-size-larger` | `round(calc(1em * 1.125 * 1.125), 1px)` |

## Font Weight

Expand Down
Loading