diff --git a/.changeset/fix-checkbox-bubble-input-a11y-3167.md b/.changeset/fix-checkbox-bubble-input-a11y-3167.md new file mode 100644 index 0000000000..2bd8117e68 --- /dev/null +++ b/.changeset/fix-checkbox-bubble-input-a11y-3167.md @@ -0,0 +1,5 @@ +--- +'@radix-ui/react-checkbox': patch +--- + +Fix bubble input accessibility by using the native `hidden` attribute instead of `aria-hidden`, and mirror label association from the control to the hidden input. diff --git a/packages/react/checkbox/src/checkbox.test.tsx b/packages/react/checkbox/src/checkbox.test.tsx index 34147891c8..6d9e9d40c4 100644 --- a/packages/react/checkbox/src/checkbox.test.tsx +++ b/packages/react/checkbox/src/checkbox.test.tsx @@ -296,6 +296,27 @@ describe('Checkbox', () => { expect(onChange).toHaveBeenCalledWith(false); }); }); + + // Regression test for https://github.com/radix-ui/primitives/issues/3167 + describe('given a Checkbox with label association in a form', () => { + it('should hide the bubble input with the native hidden attribute', async () => { + const rendered = render( +
, + ); + + const input = rendered.container.querySelector('input[type="checkbox"]'); + expect(input).toHaveAttribute('hidden'); + expect(input).not.toHaveAttribute('aria-hidden'); + expect(await axe(rendered.container)).toHaveNoViolations(); + }); + }); }); describe('Legacy Checkbox', () => { @@ -478,21 +499,9 @@ describe('Legacy Checkbox', () => { }); function LegacyCheckbox(props: React.ComponentProps