How to Detect Overflow in Div Element

How to detect overflow in div element?

You can easily do that by comparing scrollHeight with clientHeight, try the following:

<script type="text/javascript">
function GetContainerSize ()
{
var container = document.getElementById ("tempDiv");
var message = "The width of the contents with padding: " + container.scrollWidth + "px.\n";
message += "The height of the contents with padding: " + container.scrollHeight + "px.\n";

alert (message);
}
</script>

For more information please take a look at: http://help.dottoro.com/ljbixkkn.php

Check if an element's content is overflowing?

If you want to show only an identifier for more content, then you can do this with pure CSS. I use pure scrolling shadows for this. The trick is the use of background-attachment: local;. Your css looks like this:

.scrollbox {  overflow: auto;  width: 200px;  max-height: 200px;  margin: 50px auto;
background: /* Shadow covers */ linear-gradient(white 30%, rgba(255,255,255,0)), linear-gradient(rgba(255,255,255,0), white 70%) 0 100%, /* Shadows */ radial-gradient(50% 0, farthest-side, rgba(0,0,0,.2), rgba(0,0,0,0)), radial-gradient(50% 100%,farthest-side, rgba(0,0,0,.2), rgba(0,0,0,0)) 0 100%; background: /* Shadow covers */ linear-gradient(white 30%, rgba(255,255,255,0)), linear-gradient(rgba(255,255,255,0), white 70%) 0 100%, /* Shadows */ radial-gradient(farthest-side at 50% 0, rgba(0,0,0,.2), rgba(0,0,0,0)), radial-gradient(farthest-side at 50% 100%, rgba(0,0,0,.2), rgba(0,0,0,0)) 0 100%; background-repeat: no-repeat; background-color: white; background-size: 100% 40px, 100% 40px, 100% 14px, 100% 14px; /* Opera doesn't support this in the shorthand */ background-attachment: local, local, scroll, scroll;}
<div class="scrollbox">  <ul>    <li>Not enough content to scroll</li>    <li>2</li>    <li>3</li>    <li>4</li>    <li>5</li>  </ul></div>

<div class="scrollbox"> <ul> <li>Ah! Scroll below!</li> <li>2</li> <li>3</li> <li>4</li> <li>5</li> <li>6</li> <li>7</li> <li>8</li> <li>9</li> <li>10</li> <li>1</li> <li>2</li> <li>3</li> <li>4</li> <li>5</li> <li>6</li> <li>7</li> <li>8</li> <li>The end!</li> <li>No shadow there.</li> </ul></div>

Determine if an HTML element's content overflows

Normally, you can compare the client[Height|Width] with scroll[Height|Width] in order to detect this... but the values will be the same when overflow is visible. So, a detection routine must account for this:

// Determines if the passed element is overflowing its bounds,
// either vertically or horizontally.
// Will temporarily modify the "overflow" style to detect this
// if necessary.
function checkOverflow(el)
{
var curOverflow = el.style.overflow;

if ( !curOverflow || curOverflow === "visible" )
el.style.overflow = "hidden";

var isOverflowing = el.clientWidth < el.scrollWidth
|| el.clientHeight < el.scrollHeight;

el.style.overflow = curOverflow;

return isOverflowing;
}

Tested in FF3, FF40.0.2, IE6, Chrome 0.2.149.30.

How to detect overflow in a nested div (React)?

It's not possible to know if arbitrary children are fully rendered without each one offering specialized callbacks. As such, it might be better to watch elements for size changes.

We can use ResizeObserver to our advantage here.

If we create a nested pair of div:

<div class="fixed_size_overflow_auto">
<div>
{children}
</div>
</div>

making the outer div have fixed dimensions, we can listen for resize on the inner div. When we detect those resizes, we can calculate if the outer div has overflowed by comparing its offsetHeight to its scrollHeight.

Here is the idea, wrapped up in a component that can be styled using styled-components:

const DetectContentResizeElement: FC<{
className?: string;
onContentResized?: (v: { hasOverflow: boolean }) => void;
}> = ({ children, onContentResized, className }) => {

const contentRef = useRef<HTMLDivElement>(null);
const outerRef = useRef<HTMLDivElement>(null);

useEffect(() => {
if (!contentRef.current || !outerRef.current) {
return;
}

const obs = new ResizeObserver(() => {
const hasOverflow =
(outerRef.current?.offsetHeight ?? 0) <
(contentRef.current?.offsetHeight ?? 0);
onContentResized?.({ hasOverflow });
});

obs.observe(contentRef.current);
return () => obs.disconnect();
}, [onContentResized]);

return (
<div className={className} ref={outerRef}>
<div ref={contentRef}>{children}</div>
</div>
);
};

You can fix the size of this component by "subclassing" it with styled-components:

const FixedHeight = styled(DetectContentResizeElement)`
height: 200px;
width: 200px;
border: solid 1px black;
overflow: auto;
`;

so now you can use this container and get events that tell you when it overflowed:

  <FixedHeight
onContentResized={({ hasOverflow }) =>
console.log(`resized. hasOverflow: ${hasOverflow}`)
}
>
<SomeChildElement />
</FixedHeight>

See it in action in this codesandbox project (uses resize-observer-polyfill ponyfill for best compatibility)

How to check if a div is overflowing in react functional component

As Jamie Dixon suggested in the comment, I used useLayoutEffect hook to set showLink true. Here is the code

Component

import React from "react";
import "./styles.css";

export default function App(props) {
const ref = React.createRef();
const [showMore, setShowMore] = React.useState(false);
const [showLink, setShowLink] = React.useState(false);

React.useLayoutEffect(() => {
if (ref.current.clientWidth < ref.current.scrollWidth) {
setShowLink(true);
}
}, [ref]);

const onClickMore = () => {
setShowMore(!showMore);
};

return (
<div>
<div ref={ref} className={showMore ? "" : "container"}>
{props.text}
</div>
{showLink && (
<span className="link more" onClick={onClickMore}>
{showMore ? "show less" : "show more"}
</span>
)}
</div>
);
}

CSS

.container {
overflow-x: hidden;
text-overflow: ellipsis;
white-space: nowrap;
width: 200px;
}

.link {
text-decoration: underline;
cursor: pointer;
color: #0d6aa8;
}

Check with jquery if div has overflowing elements

You actually don't need any jQuery to check if there is an overflow happening or not. Using element.offsetHeight, element.offsetWidth , element.scrollHeight and element.scrollWidth you can determine if your element have content bigger than it's size:

if (element.offsetHeight < element.scrollHeight ||
element.offsetWidth < element.scrollWidth) {
// your element have overflow
} else {
// your element doesn't have overflow
}

See example in action: Fiddle

But if you want to know what element inside your element is visible or not then you need to do more calculation. There is three states for a child element in terms of visibility:

Sample Image

If you want to count semi-visible items it would be the script you need:

var invisibleItems = [];
for(var i=0; i<element.childElementCount; i++){
if (element.children[i].offsetTop + element.children[i].offsetHeight >
element.offsetTop + element.offsetHeight ||
element.children[i].offsetLeft + element.children[i].offsetWidth >
element.offsetLeft + element.offsetWidth ){

invisibleItems.push(element.children[i]);
}

}

And if you don't want to count semi-visible you can calculate with a little difference.

How to detect overflow HTML elements

Compare scrollWidth/scrollHeight with clientWidth/clientHeight of the element.

if (e.scrollWidth > e.clientWidth){/*overflow*/}

https://jsfiddle.net/pdrk50a6/

Edit: I do not know your root element, yet in the end it is going to be something like this.

document.body.onresize = function(){
var tR = [];
var tL = document.querySelectorAll('div');

for(var i=0, j=tL.length; i<j; i++)
if (tL[i].scrollWidth > tL[i].clientWidth) tR.push(tL[i])

//Do whatever you need with the tR elements (overflown)
}

How to detect whether an element that have parent `overflow: hidden;`, is hidden?

EDIT: my compulsion forced me into changing this code without jQuery and correcting a bug

Here's a jsFiddle for a quick test, I repeat the code below:

HTML:

<div id="someContainer" style="overflow:hidden; position:relative; height:26px; background-color: #ffffff;">
<div class="item">A</div>
<div class="item">B</div>
<div class="item">C</div>
</div>
<pre id="output"></pre>

JS (no jQuery):

var i, top, container, output, height;

container = document.getElementById("someContainer");
output = document.getElementById("output");
height = container.offsetHeight;

output.innerText += "Height: " + height + "px\n";

for (i = 0; i < container.children.length; i++)
{
top = container.children[i].offsetTop;
output.innerText += "Top " + i + ": " + top + "px => visible=" + (top < height) + "\n";
}

The output will be:

Height: 26px
Top 0: 0px => visible=true
Top 1: 18px => visible=true
Top 2: 36px => visible=false

The first two items are visible (at least in part, I cut the B in half on purpose), while the last item is not visible. It falls beyond the lower edge of the container.

NOTE: I had to add position: relative; to the container so that it becomes a positioning reference for child elements. Otherwise, offsetTop would compute incorrectly under specific circumstances (depending on outer HTML).



Related Topics



Leave a reply



Submit