How to tell if a DOM element is visible in the current viewport?












795















Is there an efficient way to tell if a DOM element (in an HTML document) is currently visible (appears in the viewport)?



(The question regards Firefox)










share|improve this question




















  • 14





    Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

    – Adam Wright
    Sep 23 '08 at 21:31






  • 5





    as in within the currently displayed rectangle. Thanks. Rephrased.

    – benzaita
    Sep 23 '08 at 21:40











  • Could you update the title also?

    – EoghanM
    Dec 2 '08 at 23:48






  • 2





    Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

    – Andy E
    Mar 4 '13 at 13:48











  • I've added my own solution that solves this problem

    – Andy E
    Mar 4 '13 at 14:18
















795















Is there an efficient way to tell if a DOM element (in an HTML document) is currently visible (appears in the viewport)?



(The question regards Firefox)










share|improve this question




















  • 14





    Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

    – Adam Wright
    Sep 23 '08 at 21:31






  • 5





    as in within the currently displayed rectangle. Thanks. Rephrased.

    – benzaita
    Sep 23 '08 at 21:40











  • Could you update the title also?

    – EoghanM
    Dec 2 '08 at 23:48






  • 2





    Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

    – Andy E
    Mar 4 '13 at 13:48











  • I've added my own solution that solves this problem

    – Andy E
    Mar 4 '13 at 14:18














795












795








795


457






Is there an efficient way to tell if a DOM element (in an HTML document) is currently visible (appears in the viewport)?



(The question regards Firefox)










share|improve this question
















Is there an efficient way to tell if a DOM element (in an HTML document) is currently visible (appears in the viewport)?



(The question regards Firefox)







javascript html firefox dom






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Jun 15 '18 at 6:59









Animesh

2,81085494




2,81085494










asked Sep 23 '08 at 21:24









benzaitabenzaita

4,25231521




4,25231521








  • 14





    Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

    – Adam Wright
    Sep 23 '08 at 21:31






  • 5





    as in within the currently displayed rectangle. Thanks. Rephrased.

    – benzaita
    Sep 23 '08 at 21:40











  • Could you update the title also?

    – EoghanM
    Dec 2 '08 at 23:48






  • 2





    Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

    – Andy E
    Mar 4 '13 at 13:48











  • I've added my own solution that solves this problem

    – Andy E
    Mar 4 '13 at 14:18














  • 14





    Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

    – Adam Wright
    Sep 23 '08 at 21:31






  • 5





    as in within the currently displayed rectangle. Thanks. Rephrased.

    – benzaita
    Sep 23 '08 at 21:40











  • Could you update the title also?

    – EoghanM
    Dec 2 '08 at 23:48






  • 2





    Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

    – Andy E
    Mar 4 '13 at 13:48











  • I've added my own solution that solves this problem

    – Andy E
    Mar 4 '13 at 14:18








14




14





Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

– Adam Wright
Sep 23 '08 at 21:31





Clarification: Visible, as in within the currently displayed rectangle. Visible, as in not hidden or display: none? Visible, as in not behind something else in the Z-order?

– Adam Wright
Sep 23 '08 at 21:31




5




5





as in within the currently displayed rectangle. Thanks. Rephrased.

– benzaita
Sep 23 '08 at 21:40





as in within the currently displayed rectangle. Thanks. Rephrased.

– benzaita
Sep 23 '08 at 21:40













Could you update the title also?

– EoghanM
Dec 2 '08 at 23:48





Could you update the title also?

– EoghanM
Dec 2 '08 at 23:48




2




2





Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

– Andy E
Mar 4 '13 at 13:48





Note that all of the answers here will give you a false positive for items that are outside the visible area of their parent element (e.h. with overflow hidden) but inside the viewport area.

– Andy E
Mar 4 '13 at 13:48













I've added my own solution that solves this problem

– Andy E
Mar 4 '13 at 14:18





I've added my own solution that solves this problem

– Andy E
Mar 4 '13 at 14:18












22 Answers
22






active

oldest

votes


















304














Update: Time marches on and so have our browsers. This technique is no longer recommended and you should use @Dan's solution below (https://stackoverflow.com/a/7557433/5628) if you do not need to support IE<7.



Original solution (now outdated):



This will check if the element is entirely visible in the current viewport:



function elementInViewport(el) {
var top = el.offsetTop;
var left = el.offsetLeft;
var width = el.offsetWidth;
var height = el.offsetHeight;

while(el.offsetParent) {
el = el.offsetParent;
top += el.offsetTop;
left += el.offsetLeft;
}

return (
top >= window.pageYOffset &&
left >= window.pageXOffset &&
(top + height) <= (window.pageYOffset + window.innerHeight) &&
(left + width) <= (window.pageXOffset + window.innerWidth)
);
}


You could modify this simply to determine if any part of the element is visible in the viewport:



function elementInViewport2(el) {
var top = el.offsetTop;
var left = el.offsetLeft;
var width = el.offsetWidth;
var height = el.offsetHeight;

while(el.offsetParent) {
el = el.offsetParent;
top += el.offsetTop;
left += el.offsetLeft;
}

return (
top < (window.pageYOffset + window.innerHeight) &&
left < (window.pageXOffset + window.innerWidth) &&
(top + height) > window.pageYOffset &&
(left + width) > window.pageXOffset
);
}





share|improve this answer





















  • 1





    Original function posted had a mistake. Needed to save the width/height before reassigning el...

    – Prestaul
    Sep 24 '08 at 2:56






  • 9





    What if the element lives in a scrollable div and scrolled out of a view??

    – amartynov
    Mar 6 '11 at 8:42






  • 2





    Please review a newer version of the script below

    – Dan
    Sep 26 '11 at 15:29






  • 1





    Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

    – Eric Nguyen
    Nov 7 '12 at 23:51






  • 1





    @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

    – Prestaul
    Jul 6 '15 at 15:25



















1236














Now most browsers support getBoundingClientRect method, which has become the best practice. Using an old answer is very slow, not accurate and has several bugs.



The solution selected as correct is almost never precise. You can read more about its bugs.





This solution was tested on IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, and IE Mobile 10.





function isElementInViewport (el) {

//special bonus for those using jQuery
if (typeof jQuery === "function" && el instanceof jQuery) {
el = el[0];
}

var rect = el.getBoundingClientRect();

return (
rect.top >= 0 &&
rect.left >= 0 &&
rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
);
}




How to use:



You can be sure that the function given above returns correct answer at the moment of time when it is called, but what about tracking element's visibility as an event?



Place the following code at the bottom of your <body> tag:



function onVisibilityChange(el, callback) {
var old_visible;
return function () {
var visible = isElementInViewport(el);
if (visible != old_visible) {
old_visible = visible;
if (typeof callback == 'function') {
callback();
}
}
}
}

var handler = onVisibilityChange(el, function() {
/* your code go here */
});


//jQuery
$(window).on('DOMContentLoaded load resize scroll', handler);

/* //non-jQuery
if (window.addEventListener) {
addEventListener('DOMContentLoaded', handler, false);
addEventListener('load', handler, false);
addEventListener('scroll', handler, false);
addEventListener('resize', handler, false);
} else if (window.attachEvent) {
attachEvent('onDOMContentLoaded', handler); // IE9+ :(
attachEvent('onload', handler);
attachEvent('onscroll', handler);
attachEvent('onresize', handler);
}
*/




If you do any DOM modifications, they can change your element's visibility of course.



Guidelines and common pitfalls:



Maybe you need to track page zoom / mobile device pinch? jQuery should handle zoom/pinch cross browser, otherwise first or second link should help you.



If you modify DOM, it can affect the element's visibility. You should take control over that and call handler() manually. Unfortunately, we have no cross browser onrepaint event. On the other hand that allows us to make optimizations and perform re-check only on DOM modifications that can change element's visibility.



Never Ever use it inside jQuery $(document).ready() only, because there is no warranty CSS has been applied in this moment. Your code can work locally with your CSS on hard drive, but once put on remote server it will fail.



After DOMContentLoaded is fired, styles are applied, but the images are not loaded yet. So, we should add window.onload event listener.



We can't catch zoom/pinch event yet.



The last resort could be the following code:



/* TODO: this looks like a very bad code */
setInterval(handler, 600);


You can use awesome feature pageVisibiliy HTML5 API if you care if the tab with your web page is active and visible.



TODO: this method does not handle two situations:




  • overlapping using z-index

  • using overflow-scroll in element's container


  • try something new https://pawelgrzybek.com/the-intersection-observer-api-explained/







share|improve this answer





















  • 5





    I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

    – Claudio
    Oct 20 '11 at 12:38








  • 4





    Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

    – agaase
    Dec 8 '13 at 9:04






  • 53





    The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

    – Roonaan
    Feb 21 '14 at 7:29








  • 9





    Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

    – jiminy
    Apr 12 '14 at 7:44






  • 7





    el is not defined

    – M_Willett
    Oct 18 '16 at 10:47



















141














Update



In modern browsers, you might want to check out the Intersection Observer API which provides the following benefits:




  • Better performance than listening for scroll events

  • Works in cross domain iframes

  • Can tell if an element is obstructing/intersecting another


Intersection Observer is on its way to being a full-fledged standard and is already supported in Chrome 51+, Edge 15+ and Firefox 55+ and is under development for Safari. There's also a polyfill available.





Previous answer



There are some issues with the answer provided by Dan that might make it an unsuitable approach for some situations. Some of these issues are pointed out in his answer near the bottom, that his code will give false positives for elements that are:




  • Hidden by another element in front of the one being tested

  • Outside the visible area of a parent or ancestor element

  • An element or its children hidden by using the CSS clip property


These limitations are demonstrated in the following results of a simple test:



Failed test, using isElementInViewport



The solution: isElementVisible()



Here's a solution to those problems, with the test result below and an explanation of some parts of the code.



function isElementVisible(el) {
var rect = el.getBoundingClientRect(),
vWidth = window.innerWidth || doc.documentElement.clientWidth,
vHeight = window.innerHeight || doc.documentElement.clientHeight,
efp = function (x, y) { return document.elementFromPoint(x, y) };

// Return false if it's not in the viewport
if (rect.right < 0 || rect.bottom < 0
|| rect.left > vWidth || rect.top > vHeight)
return false;

// Return true if any of its four corners are visible
return (
el.contains(efp(rect.left, rect.top))
|| el.contains(efp(rect.right, rect.top))
|| el.contains(efp(rect.right, rect.bottom))
|| el.contains(efp(rect.left, rect.bottom))
);
}



Passing test: http://jsfiddle.net/AndyE/cAY8c/




And the result:



Passed test, using isElementVisible



Additional notes



This method is not without its own limitations, however. For instance, an element being tested with a lower z-index than another element at the same location would be identified as hidden even if the element in front doesn't actually hide any part of it. Still, this method has its uses in some cases that Dan's solution doesn't cover.



Both element.getBoundingClientRect() and document.elementFromPoint() are part of the CSSOM Working Draft specification and are supported in at least IE 6 and later and most desktop browsers for a long time (albeit, not perfectly). See Quirksmode on these functions for more information.



contains() is used to see if the element returned by document.elementFromPoint() is a child node of the element we're testing for visibility. It also returns true if the element returned is the same element. This just makes the check more robust. It's supported in all major browsers, Firefox 9.0 being the last of them to add it. For older Firefox support, check this answer's history.



If you want to test more points around the element for visibility―ie, to make sure the element isn't covered by more than, say, 50%―it wouldn't take much to adjust the last part of the answer. However, be aware that it would probably be very slow if you checked every pixel to make sure it was 100% visible.






share|improve this answer





















  • 1





    Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

    – Kevin Lamping
    Mar 19 '13 at 19:34













  • @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

    – Andy E
    Mar 19 '13 at 20:14






  • 1





    For me it is not working. But inViewport() in previous answer is working in FF.

    – Satya Prakash
    Dec 28 '13 at 7:05






  • 8





    It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

    – Jared
    Mar 10 '15 at 8:15








  • 1





    Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

    – Rayjax
    Feb 18 '16 at 14:05



















51














I tried Dan's answer however the algebra used to determine the bounds means that the element must be both ≤ the viewport size and completely inside the viewport to get true, easily leading to false negatives. If you want to determine whether an element is in the viewport at all, ryanve's answer is close but the element being tested should overlap the viewport, so try this:



function isElementInViewport(el) {
var rect = el.getBoundingClientRect();

return rect.bottom > 0 &&
rect.right > 0 &&
rect.left < (window.innerWidth || document.documentElement.clientWidth) /* or $(window).width() */ &&
rect.top < (window.innerHeight || document.documentElement.clientHeight) /* or $(window).height() */;
}





share|improve this answer

































    28














    As a public service:

    Dan's answer with the correct calculations (element can be > window, especially on mobile phone screens), and correct jQuery testing, as well as adding isElementPartiallyInViewport:



    By the way, the difference between window.innerWidth and document.documentElement.clientWidth is that clientWidth/clientHeight doesn't include the scrollbar, while window.innerWidth/Height does.



    function isElementPartiallyInViewport(el)
    {
    //special bonus for those using jQuery
    if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

    var rect = el.getBoundingClientRect();
    // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
    var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
    var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

    // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
    var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
    var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

    return (vertInView && horInView);
    }


    // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
    function isElementInViewport (el)
    {
    //special bonus for those using jQuery
    if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

    var rect = el.getBoundingClientRect();
    var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
    var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

    return (
    (rect.left >= 0)
    && (rect.top >= 0)
    && ((rect.left + rect.width) <= windowWidth)
    && ((rect.top + rect.height) <= windowHeight)
    );

    }


    function fnIsVis(ele)
    {
    var inVpFull = isElementInViewport(ele);
    var inVpPartial = isElementPartiallyInViewport(ele);
    console.clear();
    console.log("Fully in viewport: " + inVpFull);
    console.log("Partially in viewport: " + inVpPartial);
    }


    Test-case



    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <meta name="description" content="">
    <meta name="author" content="">
    <title>Test</title>
    <!--
    <script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
    <script src="scrollMonitor.js"></script>
    -->

    <script type="text/javascript">

    function isElementPartiallyInViewport(el)
    {
    //special bonus for those using jQuery
    if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

    var rect = el.getBoundingClientRect();
    // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
    var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
    var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

    // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
    var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
    var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

    return (vertInView && horInView);
    }


    // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
    function isElementInViewport (el)
    {
    //special bonus for those using jQuery
    if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];


    var rect = el.getBoundingClientRect();
    var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
    var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

    return (
    (rect.left >= 0)
    && (rect.top >= 0)
    && ((rect.left + rect.width) <= windowWidth)
    && ((rect.top + rect.height) <= windowHeight)
    );

    }


    function fnIsVis(ele)
    {
    var inVpFull = isElementInViewport(ele);
    var inVpPartial = isElementPartiallyInViewport(ele);
    console.clear();
    console.log("Fully in viewport: " + inVpFull);
    console.log("Partially in viewport: " + inVpPartial);
    }


    // var scrollLeft = (window.pageXOffset !== undefined) ? window.pageXOffset : (document.documentElement || document.body.parentNode || document.body).scrollLeft,
    // var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop;

    </script>

    </head>
    <body>

    <div style="display: block; width: 2000px; height: 10000px; background-color: green;">

    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />

    <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />

    <div style="background-color: crimson; display: inline-block; width: 800px; height: 500px;" ></div>
    <div id="myele" onclick="fnIsVis(this);" style="display: inline-block; width: 100px; height: 100px; background-color: hotpink;">
    t
    </div>

    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />
    <br /><br /><br /><br /><br /><br />

    <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

    </div>

    <!--
    <script type="text/javascript">

    var element = document.getElementById("myele");
    var watcher = scrollMonitor.create( element );

    watcher.lock();

    watcher.stateChange(function() {
    console.log("state changed");
    // $(element).toggleClass('fixed', this.isAboveViewport)
    });

    </script>
    -->
    </body>
    </html>





    share|improve this answer





















    • 2





      isElementPartiallyInViewport is very useful as well. Nice one.

      – RJ Cuthbertson
      Oct 28 '15 at 13:02











    • For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

      – Arun chauhan
      Aug 13 '18 at 8:00








    • 1





      @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

      – Stefan Steiger
      Aug 13 '18 at 8:53





















    25














    There is jQuery plugin called inview that does the job






    share|improve this answer



















    • 16





      My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

      – mmmeff
      Jan 27 '14 at 23:51













    • Another solution.

      – Jonatas Walker
      Oct 1 '16 at 13:33



















    24














    See the source of verge, which uses getBoundingClientRect. It's like:



    function inViewport (el) {

    var r, html;
    if ( !el || 1 !== el.nodeType ) { return false; }
    html = document.documentElement;
    r = el.getBoundingClientRect();

    return ( !!r
    && r.bottom >= 0
    && r.right >= 0
    && r.top <= html.clientHeight
    && r.left <= html.clientWidth
    );

    }


    Returns true if any part of the element is in the viewport.






    share|improve this answer

































      22














      my shorter and faster version.



      function isElementOutViewport(el){
      var rect = el.getBoundingClientRect();
      return rect.bottom < 0 || rect.right < 0 || rect.left > window.innerWidth || rect.top > window.innerHeight;
      }


      add jsFiddle as required
      https://jsfiddle.net/on1g619L/1/






      share|improve this answer





















      • 4





        My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

        – Eric Chen
        Jan 19 '15 at 23:05






      • 1





        I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

        – Y.K.
        Sep 5 '18 at 21:09













      • @Y.K. okay, done.

        – Eric Chen
        Sep 7 '18 at 3:58



















      19














      I found it troubling that there wasn't a jQuery centric version of the functionality available. When i came across Dan's solution i spied the opportunity to provide something for folks who like to program in the jQuery OO style. Be sure to scroll up and leave an upvote on Dan's code. Its nice and snappy and works like a charm for me.



      bada bing bada boom



      $.fn.inView = function(){
      if(!this.length) return false;
      var rect = this.get(0).getBoundingClientRect();

      return (
      rect.top >= 0 &&
      rect.left >= 0 &&
      rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
      rect.right <= (window.innerWidth || document.documentElement.clientWidth)
      );

      };

      //additional examples for other use cases
      //true false whether an array of elements are all in view
      $.fn.allInView = function(){
      var all = ;
      this.forEach(function(){
      all.push( $(this).inView() );
      });
      return all.indexOf(false) === -1;
      };

      //only the class elements in view
      $('.some-class').filter(function(){
      return $(this).inView();
      });

      //only the class elements not in view
      $('.some-class').filter(function(){
      return !$(this).inView();
      });


      usage



      $(window).on('scroll',function(){ 

      if( $('footer').inView() ) {
      // do cool stuff
      }

      });





      share|improve this answer





















      • 1





        Would the curly brace be sufficient to close the if statement?

        – calasyr
        May 24 '16 at 23:58






      • 1





        I could not make it work with multiple elements of an identical class.

        – The Whiz of Oz
        Jun 20 '17 at 7:38






      • 1





        @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

        – r3wt
        Jun 20 '17 at 20:07



















      8














      I find that the accepted answer here is overly complicated for most use cases. This code does the job well (using JQuery) and differentiates between fully visible and partially visible elements.



      var element         = $("#element");
      var topOfElement = element.offset().top;
      var bottomOfElement = element.offset().top + element.outerHeight(true);
      var $window = $(window);

      $window.bind('scroll', function() {

      var scrollTopPosition = $window.scrollTop()+$window.height();
      var windowScrollTop = $window.scrollTop()

      if( windowScrollTop > topOfElement && windowScrollTop < bottomOfElement) {
      // Element is partially visible (above viewable area)
      console.log("Element is partially visible (above viewable area)");

      }else if( windowScrollTop > bottomOfElement && windowScrollTop > topOfElement ) {
      // Element is hidden (above viewable area)
      console.log("Element is hidden (above viewable area)");

      }else if( scrollTopPosition < topOfElement && scrollTopPosition < bottomOfElement ) {
      // Element is hidden (below viewable area)
      console.log("Element is hidden (below viewable area)");

      }else if( scrollTopPosition < bottomOfElement && scrollTopPosition > topOfElement ) {
      // Element is partially visible (below viewable area)
      console.log("Element is partially visible (below viewable area)");

      }else{
      // Element is completely visible
      console.log("Element is completely visible");
      }
      });





      share|improve this answer


























      • Works brilliantly! Tested on Chrome, Firefox and Safari.

        – noobsharp
        May 8 '16 at 14:45











      • You can use this.

        – Jonatas Walker
        Oct 1 '16 at 12:54











      • You should definitely cache $window = $(window) outside the scroll handler.

        – sam
        Jul 1 '17 at 19:36



















      3














      I think this is a more functional way to do it.
      The Dan's answer do not work in recursive context.



      This function solve the problem when your element is inside others scrollable divs by testing any levels recursively upper to the HTML tag, and stops in the first false.



      /**
      * fullVisible=true only returns true if the all object rect is visible
      */
      function isReallyVisible(el, fullVisible) {
      if ( el.tagName == "HTML" )
      return true;
      var parentRect=el.parentNode.getBoundingClientRect();
      var rect = arguments[2] || el.getBoundingClientRect();
      return (
      ( fullVisible ? rect.top >= parentRect.top : rect.bottom > parentRect.top ) &&
      ( fullVisible ? rect.left >= parentRect.left : rect.right > parentRect.left ) &&
      ( fullVisible ? rect.bottom <= parentRect.bottom : rect.top < parentRect.bottom ) &&
      ( fullVisible ? rect.right <= parentRect.right : rect.left < parentRect.right ) &&
      isReallyVisible(el.parentNode, fullVisible, rect)
      );
      };





      share|improve this answer































        3














        All answers I've encountered here only check if the element is positioned inside the current viewport. But that doesn't mean that it is visible.

        What if the given element is inside a div with overflowing content, and it is scrolled out of view?



        To solve that, you'd have to check if the element is contained by all parents.

        My solution does exactly that:



        It also allows you to specify how much of the element has to be visible.



        Element.prototype.isVisible = function(percentX, percentY){
        var tolerance = 0.01; //needed because the rects returned by getBoundingClientRect provide the position up to 10 decimals
        if(percentX == null){
        percentX = 100;
        }
        if(percentY == null){
        percentY = 100;
        }

        var elementRect = this.getBoundingClientRect();
        var parentRects = ;
        var element = this;

        while(element.parentElement != null){
        parentRects.push(element.parentElement.getBoundingClientRect());
        element = element.parentElement;
        }

        var visibleInAllParents = parentRects.every(function(parentRect){
        var visiblePixelX = Math.min(elementRect.right, parentRect.right) - Math.max(elementRect.left, parentRect.left);
        var visiblePixelY = Math.min(elementRect.bottom, parentRect.bottom) - Math.max(elementRect.top, parentRect.top);
        var visiblePercentageX = visiblePixelX / elementRect.width * 100;
        var visiblePercentageY = visiblePixelY / elementRect.height * 100;
        return visiblePercentageX + tolerance > percentX && visiblePercentageY + tolerance > percentY;
        });
        return visibleInAllParents;
        };


        This solution ignored the fact that elements may not be visible due to other facts, like opacity: 0.



        I have tested this solution in Chrome and Internet Explorer 11.






        share|improve this answer































          2














          Depends what you mean by visible. If you mean is it currently shown on the page, given the scroll position, you can calculate it based on the elements y offset and the current scroll position.






          share|improve this answer































            2














            Based on @dan's solution above (https://stackoverflow.com/a/7557433/5628), I had a go at cleaning up implementation so that using it multiple times on the same page is easier:



            $(function() {

            $(window).on('load resize scroll', function() {
            addClassToElementInViewport($('.bug-icon'), 'animate-bug-icon');
            addClassToElementInViewport($('.another-thing'), 'animate-thing');
            // 👏 repeat as needed ...
            });

            function addClassToElementInViewport(element, newClass) {
            if (inViewport(element)) {
            element.addClass(newClass);
            }
            }

            function inViewport(element) {
            if (typeof jQuery === "function" && element instanceof jQuery) {
            element = element[0];
            }
            var elementBounds = element.getBoundingClientRect();
            return (
            elementBounds.top >= 0 &&
            elementBounds.left >= 0 &&
            elementBounds.bottom <= $(window).height() &&
            elementBounds.right <= $(window).width()
            );
            }

            });


            The way I'm using it is that when the element scrolls into view, I'm adding a class that triggers a css keyframe animation. It's pretty straightforward and works especially well when you've got like 10+ things to conditionally animate on a page.



            Hope it helps!






            share|improve this answer


























            • You should definitely cache $window = $(window) outside the scroll handler

              – Adam Rehal
              Nov 1 '17 at 8:13



















            1














            Here's my solution, it will work if an element is hidden inside a scroll-able container.



            Here's a demo (try re-sizing the window to)



            var visibleY = function(el){
            var top = el.getBoundingClientRect().top, rect, el = el.parentNode;
            do {
            rect = el.getBoundingClientRect();
            if (top <= rect.bottom === false)
            return false;
            el = el.parentNode;
            } while (el != document.body);
            // Check its within the document viewport
            return top <= document.documentElement.clientHeight;
            };


            I only needed to check if it's visible in the Y axis (for a scrolling ajax load more records feature).






            share|improve this answer

































              1














              The easy and small solution that has worked for me.



              Example You want to see if the element is visible in parent element that has overflow scroll.



              $(window).on('scroll', function () {  

              var container = $('#sidebar');
              var containerHeight = container.height();
              var scrollPosition = $('#row1').offset().top - container.offset().top;

              if (containerHeight < scrollPosition) {
              console.log('not visible');
              } else {
              console.log('visible');
              }
              })





              share|improve this answer

































                0














                A better solution:



                function getViewportSize(w) {
                var w = w || window;
                if(w.innerWidth != null) return {w:w.innerWidth, h:w.innerHeight};
                var d = w.document;
                if (document.compatMode == "CSS1Compat") {
                return {
                w: d.documentElement.clientWidth,
                h: d.documentElement.clientHeight
                };
                }
                return { w: d.body.clientWidth, h: d.body.clientWidth };
                }
                function isViewportVisible(e) {
                var box = e.getBoundingClientRect();
                var height = box.height || (box.bottom - box.top);
                var width = box.width || (box.right - box.left);
                var viewport = getViewportSize();
                if(!height || !width) return false;
                if(box.top > viewport.h || box.bottom < 0) return false;
                if(box.right < 0 || box.left > viewport.w) return false;
                return true;
                }





                share|improve this answer



















                • 10





                  You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                  – Andy E
                  Mar 4 '13 at 13:46











                • Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                  – teter
                  May 13 '15 at 9:10





















                0














                Checks if element is at least partially in view (vertical dimension):



                function inView(element) {
                var box = element.getBoundingClientRect();
                return inViewBox(box);
                }

                function inViewBox(box) {
                return ((box.bottom < 0) || (box.top > getWindowSize().h)) ? false : true;
                }


                function getWindowSize() {
                return { w: document.body.offsetWidth || document.documentElement.offsetWidth || window.innerWidth, h: document.body.offsetHeight || document.documentElement.offsetHeight || window.innerHeight}
                }





                share|improve this answer































                  0














                  I had the same question and figured it out by using getBoundingClientRect(). This code is completely 'generic' and only has to be written once for it to work (you don't have to write it out for each element that you want to know is in the viewport). This code only checks to see if it is vertically in the viewport not horizontally. In this case, the variable (array) 'elements' holds all the elements that you are checking to be vertically in the viewport, so grab any elements you want anywhere and store them there. The 'for loop', loops through each element and checks to see if it is vertically in the viewport. This code executes every time the user scrolls! If the getBoudingClientRect().top is less than 3/4 the viewport (the element is one quarter in the viewport), it registers as 'in the viewport'. Since the code is generic, you will want to know 'which' element is in the viewport. To find that out, you can determine it by custom attribute, node name, id, class name, and more. Here is my code (Tell me if it doesn't work, it has been tested in IE 11, FireFox 40.0.3, Chrome Version 45.0.2454.85 m, Opera 31.0.1889.174, and Edge with Windows 10, [not Safari yet])...



                  //scrolling handlers...
                  window.onscroll = function(){
                  var elements = document.getElementById('whatever').getElementsByClassName('whatever');
                  for(var i = 0; i != elements.length; i++)
                  {
                  if(elements[i].getBoundingClientRect().top <= window.innerHeight*0.75 && elements[i].getBoundingClientRect().top > 0)
                  {
                  console.log(elements[i].nodeName + ' ' + elements[i].className + ' ' + elements[i].id + ' is in the viewport; proceed with whatever code you want to do here.');
                  }
                  };


                  Hope this helps someone :-)






                  share|improve this answer































                    0














                    Here is a function that tells if an element is in visible in the current viewport of a parent element:



                    function inParentViewport(el, pa) {
                    if (typeof jQuery === "function"){
                    if (el instanceof jQuery)
                    el = el[0];
                    if (pa instanceof jQuery)
                    pa = pa[0];
                    }

                    var e = el.getBoundingClientRect();
                    var p = pa.getBoundingClientRect();

                    return (
                    e.bottom >= p.top &&
                    e.right >= p.left &&
                    e.top <= p.bottom &&
                    e.left <= p.right
                    );
                    }





                    share|improve this answer































                      -1














                      I use this function (it only checks if the y is inscreen since most of the time the x is not needed)



                      function elementInViewport(el) {
                      var elinfo = {
                      "top":el.offsetTop,
                      "height":el.offsetHeight,
                      };

                      if (elinfo.top + elinfo.height < window.pageYOffset || elinfo.top > window.pageYOffset + window.innerHeight) {
                      return false;
                      } else {
                      return true;
                      }

                      }





                      share|improve this answer































                        -2














                        For a similar challenge i really enjoyed this gist which exposes a polyfill for scrollIntoViewIfNeeded().



                        All the necessary Kung Fu needed to answer is within this block:



                        var parent = this.parentNode,
                        parentComputedStyle = window.getComputedStyle(parent, null),
                        parentBorderTopWidth = parseInt(parentComputedStyle.getPropertyValue('border-top-width')),
                        parentBorderLeftWidth = parseInt(parentComputedStyle.getPropertyValue('border-left-width')),
                        overTop = this.offsetTop - parent.offsetTop < parent.scrollTop,
                        overBottom = (this.offsetTop - parent.offsetTop + this.clientHeight - parentBorderTopWidth) > (parent.scrollTop + parent.clientHeight),
                        overLeft = this.offsetLeft - parent.offsetLeft < parent.scrollLeft,
                        overRight = (this.offsetLeft - parent.offsetLeft + this.clientWidth - parentBorderLeftWidth) > (parent.scrollLeft + parent.clientWidth),
                        alignWithTop = overTop && !overBottom;


                        this refers to the element that you want to know if it is i.e. overTop or overBottom - just should get the drift...






                        share|improve this answer






















                          protected by Josh Crozier Feb 5 '15 at 3:43



                          Thank you for your interest in this question.
                          Because it has attracted low-quality or spam answers that had to be removed, posting an answer now requires 10 reputation on this site (the association bonus does not count).



                          Would you like to answer one of these unanswered questions instead?














                          22 Answers
                          22






                          active

                          oldest

                          votes








                          22 Answers
                          22






                          active

                          oldest

                          votes









                          active

                          oldest

                          votes






                          active

                          oldest

                          votes









                          304














                          Update: Time marches on and so have our browsers. This technique is no longer recommended and you should use @Dan's solution below (https://stackoverflow.com/a/7557433/5628) if you do not need to support IE<7.



                          Original solution (now outdated):



                          This will check if the element is entirely visible in the current viewport:



                          function elementInViewport(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top >= window.pageYOffset &&
                          left >= window.pageXOffset &&
                          (top + height) <= (window.pageYOffset + window.innerHeight) &&
                          (left + width) <= (window.pageXOffset + window.innerWidth)
                          );
                          }


                          You could modify this simply to determine if any part of the element is visible in the viewport:



                          function elementInViewport2(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top < (window.pageYOffset + window.innerHeight) &&
                          left < (window.pageXOffset + window.innerWidth) &&
                          (top + height) > window.pageYOffset &&
                          (left + width) > window.pageXOffset
                          );
                          }





                          share|improve this answer





















                          • 1





                            Original function posted had a mistake. Needed to save the width/height before reassigning el...

                            – Prestaul
                            Sep 24 '08 at 2:56






                          • 9





                            What if the element lives in a scrollable div and scrolled out of a view??

                            – amartynov
                            Mar 6 '11 at 8:42






                          • 2





                            Please review a newer version of the script below

                            – Dan
                            Sep 26 '11 at 15:29






                          • 1





                            Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                            – Eric Nguyen
                            Nov 7 '12 at 23:51






                          • 1





                            @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                            – Prestaul
                            Jul 6 '15 at 15:25
















                          304














                          Update: Time marches on and so have our browsers. This technique is no longer recommended and you should use @Dan's solution below (https://stackoverflow.com/a/7557433/5628) if you do not need to support IE<7.



                          Original solution (now outdated):



                          This will check if the element is entirely visible in the current viewport:



                          function elementInViewport(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top >= window.pageYOffset &&
                          left >= window.pageXOffset &&
                          (top + height) <= (window.pageYOffset + window.innerHeight) &&
                          (left + width) <= (window.pageXOffset + window.innerWidth)
                          );
                          }


                          You could modify this simply to determine if any part of the element is visible in the viewport:



                          function elementInViewport2(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top < (window.pageYOffset + window.innerHeight) &&
                          left < (window.pageXOffset + window.innerWidth) &&
                          (top + height) > window.pageYOffset &&
                          (left + width) > window.pageXOffset
                          );
                          }





                          share|improve this answer





















                          • 1





                            Original function posted had a mistake. Needed to save the width/height before reassigning el...

                            – Prestaul
                            Sep 24 '08 at 2:56






                          • 9





                            What if the element lives in a scrollable div and scrolled out of a view??

                            – amartynov
                            Mar 6 '11 at 8:42






                          • 2





                            Please review a newer version of the script below

                            – Dan
                            Sep 26 '11 at 15:29






                          • 1





                            Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                            – Eric Nguyen
                            Nov 7 '12 at 23:51






                          • 1





                            @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                            – Prestaul
                            Jul 6 '15 at 15:25














                          304












                          304








                          304







                          Update: Time marches on and so have our browsers. This technique is no longer recommended and you should use @Dan's solution below (https://stackoverflow.com/a/7557433/5628) if you do not need to support IE<7.



                          Original solution (now outdated):



                          This will check if the element is entirely visible in the current viewport:



                          function elementInViewport(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top >= window.pageYOffset &&
                          left >= window.pageXOffset &&
                          (top + height) <= (window.pageYOffset + window.innerHeight) &&
                          (left + width) <= (window.pageXOffset + window.innerWidth)
                          );
                          }


                          You could modify this simply to determine if any part of the element is visible in the viewport:



                          function elementInViewport2(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top < (window.pageYOffset + window.innerHeight) &&
                          left < (window.pageXOffset + window.innerWidth) &&
                          (top + height) > window.pageYOffset &&
                          (left + width) > window.pageXOffset
                          );
                          }





                          share|improve this answer















                          Update: Time marches on and so have our browsers. This technique is no longer recommended and you should use @Dan's solution below (https://stackoverflow.com/a/7557433/5628) if you do not need to support IE<7.



                          Original solution (now outdated):



                          This will check if the element is entirely visible in the current viewport:



                          function elementInViewport(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top >= window.pageYOffset &&
                          left >= window.pageXOffset &&
                          (top + height) <= (window.pageYOffset + window.innerHeight) &&
                          (left + width) <= (window.pageXOffset + window.innerWidth)
                          );
                          }


                          You could modify this simply to determine if any part of the element is visible in the viewport:



                          function elementInViewport2(el) {
                          var top = el.offsetTop;
                          var left = el.offsetLeft;
                          var width = el.offsetWidth;
                          var height = el.offsetHeight;

                          while(el.offsetParent) {
                          el = el.offsetParent;
                          top += el.offsetTop;
                          left += el.offsetLeft;
                          }

                          return (
                          top < (window.pageYOffset + window.innerHeight) &&
                          left < (window.pageXOffset + window.innerWidth) &&
                          (top + height) > window.pageYOffset &&
                          (left + width) > window.pageXOffset
                          );
                          }






                          share|improve this answer














                          share|improve this answer



                          share|improve this answer








                          edited May 23 '17 at 12:10









                          Community

                          11




                          11










                          answered Sep 24 '08 at 2:40









                          PrestaulPrestaul

                          65.6k96880




                          65.6k96880








                          • 1





                            Original function posted had a mistake. Needed to save the width/height before reassigning el...

                            – Prestaul
                            Sep 24 '08 at 2:56






                          • 9





                            What if the element lives in a scrollable div and scrolled out of a view??

                            – amartynov
                            Mar 6 '11 at 8:42






                          • 2





                            Please review a newer version of the script below

                            – Dan
                            Sep 26 '11 at 15:29






                          • 1





                            Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                            – Eric Nguyen
                            Nov 7 '12 at 23:51






                          • 1





                            @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                            – Prestaul
                            Jul 6 '15 at 15:25














                          • 1





                            Original function posted had a mistake. Needed to save the width/height before reassigning el...

                            – Prestaul
                            Sep 24 '08 at 2:56






                          • 9





                            What if the element lives in a scrollable div and scrolled out of a view??

                            – amartynov
                            Mar 6 '11 at 8:42






                          • 2





                            Please review a newer version of the script below

                            – Dan
                            Sep 26 '11 at 15:29






                          • 1





                            Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                            – Eric Nguyen
                            Nov 7 '12 at 23:51






                          • 1





                            @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                            – Prestaul
                            Jul 6 '15 at 15:25








                          1




                          1





                          Original function posted had a mistake. Needed to save the width/height before reassigning el...

                          – Prestaul
                          Sep 24 '08 at 2:56





                          Original function posted had a mistake. Needed to save the width/height before reassigning el...

                          – Prestaul
                          Sep 24 '08 at 2:56




                          9




                          9





                          What if the element lives in a scrollable div and scrolled out of a view??

                          – amartynov
                          Mar 6 '11 at 8:42





                          What if the element lives in a scrollable div and scrolled out of a view??

                          – amartynov
                          Mar 6 '11 at 8:42




                          2




                          2





                          Please review a newer version of the script below

                          – Dan
                          Sep 26 '11 at 15:29





                          Please review a newer version of the script below

                          – Dan
                          Sep 26 '11 at 15:29




                          1




                          1





                          Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                          – Eric Nguyen
                          Nov 7 '12 at 23:51





                          Also curious about @amartynov's question. Anyone know how to simply tell if an element is hidden due to overflow of an ancestor element? Bonus if this can be detected regardless of how deeply nested the child is.

                          – Eric Nguyen
                          Nov 7 '12 at 23:51




                          1




                          1





                          @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                          – Prestaul
                          Jul 6 '15 at 15:25





                          @deadManN recursing through the DOM is notoriously slow. That is reason enough, but the browser vendors have also created getBoundingClientRect for specifically the purpose of finding element coordinates... Why wouldn't we use it?

                          – Prestaul
                          Jul 6 '15 at 15:25













                          1236














                          Now most browsers support getBoundingClientRect method, which has become the best practice. Using an old answer is very slow, not accurate and has several bugs.



                          The solution selected as correct is almost never precise. You can read more about its bugs.





                          This solution was tested on IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, and IE Mobile 10.





                          function isElementInViewport (el) {

                          //special bonus for those using jQuery
                          if (typeof jQuery === "function" && el instanceof jQuery) {
                          el = el[0];
                          }

                          var rect = el.getBoundingClientRect();

                          return (
                          rect.top >= 0 &&
                          rect.left >= 0 &&
                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
                          rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
                          );
                          }




                          How to use:



                          You can be sure that the function given above returns correct answer at the moment of time when it is called, but what about tracking element's visibility as an event?



                          Place the following code at the bottom of your <body> tag:



                          function onVisibilityChange(el, callback) {
                          var old_visible;
                          return function () {
                          var visible = isElementInViewport(el);
                          if (visible != old_visible) {
                          old_visible = visible;
                          if (typeof callback == 'function') {
                          callback();
                          }
                          }
                          }
                          }

                          var handler = onVisibilityChange(el, function() {
                          /* your code go here */
                          });


                          //jQuery
                          $(window).on('DOMContentLoaded load resize scroll', handler);

                          /* //non-jQuery
                          if (window.addEventListener) {
                          addEventListener('DOMContentLoaded', handler, false);
                          addEventListener('load', handler, false);
                          addEventListener('scroll', handler, false);
                          addEventListener('resize', handler, false);
                          } else if (window.attachEvent) {
                          attachEvent('onDOMContentLoaded', handler); // IE9+ :(
                          attachEvent('onload', handler);
                          attachEvent('onscroll', handler);
                          attachEvent('onresize', handler);
                          }
                          */




                          If you do any DOM modifications, they can change your element's visibility of course.



                          Guidelines and common pitfalls:



                          Maybe you need to track page zoom / mobile device pinch? jQuery should handle zoom/pinch cross browser, otherwise first or second link should help you.



                          If you modify DOM, it can affect the element's visibility. You should take control over that and call handler() manually. Unfortunately, we have no cross browser onrepaint event. On the other hand that allows us to make optimizations and perform re-check only on DOM modifications that can change element's visibility.



                          Never Ever use it inside jQuery $(document).ready() only, because there is no warranty CSS has been applied in this moment. Your code can work locally with your CSS on hard drive, but once put on remote server it will fail.



                          After DOMContentLoaded is fired, styles are applied, but the images are not loaded yet. So, we should add window.onload event listener.



                          We can't catch zoom/pinch event yet.



                          The last resort could be the following code:



                          /* TODO: this looks like a very bad code */
                          setInterval(handler, 600);


                          You can use awesome feature pageVisibiliy HTML5 API if you care if the tab with your web page is active and visible.



                          TODO: this method does not handle two situations:




                          • overlapping using z-index

                          • using overflow-scroll in element's container


                          • try something new https://pawelgrzybek.com/the-intersection-observer-api-explained/







                          share|improve this answer





















                          • 5





                            I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                            – Claudio
                            Oct 20 '11 at 12:38








                          • 4





                            Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                            – agaase
                            Dec 8 '13 at 9:04






                          • 53





                            The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                            – Roonaan
                            Feb 21 '14 at 7:29








                          • 9





                            Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                            – jiminy
                            Apr 12 '14 at 7:44






                          • 7





                            el is not defined

                            – M_Willett
                            Oct 18 '16 at 10:47
















                          1236














                          Now most browsers support getBoundingClientRect method, which has become the best practice. Using an old answer is very slow, not accurate and has several bugs.



                          The solution selected as correct is almost never precise. You can read more about its bugs.





                          This solution was tested on IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, and IE Mobile 10.





                          function isElementInViewport (el) {

                          //special bonus for those using jQuery
                          if (typeof jQuery === "function" && el instanceof jQuery) {
                          el = el[0];
                          }

                          var rect = el.getBoundingClientRect();

                          return (
                          rect.top >= 0 &&
                          rect.left >= 0 &&
                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
                          rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
                          );
                          }




                          How to use:



                          You can be sure that the function given above returns correct answer at the moment of time when it is called, but what about tracking element's visibility as an event?



                          Place the following code at the bottom of your <body> tag:



                          function onVisibilityChange(el, callback) {
                          var old_visible;
                          return function () {
                          var visible = isElementInViewport(el);
                          if (visible != old_visible) {
                          old_visible = visible;
                          if (typeof callback == 'function') {
                          callback();
                          }
                          }
                          }
                          }

                          var handler = onVisibilityChange(el, function() {
                          /* your code go here */
                          });


                          //jQuery
                          $(window).on('DOMContentLoaded load resize scroll', handler);

                          /* //non-jQuery
                          if (window.addEventListener) {
                          addEventListener('DOMContentLoaded', handler, false);
                          addEventListener('load', handler, false);
                          addEventListener('scroll', handler, false);
                          addEventListener('resize', handler, false);
                          } else if (window.attachEvent) {
                          attachEvent('onDOMContentLoaded', handler); // IE9+ :(
                          attachEvent('onload', handler);
                          attachEvent('onscroll', handler);
                          attachEvent('onresize', handler);
                          }
                          */




                          If you do any DOM modifications, they can change your element's visibility of course.



                          Guidelines and common pitfalls:



                          Maybe you need to track page zoom / mobile device pinch? jQuery should handle zoom/pinch cross browser, otherwise first or second link should help you.



                          If you modify DOM, it can affect the element's visibility. You should take control over that and call handler() manually. Unfortunately, we have no cross browser onrepaint event. On the other hand that allows us to make optimizations and perform re-check only on DOM modifications that can change element's visibility.



                          Never Ever use it inside jQuery $(document).ready() only, because there is no warranty CSS has been applied in this moment. Your code can work locally with your CSS on hard drive, but once put on remote server it will fail.



                          After DOMContentLoaded is fired, styles are applied, but the images are not loaded yet. So, we should add window.onload event listener.



                          We can't catch zoom/pinch event yet.



                          The last resort could be the following code:



                          /* TODO: this looks like a very bad code */
                          setInterval(handler, 600);


                          You can use awesome feature pageVisibiliy HTML5 API if you care if the tab with your web page is active and visible.



                          TODO: this method does not handle two situations:




                          • overlapping using z-index

                          • using overflow-scroll in element's container


                          • try something new https://pawelgrzybek.com/the-intersection-observer-api-explained/







                          share|improve this answer





















                          • 5





                            I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                            – Claudio
                            Oct 20 '11 at 12:38








                          • 4





                            Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                            – agaase
                            Dec 8 '13 at 9:04






                          • 53





                            The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                            – Roonaan
                            Feb 21 '14 at 7:29








                          • 9





                            Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                            – jiminy
                            Apr 12 '14 at 7:44






                          • 7





                            el is not defined

                            – M_Willett
                            Oct 18 '16 at 10:47














                          1236












                          1236








                          1236







                          Now most browsers support getBoundingClientRect method, which has become the best practice. Using an old answer is very slow, not accurate and has several bugs.



                          The solution selected as correct is almost never precise. You can read more about its bugs.





                          This solution was tested on IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, and IE Mobile 10.





                          function isElementInViewport (el) {

                          //special bonus for those using jQuery
                          if (typeof jQuery === "function" && el instanceof jQuery) {
                          el = el[0];
                          }

                          var rect = el.getBoundingClientRect();

                          return (
                          rect.top >= 0 &&
                          rect.left >= 0 &&
                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
                          rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
                          );
                          }




                          How to use:



                          You can be sure that the function given above returns correct answer at the moment of time when it is called, but what about tracking element's visibility as an event?



                          Place the following code at the bottom of your <body> tag:



                          function onVisibilityChange(el, callback) {
                          var old_visible;
                          return function () {
                          var visible = isElementInViewport(el);
                          if (visible != old_visible) {
                          old_visible = visible;
                          if (typeof callback == 'function') {
                          callback();
                          }
                          }
                          }
                          }

                          var handler = onVisibilityChange(el, function() {
                          /* your code go here */
                          });


                          //jQuery
                          $(window).on('DOMContentLoaded load resize scroll', handler);

                          /* //non-jQuery
                          if (window.addEventListener) {
                          addEventListener('DOMContentLoaded', handler, false);
                          addEventListener('load', handler, false);
                          addEventListener('scroll', handler, false);
                          addEventListener('resize', handler, false);
                          } else if (window.attachEvent) {
                          attachEvent('onDOMContentLoaded', handler); // IE9+ :(
                          attachEvent('onload', handler);
                          attachEvent('onscroll', handler);
                          attachEvent('onresize', handler);
                          }
                          */




                          If you do any DOM modifications, they can change your element's visibility of course.



                          Guidelines and common pitfalls:



                          Maybe you need to track page zoom / mobile device pinch? jQuery should handle zoom/pinch cross browser, otherwise first or second link should help you.



                          If you modify DOM, it can affect the element's visibility. You should take control over that and call handler() manually. Unfortunately, we have no cross browser onrepaint event. On the other hand that allows us to make optimizations and perform re-check only on DOM modifications that can change element's visibility.



                          Never Ever use it inside jQuery $(document).ready() only, because there is no warranty CSS has been applied in this moment. Your code can work locally with your CSS on hard drive, but once put on remote server it will fail.



                          After DOMContentLoaded is fired, styles are applied, but the images are not loaded yet. So, we should add window.onload event listener.



                          We can't catch zoom/pinch event yet.



                          The last resort could be the following code:



                          /* TODO: this looks like a very bad code */
                          setInterval(handler, 600);


                          You can use awesome feature pageVisibiliy HTML5 API if you care if the tab with your web page is active and visible.



                          TODO: this method does not handle two situations:




                          • overlapping using z-index

                          • using overflow-scroll in element's container


                          • try something new https://pawelgrzybek.com/the-intersection-observer-api-explained/







                          share|improve this answer















                          Now most browsers support getBoundingClientRect method, which has become the best practice. Using an old answer is very slow, not accurate and has several bugs.



                          The solution selected as correct is almost never precise. You can read more about its bugs.





                          This solution was tested on IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, and IE Mobile 10.





                          function isElementInViewport (el) {

                          //special bonus for those using jQuery
                          if (typeof jQuery === "function" && el instanceof jQuery) {
                          el = el[0];
                          }

                          var rect = el.getBoundingClientRect();

                          return (
                          rect.top >= 0 &&
                          rect.left >= 0 &&
                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
                          rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
                          );
                          }




                          How to use:



                          You can be sure that the function given above returns correct answer at the moment of time when it is called, but what about tracking element's visibility as an event?



                          Place the following code at the bottom of your <body> tag:



                          function onVisibilityChange(el, callback) {
                          var old_visible;
                          return function () {
                          var visible = isElementInViewport(el);
                          if (visible != old_visible) {
                          old_visible = visible;
                          if (typeof callback == 'function') {
                          callback();
                          }
                          }
                          }
                          }

                          var handler = onVisibilityChange(el, function() {
                          /* your code go here */
                          });


                          //jQuery
                          $(window).on('DOMContentLoaded load resize scroll', handler);

                          /* //non-jQuery
                          if (window.addEventListener) {
                          addEventListener('DOMContentLoaded', handler, false);
                          addEventListener('load', handler, false);
                          addEventListener('scroll', handler, false);
                          addEventListener('resize', handler, false);
                          } else if (window.attachEvent) {
                          attachEvent('onDOMContentLoaded', handler); // IE9+ :(
                          attachEvent('onload', handler);
                          attachEvent('onscroll', handler);
                          attachEvent('onresize', handler);
                          }
                          */




                          If you do any DOM modifications, they can change your element's visibility of course.



                          Guidelines and common pitfalls:



                          Maybe you need to track page zoom / mobile device pinch? jQuery should handle zoom/pinch cross browser, otherwise first or second link should help you.



                          If you modify DOM, it can affect the element's visibility. You should take control over that and call handler() manually. Unfortunately, we have no cross browser onrepaint event. On the other hand that allows us to make optimizations and perform re-check only on DOM modifications that can change element's visibility.



                          Never Ever use it inside jQuery $(document).ready() only, because there is no warranty CSS has been applied in this moment. Your code can work locally with your CSS on hard drive, but once put on remote server it will fail.



                          After DOMContentLoaded is fired, styles are applied, but the images are not loaded yet. So, we should add window.onload event listener.



                          We can't catch zoom/pinch event yet.



                          The last resort could be the following code:



                          /* TODO: this looks like a very bad code */
                          setInterval(handler, 600);


                          You can use awesome feature pageVisibiliy HTML5 API if you care if the tab with your web page is active and visible.



                          TODO: this method does not handle two situations:




                          • overlapping using z-index

                          • using overflow-scroll in element's container


                          • try something new https://pawelgrzybek.com/the-intersection-observer-api-explained/








                          share|improve this answer














                          share|improve this answer



                          share|improve this answer








                          edited May 23 '17 at 12:34


























                          community wiki





                          27 revs, 7 users 92%
                          Dan









                          • 5





                            I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                            – Claudio
                            Oct 20 '11 at 12:38








                          • 4





                            Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                            – agaase
                            Dec 8 '13 at 9:04






                          • 53





                            The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                            – Roonaan
                            Feb 21 '14 at 7:29








                          • 9





                            Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                            – jiminy
                            Apr 12 '14 at 7:44






                          • 7





                            el is not defined

                            – M_Willett
                            Oct 18 '16 at 10:47














                          • 5





                            I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                            – Claudio
                            Oct 20 '11 at 12:38








                          • 4





                            Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                            – agaase
                            Dec 8 '13 at 9:04






                          • 53





                            The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                            – Roonaan
                            Feb 21 '14 at 7:29








                          • 9





                            Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                            – jiminy
                            Apr 12 '14 at 7:44






                          • 7





                            el is not defined

                            – M_Willett
                            Oct 18 '16 at 10:47








                          5




                          5





                          I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                          – Claudio
                          Oct 20 '11 at 12:38







                          I'm using this solution (beware the "botom" typo, though). There is also something to be aware of, when the element we're considering would have images into it. Chrome (at least) must wait for the image to be loaded to have the exact value for the boundingRectangle. Seems that Firefox does not have this "problem"

                          – Claudio
                          Oct 20 '11 at 12:38






                          4




                          4





                          Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                          – agaase
                          Dec 8 '13 at 9:04





                          Does it work when you have scrolling enabled in a container inside body. For e.g it doesn't work here - agaase.github.io/webpages/demo/isonscreen2.html isElementInViewport(document.getElementById("innerele")). innerele is present inside a container which has scrolling enabled.

                          – agaase
                          Dec 8 '13 at 9:04




                          53




                          53





                          The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                          – Roonaan
                          Feb 21 '14 at 7:29







                          The calculations assume that the element is smaller than the screen. If you have high or wide elements, it might be more accurate to use return (rect.bottom >= 0 && rect.right >= 0 && rect.top <= (window.innerHeight || document.documentElement.clientHeight) && rect.left <= (window.innerWidth || document.documentElement.clientWidth));

                          – Roonaan
                          Feb 21 '14 at 7:29






                          9




                          9





                          Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                          – jiminy
                          Apr 12 '14 at 7:44





                          Tip: To those trying to implement this with jQuery, just a friendly reminder to pass in the HTML DOM object (e.g., isElementInViewport(document.getElementById('elem'))) and not the jQuery object (e.g., isElementInViewport($("#elem))). The jQuery equivalent is to add [0] like so: isElementInViewport($("#elem)[0]).

                          – jiminy
                          Apr 12 '14 at 7:44




                          7




                          7





                          el is not defined

                          – M_Willett
                          Oct 18 '16 at 10:47





                          el is not defined

                          – M_Willett
                          Oct 18 '16 at 10:47











                          141














                          Update



                          In modern browsers, you might want to check out the Intersection Observer API which provides the following benefits:




                          • Better performance than listening for scroll events

                          • Works in cross domain iframes

                          • Can tell if an element is obstructing/intersecting another


                          Intersection Observer is on its way to being a full-fledged standard and is already supported in Chrome 51+, Edge 15+ and Firefox 55+ and is under development for Safari. There's also a polyfill available.





                          Previous answer



                          There are some issues with the answer provided by Dan that might make it an unsuitable approach for some situations. Some of these issues are pointed out in his answer near the bottom, that his code will give false positives for elements that are:




                          • Hidden by another element in front of the one being tested

                          • Outside the visible area of a parent or ancestor element

                          • An element or its children hidden by using the CSS clip property


                          These limitations are demonstrated in the following results of a simple test:



                          Failed test, using isElementInViewport



                          The solution: isElementVisible()



                          Here's a solution to those problems, with the test result below and an explanation of some parts of the code.



                          function isElementVisible(el) {
                          var rect = el.getBoundingClientRect(),
                          vWidth = window.innerWidth || doc.documentElement.clientWidth,
                          vHeight = window.innerHeight || doc.documentElement.clientHeight,
                          efp = function (x, y) { return document.elementFromPoint(x, y) };

                          // Return false if it's not in the viewport
                          if (rect.right < 0 || rect.bottom < 0
                          || rect.left > vWidth || rect.top > vHeight)
                          return false;

                          // Return true if any of its four corners are visible
                          return (
                          el.contains(efp(rect.left, rect.top))
                          || el.contains(efp(rect.right, rect.top))
                          || el.contains(efp(rect.right, rect.bottom))
                          || el.contains(efp(rect.left, rect.bottom))
                          );
                          }



                          Passing test: http://jsfiddle.net/AndyE/cAY8c/




                          And the result:



                          Passed test, using isElementVisible



                          Additional notes



                          This method is not without its own limitations, however. For instance, an element being tested with a lower z-index than another element at the same location would be identified as hidden even if the element in front doesn't actually hide any part of it. Still, this method has its uses in some cases that Dan's solution doesn't cover.



                          Both element.getBoundingClientRect() and document.elementFromPoint() are part of the CSSOM Working Draft specification and are supported in at least IE 6 and later and most desktop browsers for a long time (albeit, not perfectly). See Quirksmode on these functions for more information.



                          contains() is used to see if the element returned by document.elementFromPoint() is a child node of the element we're testing for visibility. It also returns true if the element returned is the same element. This just makes the check more robust. It's supported in all major browsers, Firefox 9.0 being the last of them to add it. For older Firefox support, check this answer's history.



                          If you want to test more points around the element for visibility―ie, to make sure the element isn't covered by more than, say, 50%―it wouldn't take much to adjust the last part of the answer. However, be aware that it would probably be very slow if you checked every pixel to make sure it was 100% visible.






                          share|improve this answer





















                          • 1





                            Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                            – Kevin Lamping
                            Mar 19 '13 at 19:34













                          • @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                            – Andy E
                            Mar 19 '13 at 20:14






                          • 1





                            For me it is not working. But inViewport() in previous answer is working in FF.

                            – Satya Prakash
                            Dec 28 '13 at 7:05






                          • 8





                            It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                            – Jared
                            Mar 10 '15 at 8:15








                          • 1





                            Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                            – Rayjax
                            Feb 18 '16 at 14:05
















                          141














                          Update



                          In modern browsers, you might want to check out the Intersection Observer API which provides the following benefits:




                          • Better performance than listening for scroll events

                          • Works in cross domain iframes

                          • Can tell if an element is obstructing/intersecting another


                          Intersection Observer is on its way to being a full-fledged standard and is already supported in Chrome 51+, Edge 15+ and Firefox 55+ and is under development for Safari. There's also a polyfill available.





                          Previous answer



                          There are some issues with the answer provided by Dan that might make it an unsuitable approach for some situations. Some of these issues are pointed out in his answer near the bottom, that his code will give false positives for elements that are:




                          • Hidden by another element in front of the one being tested

                          • Outside the visible area of a parent or ancestor element

                          • An element or its children hidden by using the CSS clip property


                          These limitations are demonstrated in the following results of a simple test:



                          Failed test, using isElementInViewport



                          The solution: isElementVisible()



                          Here's a solution to those problems, with the test result below and an explanation of some parts of the code.



                          function isElementVisible(el) {
                          var rect = el.getBoundingClientRect(),
                          vWidth = window.innerWidth || doc.documentElement.clientWidth,
                          vHeight = window.innerHeight || doc.documentElement.clientHeight,
                          efp = function (x, y) { return document.elementFromPoint(x, y) };

                          // Return false if it's not in the viewport
                          if (rect.right < 0 || rect.bottom < 0
                          || rect.left > vWidth || rect.top > vHeight)
                          return false;

                          // Return true if any of its four corners are visible
                          return (
                          el.contains(efp(rect.left, rect.top))
                          || el.contains(efp(rect.right, rect.top))
                          || el.contains(efp(rect.right, rect.bottom))
                          || el.contains(efp(rect.left, rect.bottom))
                          );
                          }



                          Passing test: http://jsfiddle.net/AndyE/cAY8c/




                          And the result:



                          Passed test, using isElementVisible



                          Additional notes



                          This method is not without its own limitations, however. For instance, an element being tested with a lower z-index than another element at the same location would be identified as hidden even if the element in front doesn't actually hide any part of it. Still, this method has its uses in some cases that Dan's solution doesn't cover.



                          Both element.getBoundingClientRect() and document.elementFromPoint() are part of the CSSOM Working Draft specification and are supported in at least IE 6 and later and most desktop browsers for a long time (albeit, not perfectly). See Quirksmode on these functions for more information.



                          contains() is used to see if the element returned by document.elementFromPoint() is a child node of the element we're testing for visibility. It also returns true if the element returned is the same element. This just makes the check more robust. It's supported in all major browsers, Firefox 9.0 being the last of them to add it. For older Firefox support, check this answer's history.



                          If you want to test more points around the element for visibility―ie, to make sure the element isn't covered by more than, say, 50%―it wouldn't take much to adjust the last part of the answer. However, be aware that it would probably be very slow if you checked every pixel to make sure it was 100% visible.






                          share|improve this answer





















                          • 1





                            Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                            – Kevin Lamping
                            Mar 19 '13 at 19:34













                          • @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                            – Andy E
                            Mar 19 '13 at 20:14






                          • 1





                            For me it is not working. But inViewport() in previous answer is working in FF.

                            – Satya Prakash
                            Dec 28 '13 at 7:05






                          • 8





                            It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                            – Jared
                            Mar 10 '15 at 8:15








                          • 1





                            Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                            – Rayjax
                            Feb 18 '16 at 14:05














                          141












                          141








                          141







                          Update



                          In modern browsers, you might want to check out the Intersection Observer API which provides the following benefits:




                          • Better performance than listening for scroll events

                          • Works in cross domain iframes

                          • Can tell if an element is obstructing/intersecting another


                          Intersection Observer is on its way to being a full-fledged standard and is already supported in Chrome 51+, Edge 15+ and Firefox 55+ and is under development for Safari. There's also a polyfill available.





                          Previous answer



                          There are some issues with the answer provided by Dan that might make it an unsuitable approach for some situations. Some of these issues are pointed out in his answer near the bottom, that his code will give false positives for elements that are:




                          • Hidden by another element in front of the one being tested

                          • Outside the visible area of a parent or ancestor element

                          • An element or its children hidden by using the CSS clip property


                          These limitations are demonstrated in the following results of a simple test:



                          Failed test, using isElementInViewport



                          The solution: isElementVisible()



                          Here's a solution to those problems, with the test result below and an explanation of some parts of the code.



                          function isElementVisible(el) {
                          var rect = el.getBoundingClientRect(),
                          vWidth = window.innerWidth || doc.documentElement.clientWidth,
                          vHeight = window.innerHeight || doc.documentElement.clientHeight,
                          efp = function (x, y) { return document.elementFromPoint(x, y) };

                          // Return false if it's not in the viewport
                          if (rect.right < 0 || rect.bottom < 0
                          || rect.left > vWidth || rect.top > vHeight)
                          return false;

                          // Return true if any of its four corners are visible
                          return (
                          el.contains(efp(rect.left, rect.top))
                          || el.contains(efp(rect.right, rect.top))
                          || el.contains(efp(rect.right, rect.bottom))
                          || el.contains(efp(rect.left, rect.bottom))
                          );
                          }



                          Passing test: http://jsfiddle.net/AndyE/cAY8c/




                          And the result:



                          Passed test, using isElementVisible



                          Additional notes



                          This method is not without its own limitations, however. For instance, an element being tested with a lower z-index than another element at the same location would be identified as hidden even if the element in front doesn't actually hide any part of it. Still, this method has its uses in some cases that Dan's solution doesn't cover.



                          Both element.getBoundingClientRect() and document.elementFromPoint() are part of the CSSOM Working Draft specification and are supported in at least IE 6 and later and most desktop browsers for a long time (albeit, not perfectly). See Quirksmode on these functions for more information.



                          contains() is used to see if the element returned by document.elementFromPoint() is a child node of the element we're testing for visibility. It also returns true if the element returned is the same element. This just makes the check more robust. It's supported in all major browsers, Firefox 9.0 being the last of them to add it. For older Firefox support, check this answer's history.



                          If you want to test more points around the element for visibility―ie, to make sure the element isn't covered by more than, say, 50%―it wouldn't take much to adjust the last part of the answer. However, be aware that it would probably be very slow if you checked every pixel to make sure it was 100% visible.






                          share|improve this answer















                          Update



                          In modern browsers, you might want to check out the Intersection Observer API which provides the following benefits:




                          • Better performance than listening for scroll events

                          • Works in cross domain iframes

                          • Can tell if an element is obstructing/intersecting another


                          Intersection Observer is on its way to being a full-fledged standard and is already supported in Chrome 51+, Edge 15+ and Firefox 55+ and is under development for Safari. There's also a polyfill available.





                          Previous answer



                          There are some issues with the answer provided by Dan that might make it an unsuitable approach for some situations. Some of these issues are pointed out in his answer near the bottom, that his code will give false positives for elements that are:




                          • Hidden by another element in front of the one being tested

                          • Outside the visible area of a parent or ancestor element

                          • An element or its children hidden by using the CSS clip property


                          These limitations are demonstrated in the following results of a simple test:



                          Failed test, using isElementInViewport



                          The solution: isElementVisible()



                          Here's a solution to those problems, with the test result below and an explanation of some parts of the code.



                          function isElementVisible(el) {
                          var rect = el.getBoundingClientRect(),
                          vWidth = window.innerWidth || doc.documentElement.clientWidth,
                          vHeight = window.innerHeight || doc.documentElement.clientHeight,
                          efp = function (x, y) { return document.elementFromPoint(x, y) };

                          // Return false if it's not in the viewport
                          if (rect.right < 0 || rect.bottom < 0
                          || rect.left > vWidth || rect.top > vHeight)
                          return false;

                          // Return true if any of its four corners are visible
                          return (
                          el.contains(efp(rect.left, rect.top))
                          || el.contains(efp(rect.right, rect.top))
                          || el.contains(efp(rect.right, rect.bottom))
                          || el.contains(efp(rect.left, rect.bottom))
                          );
                          }



                          Passing test: http://jsfiddle.net/AndyE/cAY8c/




                          And the result:



                          Passed test, using isElementVisible



                          Additional notes



                          This method is not without its own limitations, however. For instance, an element being tested with a lower z-index than another element at the same location would be identified as hidden even if the element in front doesn't actually hide any part of it. Still, this method has its uses in some cases that Dan's solution doesn't cover.



                          Both element.getBoundingClientRect() and document.elementFromPoint() are part of the CSSOM Working Draft specification and are supported in at least IE 6 and later and most desktop browsers for a long time (albeit, not perfectly). See Quirksmode on these functions for more information.



                          contains() is used to see if the element returned by document.elementFromPoint() is a child node of the element we're testing for visibility. It also returns true if the element returned is the same element. This just makes the check more robust. It's supported in all major browsers, Firefox 9.0 being the last of them to add it. For older Firefox support, check this answer's history.



                          If you want to test more points around the element for visibility―ie, to make sure the element isn't covered by more than, say, 50%―it wouldn't take much to adjust the last part of the answer. However, be aware that it would probably be very slow if you checked every pixel to make sure it was 100% visible.







                          share|improve this answer














                          share|improve this answer



                          share|improve this answer








                          edited Dec 13 '17 at 12:08

























                          answered Mar 4 '13 at 14:18









                          Andy EAndy E

                          262k67416417




                          262k67416417








                          • 1





                            Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                            – Kevin Lamping
                            Mar 19 '13 at 19:34













                          • @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                            – Andy E
                            Mar 19 '13 at 20:14






                          • 1





                            For me it is not working. But inViewport() in previous answer is working in FF.

                            – Satya Prakash
                            Dec 28 '13 at 7:05






                          • 8





                            It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                            – Jared
                            Mar 10 '15 at 8:15








                          • 1





                            Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                            – Rayjax
                            Feb 18 '16 at 14:05














                          • 1





                            Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                            – Kevin Lamping
                            Mar 19 '13 at 19:34













                          • @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                            – Andy E
                            Mar 19 '13 at 20:14






                          • 1





                            For me it is not working. But inViewport() in previous answer is working in FF.

                            – Satya Prakash
                            Dec 28 '13 at 7:05






                          • 8





                            It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                            – Jared
                            Mar 10 '15 at 8:15








                          • 1





                            Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                            – Rayjax
                            Feb 18 '16 at 14:05








                          1




                          1





                          Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                          – Kevin Lamping
                          Mar 19 '13 at 19:34







                          Did you mean to use doc.documentElement.clientWidth? Should that be 'document.documentElement' instead? On a different note, this is the only method the also works for use cases like hiding the content of an element for accessibility using the CSS 'clip' property: snook.ca/archives/html_and_css/hiding-content-for-accessibility

                          – Kevin Lamping
                          Mar 19 '13 at 19:34















                          @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                          – Andy E
                          Mar 19 '13 at 20:14





                          @klamping: good catch, thanks. I'd copied it right out of my code where I was using doc as an alias for document. Yeah, I like to think of this as a decent solution for the edge cases.

                          – Andy E
                          Mar 19 '13 at 20:14




                          1




                          1





                          For me it is not working. But inViewport() in previous answer is working in FF.

                          – Satya Prakash
                          Dec 28 '13 at 7:05





                          For me it is not working. But inViewport() in previous answer is working in FF.

                          – Satya Prakash
                          Dec 28 '13 at 7:05




                          8




                          8





                          It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                          – Jared
                          Mar 10 '15 at 8:15







                          It may also be beneficial to check that the center of the element is visible if you have rounded corners or a transform applied, as the bounding corners may not return the expected element: element.contains(efp(rect.right - (rect.width / 2), rect.bottom - (rect.height / 2)))

                          – Jared
                          Mar 10 '15 at 8:15






                          1




                          1





                          Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                          – Rayjax
                          Feb 18 '16 at 14:05





                          Did not work on inputs for me (chrome canary 50). Not sure why, maybe native rounder corners ? I had to reduce the coords slightly to make it work el.contains(efp(rect.left+1, rect.top+1)) || el.contains(efp(rect.right-1, rect.top+1)) || el.contains(efp(rect.right-1, rect.bottom-1)) || el.contains(efp(rect.left+1, rect.bottom-1))

                          – Rayjax
                          Feb 18 '16 at 14:05











                          51














                          I tried Dan's answer however the algebra used to determine the bounds means that the element must be both ≤ the viewport size and completely inside the viewport to get true, easily leading to false negatives. If you want to determine whether an element is in the viewport at all, ryanve's answer is close but the element being tested should overlap the viewport, so try this:



                          function isElementInViewport(el) {
                          var rect = el.getBoundingClientRect();

                          return rect.bottom > 0 &&
                          rect.right > 0 &&
                          rect.left < (window.innerWidth || document.documentElement.clientWidth) /* or $(window).width() */ &&
                          rect.top < (window.innerHeight || document.documentElement.clientHeight) /* or $(window).height() */;
                          }





                          share|improve this answer






























                            51














                            I tried Dan's answer however the algebra used to determine the bounds means that the element must be both ≤ the viewport size and completely inside the viewport to get true, easily leading to false negatives. If you want to determine whether an element is in the viewport at all, ryanve's answer is close but the element being tested should overlap the viewport, so try this:



                            function isElementInViewport(el) {
                            var rect = el.getBoundingClientRect();

                            return rect.bottom > 0 &&
                            rect.right > 0 &&
                            rect.left < (window.innerWidth || document.documentElement.clientWidth) /* or $(window).width() */ &&
                            rect.top < (window.innerHeight || document.documentElement.clientHeight) /* or $(window).height() */;
                            }





                            share|improve this answer




























                              51












                              51








                              51







                              I tried Dan's answer however the algebra used to determine the bounds means that the element must be both ≤ the viewport size and completely inside the viewport to get true, easily leading to false negatives. If you want to determine whether an element is in the viewport at all, ryanve's answer is close but the element being tested should overlap the viewport, so try this:



                              function isElementInViewport(el) {
                              var rect = el.getBoundingClientRect();

                              return rect.bottom > 0 &&
                              rect.right > 0 &&
                              rect.left < (window.innerWidth || document.documentElement.clientWidth) /* or $(window).width() */ &&
                              rect.top < (window.innerHeight || document.documentElement.clientHeight) /* or $(window).height() */;
                              }





                              share|improve this answer















                              I tried Dan's answer however the algebra used to determine the bounds means that the element must be both ≤ the viewport size and completely inside the viewport to get true, easily leading to false negatives. If you want to determine whether an element is in the viewport at all, ryanve's answer is close but the element being tested should overlap the viewport, so try this:



                              function isElementInViewport(el) {
                              var rect = el.getBoundingClientRect();

                              return rect.bottom > 0 &&
                              rect.right > 0 &&
                              rect.left < (window.innerWidth || document.documentElement.clientWidth) /* or $(window).width() */ &&
                              rect.top < (window.innerHeight || document.documentElement.clientHeight) /* or $(window).height() */;
                              }






                              share|improve this answer














                              share|improve this answer



                              share|improve this answer








                              edited Dec 6 '18 at 2:23

























                              answered Apr 29 '13 at 2:36









                              WalfWalf

                              4,44312242




                              4,44312242























                                  28














                                  As a public service:

                                  Dan's answer with the correct calculations (element can be > window, especially on mobile phone screens), and correct jQuery testing, as well as adding isElementPartiallyInViewport:



                                  By the way, the difference between window.innerWidth and document.documentElement.clientWidth is that clientWidth/clientHeight doesn't include the scrollbar, while window.innerWidth/Height does.



                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  Test-case



                                  <!DOCTYPE html>
                                  <html lang="en">
                                  <head>
                                  <meta charset="utf-8">
                                  <meta http-equiv="X-UA-Compatible" content="IE=edge">
                                  <meta name="viewport" content="width=device-width, initial-scale=1">
                                  <meta name="description" content="">
                                  <meta name="author" content="">
                                  <title>Test</title>
                                  <!--
                                  <script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
                                  <script src="scrollMonitor.js"></script>
                                  -->

                                  <script type="text/javascript">

                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];


                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  // var scrollLeft = (window.pageXOffset !== undefined) ? window.pageXOffset : (document.documentElement || document.body.parentNode || document.body).scrollLeft,
                                  // var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop;

                                  </script>

                                  </head>
                                  <body>

                                  <div style="display: block; width: 2000px; height: 10000px; background-color: green;">

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <div style="background-color: crimson; display: inline-block; width: 800px; height: 500px;" ></div>
                                  <div id="myele" onclick="fnIsVis(this);" style="display: inline-block; width: 100px; height: 100px; background-color: hotpink;">
                                  t
                                  </div>

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  </div>

                                  <!--
                                  <script type="text/javascript">

                                  var element = document.getElementById("myele");
                                  var watcher = scrollMonitor.create( element );

                                  watcher.lock();

                                  watcher.stateChange(function() {
                                  console.log("state changed");
                                  // $(element).toggleClass('fixed', this.isAboveViewport)
                                  });

                                  </script>
                                  -->
                                  </body>
                                  </html>





                                  share|improve this answer





















                                  • 2





                                    isElementPartiallyInViewport is very useful as well. Nice one.

                                    – RJ Cuthbertson
                                    Oct 28 '15 at 13:02











                                  • For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                    – Arun chauhan
                                    Aug 13 '18 at 8:00








                                  • 1





                                    @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                    – Stefan Steiger
                                    Aug 13 '18 at 8:53


















                                  28














                                  As a public service:

                                  Dan's answer with the correct calculations (element can be > window, especially on mobile phone screens), and correct jQuery testing, as well as adding isElementPartiallyInViewport:



                                  By the way, the difference between window.innerWidth and document.documentElement.clientWidth is that clientWidth/clientHeight doesn't include the scrollbar, while window.innerWidth/Height does.



                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  Test-case



                                  <!DOCTYPE html>
                                  <html lang="en">
                                  <head>
                                  <meta charset="utf-8">
                                  <meta http-equiv="X-UA-Compatible" content="IE=edge">
                                  <meta name="viewport" content="width=device-width, initial-scale=1">
                                  <meta name="description" content="">
                                  <meta name="author" content="">
                                  <title>Test</title>
                                  <!--
                                  <script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
                                  <script src="scrollMonitor.js"></script>
                                  -->

                                  <script type="text/javascript">

                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];


                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  // var scrollLeft = (window.pageXOffset !== undefined) ? window.pageXOffset : (document.documentElement || document.body.parentNode || document.body).scrollLeft,
                                  // var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop;

                                  </script>

                                  </head>
                                  <body>

                                  <div style="display: block; width: 2000px; height: 10000px; background-color: green;">

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <div style="background-color: crimson; display: inline-block; width: 800px; height: 500px;" ></div>
                                  <div id="myele" onclick="fnIsVis(this);" style="display: inline-block; width: 100px; height: 100px; background-color: hotpink;">
                                  t
                                  </div>

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  </div>

                                  <!--
                                  <script type="text/javascript">

                                  var element = document.getElementById("myele");
                                  var watcher = scrollMonitor.create( element );

                                  watcher.lock();

                                  watcher.stateChange(function() {
                                  console.log("state changed");
                                  // $(element).toggleClass('fixed', this.isAboveViewport)
                                  });

                                  </script>
                                  -->
                                  </body>
                                  </html>





                                  share|improve this answer





















                                  • 2





                                    isElementPartiallyInViewport is very useful as well. Nice one.

                                    – RJ Cuthbertson
                                    Oct 28 '15 at 13:02











                                  • For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                    – Arun chauhan
                                    Aug 13 '18 at 8:00








                                  • 1





                                    @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                    – Stefan Steiger
                                    Aug 13 '18 at 8:53
















                                  28












                                  28








                                  28







                                  As a public service:

                                  Dan's answer with the correct calculations (element can be > window, especially on mobile phone screens), and correct jQuery testing, as well as adding isElementPartiallyInViewport:



                                  By the way, the difference between window.innerWidth and document.documentElement.clientWidth is that clientWidth/clientHeight doesn't include the scrollbar, while window.innerWidth/Height does.



                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  Test-case



                                  <!DOCTYPE html>
                                  <html lang="en">
                                  <head>
                                  <meta charset="utf-8">
                                  <meta http-equiv="X-UA-Compatible" content="IE=edge">
                                  <meta name="viewport" content="width=device-width, initial-scale=1">
                                  <meta name="description" content="">
                                  <meta name="author" content="">
                                  <title>Test</title>
                                  <!--
                                  <script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
                                  <script src="scrollMonitor.js"></script>
                                  -->

                                  <script type="text/javascript">

                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];


                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  // var scrollLeft = (window.pageXOffset !== undefined) ? window.pageXOffset : (document.documentElement || document.body.parentNode || document.body).scrollLeft,
                                  // var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop;

                                  </script>

                                  </head>
                                  <body>

                                  <div style="display: block; width: 2000px; height: 10000px; background-color: green;">

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <div style="background-color: crimson; display: inline-block; width: 800px; height: 500px;" ></div>
                                  <div id="myele" onclick="fnIsVis(this);" style="display: inline-block; width: 100px; height: 100px; background-color: hotpink;">
                                  t
                                  </div>

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  </div>

                                  <!--
                                  <script type="text/javascript">

                                  var element = document.getElementById("myele");
                                  var watcher = scrollMonitor.create( element );

                                  watcher.lock();

                                  watcher.stateChange(function() {
                                  console.log("state changed");
                                  // $(element).toggleClass('fixed', this.isAboveViewport)
                                  });

                                  </script>
                                  -->
                                  </body>
                                  </html>





                                  share|improve this answer















                                  As a public service:

                                  Dan's answer with the correct calculations (element can be > window, especially on mobile phone screens), and correct jQuery testing, as well as adding isElementPartiallyInViewport:



                                  By the way, the difference between window.innerWidth and document.documentElement.clientWidth is that clientWidth/clientHeight doesn't include the scrollbar, while window.innerWidth/Height does.



                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  Test-case



                                  <!DOCTYPE html>
                                  <html lang="en">
                                  <head>
                                  <meta charset="utf-8">
                                  <meta http-equiv="X-UA-Compatible" content="IE=edge">
                                  <meta name="viewport" content="width=device-width, initial-scale=1">
                                  <meta name="description" content="">
                                  <meta name="author" content="">
                                  <title>Test</title>
                                  <!--
                                  <script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
                                  <script src="scrollMonitor.js"></script>
                                  -->

                                  <script type="text/javascript">

                                  function isElementPartiallyInViewport(el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];

                                  var rect = el.getBoundingClientRect();
                                  // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap
                                  var vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= 0);
                                  var horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0);

                                  return (vertInView && horInView);
                                  }


                                  // http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport
                                  function isElementInViewport (el)
                                  {
                                  //special bonus for those using jQuery
                                  if (typeof jQuery !== 'undefined' && el instanceof jQuery) el = el[0];


                                  var rect = el.getBoundingClientRect();
                                  var windowHeight = (window.innerHeight || document.documentElement.clientHeight);
                                  var windowWidth = (window.innerWidth || document.documentElement.clientWidth);

                                  return (
                                  (rect.left >= 0)
                                  && (rect.top >= 0)
                                  && ((rect.left + rect.width) <= windowWidth)
                                  && ((rect.top + rect.height) <= windowHeight)
                                  );

                                  }


                                  function fnIsVis(ele)
                                  {
                                  var inVpFull = isElementInViewport(ele);
                                  var inVpPartial = isElementPartiallyInViewport(ele);
                                  console.clear();
                                  console.log("Fully in viewport: " + inVpFull);
                                  console.log("Partially in viewport: " + inVpPartial);
                                  }


                                  // var scrollLeft = (window.pageXOffset !== undefined) ? window.pageXOffset : (document.documentElement || document.body.parentNode || document.body).scrollLeft,
                                  // var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop;

                                  </script>

                                  </head>
                                  <body>

                                  <div style="display: block; width: 2000px; height: 10000px; background-color: green;">

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <div style="background-color: crimson; display: inline-block; width: 800px; height: 500px;" ></div>
                                  <div id="myele" onclick="fnIsVis(this);" style="display: inline-block; width: 100px; height: 100px; background-color: hotpink;">
                                  t
                                  </div>

                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />
                                  <br /><br /><br /><br /><br /><br />

                                  <input type="button" onclick="fnIsVis(document.getElementById('myele'));" value="det" />

                                  </div>

                                  <!--
                                  <script type="text/javascript">

                                  var element = document.getElementById("myele");
                                  var watcher = scrollMonitor.create( element );

                                  watcher.lock();

                                  watcher.stateChange(function() {
                                  console.log("state changed");
                                  // $(element).toggleClass('fixed', this.isAboveViewport)
                                  });

                                  </script>
                                  -->
                                  </body>
                                  </html>






                                  share|improve this answer














                                  share|improve this answer



                                  share|improve this answer








                                  edited Sep 25 '14 at 13:06

























                                  answered Sep 25 '14 at 12:54









                                  Stefan SteigerStefan Steiger

                                  44.4k56265352




                                  44.4k56265352








                                  • 2





                                    isElementPartiallyInViewport is very useful as well. Nice one.

                                    – RJ Cuthbertson
                                    Oct 28 '15 at 13:02











                                  • For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                    – Arun chauhan
                                    Aug 13 '18 at 8:00








                                  • 1





                                    @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                    – Stefan Steiger
                                    Aug 13 '18 at 8:53
















                                  • 2





                                    isElementPartiallyInViewport is very useful as well. Nice one.

                                    – RJ Cuthbertson
                                    Oct 28 '15 at 13:02











                                  • For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                    – Arun chauhan
                                    Aug 13 '18 at 8:00








                                  • 1





                                    @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                    – Stefan Steiger
                                    Aug 13 '18 at 8:53










                                  2




                                  2





                                  isElementPartiallyInViewport is very useful as well. Nice one.

                                  – RJ Cuthbertson
                                  Oct 28 '15 at 13:02





                                  isElementPartiallyInViewport is very useful as well. Nice one.

                                  – RJ Cuthbertson
                                  Oct 28 '15 at 13:02













                                  For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                  – Arun chauhan
                                  Aug 13 '18 at 8:00







                                  For isElementInViewport(e) : Your code is not even loading images, This one is correct : function isElementInViewport(e) { var t = e.getBoundingClientRect(); return t.top >= 0 && t.left >= 0 && t.bottom <= (window.innerHeight || document.documentElement.clientHeight) && t.right <= (window.innerWidth || document.documentElement.clientWidth) }

                                  – Arun chauhan
                                  Aug 13 '18 at 8:00






                                  1




                                  1





                                  @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                  – Stefan Steiger
                                  Aug 13 '18 at 8:53







                                  @Arun chauhan: None of my code is loading images, so why should it, and the formula is correct.

                                  – Stefan Steiger
                                  Aug 13 '18 at 8:53













                                  25














                                  There is jQuery plugin called inview that does the job






                                  share|improve this answer



















                                  • 16





                                    My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                    – mmmeff
                                    Jan 27 '14 at 23:51













                                  • Another solution.

                                    – Jonatas Walker
                                    Oct 1 '16 at 13:33
















                                  25














                                  There is jQuery plugin called inview that does the job






                                  share|improve this answer



















                                  • 16





                                    My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                    – mmmeff
                                    Jan 27 '14 at 23:51













                                  • Another solution.

                                    – Jonatas Walker
                                    Oct 1 '16 at 13:33














                                  25












                                  25








                                  25







                                  There is jQuery plugin called inview that does the job






                                  share|improve this answer













                                  There is jQuery plugin called inview that does the job







                                  share|improve this answer












                                  share|improve this answer



                                  share|improve this answer










                                  answered May 3 '10 at 17:00









                                  Yuri SalimovskiyYuri Salimovskiy

                                  393310




                                  393310








                                  • 16





                                    My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                    – mmmeff
                                    Jan 27 '14 at 23:51













                                  • Another solution.

                                    – Jonatas Walker
                                    Oct 1 '16 at 13:33














                                  • 16





                                    My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                    – mmmeff
                                    Jan 27 '14 at 23:51













                                  • Another solution.

                                    – Jonatas Walker
                                    Oct 1 '16 at 13:33








                                  16




                                  16





                                  My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                  – mmmeff
                                  Jan 27 '14 at 23:51







                                  My team ran into some serious performance issues with this plugin so I went a head and forked it, changing the implementation to make use of getBoundingClientRect(). Check it out here: github.com/mmmeff/jquery.inview2

                                  – mmmeff
                                  Jan 27 '14 at 23:51















                                  Another solution.

                                  – Jonatas Walker
                                  Oct 1 '16 at 13:33





                                  Another solution.

                                  – Jonatas Walker
                                  Oct 1 '16 at 13:33











                                  24














                                  See the source of verge, which uses getBoundingClientRect. It's like:



                                  function inViewport (el) {

                                  var r, html;
                                  if ( !el || 1 !== el.nodeType ) { return false; }
                                  html = document.documentElement;
                                  r = el.getBoundingClientRect();

                                  return ( !!r
                                  && r.bottom >= 0
                                  && r.right >= 0
                                  && r.top <= html.clientHeight
                                  && r.left <= html.clientWidth
                                  );

                                  }


                                  Returns true if any part of the element is in the viewport.






                                  share|improve this answer






























                                    24














                                    See the source of verge, which uses getBoundingClientRect. It's like:



                                    function inViewport (el) {

                                    var r, html;
                                    if ( !el || 1 !== el.nodeType ) { return false; }
                                    html = document.documentElement;
                                    r = el.getBoundingClientRect();

                                    return ( !!r
                                    && r.bottom >= 0
                                    && r.right >= 0
                                    && r.top <= html.clientHeight
                                    && r.left <= html.clientWidth
                                    );

                                    }


                                    Returns true if any part of the element is in the viewport.






                                    share|improve this answer




























                                      24












                                      24








                                      24







                                      See the source of verge, which uses getBoundingClientRect. It's like:



                                      function inViewport (el) {

                                      var r, html;
                                      if ( !el || 1 !== el.nodeType ) { return false; }
                                      html = document.documentElement;
                                      r = el.getBoundingClientRect();

                                      return ( !!r
                                      && r.bottom >= 0
                                      && r.right >= 0
                                      && r.top <= html.clientHeight
                                      && r.left <= html.clientWidth
                                      );

                                      }


                                      Returns true if any part of the element is in the viewport.






                                      share|improve this answer















                                      See the source of verge, which uses getBoundingClientRect. It's like:



                                      function inViewport (el) {

                                      var r, html;
                                      if ( !el || 1 !== el.nodeType ) { return false; }
                                      html = document.documentElement;
                                      r = el.getBoundingClientRect();

                                      return ( !!r
                                      && r.bottom >= 0
                                      && r.right >= 0
                                      && r.top <= html.clientHeight
                                      && r.left <= html.clientWidth
                                      );

                                      }


                                      Returns true if any part of the element is in the viewport.







                                      share|improve this answer














                                      share|improve this answer



                                      share|improve this answer








                                      edited Sep 15 '12 at 10:16

























                                      answered Sep 14 '12 at 5:49









                                      ryanveryanve

                                      27.5k2270110




                                      27.5k2270110























                                          22














                                          my shorter and faster version.



                                          function isElementOutViewport(el){
                                          var rect = el.getBoundingClientRect();
                                          return rect.bottom < 0 || rect.right < 0 || rect.left > window.innerWidth || rect.top > window.innerHeight;
                                          }


                                          add jsFiddle as required
                                          https://jsfiddle.net/on1g619L/1/






                                          share|improve this answer





















                                          • 4





                                            My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                            – Eric Chen
                                            Jan 19 '15 at 23:05






                                          • 1





                                            I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                            – Y.K.
                                            Sep 5 '18 at 21:09













                                          • @Y.K. okay, done.

                                            – Eric Chen
                                            Sep 7 '18 at 3:58
















                                          22














                                          my shorter and faster version.



                                          function isElementOutViewport(el){
                                          var rect = el.getBoundingClientRect();
                                          return rect.bottom < 0 || rect.right < 0 || rect.left > window.innerWidth || rect.top > window.innerHeight;
                                          }


                                          add jsFiddle as required
                                          https://jsfiddle.net/on1g619L/1/






                                          share|improve this answer





















                                          • 4





                                            My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                            – Eric Chen
                                            Jan 19 '15 at 23:05






                                          • 1





                                            I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                            – Y.K.
                                            Sep 5 '18 at 21:09













                                          • @Y.K. okay, done.

                                            – Eric Chen
                                            Sep 7 '18 at 3:58














                                          22












                                          22








                                          22







                                          my shorter and faster version.



                                          function isElementOutViewport(el){
                                          var rect = el.getBoundingClientRect();
                                          return rect.bottom < 0 || rect.right < 0 || rect.left > window.innerWidth || rect.top > window.innerHeight;
                                          }


                                          add jsFiddle as required
                                          https://jsfiddle.net/on1g619L/1/






                                          share|improve this answer















                                          my shorter and faster version.



                                          function isElementOutViewport(el){
                                          var rect = el.getBoundingClientRect();
                                          return rect.bottom < 0 || rect.right < 0 || rect.left > window.innerWidth || rect.top > window.innerHeight;
                                          }


                                          add jsFiddle as required
                                          https://jsfiddle.net/on1g619L/1/







                                          share|improve this answer














                                          share|improve this answer



                                          share|improve this answer








                                          edited Sep 7 '18 at 3:58

























                                          answered Apr 23 '14 at 3:04









                                          Eric ChenEric Chen

                                          3,07421114




                                          3,07421114








                                          • 4





                                            My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                            – Eric Chen
                                            Jan 19 '15 at 23:05






                                          • 1





                                            I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                            – Y.K.
                                            Sep 5 '18 at 21:09













                                          • @Y.K. okay, done.

                                            – Eric Chen
                                            Sep 7 '18 at 3:58














                                          • 4





                                            My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                            – Eric Chen
                                            Jan 19 '15 at 23:05






                                          • 1





                                            I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                            – Y.K.
                                            Sep 5 '18 at 21:09













                                          • @Y.K. okay, done.

                                            – Eric Chen
                                            Sep 7 '18 at 3:58








                                          4




                                          4





                                          My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                          – Eric Chen
                                          Jan 19 '15 at 23:05





                                          My solution are more greedy and faster, when element have any pixel in viewport , it's will return false.

                                          – Eric Chen
                                          Jan 19 '15 at 23:05




                                          1




                                          1





                                          I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                          – Y.K.
                                          Sep 5 '18 at 21:09







                                          I like it. Concise. You could remove the spaces between function name and parenthesis, and between parenthesis and brace, on first line. Never liked those spaces. Maybe it's just my Text editor that color codes it all that still makes it easy to read. function aaa(arg){statements} I know that doesn't make it execute faster, falls under minifying instead.

                                          – Y.K.
                                          Sep 5 '18 at 21:09















                                          @Y.K. okay, done.

                                          – Eric Chen
                                          Sep 7 '18 at 3:58





                                          @Y.K. okay, done.

                                          – Eric Chen
                                          Sep 7 '18 at 3:58











                                          19














                                          I found it troubling that there wasn't a jQuery centric version of the functionality available. When i came across Dan's solution i spied the opportunity to provide something for folks who like to program in the jQuery OO style. Be sure to scroll up and leave an upvote on Dan's code. Its nice and snappy and works like a charm for me.



                                          bada bing bada boom



                                          $.fn.inView = function(){
                                          if(!this.length) return false;
                                          var rect = this.get(0).getBoundingClientRect();

                                          return (
                                          rect.top >= 0 &&
                                          rect.left >= 0 &&
                                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
                                          rect.right <= (window.innerWidth || document.documentElement.clientWidth)
                                          );

                                          };

                                          //additional examples for other use cases
                                          //true false whether an array of elements are all in view
                                          $.fn.allInView = function(){
                                          var all = ;
                                          this.forEach(function(){
                                          all.push( $(this).inView() );
                                          });
                                          return all.indexOf(false) === -1;
                                          };

                                          //only the class elements in view
                                          $('.some-class').filter(function(){
                                          return $(this).inView();
                                          });

                                          //only the class elements not in view
                                          $('.some-class').filter(function(){
                                          return !$(this).inView();
                                          });


                                          usage



                                          $(window).on('scroll',function(){ 

                                          if( $('footer').inView() ) {
                                          // do cool stuff
                                          }

                                          });





                                          share|improve this answer





















                                          • 1





                                            Would the curly brace be sufficient to close the if statement?

                                            – calasyr
                                            May 24 '16 at 23:58






                                          • 1





                                            I could not make it work with multiple elements of an identical class.

                                            – The Whiz of Oz
                                            Jun 20 '17 at 7:38






                                          • 1





                                            @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                            – r3wt
                                            Jun 20 '17 at 20:07
















                                          19














                                          I found it troubling that there wasn't a jQuery centric version of the functionality available. When i came across Dan's solution i spied the opportunity to provide something for folks who like to program in the jQuery OO style. Be sure to scroll up and leave an upvote on Dan's code. Its nice and snappy and works like a charm for me.



                                          bada bing bada boom



                                          $.fn.inView = function(){
                                          if(!this.length) return false;
                                          var rect = this.get(0).getBoundingClientRect();

                                          return (
                                          rect.top >= 0 &&
                                          rect.left >= 0 &&
                                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
                                          rect.right <= (window.innerWidth || document.documentElement.clientWidth)
                                          );

                                          };

                                          //additional examples for other use cases
                                          //true false whether an array of elements are all in view
                                          $.fn.allInView = function(){
                                          var all = ;
                                          this.forEach(function(){
                                          all.push( $(this).inView() );
                                          });
                                          return all.indexOf(false) === -1;
                                          };

                                          //only the class elements in view
                                          $('.some-class').filter(function(){
                                          return $(this).inView();
                                          });

                                          //only the class elements not in view
                                          $('.some-class').filter(function(){
                                          return !$(this).inView();
                                          });


                                          usage



                                          $(window).on('scroll',function(){ 

                                          if( $('footer').inView() ) {
                                          // do cool stuff
                                          }

                                          });





                                          share|improve this answer





















                                          • 1





                                            Would the curly brace be sufficient to close the if statement?

                                            – calasyr
                                            May 24 '16 at 23:58






                                          • 1





                                            I could not make it work with multiple elements of an identical class.

                                            – The Whiz of Oz
                                            Jun 20 '17 at 7:38






                                          • 1





                                            @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                            – r3wt
                                            Jun 20 '17 at 20:07














                                          19












                                          19








                                          19







                                          I found it troubling that there wasn't a jQuery centric version of the functionality available. When i came across Dan's solution i spied the opportunity to provide something for folks who like to program in the jQuery OO style. Be sure to scroll up and leave an upvote on Dan's code. Its nice and snappy and works like a charm for me.



                                          bada bing bada boom



                                          $.fn.inView = function(){
                                          if(!this.length) return false;
                                          var rect = this.get(0).getBoundingClientRect();

                                          return (
                                          rect.top >= 0 &&
                                          rect.left >= 0 &&
                                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
                                          rect.right <= (window.innerWidth || document.documentElement.clientWidth)
                                          );

                                          };

                                          //additional examples for other use cases
                                          //true false whether an array of elements are all in view
                                          $.fn.allInView = function(){
                                          var all = ;
                                          this.forEach(function(){
                                          all.push( $(this).inView() );
                                          });
                                          return all.indexOf(false) === -1;
                                          };

                                          //only the class elements in view
                                          $('.some-class').filter(function(){
                                          return $(this).inView();
                                          });

                                          //only the class elements not in view
                                          $('.some-class').filter(function(){
                                          return !$(this).inView();
                                          });


                                          usage



                                          $(window).on('scroll',function(){ 

                                          if( $('footer').inView() ) {
                                          // do cool stuff
                                          }

                                          });





                                          share|improve this answer















                                          I found it troubling that there wasn't a jQuery centric version of the functionality available. When i came across Dan's solution i spied the opportunity to provide something for folks who like to program in the jQuery OO style. Be sure to scroll up and leave an upvote on Dan's code. Its nice and snappy and works like a charm for me.



                                          bada bing bada boom



                                          $.fn.inView = function(){
                                          if(!this.length) return false;
                                          var rect = this.get(0).getBoundingClientRect();

                                          return (
                                          rect.top >= 0 &&
                                          rect.left >= 0 &&
                                          rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
                                          rect.right <= (window.innerWidth || document.documentElement.clientWidth)
                                          );

                                          };

                                          //additional examples for other use cases
                                          //true false whether an array of elements are all in view
                                          $.fn.allInView = function(){
                                          var all = ;
                                          this.forEach(function(){
                                          all.push( $(this).inView() );
                                          });
                                          return all.indexOf(false) === -1;
                                          };

                                          //only the class elements in view
                                          $('.some-class').filter(function(){
                                          return $(this).inView();
                                          });

                                          //only the class elements not in view
                                          $('.some-class').filter(function(){
                                          return !$(this).inView();
                                          });


                                          usage



                                          $(window).on('scroll',function(){ 

                                          if( $('footer').inView() ) {
                                          // do cool stuff
                                          }

                                          });






                                          share|improve this answer














                                          share|improve this answer



                                          share|improve this answer








                                          edited Jun 20 '17 at 20:06

























                                          answered Aug 2 '15 at 13:40









                                          r3wtr3wt

                                          2,9671944




                                          2,9671944








                                          • 1





                                            Would the curly brace be sufficient to close the if statement?

                                            – calasyr
                                            May 24 '16 at 23:58






                                          • 1





                                            I could not make it work with multiple elements of an identical class.

                                            – The Whiz of Oz
                                            Jun 20 '17 at 7:38






                                          • 1





                                            @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                            – r3wt
                                            Jun 20 '17 at 20:07














                                          • 1





                                            Would the curly brace be sufficient to close the if statement?

                                            – calasyr
                                            May 24 '16 at 23:58






                                          • 1





                                            I could not make it work with multiple elements of an identical class.

                                            – The Whiz of Oz
                                            Jun 20 '17 at 7:38






                                          • 1





                                            @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                            – r3wt
                                            Jun 20 '17 at 20:07








                                          1




                                          1





                                          Would the curly brace be sufficient to close the if statement?

                                          – calasyr
                                          May 24 '16 at 23:58





                                          Would the curly brace be sufficient to close the if statement?

                                          – calasyr
                                          May 24 '16 at 23:58




                                          1




                                          1





                                          I could not make it work with multiple elements of an identical class.

                                          – The Whiz of Oz
                                          Jun 20 '17 at 7:38





                                          I could not make it work with multiple elements of an identical class.

                                          – The Whiz of Oz
                                          Jun 20 '17 at 7:38




                                          1




                                          1





                                          @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                          – r3wt
                                          Jun 20 '17 at 20:07





                                          @TheWhizofOz i've updated my answer to give examples of the other possible use cases you've brought up. best of luck.

                                          – r3wt
                                          Jun 20 '17 at 20:07











                                          8














                                          I find that the accepted answer here is overly complicated for most use cases. This code does the job well (using JQuery) and differentiates between fully visible and partially visible elements.



                                          var element         = $("#element");
                                          var topOfElement = element.offset().top;
                                          var bottomOfElement = element.offset().top + element.outerHeight(true);
                                          var $window = $(window);

                                          $window.bind('scroll', function() {

                                          var scrollTopPosition = $window.scrollTop()+$window.height();
                                          var windowScrollTop = $window.scrollTop()

                                          if( windowScrollTop > topOfElement && windowScrollTop < bottomOfElement) {
                                          // Element is partially visible (above viewable area)
                                          console.log("Element is partially visible (above viewable area)");

                                          }else if( windowScrollTop > bottomOfElement && windowScrollTop > topOfElement ) {
                                          // Element is hidden (above viewable area)
                                          console.log("Element is hidden (above viewable area)");

                                          }else if( scrollTopPosition < topOfElement && scrollTopPosition < bottomOfElement ) {
                                          // Element is hidden (below viewable area)
                                          console.log("Element is hidden (below viewable area)");

                                          }else if( scrollTopPosition < bottomOfElement && scrollTopPosition > topOfElement ) {
                                          // Element is partially visible (below viewable area)
                                          console.log("Element is partially visible (below viewable area)");

                                          }else{
                                          // Element is completely visible
                                          console.log("Element is completely visible");
                                          }
                                          });





                                          share|improve this answer


























                                          • Works brilliantly! Tested on Chrome, Firefox and Safari.

                                            – noobsharp
                                            May 8 '16 at 14:45











                                          • You can use this.

                                            – Jonatas Walker
                                            Oct 1 '16 at 12:54











                                          • You should definitely cache $window = $(window) outside the scroll handler.

                                            – sam
                                            Jul 1 '17 at 19:36
















                                          8














                                          I find that the accepted answer here is overly complicated for most use cases. This code does the job well (using JQuery) and differentiates between fully visible and partially visible elements.



                                          var element         = $("#element");
                                          var topOfElement = element.offset().top;
                                          var bottomOfElement = element.offset().top + element.outerHeight(true);
                                          var $window = $(window);

                                          $window.bind('scroll', function() {

                                          var scrollTopPosition = $window.scrollTop()+$window.height();
                                          var windowScrollTop = $window.scrollTop()

                                          if( windowScrollTop > topOfElement && windowScrollTop < bottomOfElement) {
                                          // Element is partially visible (above viewable area)
                                          console.log("Element is partially visible (above viewable area)");

                                          }else if( windowScrollTop > bottomOfElement && windowScrollTop > topOfElement ) {
                                          // Element is hidden (above viewable area)
                                          console.log("Element is hidden (above viewable area)");

                                          }else if( scrollTopPosition < topOfElement && scrollTopPosition < bottomOfElement ) {
                                          // Element is hidden (below viewable area)
                                          console.log("Element is hidden (below viewable area)");

                                          }else if( scrollTopPosition < bottomOfElement && scrollTopPosition > topOfElement ) {
                                          // Element is partially visible (below viewable area)
                                          console.log("Element is partially visible (below viewable area)");

                                          }else{
                                          // Element is completely visible
                                          console.log("Element is completely visible");
                                          }
                                          });





                                          share|improve this answer


























                                          • Works brilliantly! Tested on Chrome, Firefox and Safari.

                                            – noobsharp
                                            May 8 '16 at 14:45











                                          • You can use this.

                                            – Jonatas Walker
                                            Oct 1 '16 at 12:54











                                          • You should definitely cache $window = $(window) outside the scroll handler.

                                            – sam
                                            Jul 1 '17 at 19:36














                                          8












                                          8








                                          8







                                          I find that the accepted answer here is overly complicated for most use cases. This code does the job well (using JQuery) and differentiates between fully visible and partially visible elements.



                                          var element         = $("#element");
                                          var topOfElement = element.offset().top;
                                          var bottomOfElement = element.offset().top + element.outerHeight(true);
                                          var $window = $(window);

                                          $window.bind('scroll', function() {

                                          var scrollTopPosition = $window.scrollTop()+$window.height();
                                          var windowScrollTop = $window.scrollTop()

                                          if( windowScrollTop > topOfElement && windowScrollTop < bottomOfElement) {
                                          // Element is partially visible (above viewable area)
                                          console.log("Element is partially visible (above viewable area)");

                                          }else if( windowScrollTop > bottomOfElement && windowScrollTop > topOfElement ) {
                                          // Element is hidden (above viewable area)
                                          console.log("Element is hidden (above viewable area)");

                                          }else if( scrollTopPosition < topOfElement && scrollTopPosition < bottomOfElement ) {
                                          // Element is hidden (below viewable area)
                                          console.log("Element is hidden (below viewable area)");

                                          }else if( scrollTopPosition < bottomOfElement && scrollTopPosition > topOfElement ) {
                                          // Element is partially visible (below viewable area)
                                          console.log("Element is partially visible (below viewable area)");

                                          }else{
                                          // Element is completely visible
                                          console.log("Element is completely visible");
                                          }
                                          });





                                          share|improve this answer















                                          I find that the accepted answer here is overly complicated for most use cases. This code does the job well (using JQuery) and differentiates between fully visible and partially visible elements.



                                          var element         = $("#element");
                                          var topOfElement = element.offset().top;
                                          var bottomOfElement = element.offset().top + element.outerHeight(true);
                                          var $window = $(window);

                                          $window.bind('scroll', function() {

                                          var scrollTopPosition = $window.scrollTop()+$window.height();
                                          var windowScrollTop = $window.scrollTop()

                                          if( windowScrollTop > topOfElement && windowScrollTop < bottomOfElement) {
                                          // Element is partially visible (above viewable area)
                                          console.log("Element is partially visible (above viewable area)");

                                          }else if( windowScrollTop > bottomOfElement && windowScrollTop > topOfElement ) {
                                          // Element is hidden (above viewable area)
                                          console.log("Element is hidden (above viewable area)");

                                          }else if( scrollTopPosition < topOfElement && scrollTopPosition < bottomOfElement ) {
                                          // Element is hidden (below viewable area)
                                          console.log("Element is hidden (below viewable area)");

                                          }else if( scrollTopPosition < bottomOfElement && scrollTopPosition > topOfElement ) {
                                          // Element is partially visible (below viewable area)
                                          console.log("Element is partially visible (below viewable area)");

                                          }else{
                                          // Element is completely visible
                                          console.log("Element is completely visible");
                                          }
                                          });






                                          share|improve this answer














                                          share|improve this answer



                                          share|improve this answer








                                          edited Nov 1 '17 at 8:10

























                                          answered Jan 30 '15 at 14:49









                                          Adam RehalAdam Rehal

                                          12614




                                          12614













                                          • Works brilliantly! Tested on Chrome, Firefox and Safari.

                                            – noobsharp
                                            May 8 '16 at 14:45











                                          • You can use this.

                                            – Jonatas Walker
                                            Oct 1 '16 at 12:54











                                          • You should definitely cache $window = $(window) outside the scroll handler.

                                            – sam
                                            Jul 1 '17 at 19:36



















                                          • Works brilliantly! Tested on Chrome, Firefox and Safari.

                                            – noobsharp
                                            May 8 '16 at 14:45











                                          • You can use this.

                                            – Jonatas Walker
                                            Oct 1 '16 at 12:54











                                          • You should definitely cache $window = $(window) outside the scroll handler.

                                            – sam
                                            Jul 1 '17 at 19:36

















                                          Works brilliantly! Tested on Chrome, Firefox and Safari.

                                          – noobsharp
                                          May 8 '16 at 14:45





                                          Works brilliantly! Tested on Chrome, Firefox and Safari.

                                          – noobsharp
                                          May 8 '16 at 14:45













                                          You can use this.

                                          – Jonatas Walker
                                          Oct 1 '16 at 12:54





                                          You can use this.

                                          – Jonatas Walker
                                          Oct 1 '16 at 12:54













                                          You should definitely cache $window = $(window) outside the scroll handler.

                                          – sam
                                          Jul 1 '17 at 19:36





                                          You should definitely cache $window = $(window) outside the scroll handler.

                                          – sam
                                          Jul 1 '17 at 19:36











                                          3














                                          I think this is a more functional way to do it.
                                          The Dan's answer do not work in recursive context.



                                          This function solve the problem when your element is inside others scrollable divs by testing any levels recursively upper to the HTML tag, and stops in the first false.



                                          /**
                                          * fullVisible=true only returns true if the all object rect is visible
                                          */
                                          function isReallyVisible(el, fullVisible) {
                                          if ( el.tagName == "HTML" )
                                          return true;
                                          var parentRect=el.parentNode.getBoundingClientRect();
                                          var rect = arguments[2] || el.getBoundingClientRect();
                                          return (
                                          ( fullVisible ? rect.top >= parentRect.top : rect.bottom > parentRect.top ) &&
                                          ( fullVisible ? rect.left >= parentRect.left : rect.right > parentRect.left ) &&
                                          ( fullVisible ? rect.bottom <= parentRect.bottom : rect.top < parentRect.bottom ) &&
                                          ( fullVisible ? rect.right <= parentRect.right : rect.left < parentRect.right ) &&
                                          isReallyVisible(el.parentNode, fullVisible, rect)
                                          );
                                          };





                                          share|improve this answer




























                                            3














                                            I think this is a more functional way to do it.
                                            The Dan's answer do not work in recursive context.



                                            This function solve the problem when your element is inside others scrollable divs by testing any levels recursively upper to the HTML tag, and stops in the first false.



                                            /**
                                            * fullVisible=true only returns true if the all object rect is visible
                                            */
                                            function isReallyVisible(el, fullVisible) {
                                            if ( el.tagName == "HTML" )
                                            return true;
                                            var parentRect=el.parentNode.getBoundingClientRect();
                                            var rect = arguments[2] || el.getBoundingClientRect();
                                            return (
                                            ( fullVisible ? rect.top >= parentRect.top : rect.bottom > parentRect.top ) &&
                                            ( fullVisible ? rect.left >= parentRect.left : rect.right > parentRect.left ) &&
                                            ( fullVisible ? rect.bottom <= parentRect.bottom : rect.top < parentRect.bottom ) &&
                                            ( fullVisible ? rect.right <= parentRect.right : rect.left < parentRect.right ) &&
                                            isReallyVisible(el.parentNode, fullVisible, rect)
                                            );
                                            };





                                            share|improve this answer


























                                              3












                                              3








                                              3







                                              I think this is a more functional way to do it.
                                              The Dan's answer do not work in recursive context.



                                              This function solve the problem when your element is inside others scrollable divs by testing any levels recursively upper to the HTML tag, and stops in the first false.



                                              /**
                                              * fullVisible=true only returns true if the all object rect is visible
                                              */
                                              function isReallyVisible(el, fullVisible) {
                                              if ( el.tagName == "HTML" )
                                              return true;
                                              var parentRect=el.parentNode.getBoundingClientRect();
                                              var rect = arguments[2] || el.getBoundingClientRect();
                                              return (
                                              ( fullVisible ? rect.top >= parentRect.top : rect.bottom > parentRect.top ) &&
                                              ( fullVisible ? rect.left >= parentRect.left : rect.right > parentRect.left ) &&
                                              ( fullVisible ? rect.bottom <= parentRect.bottom : rect.top < parentRect.bottom ) &&
                                              ( fullVisible ? rect.right <= parentRect.right : rect.left < parentRect.right ) &&
                                              isReallyVisible(el.parentNode, fullVisible, rect)
                                              );
                                              };





                                              share|improve this answer













                                              I think this is a more functional way to do it.
                                              The Dan's answer do not work in recursive context.



                                              This function solve the problem when your element is inside others scrollable divs by testing any levels recursively upper to the HTML tag, and stops in the first false.



                                              /**
                                              * fullVisible=true only returns true if the all object rect is visible
                                              */
                                              function isReallyVisible(el, fullVisible) {
                                              if ( el.tagName == "HTML" )
                                              return true;
                                              var parentRect=el.parentNode.getBoundingClientRect();
                                              var rect = arguments[2] || el.getBoundingClientRect();
                                              return (
                                              ( fullVisible ? rect.top >= parentRect.top : rect.bottom > parentRect.top ) &&
                                              ( fullVisible ? rect.left >= parentRect.left : rect.right > parentRect.left ) &&
                                              ( fullVisible ? rect.bottom <= parentRect.bottom : rect.top < parentRect.bottom ) &&
                                              ( fullVisible ? rect.right <= parentRect.right : rect.left < parentRect.right ) &&
                                              isReallyVisible(el.parentNode, fullVisible, rect)
                                              );
                                              };






                                              share|improve this answer












                                              share|improve this answer



                                              share|improve this answer










                                              answered Apr 24 '15 at 15:12









                                              tonton

                                              1,1371621




                                              1,1371621























                                                  3














                                                  All answers I've encountered here only check if the element is positioned inside the current viewport. But that doesn't mean that it is visible.

                                                  What if the given element is inside a div with overflowing content, and it is scrolled out of view?



                                                  To solve that, you'd have to check if the element is contained by all parents.

                                                  My solution does exactly that:



                                                  It also allows you to specify how much of the element has to be visible.



                                                  Element.prototype.isVisible = function(percentX, percentY){
                                                  var tolerance = 0.01; //needed because the rects returned by getBoundingClientRect provide the position up to 10 decimals
                                                  if(percentX == null){
                                                  percentX = 100;
                                                  }
                                                  if(percentY == null){
                                                  percentY = 100;
                                                  }

                                                  var elementRect = this.getBoundingClientRect();
                                                  var parentRects = ;
                                                  var element = this;

                                                  while(element.parentElement != null){
                                                  parentRects.push(element.parentElement.getBoundingClientRect());
                                                  element = element.parentElement;
                                                  }

                                                  var visibleInAllParents = parentRects.every(function(parentRect){
                                                  var visiblePixelX = Math.min(elementRect.right, parentRect.right) - Math.max(elementRect.left, parentRect.left);
                                                  var visiblePixelY = Math.min(elementRect.bottom, parentRect.bottom) - Math.max(elementRect.top, parentRect.top);
                                                  var visiblePercentageX = visiblePixelX / elementRect.width * 100;
                                                  var visiblePercentageY = visiblePixelY / elementRect.height * 100;
                                                  return visiblePercentageX + tolerance > percentX && visiblePercentageY + tolerance > percentY;
                                                  });
                                                  return visibleInAllParents;
                                                  };


                                                  This solution ignored the fact that elements may not be visible due to other facts, like opacity: 0.



                                                  I have tested this solution in Chrome and Internet Explorer 11.






                                                  share|improve this answer




























                                                    3














                                                    All answers I've encountered here only check if the element is positioned inside the current viewport. But that doesn't mean that it is visible.

                                                    What if the given element is inside a div with overflowing content, and it is scrolled out of view?



                                                    To solve that, you'd have to check if the element is contained by all parents.

                                                    My solution does exactly that:



                                                    It also allows you to specify how much of the element has to be visible.



                                                    Element.prototype.isVisible = function(percentX, percentY){
                                                    var tolerance = 0.01; //needed because the rects returned by getBoundingClientRect provide the position up to 10 decimals
                                                    if(percentX == null){
                                                    percentX = 100;
                                                    }
                                                    if(percentY == null){
                                                    percentY = 100;
                                                    }

                                                    var elementRect = this.getBoundingClientRect();
                                                    var parentRects = ;
                                                    var element = this;

                                                    while(element.parentElement != null){
                                                    parentRects.push(element.parentElement.getBoundingClientRect());
                                                    element = element.parentElement;
                                                    }

                                                    var visibleInAllParents = parentRects.every(function(parentRect){
                                                    var visiblePixelX = Math.min(elementRect.right, parentRect.right) - Math.max(elementRect.left, parentRect.left);
                                                    var visiblePixelY = Math.min(elementRect.bottom, parentRect.bottom) - Math.max(elementRect.top, parentRect.top);
                                                    var visiblePercentageX = visiblePixelX / elementRect.width * 100;
                                                    var visiblePercentageY = visiblePixelY / elementRect.height * 100;
                                                    return visiblePercentageX + tolerance > percentX && visiblePercentageY + tolerance > percentY;
                                                    });
                                                    return visibleInAllParents;
                                                    };


                                                    This solution ignored the fact that elements may not be visible due to other facts, like opacity: 0.



                                                    I have tested this solution in Chrome and Internet Explorer 11.






                                                    share|improve this answer


























                                                      3












                                                      3








                                                      3







                                                      All answers I've encountered here only check if the element is positioned inside the current viewport. But that doesn't mean that it is visible.

                                                      What if the given element is inside a div with overflowing content, and it is scrolled out of view?



                                                      To solve that, you'd have to check if the element is contained by all parents.

                                                      My solution does exactly that:



                                                      It also allows you to specify how much of the element has to be visible.



                                                      Element.prototype.isVisible = function(percentX, percentY){
                                                      var tolerance = 0.01; //needed because the rects returned by getBoundingClientRect provide the position up to 10 decimals
                                                      if(percentX == null){
                                                      percentX = 100;
                                                      }
                                                      if(percentY == null){
                                                      percentY = 100;
                                                      }

                                                      var elementRect = this.getBoundingClientRect();
                                                      var parentRects = ;
                                                      var element = this;

                                                      while(element.parentElement != null){
                                                      parentRects.push(element.parentElement.getBoundingClientRect());
                                                      element = element.parentElement;
                                                      }

                                                      var visibleInAllParents = parentRects.every(function(parentRect){
                                                      var visiblePixelX = Math.min(elementRect.right, parentRect.right) - Math.max(elementRect.left, parentRect.left);
                                                      var visiblePixelY = Math.min(elementRect.bottom, parentRect.bottom) - Math.max(elementRect.top, parentRect.top);
                                                      var visiblePercentageX = visiblePixelX / elementRect.width * 100;
                                                      var visiblePercentageY = visiblePixelY / elementRect.height * 100;
                                                      return visiblePercentageX + tolerance > percentX && visiblePercentageY + tolerance > percentY;
                                                      });
                                                      return visibleInAllParents;
                                                      };


                                                      This solution ignored the fact that elements may not be visible due to other facts, like opacity: 0.



                                                      I have tested this solution in Chrome and Internet Explorer 11.






                                                      share|improve this answer













                                                      All answers I've encountered here only check if the element is positioned inside the current viewport. But that doesn't mean that it is visible.

                                                      What if the given element is inside a div with overflowing content, and it is scrolled out of view?



                                                      To solve that, you'd have to check if the element is contained by all parents.

                                                      My solution does exactly that:



                                                      It also allows you to specify how much of the element has to be visible.



                                                      Element.prototype.isVisible = function(percentX, percentY){
                                                      var tolerance = 0.01; //needed because the rects returned by getBoundingClientRect provide the position up to 10 decimals
                                                      if(percentX == null){
                                                      percentX = 100;
                                                      }
                                                      if(percentY == null){
                                                      percentY = 100;
                                                      }

                                                      var elementRect = this.getBoundingClientRect();
                                                      var parentRects = ;
                                                      var element = this;

                                                      while(element.parentElement != null){
                                                      parentRects.push(element.parentElement.getBoundingClientRect());
                                                      element = element.parentElement;
                                                      }

                                                      var visibleInAllParents = parentRects.every(function(parentRect){
                                                      var visiblePixelX = Math.min(elementRect.right, parentRect.right) - Math.max(elementRect.left, parentRect.left);
                                                      var visiblePixelY = Math.min(elementRect.bottom, parentRect.bottom) - Math.max(elementRect.top, parentRect.top);
                                                      var visiblePercentageX = visiblePixelX / elementRect.width * 100;
                                                      var visiblePercentageY = visiblePixelY / elementRect.height * 100;
                                                      return visiblePercentageX + tolerance > percentX && visiblePercentageY + tolerance > percentY;
                                                      });
                                                      return visibleInAllParents;
                                                      };


                                                      This solution ignored the fact that elements may not be visible due to other facts, like opacity: 0.



                                                      I have tested this solution in Chrome and Internet Explorer 11.







                                                      share|improve this answer












                                                      share|improve this answer



                                                      share|improve this answer










                                                      answered Jun 23 '16 at 17:47









                                                      DomyseeDomysee

                                                      9,10884163




                                                      9,10884163























                                                          2














                                                          Depends what you mean by visible. If you mean is it currently shown on the page, given the scroll position, you can calculate it based on the elements y offset and the current scroll position.






                                                          share|improve this answer




























                                                            2














                                                            Depends what you mean by visible. If you mean is it currently shown on the page, given the scroll position, you can calculate it based on the elements y offset and the current scroll position.






                                                            share|improve this answer


























                                                              2












                                                              2








                                                              2







                                                              Depends what you mean by visible. If you mean is it currently shown on the page, given the scroll position, you can calculate it based on the elements y offset and the current scroll position.






                                                              share|improve this answer













                                                              Depends what you mean by visible. If you mean is it currently shown on the page, given the scroll position, you can calculate it based on the elements y offset and the current scroll position.







                                                              share|improve this answer












                                                              share|improve this answer



                                                              share|improve this answer










                                                              answered Sep 23 '08 at 21:29









                                                              roryfroryf

                                                              21.1k1572100




                                                              21.1k1572100























                                                                  2














                                                                  Based on @dan's solution above (https://stackoverflow.com/a/7557433/5628), I had a go at cleaning up implementation so that using it multiple times on the same page is easier:



                                                                  $(function() {

                                                                  $(window).on('load resize scroll', function() {
                                                                  addClassToElementInViewport($('.bug-icon'), 'animate-bug-icon');
                                                                  addClassToElementInViewport($('.another-thing'), 'animate-thing');
                                                                  // 👏 repeat as needed ...
                                                                  });

                                                                  function addClassToElementInViewport(element, newClass) {
                                                                  if (inViewport(element)) {
                                                                  element.addClass(newClass);
                                                                  }
                                                                  }

                                                                  function inViewport(element) {
                                                                  if (typeof jQuery === "function" && element instanceof jQuery) {
                                                                  element = element[0];
                                                                  }
                                                                  var elementBounds = element.getBoundingClientRect();
                                                                  return (
                                                                  elementBounds.top >= 0 &&
                                                                  elementBounds.left >= 0 &&
                                                                  elementBounds.bottom <= $(window).height() &&
                                                                  elementBounds.right <= $(window).width()
                                                                  );
                                                                  }

                                                                  });


                                                                  The way I'm using it is that when the element scrolls into view, I'm adding a class that triggers a css keyframe animation. It's pretty straightforward and works especially well when you've got like 10+ things to conditionally animate on a page.



                                                                  Hope it helps!






                                                                  share|improve this answer


























                                                                  • You should definitely cache $window = $(window) outside the scroll handler

                                                                    – Adam Rehal
                                                                    Nov 1 '17 at 8:13
















                                                                  2














                                                                  Based on @dan's solution above (https://stackoverflow.com/a/7557433/5628), I had a go at cleaning up implementation so that using it multiple times on the same page is easier:



                                                                  $(function() {

                                                                  $(window).on('load resize scroll', function() {
                                                                  addClassToElementInViewport($('.bug-icon'), 'animate-bug-icon');
                                                                  addClassToElementInViewport($('.another-thing'), 'animate-thing');
                                                                  // 👏 repeat as needed ...
                                                                  });

                                                                  function addClassToElementInViewport(element, newClass) {
                                                                  if (inViewport(element)) {
                                                                  element.addClass(newClass);
                                                                  }
                                                                  }

                                                                  function inViewport(element) {
                                                                  if (typeof jQuery === "function" && element instanceof jQuery) {
                                                                  element = element[0];
                                                                  }
                                                                  var elementBounds = element.getBoundingClientRect();
                                                                  return (
                                                                  elementBounds.top >= 0 &&
                                                                  elementBounds.left >= 0 &&
                                                                  elementBounds.bottom <= $(window).height() &&
                                                                  elementBounds.right <= $(window).width()
                                                                  );
                                                                  }

                                                                  });


                                                                  The way I'm using it is that when the element scrolls into view, I'm adding a class that triggers a css keyframe animation. It's pretty straightforward and works especially well when you've got like 10+ things to conditionally animate on a page.



                                                                  Hope it helps!






                                                                  share|improve this answer


























                                                                  • You should definitely cache $window = $(window) outside the scroll handler

                                                                    – Adam Rehal
                                                                    Nov 1 '17 at 8:13














                                                                  2












                                                                  2








                                                                  2







                                                                  Based on @dan's solution above (https://stackoverflow.com/a/7557433/5628), I had a go at cleaning up implementation so that using it multiple times on the same page is easier:



                                                                  $(function() {

                                                                  $(window).on('load resize scroll', function() {
                                                                  addClassToElementInViewport($('.bug-icon'), 'animate-bug-icon');
                                                                  addClassToElementInViewport($('.another-thing'), 'animate-thing');
                                                                  // 👏 repeat as needed ...
                                                                  });

                                                                  function addClassToElementInViewport(element, newClass) {
                                                                  if (inViewport(element)) {
                                                                  element.addClass(newClass);
                                                                  }
                                                                  }

                                                                  function inViewport(element) {
                                                                  if (typeof jQuery === "function" && element instanceof jQuery) {
                                                                  element = element[0];
                                                                  }
                                                                  var elementBounds = element.getBoundingClientRect();
                                                                  return (
                                                                  elementBounds.top >= 0 &&
                                                                  elementBounds.left >= 0 &&
                                                                  elementBounds.bottom <= $(window).height() &&
                                                                  elementBounds.right <= $(window).width()
                                                                  );
                                                                  }

                                                                  });


                                                                  The way I'm using it is that when the element scrolls into view, I'm adding a class that triggers a css keyframe animation. It's pretty straightforward and works especially well when you've got like 10+ things to conditionally animate on a page.



                                                                  Hope it helps!






                                                                  share|improve this answer















                                                                  Based on @dan's solution above (https://stackoverflow.com/a/7557433/5628), I had a go at cleaning up implementation so that using it multiple times on the same page is easier:



                                                                  $(function() {

                                                                  $(window).on('load resize scroll', function() {
                                                                  addClassToElementInViewport($('.bug-icon'), 'animate-bug-icon');
                                                                  addClassToElementInViewport($('.another-thing'), 'animate-thing');
                                                                  // 👏 repeat as needed ...
                                                                  });

                                                                  function addClassToElementInViewport(element, newClass) {
                                                                  if (inViewport(element)) {
                                                                  element.addClass(newClass);
                                                                  }
                                                                  }

                                                                  function inViewport(element) {
                                                                  if (typeof jQuery === "function" && element instanceof jQuery) {
                                                                  element = element[0];
                                                                  }
                                                                  var elementBounds = element.getBoundingClientRect();
                                                                  return (
                                                                  elementBounds.top >= 0 &&
                                                                  elementBounds.left >= 0 &&
                                                                  elementBounds.bottom <= $(window).height() &&
                                                                  elementBounds.right <= $(window).width()
                                                                  );
                                                                  }

                                                                  });


                                                                  The way I'm using it is that when the element scrolls into view, I'm adding a class that triggers a css keyframe animation. It's pretty straightforward and works especially well when you've got like 10+ things to conditionally animate on a page.



                                                                  Hope it helps!







                                                                  share|improve this answer














                                                                  share|improve this answer



                                                                  share|improve this answer








                                                                  edited May 23 '17 at 11:55









                                                                  Community

                                                                  11




                                                                  11










                                                                  answered Dec 26 '14 at 21:00









                                                                  PirijanPirijan

                                                                  2,09231126




                                                                  2,09231126













                                                                  • You should definitely cache $window = $(window) outside the scroll handler

                                                                    – Adam Rehal
                                                                    Nov 1 '17 at 8:13



















                                                                  • You should definitely cache $window = $(window) outside the scroll handler

                                                                    – Adam Rehal
                                                                    Nov 1 '17 at 8:13

















                                                                  You should definitely cache $window = $(window) outside the scroll handler

                                                                  – Adam Rehal
                                                                  Nov 1 '17 at 8:13





                                                                  You should definitely cache $window = $(window) outside the scroll handler

                                                                  – Adam Rehal
                                                                  Nov 1 '17 at 8:13











                                                                  1














                                                                  Here's my solution, it will work if an element is hidden inside a scroll-able container.



                                                                  Here's a demo (try re-sizing the window to)



                                                                  var visibleY = function(el){
                                                                  var top = el.getBoundingClientRect().top, rect, el = el.parentNode;
                                                                  do {
                                                                  rect = el.getBoundingClientRect();
                                                                  if (top <= rect.bottom === false)
                                                                  return false;
                                                                  el = el.parentNode;
                                                                  } while (el != document.body);
                                                                  // Check its within the document viewport
                                                                  return top <= document.documentElement.clientHeight;
                                                                  };


                                                                  I only needed to check if it's visible in the Y axis (for a scrolling ajax load more records feature).






                                                                  share|improve this answer






























                                                                    1














                                                                    Here's my solution, it will work if an element is hidden inside a scroll-able container.



                                                                    Here's a demo (try re-sizing the window to)



                                                                    var visibleY = function(el){
                                                                    var top = el.getBoundingClientRect().top, rect, el = el.parentNode;
                                                                    do {
                                                                    rect = el.getBoundingClientRect();
                                                                    if (top <= rect.bottom === false)
                                                                    return false;
                                                                    el = el.parentNode;
                                                                    } while (el != document.body);
                                                                    // Check its within the document viewport
                                                                    return top <= document.documentElement.clientHeight;
                                                                    };


                                                                    I only needed to check if it's visible in the Y axis (for a scrolling ajax load more records feature).






                                                                    share|improve this answer




























                                                                      1












                                                                      1








                                                                      1







                                                                      Here's my solution, it will work if an element is hidden inside a scroll-able container.



                                                                      Here's a demo (try re-sizing the window to)



                                                                      var visibleY = function(el){
                                                                      var top = el.getBoundingClientRect().top, rect, el = el.parentNode;
                                                                      do {
                                                                      rect = el.getBoundingClientRect();
                                                                      if (top <= rect.bottom === false)
                                                                      return false;
                                                                      el = el.parentNode;
                                                                      } while (el != document.body);
                                                                      // Check its within the document viewport
                                                                      return top <= document.documentElement.clientHeight;
                                                                      };


                                                                      I only needed to check if it's visible in the Y axis (for a scrolling ajax load more records feature).






                                                                      share|improve this answer















                                                                      Here's my solution, it will work if an element is hidden inside a scroll-able container.



                                                                      Here's a demo (try re-sizing the window to)



                                                                      var visibleY = function(el){
                                                                      var top = el.getBoundingClientRect().top, rect, el = el.parentNode;
                                                                      do {
                                                                      rect = el.getBoundingClientRect();
                                                                      if (top <= rect.bottom === false)
                                                                      return false;
                                                                      el = el.parentNode;
                                                                      } while (el != document.body);
                                                                      // Check its within the document viewport
                                                                      return top <= document.documentElement.clientHeight;
                                                                      };


                                                                      I only needed to check if it's visible in the Y axis (for a scrolling ajax load more records feature).







                                                                      share|improve this answer














                                                                      share|improve this answer



                                                                      share|improve this answer








                                                                      edited Feb 7 '14 at 13:03

























                                                                      answered Feb 7 '14 at 11:39









                                                                      AllyAlly

                                                                      3,09132639




                                                                      3,09132639























                                                                          1














                                                                          The easy and small solution that has worked for me.



                                                                          Example You want to see if the element is visible in parent element that has overflow scroll.



                                                                          $(window).on('scroll', function () {  

                                                                          var container = $('#sidebar');
                                                                          var containerHeight = container.height();
                                                                          var scrollPosition = $('#row1').offset().top - container.offset().top;

                                                                          if (containerHeight < scrollPosition) {
                                                                          console.log('not visible');
                                                                          } else {
                                                                          console.log('visible');
                                                                          }
                                                                          })





                                                                          share|improve this answer






























                                                                            1














                                                                            The easy and small solution that has worked for me.



                                                                            Example You want to see if the element is visible in parent element that has overflow scroll.



                                                                            $(window).on('scroll', function () {  

                                                                            var container = $('#sidebar');
                                                                            var containerHeight = container.height();
                                                                            var scrollPosition = $('#row1').offset().top - container.offset().top;

                                                                            if (containerHeight < scrollPosition) {
                                                                            console.log('not visible');
                                                                            } else {
                                                                            console.log('visible');
                                                                            }
                                                                            })





                                                                            share|improve this answer




























                                                                              1












                                                                              1








                                                                              1







                                                                              The easy and small solution that has worked for me.



                                                                              Example You want to see if the element is visible in parent element that has overflow scroll.



                                                                              $(window).on('scroll', function () {  

                                                                              var container = $('#sidebar');
                                                                              var containerHeight = container.height();
                                                                              var scrollPosition = $('#row1').offset().top - container.offset().top;

                                                                              if (containerHeight < scrollPosition) {
                                                                              console.log('not visible');
                                                                              } else {
                                                                              console.log('visible');
                                                                              }
                                                                              })





                                                                              share|improve this answer















                                                                              The easy and small solution that has worked for me.



                                                                              Example You want to see if the element is visible in parent element that has overflow scroll.



                                                                              $(window).on('scroll', function () {  

                                                                              var container = $('#sidebar');
                                                                              var containerHeight = container.height();
                                                                              var scrollPosition = $('#row1').offset().top - container.offset().top;

                                                                              if (containerHeight < scrollPosition) {
                                                                              console.log('not visible');
                                                                              } else {
                                                                              console.log('visible');
                                                                              }
                                                                              })






                                                                              share|improve this answer














                                                                              share|improve this answer



                                                                              share|improve this answer








                                                                              edited Dec 9 '17 at 19:56









                                                                              Dave

                                                                              5,86773348




                                                                              5,86773348










                                                                              answered Jun 19 '17 at 10:49









                                                                              Stevan TosicStevan Tosic

                                                                              1,18711035




                                                                              1,18711035























                                                                                  0














                                                                                  A better solution:



                                                                                  function getViewportSize(w) {
                                                                                  var w = w || window;
                                                                                  if(w.innerWidth != null) return {w:w.innerWidth, h:w.innerHeight};
                                                                                  var d = w.document;
                                                                                  if (document.compatMode == "CSS1Compat") {
                                                                                  return {
                                                                                  w: d.documentElement.clientWidth,
                                                                                  h: d.documentElement.clientHeight
                                                                                  };
                                                                                  }
                                                                                  return { w: d.body.clientWidth, h: d.body.clientWidth };
                                                                                  }
                                                                                  function isViewportVisible(e) {
                                                                                  var box = e.getBoundingClientRect();
                                                                                  var height = box.height || (box.bottom - box.top);
                                                                                  var width = box.width || (box.right - box.left);
                                                                                  var viewport = getViewportSize();
                                                                                  if(!height || !width) return false;
                                                                                  if(box.top > viewport.h || box.bottom < 0) return false;
                                                                                  if(box.right < 0 || box.left > viewport.w) return false;
                                                                                  return true;
                                                                                  }





                                                                                  share|improve this answer



















                                                                                  • 10





                                                                                    You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                    – Andy E
                                                                                    Mar 4 '13 at 13:46











                                                                                  • Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                    – teter
                                                                                    May 13 '15 at 9:10


















                                                                                  0














                                                                                  A better solution:



                                                                                  function getViewportSize(w) {
                                                                                  var w = w || window;
                                                                                  if(w.innerWidth != null) return {w:w.innerWidth, h:w.innerHeight};
                                                                                  var d = w.document;
                                                                                  if (document.compatMode == "CSS1Compat") {
                                                                                  return {
                                                                                  w: d.documentElement.clientWidth,
                                                                                  h: d.documentElement.clientHeight
                                                                                  };
                                                                                  }
                                                                                  return { w: d.body.clientWidth, h: d.body.clientWidth };
                                                                                  }
                                                                                  function isViewportVisible(e) {
                                                                                  var box = e.getBoundingClientRect();
                                                                                  var height = box.height || (box.bottom - box.top);
                                                                                  var width = box.width || (box.right - box.left);
                                                                                  var viewport = getViewportSize();
                                                                                  if(!height || !width) return false;
                                                                                  if(box.top > viewport.h || box.bottom < 0) return false;
                                                                                  if(box.right < 0 || box.left > viewport.w) return false;
                                                                                  return true;
                                                                                  }





                                                                                  share|improve this answer



















                                                                                  • 10





                                                                                    You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                    – Andy E
                                                                                    Mar 4 '13 at 13:46











                                                                                  • Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                    – teter
                                                                                    May 13 '15 at 9:10
















                                                                                  0












                                                                                  0








                                                                                  0







                                                                                  A better solution:



                                                                                  function getViewportSize(w) {
                                                                                  var w = w || window;
                                                                                  if(w.innerWidth != null) return {w:w.innerWidth, h:w.innerHeight};
                                                                                  var d = w.document;
                                                                                  if (document.compatMode == "CSS1Compat") {
                                                                                  return {
                                                                                  w: d.documentElement.clientWidth,
                                                                                  h: d.documentElement.clientHeight
                                                                                  };
                                                                                  }
                                                                                  return { w: d.body.clientWidth, h: d.body.clientWidth };
                                                                                  }
                                                                                  function isViewportVisible(e) {
                                                                                  var box = e.getBoundingClientRect();
                                                                                  var height = box.height || (box.bottom - box.top);
                                                                                  var width = box.width || (box.right - box.left);
                                                                                  var viewport = getViewportSize();
                                                                                  if(!height || !width) return false;
                                                                                  if(box.top > viewport.h || box.bottom < 0) return false;
                                                                                  if(box.right < 0 || box.left > viewport.w) return false;
                                                                                  return true;
                                                                                  }





                                                                                  share|improve this answer













                                                                                  A better solution:



                                                                                  function getViewportSize(w) {
                                                                                  var w = w || window;
                                                                                  if(w.innerWidth != null) return {w:w.innerWidth, h:w.innerHeight};
                                                                                  var d = w.document;
                                                                                  if (document.compatMode == "CSS1Compat") {
                                                                                  return {
                                                                                  w: d.documentElement.clientWidth,
                                                                                  h: d.documentElement.clientHeight
                                                                                  };
                                                                                  }
                                                                                  return { w: d.body.clientWidth, h: d.body.clientWidth };
                                                                                  }
                                                                                  function isViewportVisible(e) {
                                                                                  var box = e.getBoundingClientRect();
                                                                                  var height = box.height || (box.bottom - box.top);
                                                                                  var width = box.width || (box.right - box.left);
                                                                                  var viewport = getViewportSize();
                                                                                  if(!height || !width) return false;
                                                                                  if(box.top > viewport.h || box.bottom < 0) return false;
                                                                                  if(box.right < 0 || box.left > viewport.w) return false;
                                                                                  return true;
                                                                                  }






                                                                                  share|improve this answer












                                                                                  share|improve this answer



                                                                                  share|improve this answer










                                                                                  answered Feb 8 '13 at 8:57









                                                                                  rainyjunerainyjune

                                                                                  21




                                                                                  21








                                                                                  • 10





                                                                                    You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                    – Andy E
                                                                                    Mar 4 '13 at 13:46











                                                                                  • Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                    – teter
                                                                                    May 13 '15 at 9:10
















                                                                                  • 10





                                                                                    You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                    – Andy E
                                                                                    Mar 4 '13 at 13:46











                                                                                  • Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                    – teter
                                                                                    May 13 '15 at 9:10










                                                                                  10




                                                                                  10





                                                                                  You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                  – Andy E
                                                                                  Mar 4 '13 at 13:46





                                                                                  You should try and explain why your version is better. As it stands, it looks more or less the same as the other solutions.

                                                                                  – Andy E
                                                                                  Mar 4 '13 at 13:46













                                                                                  Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                  – teter
                                                                                  May 13 '15 at 9:10







                                                                                  Great solution it has a BOX/ScrollContainer and is not using the WINDOW (only if its not specified). Take a look at the code than rate it is a more universal solution (Was searching for it a lot)

                                                                                  – teter
                                                                                  May 13 '15 at 9:10













                                                                                  0














                                                                                  Checks if element is at least partially in view (vertical dimension):



                                                                                  function inView(element) {
                                                                                  var box = element.getBoundingClientRect();
                                                                                  return inViewBox(box);
                                                                                  }

                                                                                  function inViewBox(box) {
                                                                                  return ((box.bottom < 0) || (box.top > getWindowSize().h)) ? false : true;
                                                                                  }


                                                                                  function getWindowSize() {
                                                                                  return { w: document.body.offsetWidth || document.documentElement.offsetWidth || window.innerWidth, h: document.body.offsetHeight || document.documentElement.offsetHeight || window.innerHeight}
                                                                                  }





                                                                                  share|improve this answer




























                                                                                    0














                                                                                    Checks if element is at least partially in view (vertical dimension):



                                                                                    function inView(element) {
                                                                                    var box = element.getBoundingClientRect();
                                                                                    return inViewBox(box);
                                                                                    }

                                                                                    function inViewBox(box) {
                                                                                    return ((box.bottom < 0) || (box.top > getWindowSize().h)) ? false : true;
                                                                                    }


                                                                                    function getWindowSize() {
                                                                                    return { w: document.body.offsetWidth || document.documentElement.offsetWidth || window.innerWidth, h: document.body.offsetHeight || document.documentElement.offsetHeight || window.innerHeight}
                                                                                    }





                                                                                    share|improve this answer


























                                                                                      0












                                                                                      0








                                                                                      0







                                                                                      Checks if element is at least partially in view (vertical dimension):



                                                                                      function inView(element) {
                                                                                      var box = element.getBoundingClientRect();
                                                                                      return inViewBox(box);
                                                                                      }

                                                                                      function inViewBox(box) {
                                                                                      return ((box.bottom < 0) || (box.top > getWindowSize().h)) ? false : true;
                                                                                      }


                                                                                      function getWindowSize() {
                                                                                      return { w: document.body.offsetWidth || document.documentElement.offsetWidth || window.innerWidth, h: document.body.offsetHeight || document.documentElement.offsetHeight || window.innerHeight}
                                                                                      }





                                                                                      share|improve this answer













                                                                                      Checks if element is at least partially in view (vertical dimension):



                                                                                      function inView(element) {
                                                                                      var box = element.getBoundingClientRect();
                                                                                      return inViewBox(box);
                                                                                      }

                                                                                      function inViewBox(box) {
                                                                                      return ((box.bottom < 0) || (box.top > getWindowSize().h)) ? false : true;
                                                                                      }


                                                                                      function getWindowSize() {
                                                                                      return { w: document.body.offsetWidth || document.documentElement.offsetWidth || window.innerWidth, h: document.body.offsetHeight || document.documentElement.offsetHeight || window.innerHeight}
                                                                                      }






                                                                                      share|improve this answer












                                                                                      share|improve this answer



                                                                                      share|improve this answer










                                                                                      answered Jan 2 '15 at 12:17









                                                                                      LumicLumic

                                                                                      332




                                                                                      332























                                                                                          0














                                                                                          I had the same question and figured it out by using getBoundingClientRect(). This code is completely 'generic' and only has to be written once for it to work (you don't have to write it out for each element that you want to know is in the viewport). This code only checks to see if it is vertically in the viewport not horizontally. In this case, the variable (array) 'elements' holds all the elements that you are checking to be vertically in the viewport, so grab any elements you want anywhere and store them there. The 'for loop', loops through each element and checks to see if it is vertically in the viewport. This code executes every time the user scrolls! If the getBoudingClientRect().top is less than 3/4 the viewport (the element is one quarter in the viewport), it registers as 'in the viewport'. Since the code is generic, you will want to know 'which' element is in the viewport. To find that out, you can determine it by custom attribute, node name, id, class name, and more. Here is my code (Tell me if it doesn't work, it has been tested in IE 11, FireFox 40.0.3, Chrome Version 45.0.2454.85 m, Opera 31.0.1889.174, and Edge with Windows 10, [not Safari yet])...



                                                                                          //scrolling handlers...
                                                                                          window.onscroll = function(){
                                                                                          var elements = document.getElementById('whatever').getElementsByClassName('whatever');
                                                                                          for(var i = 0; i != elements.length; i++)
                                                                                          {
                                                                                          if(elements[i].getBoundingClientRect().top <= window.innerHeight*0.75 && elements[i].getBoundingClientRect().top > 0)
                                                                                          {
                                                                                          console.log(elements[i].nodeName + ' ' + elements[i].className + ' ' + elements[i].id + ' is in the viewport; proceed with whatever code you want to do here.');
                                                                                          }
                                                                                          };


                                                                                          Hope this helps someone :-)






                                                                                          share|improve this answer




























                                                                                            0














                                                                                            I had the same question and figured it out by using getBoundingClientRect(). This code is completely 'generic' and only has to be written once for it to work (you don't have to write it out for each element that you want to know is in the viewport). This code only checks to see if it is vertically in the viewport not horizontally. In this case, the variable (array) 'elements' holds all the elements that you are checking to be vertically in the viewport, so grab any elements you want anywhere and store them there. The 'for loop', loops through each element and checks to see if it is vertically in the viewport. This code executes every time the user scrolls! If the getBoudingClientRect().top is less than 3/4 the viewport (the element is one quarter in the viewport), it registers as 'in the viewport'. Since the code is generic, you will want to know 'which' element is in the viewport. To find that out, you can determine it by custom attribute, node name, id, class name, and more. Here is my code (Tell me if it doesn't work, it has been tested in IE 11, FireFox 40.0.3, Chrome Version 45.0.2454.85 m, Opera 31.0.1889.174, and Edge with Windows 10, [not Safari yet])...



                                                                                            //scrolling handlers...
                                                                                            window.onscroll = function(){
                                                                                            var elements = document.getElementById('whatever').getElementsByClassName('whatever');
                                                                                            for(var i = 0; i != elements.length; i++)
                                                                                            {
                                                                                            if(elements[i].getBoundingClientRect().top <= window.innerHeight*0.75 && elements[i].getBoundingClientRect().top > 0)
                                                                                            {
                                                                                            console.log(elements[i].nodeName + ' ' + elements[i].className + ' ' + elements[i].id + ' is in the viewport; proceed with whatever code you want to do here.');
                                                                                            }
                                                                                            };


                                                                                            Hope this helps someone :-)






                                                                                            share|improve this answer


























                                                                                              0












                                                                                              0








                                                                                              0







                                                                                              I had the same question and figured it out by using getBoundingClientRect(). This code is completely 'generic' and only has to be written once for it to work (you don't have to write it out for each element that you want to know is in the viewport). This code only checks to see if it is vertically in the viewport not horizontally. In this case, the variable (array) 'elements' holds all the elements that you are checking to be vertically in the viewport, so grab any elements you want anywhere and store them there. The 'for loop', loops through each element and checks to see if it is vertically in the viewport. This code executes every time the user scrolls! If the getBoudingClientRect().top is less than 3/4 the viewport (the element is one quarter in the viewport), it registers as 'in the viewport'. Since the code is generic, you will want to know 'which' element is in the viewport. To find that out, you can determine it by custom attribute, node name, id, class name, and more. Here is my code (Tell me if it doesn't work, it has been tested in IE 11, FireFox 40.0.3, Chrome Version 45.0.2454.85 m, Opera 31.0.1889.174, and Edge with Windows 10, [not Safari yet])...



                                                                                              //scrolling handlers...
                                                                                              window.onscroll = function(){
                                                                                              var elements = document.getElementById('whatever').getElementsByClassName('whatever');
                                                                                              for(var i = 0; i != elements.length; i++)
                                                                                              {
                                                                                              if(elements[i].getBoundingClientRect().top <= window.innerHeight*0.75 && elements[i].getBoundingClientRect().top > 0)
                                                                                              {
                                                                                              console.log(elements[i].nodeName + ' ' + elements[i].className + ' ' + elements[i].id + ' is in the viewport; proceed with whatever code you want to do here.');
                                                                                              }
                                                                                              };


                                                                                              Hope this helps someone :-)






                                                                                              share|improve this answer













                                                                                              I had the same question and figured it out by using getBoundingClientRect(). This code is completely 'generic' and only has to be written once for it to work (you don't have to write it out for each element that you want to know is in the viewport). This code only checks to see if it is vertically in the viewport not horizontally. In this case, the variable (array) 'elements' holds all the elements that you are checking to be vertically in the viewport, so grab any elements you want anywhere and store them there. The 'for loop', loops through each element and checks to see if it is vertically in the viewport. This code executes every time the user scrolls! If the getBoudingClientRect().top is less than 3/4 the viewport (the element is one quarter in the viewport), it registers as 'in the viewport'. Since the code is generic, you will want to know 'which' element is in the viewport. To find that out, you can determine it by custom attribute, node name, id, class name, and more. Here is my code (Tell me if it doesn't work, it has been tested in IE 11, FireFox 40.0.3, Chrome Version 45.0.2454.85 m, Opera 31.0.1889.174, and Edge with Windows 10, [not Safari yet])...



                                                                                              //scrolling handlers...
                                                                                              window.onscroll = function(){
                                                                                              var elements = document.getElementById('whatever').getElementsByClassName('whatever');
                                                                                              for(var i = 0; i != elements.length; i++)
                                                                                              {
                                                                                              if(elements[i].getBoundingClientRect().top <= window.innerHeight*0.75 && elements[i].getBoundingClientRect().top > 0)
                                                                                              {
                                                                                              console.log(elements[i].nodeName + ' ' + elements[i].className + ' ' + elements[i].id + ' is in the viewport; proceed with whatever code you want to do here.');
                                                                                              }
                                                                                              };


                                                                                              Hope this helps someone :-)







                                                                                              share|improve this answer












                                                                                              share|improve this answer



                                                                                              share|improve this answer










                                                                                              answered Sep 13 '15 at 13:59









                                                                                              www139www139

                                                                                              2,92811636




                                                                                              2,92811636























                                                                                                  0














                                                                                                  Here is a function that tells if an element is in visible in the current viewport of a parent element:



                                                                                                  function inParentViewport(el, pa) {
                                                                                                  if (typeof jQuery === "function"){
                                                                                                  if (el instanceof jQuery)
                                                                                                  el = el[0];
                                                                                                  if (pa instanceof jQuery)
                                                                                                  pa = pa[0];
                                                                                                  }

                                                                                                  var e = el.getBoundingClientRect();
                                                                                                  var p = pa.getBoundingClientRect();

                                                                                                  return (
                                                                                                  e.bottom >= p.top &&
                                                                                                  e.right >= p.left &&
                                                                                                  e.top <= p.bottom &&
                                                                                                  e.left <= p.right
                                                                                                  );
                                                                                                  }





                                                                                                  share|improve this answer




























                                                                                                    0














                                                                                                    Here is a function that tells if an element is in visible in the current viewport of a parent element:



                                                                                                    function inParentViewport(el, pa) {
                                                                                                    if (typeof jQuery === "function"){
                                                                                                    if (el instanceof jQuery)
                                                                                                    el = el[0];
                                                                                                    if (pa instanceof jQuery)
                                                                                                    pa = pa[0];
                                                                                                    }

                                                                                                    var e = el.getBoundingClientRect();
                                                                                                    var p = pa.getBoundingClientRect();

                                                                                                    return (
                                                                                                    e.bottom >= p.top &&
                                                                                                    e.right >= p.left &&
                                                                                                    e.top <= p.bottom &&
                                                                                                    e.left <= p.right
                                                                                                    );
                                                                                                    }





                                                                                                    share|improve this answer


























                                                                                                      0












                                                                                                      0








                                                                                                      0







                                                                                                      Here is a function that tells if an element is in visible in the current viewport of a parent element:



                                                                                                      function inParentViewport(el, pa) {
                                                                                                      if (typeof jQuery === "function"){
                                                                                                      if (el instanceof jQuery)
                                                                                                      el = el[0];
                                                                                                      if (pa instanceof jQuery)
                                                                                                      pa = pa[0];
                                                                                                      }

                                                                                                      var e = el.getBoundingClientRect();
                                                                                                      var p = pa.getBoundingClientRect();

                                                                                                      return (
                                                                                                      e.bottom >= p.top &&
                                                                                                      e.right >= p.left &&
                                                                                                      e.top <= p.bottom &&
                                                                                                      e.left <= p.right
                                                                                                      );
                                                                                                      }





                                                                                                      share|improve this answer













                                                                                                      Here is a function that tells if an element is in visible in the current viewport of a parent element:



                                                                                                      function inParentViewport(el, pa) {
                                                                                                      if (typeof jQuery === "function"){
                                                                                                      if (el instanceof jQuery)
                                                                                                      el = el[0];
                                                                                                      if (pa instanceof jQuery)
                                                                                                      pa = pa[0];
                                                                                                      }

                                                                                                      var e = el.getBoundingClientRect();
                                                                                                      var p = pa.getBoundingClientRect();

                                                                                                      return (
                                                                                                      e.bottom >= p.top &&
                                                                                                      e.right >= p.left &&
                                                                                                      e.top <= p.bottom &&
                                                                                                      e.left <= p.right
                                                                                                      );
                                                                                                      }






                                                                                                      share|improve this answer












                                                                                                      share|improve this answer



                                                                                                      share|improve this answer










                                                                                                      answered Sep 28 '18 at 10:01









                                                                                                      sstenssten

                                                                                                      394313




                                                                                                      394313























                                                                                                          -1














                                                                                                          I use this function (it only checks if the y is inscreen since most of the time the x is not needed)



                                                                                                          function elementInViewport(el) {
                                                                                                          var elinfo = {
                                                                                                          "top":el.offsetTop,
                                                                                                          "height":el.offsetHeight,
                                                                                                          };

                                                                                                          if (elinfo.top + elinfo.height < window.pageYOffset || elinfo.top > window.pageYOffset + window.innerHeight) {
                                                                                                          return false;
                                                                                                          } else {
                                                                                                          return true;
                                                                                                          }

                                                                                                          }





                                                                                                          share|improve this answer




























                                                                                                            -1














                                                                                                            I use this function (it only checks if the y is inscreen since most of the time the x is not needed)



                                                                                                            function elementInViewport(el) {
                                                                                                            var elinfo = {
                                                                                                            "top":el.offsetTop,
                                                                                                            "height":el.offsetHeight,
                                                                                                            };

                                                                                                            if (elinfo.top + elinfo.height < window.pageYOffset || elinfo.top > window.pageYOffset + window.innerHeight) {
                                                                                                            return false;
                                                                                                            } else {
                                                                                                            return true;
                                                                                                            }

                                                                                                            }





                                                                                                            share|improve this answer


























                                                                                                              -1












                                                                                                              -1








                                                                                                              -1







                                                                                                              I use this function (it only checks if the y is inscreen since most of the time the x is not needed)



                                                                                                              function elementInViewport(el) {
                                                                                                              var elinfo = {
                                                                                                              "top":el.offsetTop,
                                                                                                              "height":el.offsetHeight,
                                                                                                              };

                                                                                                              if (elinfo.top + elinfo.height < window.pageYOffset || elinfo.top > window.pageYOffset + window.innerHeight) {
                                                                                                              return false;
                                                                                                              } else {
                                                                                                              return true;
                                                                                                              }

                                                                                                              }





                                                                                                              share|improve this answer













                                                                                                              I use this function (it only checks if the y is inscreen since most of the time the x is not needed)



                                                                                                              function elementInViewport(el) {
                                                                                                              var elinfo = {
                                                                                                              "top":el.offsetTop,
                                                                                                              "height":el.offsetHeight,
                                                                                                              };

                                                                                                              if (elinfo.top + elinfo.height < window.pageYOffset || elinfo.top > window.pageYOffset + window.innerHeight) {
                                                                                                              return false;
                                                                                                              } else {
                                                                                                              return true;
                                                                                                              }

                                                                                                              }






                                                                                                              share|improve this answer












                                                                                                              share|improve this answer



                                                                                                              share|improve this answer










                                                                                                              answered Jan 13 '17 at 6:57









                                                                                                              sanderjonk01sanderjonk01

                                                                                                              123




                                                                                                              123























                                                                                                                  -2














                                                                                                                  For a similar challenge i really enjoyed this gist which exposes a polyfill for scrollIntoViewIfNeeded().



                                                                                                                  All the necessary Kung Fu needed to answer is within this block:



                                                                                                                  var parent = this.parentNode,
                                                                                                                  parentComputedStyle = window.getComputedStyle(parent, null),
                                                                                                                  parentBorderTopWidth = parseInt(parentComputedStyle.getPropertyValue('border-top-width')),
                                                                                                                  parentBorderLeftWidth = parseInt(parentComputedStyle.getPropertyValue('border-left-width')),
                                                                                                                  overTop = this.offsetTop - parent.offsetTop < parent.scrollTop,
                                                                                                                  overBottom = (this.offsetTop - parent.offsetTop + this.clientHeight - parentBorderTopWidth) > (parent.scrollTop + parent.clientHeight),
                                                                                                                  overLeft = this.offsetLeft - parent.offsetLeft < parent.scrollLeft,
                                                                                                                  overRight = (this.offsetLeft - parent.offsetLeft + this.clientWidth - parentBorderLeftWidth) > (parent.scrollLeft + parent.clientWidth),
                                                                                                                  alignWithTop = overTop && !overBottom;


                                                                                                                  this refers to the element that you want to know if it is i.e. overTop or overBottom - just should get the drift...






                                                                                                                  share|improve this answer




























                                                                                                                    -2














                                                                                                                    For a similar challenge i really enjoyed this gist which exposes a polyfill for scrollIntoViewIfNeeded().



                                                                                                                    All the necessary Kung Fu needed to answer is within this block:



                                                                                                                    var parent = this.parentNode,
                                                                                                                    parentComputedStyle = window.getComputedStyle(parent, null),
                                                                                                                    parentBorderTopWidth = parseInt(parentComputedStyle.getPropertyValue('border-top-width')),
                                                                                                                    parentBorderLeftWidth = parseInt(parentComputedStyle.getPropertyValue('border-left-width')),
                                                                                                                    overTop = this.offsetTop - parent.offsetTop < parent.scrollTop,
                                                                                                                    overBottom = (this.offsetTop - parent.offsetTop + this.clientHeight - parentBorderTopWidth) > (parent.scrollTop + parent.clientHeight),
                                                                                                                    overLeft = this.offsetLeft - parent.offsetLeft < parent.scrollLeft,
                                                                                                                    overRight = (this.offsetLeft - parent.offsetLeft + this.clientWidth - parentBorderLeftWidth) > (parent.scrollLeft + parent.clientWidth),
                                                                                                                    alignWithTop = overTop && !overBottom;


                                                                                                                    this refers to the element that you want to know if it is i.e. overTop or overBottom - just should get the drift...






                                                                                                                    share|improve this answer


























                                                                                                                      -2












                                                                                                                      -2








                                                                                                                      -2







                                                                                                                      For a similar challenge i really enjoyed this gist which exposes a polyfill for scrollIntoViewIfNeeded().



                                                                                                                      All the necessary Kung Fu needed to answer is within this block:



                                                                                                                      var parent = this.parentNode,
                                                                                                                      parentComputedStyle = window.getComputedStyle(parent, null),
                                                                                                                      parentBorderTopWidth = parseInt(parentComputedStyle.getPropertyValue('border-top-width')),
                                                                                                                      parentBorderLeftWidth = parseInt(parentComputedStyle.getPropertyValue('border-left-width')),
                                                                                                                      overTop = this.offsetTop - parent.offsetTop < parent.scrollTop,
                                                                                                                      overBottom = (this.offsetTop - parent.offsetTop + this.clientHeight - parentBorderTopWidth) > (parent.scrollTop + parent.clientHeight),
                                                                                                                      overLeft = this.offsetLeft - parent.offsetLeft < parent.scrollLeft,
                                                                                                                      overRight = (this.offsetLeft - parent.offsetLeft + this.clientWidth - parentBorderLeftWidth) > (parent.scrollLeft + parent.clientWidth),
                                                                                                                      alignWithTop = overTop && !overBottom;


                                                                                                                      this refers to the element that you want to know if it is i.e. overTop or overBottom - just should get the drift...






                                                                                                                      share|improve this answer













                                                                                                                      For a similar challenge i really enjoyed this gist which exposes a polyfill for scrollIntoViewIfNeeded().



                                                                                                                      All the necessary Kung Fu needed to answer is within this block:



                                                                                                                      var parent = this.parentNode,
                                                                                                                      parentComputedStyle = window.getComputedStyle(parent, null),
                                                                                                                      parentBorderTopWidth = parseInt(parentComputedStyle.getPropertyValue('border-top-width')),
                                                                                                                      parentBorderLeftWidth = parseInt(parentComputedStyle.getPropertyValue('border-left-width')),
                                                                                                                      overTop = this.offsetTop - parent.offsetTop < parent.scrollTop,
                                                                                                                      overBottom = (this.offsetTop - parent.offsetTop + this.clientHeight - parentBorderTopWidth) > (parent.scrollTop + parent.clientHeight),
                                                                                                                      overLeft = this.offsetLeft - parent.offsetLeft < parent.scrollLeft,
                                                                                                                      overRight = (this.offsetLeft - parent.offsetLeft + this.clientWidth - parentBorderLeftWidth) > (parent.scrollLeft + parent.clientWidth),
                                                                                                                      alignWithTop = overTop && !overBottom;


                                                                                                                      this refers to the element that you want to know if it is i.e. overTop or overBottom - just should get the drift...







                                                                                                                      share|improve this answer












                                                                                                                      share|improve this answer



                                                                                                                      share|improve this answer










                                                                                                                      answered Mar 14 '16 at 13:14









                                                                                                                      PhilzenPhilzen

                                                                                                                      1,9231630




                                                                                                                      1,9231630

















                                                                                                                          protected by Josh Crozier Feb 5 '15 at 3:43



                                                                                                                          Thank you for your interest in this question.
                                                                                                                          Because it has attracted low-quality or spam answers that had to be removed, posting an answer now requires 10 reputation on this site (the association bonus does not count).



                                                                                                                          Would you like to answer one of these unanswered questions instead?



                                                                                                                          Popular posts from this blog

                                                                                                                          Mossoró

                                                                                                                          Error while reading .h5 file using the rhdf5 package in R

                                                                                                                          Pushsharp Apns notification error: 'InvalidToken'