How to check with javascript/jquery which object(s) is(is) triggering a scroll bar on the page?

Asked

Viewed 1,101 times

4

I would like to build a verification script, because it is often difficult to find why the page is scrolling, especially when we use some responsive framework that has a lot of css code and a lot of js code manipulating.

I need tips to make a logic that would point out to me the objects that are causing the scrollbar to appear. I have no idea how to start. Suddenly we can together build something that can be useful to everyone, or if someone already has a better ready.

My test code is the answer in case someone wants to improve.

  • One way that should work (without thinking about efficiency) is to check the position and height of all page elements, and see if any of them exceeds the height of the window.

4 answers

4


Your question is very interesting, here is my solution:

function escanearPagina(el) {
    var i = [],
    t, x, y, w, h,
    ww = $(window).width(),
    wh = $(window).height();

    el.each(function(){
        t = $(this);
        x = t[0].offsetLeft;
        y = t[0].offsetTop;
        w = t.outerWidth();
        h = t.outerHeight();

        if (w > ww || +x + w > ww || h > wh || +y + h > wh) {
            i.push(t[0]);
        }
    });
    return i;
}

Perks:

  • Allows you to define which area of the page you want it to scan;
  • Also calculates based on padding, and not only on the width of the elements (box-sizing:border-box does not affect the script);
  • Returns an array of found elements;

How to use:

var resultado = escanearPagina($('body *')); //retorna todos os elementos dentro do body que geram scroll
$(resultado).addClass('eu-quebro-o-layout');

Following example: FIDDLE

  • 1

    Quite cool your solution, goes beyond the issue of the size of a single object. I will try to use it.

  • @Joaopaulo I gave an update on the code and in the example, I made some improvements, in case you already got the code only updated by the new one here :)

  • I would add in if x < 0 || y < 0

  • @Leandroamorim then, I did not add check to x and y negative because they do not generate window scroll. As the question was only about the elements that generate scroll on the page, I preferred not to "scan" these elements. Although I think that depending on the case it would be interesting to implement this verification as well. :)

1

You can test with this function:

function isOverflowed(element){
    return element.scrollHeight > element.clientHeight || element.scrollWidth > element.clientWidth;
}
  • It seemed very interesting. But I simulated with a div q exceeded the width of the page and returned false.

  • The function is correct, you must pass the HTML element. If you are using jQuery or some other element, extract it. For example, you can use it here in Stackoverflow itself, opening your console, inserting the function and then sending the commands: isOverflowed($(". vote-Count-post"). get(0)) or isOverflowed($(". post-text"). get(0))

  • I tested like this: $('div'). each(Function(){ Alert(isOverflowed($(this)); }); this is wrong?

  • Yes, when you pull the $("div") you have a jQuery object instead of a DOM object. Hence: $(".post-text"). clientHeight = Undefined and $(".post-text"). get(0). clientHeight = 268.

1

I implemented a script to do this using jQuery:

$(function () {
    var $w = $(window),
        wb = $w.height(),
        wr = $w.width(),
        arr = [];

    $('*').each(function () {

        var $this = $(this),
            ofs = $this.offset(),
            eb = ofs.top + $this.height(),
            er = ofs.left + $this.width();

        if (eb > wb || er > wr) {
            arr.push(this);
        }

    });

    var msg = "Array contains: " + arr.length + "\n";
    for (var it = 0; it < arr.length; it++) {
        msg += arr[it].tagName + " - ";
        msg += "Largura: " + $(arr[it]).css('width') + "; ";
        msg += "Altura: " + $(arr[it]).css('height') + "; ";
        msg += "\n";
    }

    alert(msg);
});

jsfiddle

  • I tested here by changing '*' to 'div' in my blank html that only contains a 1500 wide div plus 250 padding on each side. My document is 1440 wide. An Alert appeared like this: Array contains: 0

  • It is because I only tested the height. = D I will edit to also consider the width!

0

I am posting here my test code and would like help to improve it. Can edit.

$(document).ready(function(){
    debugger;
    var docWidth = toInt($("html").css('width'));
    var docHeight = toInt($("html").css('height'));
    $('div').each(function(){
        var objWidth  = toInt($(this).css("width")) + toInt($(this).css("padding-left")) + toInt($(this).css("padding-right"));                    
        var objHeight = toInt($(this).css("height")) + toInt($(this).css("padding-top")) + toInt($(this).css("padding-bottom"));
        if ( objWidth > docWidth ){
            alert("Tamanho do objeto " + $(this).tagName + " excedeu a página: " + objWidth);
        }

        if ( objHeight > docHeight ){
            alert("Tamanho do objeto " + $(this).tagName + "excedeu a página: " + objHeight);
        }
    }); 
   function toInt(str){
        return parseInt(str.replace(/[^\d]+/g,''));
   }   
});

At first it is checking correctly. But tagname is always coming Undefined (setei div for now for testing, but should be '*'). Then I will be in several situations to see if you are really capturing everything in the right way. I think I missed implementing the margin.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.