Last active
February 22, 2024 18:02
-
-
Save joshcawthorne/43e129d7aa8444d7a0876ba8a40c456b to your computer and use it in GitHub Desktop.
Debugging Sticky CSS with React: Identifying Overflow Issues in Parent Elements
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// This React component utilizes a useEffect hook to traverse up the DOM tree from a referenced element, | |
// identifying any parent elements with an overflow property that could interfere with the intended 'sticky' | |
// positioning of the element. It logs each parent's overflow status and highlights those that may cause issues. | |
// Useful in debugging layout issues related to 'sticky' positioned elements. | |
// | |
// Usage: | |
// Simply include this component within your React application. The referenced element is automatically checked | |
// on component mount. For non-React code, the logic within useEffect could be extracted and run after the DOM | |
// has fully loaded, using a direct DOM element reference instead of a ref. | |
// | |
// Example for non-React: | |
// document.addEventListener('DOMContentLoaded', (event) => { | |
// let element = document.querySelector('.your-sticky-element-class'); | |
// // Implement the logic from the useEffect here, replacing `stickyRef.current` with `element`. | |
// }); | |
import { useEffect, useRef } from "react"; | |
const StickyComponent: React.FC = () => { | |
const stickyRef = useRef<HTMLDivElement>(null); | |
useEffect(() => { | |
if (!stickyRef.current) return; | |
let parent = stickyRef.current.parentElement; | |
let checkedCount = 0; | |
let offendingCount = 0; | |
while (parent) { | |
const hasOverflow = getComputedStyle(parent).overflow; | |
if (hasOverflow !== 'visible') { | |
console.warn(`Parent blocks "position: sticky":`, hasOverflow, parent); | |
offendingCount++; | |
} | |
parent = parent.parentElement; | |
checkedCount++; | |
} | |
console.info(`Checked ${checkedCount} components, ${offendingCount} affecting sticky.`); | |
}, [stickyRef]); | |
return ( | |
<div ref={stickyRef} style={{ position: 'sticky', top: 0 }}> | |
I should stick | |
</div> | |
); | |
}; | |
export default StickyComponent; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment