Split motion packs from accessibility overrides

This commit is contained in:
2026-03-20 12:03:46 +08:00
parent 010638503f
commit e5434bada9
8 changed files with 320 additions and 64 deletions
+60 -27
View File
@@ -1,3 +1,8 @@
import {
motionPackDetails,
motionPackNames,
type MotionPackName
} from "@ai-ui/tokens";
import {
Button,
Card,
@@ -21,18 +26,18 @@ import {
} from "@ai-ui/ui";
import type { Meta, StoryObj } from "@storybook/react";
const motionModes = [
const motionAccessibilityModes = [
{
label: "System motion",
label: "System accessibility",
value: "system"
},
{
label: "Reduced motion",
label: "Reduced accessibility",
value: "reduced"
}
] as const;
type MotionMode = (typeof motionModes)[number]["value"];
type MotionAccessibilityMode = (typeof motionAccessibilityModes)[number]["value"];
function RuntimePill({ children }: { children: React.ReactNode }) {
return (
@@ -78,21 +83,25 @@ function PanelPreview() {
}
function ComparisonCell({
motion,
motionAccessibility,
motionPack,
skin
}: {
motion: MotionMode;
motionAccessibility: MotionAccessibilityMode;
motionPack: MotionPackName;
skin: SkinName;
}) {
return (
<section
className="grid gap-4 rounded-[var(--radius-lg)] border border-[var(--color-border)] bg-[var(--color-card)] p-4 shadow-[var(--shadow-sm)]"
data-motion={motion === "reduced" ? "reduced" : undefined}
data-motion={motionAccessibility === "reduced" ? "reduced" : undefined}
data-motion-pack={motionPack}
data-skin={skin}
>
<div className="flex flex-wrap gap-2">
<RuntimePill>{motionPackDetails[motionPack].label}</RuntimePill>
<RuntimePill>{skinDetails[skin].label}</RuntimePill>
<RuntimePill>{motion}</RuntimePill>
<RuntimePill>{motionAccessibility}</RuntimePill>
</div>
<Card interactive tone="default">
@@ -166,29 +175,52 @@ function StyleMatrixShowcase() {
</h1>
<p className="max-w-3xl text-[var(--text-lg)] leading-[var(--leading-loose)] text-[var(--color-muted-foreground)]">
This page is the screenshot-friendly regression target for the pilot skin work.
The grid uses nested `data-skin` and `data-motion` scopes so the same building
blocks can be reviewed side by side.
The grid uses nested `data-skin`, `data-motion-pack`, and
`data-motion=&quot;reduced&quot;` scopes so the same building blocks can be
reviewed side by side.
</p>
</header>
<section className="grid gap-4">
{motionModes.map((motionMode) => (
<div key={motionMode.value} className="grid gap-3">
<div className="flex items-center justify-between gap-4">
<div>
<h2 className="text-2xl font-semibold">{motionMode.label}</h2>
<p className="mt-1 text-sm text-[var(--color-muted-foreground)]">
`{motionMode.value === "reduced" ? 'data-motion="reduced"' : "default"}`
{" "}
on the wrapper scope.
</p>
{motionPackNames.map((motionPack) => (
<div key={motionPack} className="grid gap-4">
<div>
<h2 className="text-2xl font-semibold">{motionPackDetails[motionPack].label}</h2>
<p className="mt-1 max-w-3xl text-sm leading-6 text-[var(--color-muted-foreground)]">
{motionPackDetails[motionPack].note}
</p>
</div>
{motionAccessibilityModes.map((motionAccessibilityMode) => (
<div key={`${motionPack}-${motionAccessibilityMode.value}`} className="grid gap-3">
<div className="flex items-center justify-between gap-4">
<div>
<h3 className="text-xl font-semibold">
{motionAccessibilityMode.label}
</h3>
<p className="mt-1 text-sm text-[var(--color-muted-foreground)]">
{motionAccessibilityMode.value === "reduced"
? '`data-motion="reduced"`'
: "System preference"}
{" "}with{" "}
<code className="text-[var(--color-foreground)]">
{`data-motion-pack="${motionPack}"`}
</code>
.
</p>
</div>
</div>
<div className="grid gap-4 xl:grid-cols-3">
{skinNames.map((skin) => (
<ComparisonCell
key={`${motionPack}-${motionAccessibilityMode.value}-${skin}`}
motionAccessibility={motionAccessibilityMode.value}
motionPack={motionPack}
skin={skin}
/>
))}
</div>
</div>
</div>
<div className="grid gap-4 xl:grid-cols-3">
{skinNames.map((skin) => (
<ComparisonCell key={`${motionMode.value}-${skin}`} motion={motionMode.value} skin={skin} />
))}
</div>
))}
</div>
))}
</section>
@@ -199,7 +231,8 @@ function StyleMatrixShowcase() {
<p className="mt-2 max-w-3xl text-sm leading-6 text-[var(--color-muted-foreground)]">
Dialog still portals to the document root, so compare its real overlay and
panel treatment with the Storybook toolbar. The matrix above covers scoped
inline regression. The control below covers the live overlay behavior.
inline regression across packs and reduced-motion overlay. The control below
covers the live overlay behavior.
</p>
</div>
<div className="flex justify-start lg:justify-end">