diff --git a/lib/commons/color/get-background-color.js b/lib/commons/color/get-background-color.js
index 47e19e2a93..a64a95a0fc 100644
--- a/lib/commons/color/get-background-color.js
+++ b/lib/commons/color/get-background-color.js
@@ -121,29 +121,34 @@ function elmPartiallyObscured(elm, bgElm, bgColor) {
* @param {Element} elm
*/
function includeMissingElements(elmStack, elm) {
- const elementMap = {'TD': 'TR', 'TH': 'TR', 'INPUT': 'LABEL'};
+ const elementMap = {'TD': ['TR', 'TBODY'], 'TH': ['TR', 'THEAD'], 'INPUT': ['LABEL']};
const tagArray = elmStack.map((elm) => {
return elm.tagName;
});
let bgNodes = elmStack;
+ //jshint maxdepth:7
for (let candidate in elementMap) {
- // check that TR or LABEL has paired nodeName from elementMap, but don't expect elm to be that candidate
+ // check that TR or LABEL has paired nodeName from elementMap, but don't expect elm to be that candidate
if (tagArray.includes(candidate)) {
- // look up the tree for a matching candidate
- let ancestorMatch = axe.commons.dom.findUp(elm, elementMap[candidate]);
- if (ancestorMatch && elmStack.indexOf(ancestorMatch) === -1) {
- // found an ancestor not in elmStack, and it overlaps
- let overlaps = axe.commons.dom.visuallyOverlaps(elm.getBoundingClientRect(), ancestorMatch);
- if (overlaps) {
- // if target is in the elementMap, use its position.
- bgNodes.splice(tagArray.indexOf(candidate) + 1, 0, ancestorMatch);
+ for (let candidateIndex in elementMap[candidate]) {
+ if (candidate.hasOwnProperty(candidateIndex)) {
+ // look up the tree for a matching candidate
+ let ancestorMatch = axe.commons.dom.findUp(elm, elementMap[candidate][candidateIndex]);
+ if (ancestorMatch && elmStack.indexOf(ancestorMatch) === -1) {
+ // found an ancestor not in elmStack, and it overlaps
+ let overlaps = axe.commons.dom.visuallyOverlaps(elm.getBoundingClientRect(), ancestorMatch);
+ if (overlaps) {
+ // if target is in the elementMap, use its position.
+ bgNodes.splice(tagArray.indexOf(candidate) + 1, 0, ancestorMatch);
+ }
+ }
+ // tagName matches value
+ // (such as LABEL, when matching itself. It should be in the list, but Phantom skips it)
+ if (elm.tagName === elementMap[candidate][candidateIndex] && tagArray.indexOf(elm.tagName) === -1) {
+ bgNodes.splice(tagArray.indexOf(candidate) + 1, 0, elm);
+ }
}
}
- // tagName matches value
- // (such as LABEL, when matching itself. It should be in the list, but Phantom skips it)
- if (elm.tagName === elementMap[candidate] && tagArray.indexOf(elm.tagName) === -1) {
- bgNodes.splice(tagArray.indexOf(candidate) + 1, 0, elm);
- }
}
}
return bgNodes;
diff --git a/test/checks/color/color-contrast.js b/test/checks/color/color-contrast.js
index 340dd3c2f6..faca6291bb 100644
--- a/test/checks/color/color-contrast.js
+++ b/test/checks/color/color-contrast.js
@@ -190,6 +190,20 @@ describe('color-contrast', function () {
assert.isTrue(result);
});
+ it('should return true when there is sufficient contrast based on thead', function () {
+ fixture.innerHTML = '
';
+ var target = fixture.querySelector('#target');
+ assert.isTrue(checks['color-contrast'].evaluate.call(checkContext, target));
+ assert.deepEqual(checkContext._relatedNodes, []);
+ });
+
+ it('should return true when there is sufficient contrast based on tbody', function () {
+ fixture.innerHTML = '';
+ var target = fixture.querySelector('#target');
+ assert.isTrue(checks['color-contrast'].evaluate.call(checkContext, target));
+ assert.deepEqual(checkContext._relatedNodes, []);
+ });
+
it('should return undefined if element overlaps text content', function () {
fixture.innerHTML = '