Skip to content

@Raynos /gist:1677639 forked from Zirak/gist:1677020
Created

Embed URL

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Visibility API
// assumes an ES5 compliant browser for Array.prototype.forEach
// and Object.defineProperty
// and a sane browser for Element.prototype.addEventListener
(function () {
"use strict";
//no need to shim if it's already there
if ( 'hidden' in document && 'onvisibilitychange' in document ) {
return;
}
// no-op on legacy browsers.
if ( !document.addEventListener ||
!Array.prototype.forEach ||
!Object.defineProperty ||
!window.addEventListener
) {
return;
}
//check to see if there's a native implementation
var prefixes = [ 'webkit', 'moz', 'o', 'ms' ], native = '', hiddenName = 'hidden';
prefixes.forEach(function ( prefix ) {
if ( (prefix + 'Hidden') in document ) {
native = prefix;
hiddenName = prefix + 'Hidden';
}
});
//will be called whenever the visibility has been changed
var visibilityChange = function () {
document[hiddenName] = hidden;
document.visibilityState = document.hidden ? 'hidden' : 'visible';
//create the visibilitychange event
var evt = document.createEvent( 'Event' );
evt.initEvent( 'visibilitychange', true, true );
//you're FIRED!
document.dispatchEvent( evt );
//check for document.onvisibilitychange and call it if it exists
var vischange = 'onvisibilitychange'; //it's really long to write...
if ( document[vischange] && document[vischange].call ) {
document[ vischange ].call( document, evt );
}
}, hidden = false;
//add the event listeners to tap into native functionality
if ( native ) {
document.addEventListener( native + 'visibilitychange', visibilityChange );
} else {
//the window.focus and window.blur events are, well, close enough
window.addEventListener( 'focus', function () {
hidden = false;
visibilityChange();
});
window.addEventListener( 'blur', function () {
hidden = true;
visibilityChange();
});
}
//add document.hidden, document.visibilityState
Object.defineProperty( document, 'hidden', {
value: hidden,
configurable: true
});
Object.defineProperty( document, 'visibilityState', {
value: document.hidden ? 'hidden' : 'visible',
configurable: true
});
}());
@domenic

The onvisibilitychange addition wasn't useless; it made it non-enumerable and null instead of undefined, like all other document.onwhatever properties.

@Raynos
Owner

@DomenicDenicola document.onclick === undefined; // true in Firefox.

@domenic

Not in Firefox 9... I'd screenshot my console window if I was a bit less lazy.

@Zirak

@Raynos defineProperty defines the property, it's an "I exist, acknowledge me". That way, things like the test in the beginning of the script, 'onvisibilitychange' in document, will give the correct results.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.