angular-cached-resource
Version:
An AngularJS module to interact with RESTful resources, even when browser is offline
151 lines (129 loc) • 5.08 kB
JavaScript
;
angular.module('mgcrea.ngStrap.helpers.dimensions', [])
.factory('dimensions', function($document, $window) {
var jqLite = angular.element;
var fn = {};
/**
* Test the element nodeName
* @param element
* @param name
*/
var nodeName = fn.nodeName = function(element, name) {
return element.nodeName && element.nodeName.toLowerCase() === name.toLowerCase();
};
/**
* Returns the element computed style
* @param element
* @param prop
* @param extra
*/
fn.css = function(element, prop, extra) {
var value;
if (element.currentStyle) { //IE
value = element.currentStyle[prop];
} else if (window.getComputedStyle) {
value = window.getComputedStyle(element)[prop];
} else {
value = element.style[prop];
}
return extra === true ? parseFloat(value) || 0 : value;
};
/**
* Provides read-only equivalent of jQuery's offset function:
* @required-by bootstrap-tooltip, bootstrap-affix
* @url http://api.jquery.com/offset/
* @param element
*/
fn.offset = function(element) {
var boxRect = element.getBoundingClientRect();
var docElement = element.ownerDocument;
return {
width: element.offsetWidth,
height: element.offsetHeight,
top: boxRect.top + (window.pageYOffset || docElement.documentElement.scrollTop) - (docElement.documentElement.clientTop || 0),
left: boxRect.left + (window.pageXOffset || docElement.documentElement.scrollLeft) - (docElement.documentElement.clientLeft || 0)
};
};
/**
* Provides read-only equivalent of jQuery's position function
* @required-by bootstrap-tooltip, bootstrap-affix
* @url http://api.jquery.com/offset/
* @param element
*/
fn.position = function(element) {
var offsetParentRect = {top: 0, left: 0},
offsetParentElement,
offset;
// Fixed elements are offset from window (parentOffset = {top:0, left: 0}, because it is it's only offset parent
if (fn.css(element, 'position') === 'fixed') {
// We assume that getBoundingClientRect is available when computed position is fixed
offset = element.getBoundingClientRect();
} else {
// Get *real* offsetParentElement
offsetParentElement = offsetParent(element);
offset = fn.offset(element);
// Get correct offsets
offset = fn.offset(element);
if (!nodeName(offsetParentElement, 'html')) {
offsetParentRect = fn.offset(offsetParentElement);
}
// Add offsetParent borders
offsetParentRect.top += fn.css(offsetParentElement, 'borderTopWidth', true);
offsetParentRect.left += fn.css(offsetParentElement, 'borderLeftWidth', true);
}
// Subtract parent offsets and element margins
return {
width: element.offsetWidth,
height: element.offsetHeight,
top: offset.top - offsetParentRect.top - fn.css(element, 'marginTop', true),
left: offset.left - offsetParentRect.left - fn.css(element, 'marginLeft', true)
};
};
/**
* Returns the closest, non-statically positioned offsetParent of a given element
* @required-by fn.position
* @param element
*/
var offsetParent = function offsetParentElement(element) {
var docElement = element.ownerDocument;
var offsetParent = element.offsetParent || docElement;
if(nodeName(offsetParent, '#document')) return docElement.documentElement;
while(offsetParent && !nodeName(offsetParent, 'html') && fn.css(offsetParent, 'position') === 'static') {
offsetParent = offsetParent.offsetParent;
}
return offsetParent || docElement.documentElement;
};
/**
* Provides equivalent of jQuery's height function
* @required-by bootstrap-affix
* @url http://api.jquery.com/height/
* @param element
* @param outer
*/
fn.height = function(element, outer) {
var value = element.offsetHeight;
if(outer) {
value += fn.css(element, 'marginTop', true) + fn.css(element, 'marginBottom', true);
} else {
value -= fn.css(element, 'paddingTop', true) + fn.css(element, 'paddingBottom', true) + fn.css(element, 'borderTopWidth', true) + fn.css(element, 'borderBottomWidth', true);
}
return value;
};
/**
* Provides equivalent of jQuery's height function
* @required-by bootstrap-affix
* @url http://api.jquery.com/width/
* @param element
* @param outer
*/
fn.width = function(element, outer) {
var value = element.offsetWidth;
if(outer) {
value += fn.css(element, 'marginLeft', true) + fn.css(element, 'marginRight', true);
} else {
value -= fn.css(element, 'paddingLeft', true) + fn.css(element, 'paddingRight', true) + fn.css(element, 'borderLeftWidth', true) + fn.css(element, 'borderRightWidth', true);
}
return value;
};
return fn;
});