Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
2 changes: 1 addition & 1 deletion packages/react/src/Spinner/Spinner.docs.json
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,7 +19,7 @@
},
{
"name": "aria-label",
"type": "string | null",
"type": "string",
"description": "Sets the text conveyed by assistive technologies such as screen readers.",
"deprecated": true
},
Expand Down
11 changes: 6 additions & 5 deletions packages/react/src/Spinner/Spinner.tsx
Original file line numberDiff line numberDiff line change
Expand Up@@ -18,14 +18,14 @@ export type SpinnerProps = {
/** Sets the text conveyed by assistive technologies such as screen readers. Set to `null` if the loading state is displayed in a text node somewhere else on the page. */
srText?: string | null
/** @deprecated Use `srText` instead. */
'aria-label'?: string | null
'aria-label'?: string
} & HTMLDataAttributes &
SxProp

function Spinner({size: sizeKey = 'medium', srText = 'Loading', 'aria-label': ariaLabel, ...props}: SpinnerProps) {
const size = sizeMap[sizeKey]
const hasSrAnnouncement = Boolean(srText || ariaLabel)
const ariaLabelId = useId()
const hasHiddenLabel = srText !== null && ariaLabel === undefined
const labelId = useId()

return (
/* inline-flex removes the extra line height */
Expand All@@ -36,7 +36,8 @@ function Spinner({size: sizeKey = 'medium', srText = 'Loading', 'aria-label': ar
viewBox="0 0 16 16"
fill="none"
aria-hidden
aria-labelledby={ariaLabelId}
aria-label={ariaLabel ?? undefined}
aria-labelledby={hasHiddenLabel ? labelId : undefined}
{...props}
>
<circle
Expand All@@ -56,7 +57,7 @@ function Spinner({size: sizeKey = 'medium', srText = 'Loading', 'aria-label': ar
vectorEffect="non-scaling-stroke"
/>
</svg>
{hasSrAnnouncement ? <VisuallyHidden id={ariaLabelId}>{srText || ariaLabel}</VisuallyHidden> : null}
{hasHiddenLabel ? <VisuallyHidden id={labelId}>{srText}</VisuallyHidden> : null}
</Box>
)
}
Expand Down
9 changes: 7 additions & 2 deletions packages/react/src/__tests__/Spinner.test.tsx
Original file line numberDiff line numberDiff line change
Expand Up@@ -3,7 +3,7 @@ import axe from 'axe-core'
import type {SpinnerProps} from '..'
import {Spinner} from '..'
import {behavesAsComponent, checkExports} from '../utils/testing'
import {render as HTMLRender} from '@testing-library/react'
import {render as HTMLRender, screen} from '@testing-library/react'

describe('Spinner', () => {
behavesAsComponent({
Expand All@@ -26,12 +26,17 @@ describe('Spinner', () => {
expect(getByLabelText('Custom loading text')).toBeInTheDocument()
})

it('should not label the spinner with with loading text when `srText` is set to `null`', async () => {
it('should not label the spinner with with loading text when `srText` is set to `null`', () => {
const {getByLabelText} = HTMLRender(<Spinner srText={null} />)

expect(() => getByLabelText('Loading')).toThrow()
})

it('should use `aria-label` over `srText` if `aria-label` is provided', () => {
HTMLRender(<Spinner aria-label="Test label" />)
expect(screen.getByLabelText('Test label')).toBeInTheDocument()
})

it('should have no axe violations', async () => {
const {container} = HTMLRender(<Spinner />)
const results = await axe.run(container)
Expand Down