1- import { getNodeFromTree , memoize } from '../../core/utils' ;
1+ import { getNodeFromTree } from '../../core/utils' ;
22import { sanitize } from '../text' ;
33import { getIntersectionRect , getRectCenter , isPointInRect } from '../math' ;
44import getOverflowHiddenAncestors from './get-overflow-hidden-ancestors' ;
@@ -11,49 +11,72 @@ import cache from '../../core/base/cache';
1111 * @instance
1212 * @param {Element } node
1313 */
14- const getVisibleChildTextRects = memoize (
15- function getVisibleChildTextRectsMemoized ( node ) {
16- const vNode = getNodeFromTree ( node ) ;
17- const nodeRect = vNode . boundingClientRect ;
18- const clientRects = [ ] ;
19- const overflowHiddenNodes = getOverflowHiddenAncestors ( vNode ) ;
14+ const getVisibleChildTextRects = ( node , options = { } ) => {
15+ const {
16+ checkTextRectOutsideNodeBoundingRect = false ,
17+ includeOutsideBounds = true ,
18+ includeOverflowHidden = false ,
19+ checkNoVisibleRectsIdentified = false
20+ } = options ;
21+ const vNode = getNodeFromTree ( node ) ;
22+ const nodeRect = vNode . boundingClientRect ;
23+ const clientRects = [ ] ;
24+ const overflowHiddenNodes = getOverflowHiddenAncestors ( vNode ) ;
2025
21- node . childNodes . forEach ( textNode => {
22- if ( textNode . nodeType !== 3 || sanitize ( textNode . nodeValue ) === '' ) {
23- return ;
24- }
26+ node . childNodes . forEach ( textNode => {
27+ if ( textNode . nodeType !== 3 || sanitize ( textNode . nodeValue ) === '' ) {
28+ return ;
29+ }
2530
26- const contentRects = getContentRects ( textNode ) ;
27- if ( isOutsideNodeBounds ( contentRects , nodeRect ) && ! cache . get ( 'ruleId' ) ) {
28- return ;
29- }
31+ const contentRects = getContentRects ( textNode ) ;
32+ if (
33+ includeOutsideBounds &&
34+ isOutsideNodeBounds (
35+ contentRects ,
36+ nodeRect ,
37+ checkTextRectOutsideNodeBoundingRect
38+ ) &&
39+ ( ! cache . get ( 'ruleId' ) ||
40+ cache . get ( 'ruleId' ) === 'reflow-4x-zoom-scroll' ||
41+ cache . get ( 'ruleId' ) === 'color-contrast' )
42+ ) {
43+ return ;
44+ }
3045
31- clientRects . push ( ...filterHiddenRects ( contentRects , overflowHiddenNodes ) ) ;
32- } ) ;
46+ clientRects . push (
47+ ...filterHiddenRects (
48+ contentRects ,
49+ includeOverflowHidden ? [ ] : overflowHiddenNodes
50+ )
51+ ) ;
52+ } ) ;
3353
34- // a11y-engine-domforge change
35- if ( clientRects . length <= 0 ) {
36- return [ ] ;
37- }
38- /**
39- * if all text rects are larger than the bounds of the node,
40- * or goes outside of the bounds of the node, we need to use
41- * the nodes bounding rect so we stay within the bounds of the
42- * element.
43- *
44- * @see https://github.com/dequelabs/axe-core/issues/2178
45- * @see https://github.com/dequelabs/axe-core/issues/2483
46- * @see https://github.com/dequelabs/axe-core/issues/2681
47- *
48- * also need to resize the nodeRect to fit within the bounds of any overflow: hidden ancestors.
49- *
50- * @see https://github.com/dequelabs/axe-core/issues/4253
51- */
52- return clientRects . length
53- ? clientRects
54- : filterHiddenRects ( [ nodeRect ] , overflowHiddenNodes ) ;
54+ // a11y-engine-domforge change
55+ if (
56+ clientRects . length <= 0 &&
57+ ( ( cache . get ( 'ruleId' ) && cache . get ( 'ruleId' ) === 'resize-2x-zoom' ) ||
58+ checkNoVisibleRectsIdentified )
59+ ) {
60+ return [ ] ;
5561 }
56- ) ;
62+ /**
63+ * if all text rects are larger than the bounds of the node,
64+ * or goes outside of the bounds of the node, we need to use
65+ * the nodes bounding rect so we stay within the bounds of the
66+ * element.
67+ *
68+ * @see https://github.com/dequelabs/axe-core/issues/2178
69+ * @see https://github.com/dequelabs/axe-core/issues/2483
70+ * @see https://github.com/dequelabs/axe-core/issues/2681
71+ *
72+ * also need to resize the nodeRect to fit within the bounds of any overflow: hidden ancestors.
73+ *
74+ * @see https://github.com/dequelabs/axe-core/issues/4253
75+ */
76+ return clientRects . length
77+ ? clientRects
78+ : filterHiddenRects ( [ nodeRect ] , overflowHiddenNodes ) ;
79+ } ;
5780export default getVisibleChildTextRects ;
5881
5982function getContentRects ( node ) {
@@ -68,10 +91,20 @@ function getContentRects(node) {
6891 * when determining the rect stack we will also use the midpoint
6992 * of the text rect to determine out of bounds
7093 */
71- function isOutsideNodeBounds ( rects , nodeRect ) {
94+ function isOutsideNodeBounds (
95+ rects ,
96+ nodeRect ,
97+ checkTextRectOutsideNodeBoundingRect = false
98+ ) {
7299 return rects . some ( rect => {
73100 const centerPoint = getRectCenter ( rect ) ;
74- return ! isPointInRect ( centerPoint , nodeRect ) ;
101+ if ( checkTextRectOutsideNodeBoundingRect ) {
102+ return (
103+ ! isPointInRect ( centerPoint , nodeRect ) || rect . right > nodeRect . right
104+ ) ;
105+ } else {
106+ return ! isPointInRect ( centerPoint , nodeRect ) ;
107+ }
75108 } ) ;
76109}
77110
0 commit comments