Skip to content

Commit d15238b

Browse files
authored
Merge branch 'master' into pr/pr_typescript_migration
2 parents a2b9e44 + f753c8a commit d15238b

File tree

4 files changed

+58
-0
lines changed

4 files changed

+58
-0
lines changed

src/__tests__/ariaAttributes.js

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,15 @@ test('`checked` throws on unsupported roles', () => {
2727
)
2828
})
2929

30+
test('`expanded` throws on unsupported roles', () => {
31+
const {getByRole} = render(`<h1 aria-expanded="true">Heading</h1>`)
32+
expect(() =>
33+
getByRole('heading', {expanded: true}),
34+
).toThrowErrorMatchingInlineSnapshot(
35+
`"\\"aria-expanded\\" is not supported on role \\"heading\\"."`,
36+
)
37+
})
38+
3039
test('`checked: true|false` matches `checked` checkboxes', () => {
3140
const {getByRole} = renderIntoDocument(
3241
`<div>
@@ -202,3 +211,25 @@ test('`level` throws on unsupported roles', () => {
202211
`"Role \\"button\\" cannot have \\"level\\" property."`,
203212
)
204213
})
214+
215+
test('`expanded: true|false` matches `expanded` buttons', () => {
216+
const {getByRole} = renderIntoDocument(
217+
`<div>
218+
<button aria-expanded="true" />
219+
<button aria-expanded="false" />
220+
</div>`,
221+
)
222+
expect(getByRole('button', {expanded: true})).toBeInTheDocument()
223+
expect(getByRole('button', {expanded: false})).toBeInTheDocument()
224+
})
225+
226+
test('`expanded: true|false` matches `expanded` elements with proper role', () => {
227+
const {getByRole} = renderIntoDocument(
228+
`<div>
229+
<span role="button" aria-expanded="true">✔</span>
230+
<span role="button" aria-expanded="false">𝒙</span>
231+
</div>`,
232+
)
233+
expect(getByRole('button', {expanded: true})).toBeInTheDocument()
234+
expect(getByRole('button', {expanded: false})).toBeInTheDocument()
235+
})

src/queries/role.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import {
44
computeAriaSelected,
55
computeAriaChecked,
66
computeAriaPressed,
7+
computeAriaExpanded,
78
computeHeadingLevel,
89
getImplicitAriaRoles,
910
prettyRoles,
@@ -35,6 +36,7 @@ function queryAllByRole(
3536
checked,
3637
pressed,
3738
level,
39+
expanded,
3840
} = {},
3941
) {
4042
checkContainerType(container)
@@ -69,6 +71,13 @@ function queryAllByRole(
6971
}
7072
}
7173

74+
if (expanded !== undefined) {
75+
// guard against unknown roles
76+
if (allRoles.get(role)?.props['aria-expanded'] === undefined) {
77+
throw new Error(`"aria-expanded" is not supported on role "${role}".`)
78+
}
79+
}
80+
7281
const subtreeIsInaccessibleCache = new WeakMap()
7382
function cachedIsSubtreeInaccessible(element) {
7483
if (!subtreeIsInaccessibleCache.has(element)) {
@@ -115,6 +124,9 @@ function queryAllByRole(
115124
if (pressed !== undefined) {
116125
return pressed === computeAriaPressed(element)
117126
}
127+
if (expanded !== undefined) {
128+
return expanded === computeAriaExpanded(element)
129+
}
118130
if (level !== undefined) {
119131
return level === computeHeadingLevel(element)
120132
}

src/role-helpers.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -247,6 +247,15 @@ function computeAriaPressed(element) {
247247
return checkBooleanAttribute(element, 'aria-pressed')
248248
}
249249

250+
/**
251+
* @param {Element} element -
252+
* @returns {boolean | undefined} - false/true if (not)expanded, undefined if not expand-able
253+
*/
254+
function computeAriaExpanded(element) {
255+
// https://www.w3.org/TR/wai-aria-1.1/#aria-expanded
256+
return checkBooleanAttribute(element, 'aria-expanded')
257+
}
258+
250259
function checkBooleanAttribute(element, attribute) {
251260
const attributeValue = element.getAttribute(attribute)
252261
if (attributeValue === 'true') {
@@ -292,5 +301,6 @@ export {
292301
computeAriaSelected,
293302
computeAriaChecked,
294303
computeAriaPressed,
304+
computeAriaExpanded,
295305
computeHeadingLevel,
296306
}

types/queries.d.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,11 @@ export interface ByRoleOptions extends MatcherOptions {
8888
* pressed in the accessibility tree, i.e., `aria-pressed="true"`
8989
*/
9090
pressed?: boolean
91+
/**
92+
* If true only includes elements in the query set that are marked as
93+
* expanded in the accessibility tree, i.e., `aria-expanded="true"`
94+
*/
95+
expanded?: boolean
9196
/**
9297
* Includes elements with the `"heading"` role matching the indicated level,
9398
* either by the semantic HTML heading elements `<h1>-<h6>` or matching

0 commit comments

Comments
 (0)