diff options
author | Federico Ceratto <federico.ceratto@gmail.com> | 2016-03-30 21:40:42 +0000 |
---|---|---|
committer | Federico Ceratto <federico.ceratto@gmail.com> | 2016-03-30 21:40:42 +0000 |
commit | 9ce153ce7167c11adba8ac225edc7a707e97c6eb (patch) | |
tree | 9f6e849cce2dcc7e5b4e9e6252c843dc2d0787a2 /web/lib/ResizeSensor.js | |
download | netdata-9ce153ce7167c11adba8ac225edc7a707e97c6eb.tar.xz netdata-9ce153ce7167c11adba8ac225edc7a707e97c6eb.zip |
Imported Upstream version 1.0.0upstream/1.0.0
Diffstat (limited to 'web/lib/ResizeSensor.js')
-rwxr-xr-x | web/lib/ResizeSensor.js | 166 |
1 files changed, 166 insertions, 0 deletions
diff --git a/web/lib/ResizeSensor.js b/web/lib/ResizeSensor.js new file mode 100755 index 000000000..e5ce136a8 --- /dev/null +++ b/web/lib/ResizeSensor.js @@ -0,0 +1,166 @@ +/** + * Copyright Marc J. Schmidt. See the LICENSE file at the top-level + * directory of this distribution and at + * https://github.com/marcj/css-element-queries/blob/master/LICENSE. + */ +; +(function() { + + /** + * Class for dimension change detection. + * + * @param {Element|Element[]|Elements|jQuery} element + * @param {Function} callback + * + * @constructor + */ + this.ResizeSensor = function(element, callback) { + /** + * + * @constructor + */ + function EventQueue() { + this.q = []; + this.add = function(ev) { + this.q.push(ev); + }; + + var i, j; + this.call = function() { + for (i = 0, j = this.q.length; i < j; i++) { + this.q[i].call(); + } + }; + } + + /** + * @param {HTMLElement} element + * @param {String} prop + * @returns {String|Number} + */ + function getComputedStyle(element, prop) { + if (element.currentStyle) { + return element.currentStyle[prop]; + } else if (window.getComputedStyle) { + return window.getComputedStyle(element, null).getPropertyValue(prop); + } else { + return element.style[prop]; + } + } + + /** + * + * @param {HTMLElement} element + * @param {Function} resized + */ + function attachResizeEvent(element, resized) { + if (!element.resizedAttached) { + element.resizedAttached = new EventQueue(); + element.resizedAttached.add(resized); + } else if (element.resizedAttached) { + element.resizedAttached.add(resized); + return; + } + + element.resizeSensor = document.createElement('div'); + element.resizeSensor.className = 'resize-sensor'; + var style = 'position: absolute; left: 0; top: 0; right: 0; bottom: 0; overflow: scroll; z-index: -1; visibility: hidden;'; + var styleChild = 'position: absolute; left: 0; top: 0;'; + + element.resizeSensor.style.cssText = style; + element.resizeSensor.innerHTML = + '<div class="resize-sensor-expand" style="' + style + '">' + + '<div style="' + styleChild + '"></div>' + + '</div>' + + '<div class="resize-sensor-shrink" style="' + style + '">' + + '<div style="' + styleChild + ' width: 200%; height: 200%"></div>' + + '</div>'; + element.appendChild(element.resizeSensor); + + if (!{fixed: 1, absolute: 1}[getComputedStyle(element, 'position')]) { + element.style.position = 'relative'; + } + + var expand = element.resizeSensor.childNodes[0]; + var expandChild = expand.childNodes[0]; + var shrink = element.resizeSensor.childNodes[1]; + var shrinkChild = shrink.childNodes[0]; + + var lastWidth, lastHeight; + + var reset = function() { + expandChild.style.width = expand.offsetWidth + 10 + 'px'; + expandChild.style.height = expand.offsetHeight + 10 + 'px'; + expand.scrollLeft = expand.scrollWidth; + expand.scrollTop = expand.scrollHeight; + shrink.scrollLeft = shrink.scrollWidth; + shrink.scrollTop = shrink.scrollHeight; + lastWidth = element.offsetWidth; + lastHeight = element.offsetHeight; + }; + + reset(); + + var changed = function() { + if (element.resizedAttached) { + element.resizedAttached.call(); + } + }; + + var addEvent = function(el, name, cb) { + if (el.attachEvent) { + el.attachEvent('on' + name, cb); + } else { + el.addEventListener(name, cb); + } + }; + + var onScroll = function() { + if (element.offsetWidth != lastWidth || element.offsetHeight != lastHeight) { + changed(); + } + reset(); + } + + addEvent(expand, 'scroll', onScroll); + addEvent(shrink, 'scroll', onScroll); + } + + var elementType = Object.prototype.toString.call(element); + var isCollectionTyped = ('[object Array]' === elementType + || ('[object NodeList]' === elementType) + || ('[object HTMLCollection]' === elementType) + || ('undefined' !== typeof jQuery && element instanceof jQuery) //jquery + || ('undefined' !== typeof Elements && element instanceof Elements) //mootools + ); + + if (isCollectionTyped) { + var i = 0, j = element.length; + for (; i < j; i++) { + attachResizeEvent(element[i], callback); + } + } else { + attachResizeEvent(element, callback); + } + + this.detach = function() { + if (isCollectionTyped) { + var i = 0, j = element.length; + for (; i < j; i++) { + ResizeSensor.detach(element[i]); + } + } else { + ResizeSensor.detach(element); + } + }; + }; + + this.ResizeSensor.detach = function(element) { + if (element.resizeSensor) { + element.removeChild(element.resizeSensor); + delete element.resizeSensor; + delete element.resizedAttached; + } + }; + +})(); |