Skip to content

Commit 7e35d35

Browse files
committed
Update ResizeSensor.js
1 parent 0e53b12 commit 7e35d35

File tree

1 file changed

+87
-120
lines changed

1 file changed

+87
-120
lines changed

src/ResizeSensor.js

Lines changed: 87 additions & 120 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
/**
2-
* Copyright 2013 Marc J. Schmidt. See the LICENSE file at the top-level
2+
* Copyright Marc J. Schmidt. See the LICENSE file at the top-level
33
* directory of this distribution and at
44
* https://github.com/marcj/css-element-queries/blob/master/LICENSE.
55
*/
66
;
77
(function() {
8-
var hasNativeResizeEvent = 'onresize' in document.createElement("span") && !(/Chrome/).test(navigator.userAgent);
8+
99
/**
1010
* Class for dimension change detection.
1111
*
@@ -15,28 +15,6 @@
1515
* @constructor
1616
*/
1717
this.ResizeSensor = function(element, callback) {
18-
/**
19-
* Adds a listener to the over/under-flow event.
20-
*
21-
* @param {HTMLElement} element
22-
* @param {Function} callback
23-
*/
24-
function addResizeListener(element, callback) {
25-
if (window.OverflowEvent) {
26-
//webkit
27-
element.addEventListener('overflowchanged', function(e) {
28-
callback.call(this, e);
29-
});
30-
} else {
31-
element.addEventListener('overflow', function(e) {
32-
callback.call(this, e);
33-
});
34-
element.addEventListener('underflow', function(e) {
35-
callback.call(this, e);
36-
});
37-
}
38-
}
39-
4018
/**
4119
*
4220
* @constructor
@@ -48,14 +26,14 @@
4826
};
4927

5028
this.remove = function(ev) {
51-
var index = this.q.indexOf(ev);
52-
if (index !== -1) {
53-
this.q.splice(index, 1);
54-
}
29+
var index = this.q.indexOf(ev);
30+
if (index !== -1) {
31+
this.q.splice(index, 1);
32+
}
5533
};
5634

5735
this.empty = function() {
58-
return !this.q.length;
36+
return !this.q.length;
5937
};
6038

6139
var i, j;
@@ -81,109 +59,98 @@
8159
}
8260
}
8361

84-
function callEventQueue() {
85-
element.resizedAttached.call();
86-
}
87-
8862
/**
8963
*
9064
* @param {HTMLElement} element
9165
* @param {Function} resized
9266
*/
9367
function attachResizeEvent(element, resized) {
94-
if (element.resizedAttached) {
68+
if (!element.resizedAttached) {
69+
element.resizedAttached = new EventQueue();
70+
element.resizedAttached.add(resized);
71+
} else if (element.resizedAttached) {
9572
element.resizedAttached.add(resized);
9673
return;
9774
}
9875

99-
element.resizedAttached = new EventQueue();
100-
element.resizedAttached.add(resized);
76+
element.resizeSensor = document.createElement('div');
77+
element.resizeSensor.className = 'resize-sensor';
78+
var style = 'position: absolute; left: 0; top: 0; right: 0; bottom: 0; overflow: scroll; z-index: -1; visibility: hidden;';
79+
var styleChild = 'position: absolute; left: 0; top: 0;';
80+
81+
element.resizeSensor.style.cssText = style;
82+
element.resizeSensor.innerHTML =
83+
'<div class="resize-sensor-expand" style="' + style + '">' +
84+
'<div style="' + styleChild + '"></div>' +
85+
'</div>' +
86+
'<div class="resize-sensor-shrink" style="' + style + '">' +
87+
'<div style="' + styleChild + ' width: 200%; height: 200%"></div>' +
88+
'</div>';
89+
element.appendChild(element.resizeSensor);
90+
91+
if ('absolute' !== getComputedStyle(element, 'position')) {
92+
element.style.position = 'relative';
93+
}
10194

102-
if (hasNativeResizeEvent) {
103-
//internet explorer
104-
if (element.attachEvent) {
105-
element.attachEvent('onresize', callEventQueue);
106-
} else if (element.addEventListener) {
107-
element.addEventListener('resize', callEventQueue);
108-
}
109-
} else {
110-
var myResized = function() {
111-
if (setupSensor()) {
112-
element.resizedAttached.call();
113-
}
114-
};
115-
element.resizeSensor = document.createElement('div');
116-
element.resizeSensor.className = 'resize-sensor';
117-
var style =
118-
'position: absolute; left: 0; top: 0; right: 0; bottom: 0; overflow: hidden; z-index: -1;';
119-
element.resizeSensor.style.cssText = style;
120-
element.resizeSensor.innerHTML =
121-
'<div class="resize-sensor-overflow" style="' + style + '">' +
122-
'<div></div>' +
123-
'</div>' +
124-
'<div class="resize-sensor-underflow" style="' + style + '">' +
125-
'<div></div>' +
126-
'</div>';
127-
element.appendChild(element.resizeSensor);
128-
129-
if ('absolute' !== getComputedStyle(element, 'position')) {
130-
element.style.position = 'relative';
95+
var expand = element.resizeSensor.childNodes[0];
96+
var expandChild = expand.childNodes[0];
97+
var shrink = element.resizeSensor.childNodes[1];
98+
99+
var lastWidth, lastHeight;
100+
101+
var reset = function() {
102+
expandChild.style.width = expand.offsetWidth + 10 + 'px';
103+
expandChild.style.height = expand.offsetHeight + 10 + 'px';
104+
expand.scrollLeft = expand.scrollWidth;
105+
expand.scrollTop = expand.scrollHeight;
106+
shrink.scrollLeft = shrink.scrollWidth;
107+
shrink.scrollTop = shrink.scrollHeight;
108+
lastWidth = element.offsetWidth;
109+
lastHeight = element.offsetHeight;
110+
};
111+
112+
reset();
113+
114+
var changed = function() {
115+
element.resizedAttached.call();
116+
};
117+
118+
var addEvent = function(el, name, cb) {
119+
if (el.attachEvent) {
120+
el.attachEvent('on' + name, cb);
121+
} else {
122+
el.addEventListener(name, cb);
131123
}
124+
};
132125

133-
var x = -1,
134-
y = -1,
135-
firstStyle = element.resizeSensor.firstElementChild.firstChild.style,
136-
lastStyle = element.resizeSensor.lastElementChild.firstChild.style;
137-
138-
function setupSensor() {
139-
var change = false,
140-
width = element.resizeSensor.offsetWidth,
141-
height = element.resizeSensor.offsetHeight;
142-
143-
if (x != width) {
144-
firstStyle.width = (width - 1) + 'px';
145-
lastStyle.width = (width + 1) + 'px';
146-
change = true;
147-
x = width;
148-
}
149-
if (y != height) {
150-
firstStyle.height = (height - 1) + 'px';
151-
lastStyle.height = (height + 1) + 'px';
152-
change = true;
153-
y = height;
154-
}
155-
return change;
126+
addEvent(expand, 'scroll', function() {
127+
if (element.offsetWidth > lastWidth || element.offsetHeight > lastHeight) {
128+
changed();
156129
}
130+
reset();
131+
});
157132

158-
setupSensor();
159-
addResizeListener(element.resizeSensor, myResized);
160-
addResizeListener(element.resizeSensor.firstElementChild, myResized);
161-
addResizeListener(element.resizeSensor.lastElementChild, myResized);
162-
}
133+
addEvent(shrink, 'scroll',function() {
134+
if (element.offsetWidth < lastWidth || element.offsetHeight < lastHeight) {
135+
changed();
136+
}
137+
reset();
138+
});
163139
}
164140

165141
function detachResizeEvent(element, resized) {
166-
element.resizedAttached.remove(resized);
167-
if (!element.resizedAttached.empty()) {
168-
return;
169-
}
170-
171-
if (hasNativeResizeEvent) {
172-
//internet explorer
173-
if (element.detachEvent) {
174-
element.detachEvent('onresize', callEventQueue);
175-
} else if (element.removeEventListener) {
176-
element.removeEventListener('resize', callEventQueue);
142+
element.resizedAttached.remove(resized);
143+
if (!element.resizedAttached.empty()) {
144+
return;
177145
}
178-
} else {
146+
179147
var parentNode = element.resizeSensor.parentNode;
180148
if (parentNode) {
181-
parentNode.removeChild(element.resizeSensor);
149+
parentNode.removeChild(element.resizeSensor);
182150
}
183-
}
184-
185-
delete element.resizedAttached;
186-
delete element.resizeSensor;
151+
152+
delete element.resizedAttached;
153+
delete element.resizeSensor;
187154
}
188155

189156
var isCollection = 'array' === typeof element
@@ -198,19 +165,19 @@
198165
} else {
199166
attachResizeEvent(element, callback);
200167
}
201-
168+
202169
return {
203170
destroy: function() {
204-
if (isCollection) {
205-
var i = 0, j = element.length;
206-
for (; i < j; i++) {
207-
detachResizeEvent(element[i], callback);
208-
}
209-
} else {
210-
detachResizeEvent(element, callback);
211-
}
171+
if (isCollection) {
172+
var i = 0, j = element.length;
173+
for (; i < j; i++) {
174+
detachResizeEvent(element[i], callback);
175+
}
176+
} else {
177+
detachResizeEvent(element, callback);
178+
}
212179
}
213180
};
214-
}
181+
};
215182

216183
})();

0 commit comments

Comments
 (0)