Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(color-contrast): correctly compute color contrast of <slot> elements #3847

Merged
merged 2 commits into from
Jan 6, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
10 changes: 9 additions & 1 deletion lib/commons/dom/create-grid.js
Original file line number Diff line number Diff line change
Expand Up @@ -54,10 +54,18 @@ export default function createGrid(
while (node) {
let vNode = getNodeFromTree(node);

if (vNode && vNode.parent) {
parentVNode = vNode.parent;
}
// elements with an assigned slot need
// need to be a child of the slot element
straker marked this conversation as resolved.
Show resolved Hide resolved
else if (node.assignedSlot) {
parentVNode = getNodeFromTree(node.assignedSlot);
}
// an svg in IE11 does not have a parentElement but instead has a
// parentNode. but parentNode could be a shadow root so we need to
// verify it's in the tree first
if (node.parentElement) {
else if (node.parentElement) {
parentVNode = getNodeFromTree(node.parentElement);
} else if (node.parentNode && getNodeFromTree(node.parentNode)) {
parentVNode = getNodeFromTree(node.parentNode);
Expand Down
23 changes: 23 additions & 0 deletions test/checks/color/color-contrast.js
Original file line number Diff line number Diff line change
Expand Up @@ -906,6 +906,29 @@ describe('color-contrast', function () {
}
);

(shadowSupported ? it : xit)('handles <slot> elements', () => {
fixture.innerHTML =
Copy link
Contributor Author

@straker straker Jan 5, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I couldn't use shadowCheckSetup because I needed the final node to be the paragraph, but trying to have the paragraph in the first parameter had the code add the shadow dom to it rather than the container element.

'<div id="container" style="height: 100px;"><p id="target" style="color: #333;">Slotted text</p></div>';
const container = fixture.querySelector('#container');
const shadow = container.attachShadow({ mode: 'open' });

shadow.innerHTML =
'<div id="shadowContainer" style="position: absolute; background: black;"><slot></slot></div>';
const shadowContainer = shadow.querySelector('#shadowContainer');
axe.testUtils.flatTreeSetup(fixture);

const target = fixture.querySelector('#target');
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Couldn't use axe.utils.querySelector since the element is in the shadow dom in the virtual tree, so would need to select the shadow element and query selector from there.

const vNode = axe.utils.getNodeFromTree(target);
const result = contrastEvaluate.call(
checkContext,
vNode.actualNode,
null,
vNode
);
assert.isFalse(result);
assert.deepEqual(checkContext._relatedNodes, [shadowContainer]);
});

describe('with text-shadow', function () {
it('passes if thin text shadows have sufficient contrast with the text', function () {
var params = checkSetup(
Expand Down
20 changes: 20 additions & 0 deletions test/commons/dom/get-element-stack.js
Original file line number Diff line number Diff line change
Expand Up @@ -570,6 +570,26 @@ describe('dom.getElementStack', function () {
]);
}
);

(shadowSupported ? it : xit)('should sort <slot> elements', () => {
fixture.innerHTML =
'<div id="container" style="height: 100px;"><p id="target">Slotted text</p></div>';
const container = fixture.querySelector('#container');
const shadow = container.attachShadow({ mode: 'open' });

shadow.innerHTML =
'<div id="shadowContainer" style="position: absolute;"><slot></slot></div>';
axe.testUtils.flatTreeSetup(fixture);

const target = fixture.querySelector('#target');
const stack = mapToIDs(getElementStack(target));
assert.deepEqual(stack, [
'target',
'shadowContainer',
'container',
'fixture'
]);
});
});

describe('scroll regions', function () {
Expand Down