Skip to content

Instantly share code, notes, and snippets.

@subchen
Last active August 29, 2015 14:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save subchen/8dba405b182bc6f7358a to your computer and use it in GitHub Desktop.
Save subchen/8dba405b182bc6f7358a to your computer and use it in GitHub Desktop.
检查该元素是完全可见在当前视口 (How to tell if a DOM element is visible in the current viewport?)

see: http://ejohn.org/blog/getboundingclientrect-is-awesome/

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.

IE8 supports it fully, IE7 is not perfect, however it works better than the old answer.

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

Recommended by John Resig solution:

(tested: IE7+, iOS5+ Safari, Android2+, Blackberry, Opera Mobile, IE Mobile)

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 callback () {
    //your code here, e.g. console.log('is visible now');
} 


function fireIfElementVisible (el, callback) {
    return function () {
        if ( isElementInViewport(el) ) {
            callback();
        }
    }
}

var handler = fireIfElementVisible (el, callback);


//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);
}
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment