diff --git a/docs/design/tpr-ui-kit.html b/docs/design/tpr-ui-kit.html index c18594cd..cad5bc77 100644 --- a/docs/design/tpr-ui-kit.html +++ b/docs/design/tpr-ui-kit.html @@ -1080,6 +1080,7 @@ background: none; border: none; border-bottom: 2px solid transparent; + border-radius: 6px 6px 0 0; margin-bottom: -1px; padding: 10px 16px; font-size: 14px; @@ -1091,10 +1092,13 @@ .tablist button:hover { color: var(--color-bluespruce); border-bottom-color: var(--color-neutral-300); + background: var(--color-neutral-50); } .tablist button[aria-selected="true"] { color: var(--color-bluespruce); border-bottom-color: var(--color-bluespruce); + background: none; + font-weight: 600; } .tablist button.focus-demo { box-shadow: @@ -4065,13 +4069,15 @@

Tabs v2

Tab list — selected / resting / keyboard focus

Tabs.tsx — Tabs + TabPanel + useActiveTab

- px-4 py-2.5 text-sm font-mediumborder-b-2px-4 py-2.5 text-smborder-b-2 rounded-t-md cursor-pointerselected: border-bluespruce text-bluespruceresting: text-rmigray-600selected: font-semibold border-bluespruce + text-bluespruceresting: font-medium text-rmigray-600hover:text-bluespruce hover:border-neutral-300hover:text-bluespruce hover:border-neutral-300 + hover:bg-neutral-50focus-visible:ring-energy
diff --git a/src/components/Tabs.test.tsx b/src/components/Tabs.test.tsx index 78d73c8d..7b688416 100644 --- a/src/components/Tabs.test.tsx +++ b/src/components/Tabs.test.tsx @@ -50,6 +50,15 @@ describe("Tabs", () => { expect(screen.getAllByRole("tab")).toHaveLength(3); }); + it("names each tab by its label alone", () => { + renderHarness(); + // Each tab also holds a hidden copy of its label to reserve the semibold + // width; it must not be read out a second time ("One One"). + for (const { label } of TABS) { + expect(screen.getByRole("tab", { name: label })).toBeInTheDocument(); + } + }); + it("defaults to the first tab and shows only its panel", () => { renderHarness(); expect(screen.getByRole("tab", { name: "One" })).toHaveAttribute( diff --git a/src/components/Tabs.tsx b/src/components/Tabs.tsx index 81231867..9313535b 100644 --- a/src/components/Tabs.tsx +++ b/src/components/Tabs.tsx @@ -114,13 +114,23 @@ export const Tabs: React.FC = ({ tabIndex={selected ? 0 : -1} onClick={() => onChange(t.id)} className={clsx( - "px-4 py-2.5 text-sm font-medium border-b-2 transition-colors duration-150 focus:outline-none focus-visible:ring-2 focus-visible:ring-energy focus-visible:ring-offset-1", + "px-4 py-2.5 text-sm border-b-2 rounded-t-md cursor-pointer transition-colors duration-150 focus:outline-none focus-visible:ring-2 focus-visible:ring-energy focus-visible:ring-offset-1", selected - ? "border-bluespruce text-bluespruce" - : "border-transparent text-rmigray-600 hover:text-bluespruce hover:border-neutral-300", + ? "font-semibold border-bluespruce text-bluespruce" + : "font-medium border-transparent text-rmigray-600 hover:text-bluespruce hover:border-neutral-300 hover:bg-neutral-50", )} > - {t.label} + + {t.label} + {/* Reserves the semibold width, so selecting a tab doesn't + nudge the tabs after it sideways. */} + + ); })}