Created
August 2, 2012 09:20
-
-
Save hinke/3235736 to your computer and use it in GitHub Desktop.
Readmill send script
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
aavunction(window) { | |
var WIDGET_BASE_DOMAIN = 'https://widgets.readmill.com', | |
PLATFORM_BASE_DOMAIN = 'https://platform.readmill.com', | |
hasAutoTriggerProcessMarkersFired = false, doc = window.document; | |
/* | |
* Select most suitable method for getting all elements by tag name | |
* to support browsers that does not have getElementsByClassName | |
*/ | |
function getElementsByClassName(clsName) { | |
// Preferably use the native version | |
if(doc.getElementsByClassName) { | |
return doc.getElementsByClassName(clsName); | |
} | |
// Construct a manual getElementsByClassName (for IE < 9) | |
return (function() { | |
var elements = doc.getElementsByTagName('*'), | |
result = [], | |
clsRegex = new RegExp('(\\s|^)' + clsName + '(\\s|$)'); | |
for (i = elements.length; i--;) { | |
var el = elements[i], elementClass = el.className || el.getAttribute('class') || ''; | |
if (elementClass.match(clsRegex)) { | |
result.push(el); | |
} | |
} | |
return result; | |
})(); | |
} | |
/* | |
* Helper function that takes an attribute from the given element | |
* and converts it into a parameter string (with a default value) | |
* and pushes it to a given array. | |
*/ | |
function pushAttributeToParams(element, attrName, params, paramName) { | |
var attrValue; | |
if(attrValue = element.getAttribute(attrName)) { | |
params.push(paramName + '=' + encodeURIComponent(attrValue)); | |
} | |
} | |
// Helper to apply styling according to display class | |
function styleIFrame(iframe, displayClass) { | |
var style = 'margin-top: 0px; margin-right: 0px; margin-bottom: 0px; margin-left: 0px; border-top-style: none; border-right-style: none; border-bottom-style: none; border-left-style: none; position: static; left: 0px; top: 0px;', | |
placeHolderUrl; | |
switch(displayClass) { | |
case 'large': | |
style += 'width: 170px !important; height: 40px !important;'; | |
placeHolderUrl = PLATFORM_BASE_DOMAIN + '/assets/platform/btn_ph_str_large.png'; | |
break; | |
case 'small': | |
style += 'width: 72px !important; height: 26px !important; '; | |
placeHolderUrl = PLATFORM_BASE_DOMAIN + '/assets/platform/btn_ph_str_small.png'; | |
break; | |
} | |
iframe.style.cssText = "background: transparent url(" + placeHolderUrl + ") !important; " + style; | |
// Move into a function for better minimization | |
function _applyAttribute(attrName, value) { | |
iframe.setAttribute(attrName, value); | |
} | |
// NOTE Be careful about capitalization here. Internet explorer | |
// does not care about attributes unless they are camel cased | |
_applyAttribute('allowTransparency', 'true'); // Let transparency shine through | |
_applyAttribute('frameBorder', '0'); // Hide ugly iframe border | |
_applyAttribute('tabIndex', '0'); // Disable tabbing to the iframe | |
_applyAttribute('scrolling', 'no'); // Disable scrolling overflowing content | |
if(iframe.className) { | |
iframe.className = 'send-to-readmill ' + displayClass; | |
} else { | |
iframe.setAttribute('class', 'send-to-readmill ' + displayClass); | |
} | |
} | |
/* | |
* Goes through all div's that has the class 'send-to-readmill' on them and replaces | |
* them with an iframe containing the Send to Readmill button. | |
*/ | |
function processMarkers() { | |
// Collect all send to readmill (str) elements that should be replaced | |
var strElements = getElementsByClassName('send-to-readmill'); | |
// Insert an iframe for each marked div | |
for(var i = strElements.length; i--;) { | |
var element = strElements[i], parentNode = element.parentNode, params = [], src, iframe, displayClass; | |
// Only care about div.send-to-readmill | |
if(element.tagName.toLowerCase() !== 'div') { continue; } | |
// Base source of the iframe | |
src = WIDGET_BASE_DOMAIN + '/send'; | |
// Convert data attributes to source parameters | |
pushAttributeToParams(element, 'data-download-url', params, 'download_url'); | |
pushAttributeToParams(element, 'data-buy-url', params, 'buy_url'); | |
// Display data attribute is a bit special since we have restriction | |
// on its value (large or small) as well as a default value (large) | |
displayClass = (element.getAttribute('data-display') || '').toLowerCase(); | |
if((displayClass != 'large') && (displayClass != 'small')) { | |
displayClass = 'large'; // Fall back to default unless display is allowed value | |
} | |
params.push('display=' + displayClass); | |
// Append the origin domain to enable showing a customized sign in screen | |
params.push('origin_domain=' + encodeURIComponent(doc.domain)); | |
// Concatenate the final souce for the iframe | |
src += '?' + params.join('&'); | |
// Insert the actual iframe | |
iframe = doc.createElement('iframe'); | |
styleIFrame(iframe, displayClass); | |
iframe.src = src; | |
parentNode.insertBefore(iframe, element); | |
parentNode.removeChild(element); | |
} | |
} | |
/* | |
* Trigger processing of markers (div.send-to-readmill) automatically whenever | |
* the DOM is ready | |
*/ | |
function autoTriggerProcessMarkers() { | |
if(!hasAutoTriggerProcessMarkersFired) { | |
hasAutoTriggerProcessMarkersFired = true; | |
processMarkers(); | |
} | |
} | |
/* | |
* Attach a callback to the DOM ready event with as broad browser support | |
* as possible. | |
*/ | |
if(doc.addEventListener ) { | |
// Webkit, Opera, Firefox | |
doc.addEventListener("DOMContentLoaded", autoTriggerProcessMarkers, false); | |
window.addEventListener("load", autoTriggerProcessMarkers, false); | |
} else if (doc.attachEvent) { | |
// Internet explorer < 9 | |
doc.attachEvent("onreadystatechange", function(){ | |
if(doc.readyState === "complete") { | |
autoTriggerProcessMarkers(); | |
} | |
}); | |
doc.attachEvent('onload', autoTriggerProcessMarkers); | |
} else { | |
doc.onload = autoTriggerProcessMarkers; | |
} | |
// Handle the case where the script is inserted after the DOM loaded event | |
// has already happened | |
if(doc.readyState === 'complete') { | |
setTimeout(function() { autoTriggerProcessMarkers(); }, 1); | |
} | |
// Expose the processing method to allow dynamic processing of | |
// elements that are added later (via ajax for example) | |
window.Readmill = window.Readmill || {}; | |
window.Readmill.SendToReadmill = { | |
build: processMarkers | |
}; | |
})(window); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment