diff --git a/UPGRADE.md b/UPGRADE.md new file mode 100644 index 00000000..454a2200 --- /dev/null +++ b/UPGRADE.md @@ -0,0 +1,120 @@ +# Upgrading + +## From 1.x to 2.0.0 + +2.0.0 aligns the library with Material Design 3 Expressive as Google documents it +(m3.material.io, checked page by page; the audits are in `docs/audits/m3-alignment/`). Most of +the change is inside the components. What reaches an application is below, in the order to do it. + +### 1. Breakpoints are M3's window size classes + +Tailwind's `sm:`, `md:`, `lg:`, `xl:` and `2xl:` no longer compile. The variants are +`medium:` (600px), `expanded:` (840px), `large:` (1200px) and `extra-large:` (1600px), plus +`max-medium:` and friends for "below"; compact is everything below `medium`. Replace every +prefix in the application's views: + +| Was | Becomes | +|---|---| +| `sm:` / `max-sm:` (640) | `medium:` / `max-medium:` (600) | +| `md:` / `max-md:` (768) | `medium:` or `expanded:` — choose by what the layout means | +| `lg:` / `max-lg:` (1024) | `expanded:` / `max-expanded:` (840) | +| `xl:` / `max-xl:` (1280) | `large:` / `max-large:` (1200) | +| `2xl:` (1536) | `extra-large:` (1600) | + +Scripts read the same numbers from `resources/js/breakpoints.js` (`from('expanded')`, +`upTo('medium')`). `DesignGuard` reports every leftover prefix with its replacement. + +### 2. Only M3's scales compile + +Tailwind's default radius, shadow, text-size, weight, leading, tracking and easing utilities are +cleared like its palette was: + +| Was | Becomes | +|---|---| +| `rounded-sm` … `rounded-4xl` | `rounded-corner-xs` … `rounded-corner-xxl` (`rounded-corner-full`, `rounded-corner-none`) | +| `shadow-sm` … `shadow-2xl` | `shadow-elevation-1` … `shadow-elevation-5` | +| `text-xs` … `text-9xl`, `leading-*`, `tracking-*`, `font-medium` … `font-black` | one `type-*` style (`type-body-md`, `type-emphasized-title-md` …) | +| `ease-in`, `ease-out`, `ease-in-out`, `duration-300` | `ease-spatial-*` / `ease-effects-*` with `duration-(--md-sys-motion-…-duration)` | + +The 4px spacing scale is unchanged. `DesignGuard` names each one with its replacement. + +### 3. Regenerate the colour scheme + +```bash +php artisan material:scheme "#4f46e5" --variant=tonal-spot # the command in the file's header +``` + +- `success`, `warning` and `info` are now built on the 2025 colour spec with the contrast level, + like `error`; their values change. `--harmonize` blends them toward the seed (off by default). +- The stylesheet gains medium and high contrast blocks, and `material-scheme.json` gains a + `contrast` key; `light`/`dark` at the top level are still the standard scheme, so the mail + theme needs nothing. `--contrast` must now be below 0.5; medium (0.5) and high (1.0) are + generated alongside. +- Config: `theme.contrast` (`default` `system` | `standard` | `medium` | `high`, `storage_key`) + and `motion.scheme` (`expressive` | `standard`). `$store.theme` gains `contrast`, + `resolvedContrast` and `setContrast()`; `` is a row of three. + +### 4. Inks are roles, not opacities + +`text-meta`, `text-quiet`, `border-chrome` and `border-divider` keep their names but now resolve +to `on-surface-variant`, `outline`, `outline-variant` and `outline-variant`. Where the old +translucent grey was intended, nothing to do; where a template relied on the opacity to blend +over a colour, use the role directly. + +### 5. Changed defaults and props + +- `` no longer draws a state icon; `type` only picks the announcement role (`alert` for + error and warning, `status` otherwise). An actioned snackbar stays until acted on; Escape + dismisses a focused one. +- `` has no `disabled` prop: M3 says to remove a FAB whose action is unavailable, so hide + it instead (a form-submit FAB uses `wire:loading.attr="disabled"`). +- `` is `role="status"` for every colour; pass `assertive` where the notice answers + something the person just did. +- `` and `` are 8px wider; a `` no longer + wraps; connected `xs`/`sm` segments have a 48px minimum width. +- `` rows are 48px with 16px sides; a selected item draws a trailing check unless it + has `icon-right`; a long menu scrolls. +- `` renders a close button by default (`:with-close-button="false"` to drop it, ignored + on a `pane` or when Escape and the scrim are off) and left-aligns its `actions` in a 72px row. +- `` opens at `50dvh` (was `90dvh`); any `height` is capped at + `calc(100dvh - 72px)`. +- `` `padding` defaults to `16`; `layout="full-screen"` scrolls vertically with + edge-to-edge items; items, not the row, are the tab stops. +- `` draws a 16px-inset rule; `` or `selection="single|multi"` + makes it a `listbox` of `option`s with `aria-selected`. +- `` changes elevation on hover instead of its corner; `data-card` carries the variant. +- `` pins its header and actions and scrolls only the body; a `box-class` that set + `overflow` no longer applies. +- `` rows are 52px and the automatic fine-pointer density is gone: pass `dense` for 36px + rows (`size="xs" dense` is 24px). +- A field in error draws a trailing `error` icon unless it already trails something; a read-only + field no longer draws a dashed outline. +- The time picker's AM/PM buttons are radios (`aria-checked`); the password reveal no longer sets + `aria-pressed`. +- `` grows from 44 to 52px and every value indicator from 32 to 44px tall. +- `` is a connected group over native radios: the + `data-theme-option` hooks are gone; target `input[name="material-theme"][value="…"]`. +- `` panels render `id`, `aria-labelledby` and `display: none` from the server. +- `` with five or more sections is a scrollable tab bar, not a grid. The tab bar is + 10px taller; the focus ring sits outside. +- The navigation bar's horizontal label is `label-md`; `place="bottom"` toolbars sit above + `--material-bottom-bar`; a standard toolbar's icon buttons are `primary`. +- The centred app bar headline is a grid column; the `search` variant bounds its own width, so + drop hand-written `max-w-*` wrappers. +- `` is a column with a nested row and gains a `banner` slot; ``'s + `header` slot takes one `` that morphs (replace the two-FAB + `rail-collapsed:` swap); new `divider` and `fill` props. +- `` selects the optical-size-20 cut; the components pass it for their own + small icons, applications pass it for icons drawn at 20px or less. + +### 6. Tests and guards + +Add `DesignGuard`'s new checks to the application's design test (`forbidOpacityInk()` and +`forbidAbsolutes()` are opt-in). Browser tests that assert widths switch at 640/1024/1280 now +switch at 600/840/1200; tests that read `role="alert"` on an alert, `aria-pressed` on the time +picker's period buttons or `data-theme-option` need the new hooks above. + +### 7. For AI agents + +`php artisan boost:update --discover` picks up the new `material-3` guideline and the +`material-3-design` skill, which state M3's rules and tables beside the library's utilities.