Created
July 11, 2012 16:39
-
-
Save ryankinal/3091608 to your computer and use it in GitHub Desktop.
POJS lightbox
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
These two functions (addEvent and removeEvent) should be added to common.js | |
- they are generally useful functions that could be used across the entire site | |
when custom javascript is needed. The lightbox requires them for use. | |
**/ | |
function addEvent( obj, type, fn ) | |
{ | |
if (obj.addEventListener) | |
{ | |
obj.addEventListener( type, fn, false ); | |
} | |
else if (obj.attachEvent) | |
{ | |
obj["e"+type+fn] = fn; | |
obj[type+fn] = function() { return obj["e"+type+fn]( window.event ); }; | |
obj.attachEvent( "on"+type, obj[type+fn] ); | |
} | |
} | |
function removeEvent( obj, type, fn ) | |
{ | |
if (obj.removeEventListener) | |
{ | |
obj.removeEventListener( type, fn, false ); | |
} | |
else if (obj.detachEvent) | |
{ | |
obj.detachEvent( "on"+type, obj[type+fn] ); | |
obj[type+fn] = null; | |
obj["e"+type+fn] = null; | |
} | |
} | |
/** | |
Gets the current scroll position of the window - might want to add | |
to common.js? Not sure we'll use it elsewhere. | |
**/ | |
var getScrollTop = function() | |
{ | |
var w = window.pageYOffset; | |
var d = document.documentElement ? document.documentElement.scrollTop : 0; | |
var b = document.body ? document.body.scrolltop : 0; | |
var val = w || d || b; | |
if (val) | |
{ | |
return val; | |
} | |
else | |
{ | |
return 0; | |
} | |
}; | |
/** | |
Gets the height of the window - not the document, but the viewport. Again, | |
may want to add to common.js. | |
**/ | |
var getWindowHeight = function() | |
{ | |
var w = window.innerHeight; | |
var d = document.documentElement ? document.documentElement.clientHeight : 0; | |
var b = document.body ? document.body.clientHeight : 0; | |
var val = w || d || b; | |
if (val) | |
{ | |
return val; | |
} | |
else | |
{ | |
return 0; | |
} | |
}; | |
/** | |
Gets the width of the window - not the document, but the viewport. Again, | |
may want to add to common.js | |
**/ | |
var getWindowWidth = function() | |
{ | |
var w = window.innerwidth; | |
var d = document.documentElement ? document.documentElement.clientWidth : 0; | |
var b = document.body ? document.body.clientWidth : 0; | |
var val = w || d || b; | |
if (val) | |
{ | |
return val; | |
} | |
else | |
{ | |
return 0; | |
} | |
}; | |
/** | |
Call this function to initialize ALL lightbox elements on the page | |
- lightbox elements are determined by links (<a> tags) with rel="lightbox". | |
The href should be #id where id is the id of the element to be shown | |
by that link. | |
You can pass a parameters object to the function to customize its behavior: | |
openCallBack: The function to be called after the lightbox opens | |
closeCallBack: The function to be called after the lightbox closes | |
sticky: Whether clicking outside the lightbox will close the lightbox - defaults to false | |
blanketColor: The color of the blanket fade-in - defaults to '#FFF' | |
ex: lb = lightbox({closeCallBack: function, sticky: true, blanketColor: '#000'}); | |
KNOWN ISSUE: | |
If 'sticky' is false, checkboxes will not function within the lightbox in Internet Explorer | |
**/ | |
var lightbox = function(p_params) | |
{ | |
var openCallBack; | |
var closeCallBack; | |
var sticky = false; | |
var blanketColor = '#FFF'; | |
if (p_params) | |
{ | |
if (p_params.hasOwnProperty('openCallBack') && typeof p_params.openCallBack === 'function') | |
{ | |
openCallBack = p_params.openCallBack; | |
} | |
if (p_params.hasOwnProperty('closeCallBack') && typeof p_params.closeCallBack === 'function') | |
{ | |
closeCallBack = p_params.closeCallBack; | |
} | |
if (p_params.hasOwnProperty('sticky') && typeof p_params.sticky === 'boolean') | |
{ | |
sticky = p_params.sticky; | |
} | |
if (p_params.hasOwnProperty('blanketColor') && typeof p_params.blanketColor === 'string') | |
{ | |
blanketColor = p_params.blanketColor; | |
} | |
} | |
/** | |
The blanket that covers the rest of the content while | |
the lightbox is shown. There is only one. | |
**/ | |
var blanket = document.getElementById('lightboxBlanket'); | |
if (!blanket) | |
{ | |
blanket = document.createElement('div'); | |
blanket.id = 'lightboxBlanket'; | |
blanket.style.position = 'absolute'; | |
blanket.style.left = '0'; | |
blanket.style.top = '0'; | |
blanket.style.width = '100%'; | |
blanket.style.height = '100%'; | |
blanket.style.display = 'none'; | |
blanket.style.backgroundColor = blanketColor; | |
blanket.style.filter = 'alpha(opacity=80)'; | |
blanket.style.opacity = '0.8'; | |
blanket.style.zIndex = '2000'; | |
} | |
document.body.appendChild(blanket); | |
/** | |
Fades the blanket in | |
**/ | |
var fadeBlanketIn = function() | |
{ | |
var max = 70; | |
var helper = function(p_opacity) | |
{ | |
if (p_opacity < max) | |
{ | |
blanket.style.opacity = p_opacity / 100; | |
blanket.style.filter = 'alpha(opacity=' + p_opacity + ')'; | |
setTimeout(function() { helper(p_opacity + 5); }, 3); | |
} | |
else | |
{ | |
blanket.style.opacity = max / 100; | |
blanket.style.filter = 'alpha(opacity=' + max + ')'; | |
} | |
}; | |
helper(0); | |
}; | |
/** | |
The close link - there is only one, and it gets passed around | |
between each of the lightboxes. | |
**/ | |
var closeLink = document.getElementById('lightboxClose'); | |
if (!closeLink) | |
{ | |
closeLink = document.createElement('a'); | |
var closeText = document.createTextNode('close'); | |
closeLink.href = '#'; | |
closeLink.className = 'lightboxClose'; | |
closeLink.id = 'lightboxClose'; | |
closeLink.style.display = 'block'; | |
closeLink.style.clear = 'both'; | |
closeLink.appendChild(closeText); | |
} | |
// Keep track of which lightbox is displayed | |
var displayed; | |
// A function to close the displayed lightbox - almost always called as an event handler | |
var closeDisplayed = function(e) | |
{ | |
if (displayed) | |
{ | |
displayed.style.display = 'none'; | |
blanket.style.display = 'none'; | |
if (!sticky) | |
{ | |
removeEvent(document, 'click', closeDisplayed); | |
} | |
displayed = undefined; | |
if (closeCallBack) | |
{ | |
closeCallBack(); | |
} | |
} | |
if (e && e.preventDefault) | |
{ | |
e.preventDefault(); | |
} | |
else if (window.event && window.event.returnValue) | |
{ | |
window.eventReturnValue = false; | |
} | |
return false; | |
}; | |
// Add the 'close' event | |
addEvent(closeLink, 'click', closeDisplayed); | |
// Add a resize event, so the blanket doesn't get screwed up | |
addEvent(window, 'resize', function() { | |
if (displayed) | |
{ | |
blanket.style.width = getWindowWidth() + 'px'; | |
blanket.style.height = Math.max(displayed.offsetHeight + 60, Math.max(document.body.offsetHeight + 30, getWindowHeight())) + 'px'; | |
} | |
}); | |
/** | |
Makes a click handler for the rel="lightbox" links, and returns it | |
This is where all the actual work happens. | |
**/ | |
var makeClick = function(p_href) | |
{ | |
/** Checking to see if the ID from p_href is valid **/ | |
var id = p_href.substring(p_href.indexOf('#') + 1); | |
var elem = document.getElementById(id); | |
if (elem) | |
{ | |
elem.style.position = 'absolute'; | |
elem.style.top = '50%'; | |
elem.style.left = '50%'; | |
elem.style.zIndex = parseInt(blanket.style.zIndex, 10) + 1; | |
/** The actual event handler **/ | |
return function(e) { | |
/** close anything that's displayed **/ | |
closeDisplayed(); | |
/** display the blanket **/ | |
blanket.style.display = 'block'; | |
blanket.style.width = getWindowWidth() + 'px'; | |
fadeBlanketIn(); | |
/** display and position the actual lightbox element **/ | |
elem.style.display = 'block'; | |
var adjustedOffset; | |
if (elem.offsetHeight > getWindowHeight()) | |
{ | |
// Element is bigger than the viewport | |
adjustedOffset = ((getWindowHeight() / 2) - 30) * -1; | |
} | |
else | |
{ | |
adjustedOffset = ((elem.offsetHeight / 2) - getScrollTop()) * -1; | |
} | |
elem.style.marginTop = adjustedOffset + 'px'; | |
elem.style.marginLeft = '-' + (elem.offsetWidth / 2) + 'px'; | |
elem.appendChild(closeLink); | |
displayed = elem; | |
/** | |
If the user clicks anywhere on the document, other than the | |
lightbox, it closes the lightbox. | |
**/ | |
if (!sticky) | |
{ | |
addEvent(document, 'click', closeDisplayed); | |
/** | |
Make sure that if the user clicks on the actual element, | |
it doesn't disappear - this stops the event bubble | |
**/ | |
addEvent(elem, 'click', function(e) { | |
if (!e) | |
{ | |
e = window.event; | |
} | |
e.cancelBubble = true; | |
if (e.stopPropagation) | |
{ | |
e.stopPropagation(); | |
} | |
return false; | |
}); | |
} | |
/** Set the blanket height after the element is displayed, to make sure we are | |
getting accurate measurements **/ | |
blanket.style.height = Math.max(elem.offsetHeight + 60, Math.max(document.body.offsetHeight + 30, getWindowHeight())) + 'px'; | |
/** | |
Stop event bubbling | |
**/ | |
if (!e) | |
{ | |
e = window.event; | |
} | |
e.cancelBubble = true; | |
if (e.stopPropagation) | |
{ | |
e.stopPropagation(); | |
} | |
/** | |
Prevent the default action (i.e. following the link) for newer browsers | |
**/ | |
if (e &&e.preventDefault) | |
{ | |
e.preventDefault(); | |
} | |
else if (window.event && window.event.returnValue) | |
{ | |
window.eventReturnValue = false; | |
} | |
if (openCallBack) | |
{ | |
openCallBack(); | |
} | |
/** | |
Prevent the default action (i.e. following the link) for older browsers | |
**/ | |
return false; | |
}; | |
} | |
else | |
{ | |
/** | |
If no element with the given ID exists, use the default action | |
**/ | |
return function() { return true; }; | |
} | |
}; | |
/** | |
Get all the anchors in the document, check to see if they're lightbox links, | |
and if they are, make them a click handler via makeClick() | |
**/ | |
var anchors = document.getElementsByTagName('a'); | |
var i = 0; | |
for (i =0; i < anchors.length; i = i + 1) | |
{ | |
if (anchors[i].rel === 'lightbox') | |
{ | |
addEvent(anchors[i], 'click', makeClick(anchors[i].href)); | |
} | |
} | |
/** | |
Return an object to control various aspects of the lightbox | |
- setCloseCallBack - sets a function to be run when the lightbox is closed | |
- setOpenCallBack - sets a function to be run when the lightbox is opened | |
- close - closes the lightbox | |
- getDisplayed - gets the element currently displayed in the lightbox | |
- setBlanketColor - changes the color of the blanket | |
**/ | |
var controlObject = { | |
setCloseCallBack: function(p_callback) | |
{ | |
if (typeof p_callback === 'function') | |
{ | |
closeCallBack = p_callback; | |
return true; | |
} | |
return false; | |
}, | |
setOpenCallBack: function(p_callback) | |
{ | |
if (typeof p_callback === 'function') | |
{ | |
openCallBack = p_callback; | |
return true; | |
} | |
return false; | |
}, | |
close: function() | |
{ | |
closeDisplayed(); | |
}, | |
getDisplayed: function() | |
{ | |
return displayed; | |
}, | |
setBlanketColor: function(p_color) | |
{ | |
if (typeof p_color === 'string') | |
{ | |
blanket.style.backgroundColor = p_color | |
} | |
} | |
}; | |
return controlObject; | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment