-
-
Notifications
You must be signed in to change notification settings - Fork 51
/
verge.js
161 lines (147 loc) · 4.56 KB
/
verge.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
/*!
* verge 1.10.2+201705300050
* http://npm.im/verge
* MIT Ryan Van Etten
*/
!function(root, name, make) {
if (typeof module != 'undefined' && module['exports']) module['exports'] = make();
else root[name] = make();
}(this, 'verge', function() {
var xports = {}
, win = typeof window != 'undefined' && window
, doc = typeof document != 'undefined' && document
, docElem = doc && doc.documentElement
, matchMedia = win['matchMedia'] || win['msMatchMedia']
, mq = matchMedia ? function(q) {
return !!matchMedia.call(win, q).matches;
} : function() {
return false;
}
, viewportW = xports['viewportW'] = function() {
var a = docElem['clientWidth'], b = win['innerWidth'];
return a < b ? b : a;
}
, viewportH = xports['viewportH'] = function() {
var a = docElem['clientHeight'], b = win['innerHeight'];
return a < b ? b : a;
};
/**
* Test if a media query is active. Like Modernizr.mq
* @since 1.6.0
* @return {boolean}
*/
xports['mq'] = mq;
/**
* Normalized matchMedia
* @since 1.6.0
* @return {MediaQueryList|Object}
*/
xports['matchMedia'] = matchMedia ? function() {
// matchMedia must be binded to window
return matchMedia.apply(win, arguments);
} : function() {
// Gracefully degrade to plain object
return {};
};
/**
* @since 1.8.0
* @return {{width:number, height:number}}
*/
function viewport() {
return {'width':viewportW(), 'height':viewportH()};
}
xports['viewport'] = viewport;
/**
* Cross-browser window.scrollX
* @since 1.0.0
* @return {number}
*/
xports['scrollX'] = function() {
return win.pageXOffset || docElem.scrollLeft;
};
/**
* Cross-browser window.scrollY
* @since 1.0.0
* @return {number}
*/
xports['scrollY'] = function() {
return win.pageYOffset || docElem.scrollTop;
};
/**
* @param {{top:number, right:number, bottom:number, left:number}} coords
* @param {number=} cushion adjustment
* @return {Object}
*/
function calibrate(coords, cushion) {
var o = {};
cushion = +cushion || 0;
o['width'] = (o['right'] = coords['right'] + cushion) - (o['left'] = coords['left'] - cushion);
o['height'] = (o['bottom'] = coords['bottom'] + cushion) - (o['top'] = coords['top'] - cushion);
return o;
}
/**
* Cross-browser element.getBoundingClientRect plus optional cushion.
* Coords are relative to the top-left corner of the viewport.
* @since 1.0.0
* @param {Element|Object} el element or stack (uses first item)
* @param {number=} cushion +/- pixel adjustment amount
* @return {Object|boolean}
*/
function rectangle(el, cushion) {
el = el && !el.nodeType ? el[0] : el;
if (!el || 1 !== el.nodeType) return false;
return calibrate(el.getBoundingClientRect(), cushion);
}
xports['rectangle'] = rectangle;
/**
* Get the viewport aspect ratio (or the aspect ratio of an object or element)
* @since 1.7.0
* @param {(Element|Object)=} o optional object with width/height props or methods
* @return {number}
* @link http://w3.org/TR/css3-mediaqueries/#orientation
*/
function aspect(o) {
o = null == o ? viewport() : 1 === o.nodeType ? rectangle(o) : o;
var h = o['height'], w = o['width'];
h = typeof h == 'function' ? h.call(o) : h;
w = typeof w == 'function' ? w.call(o) : w;
return w/h;
}
xports['aspect'] = aspect;
/**
* Test if an element is in the same x-axis section as the viewport.
* @since 1.0.0
* @param {Element|Object} el
* @param {number=} cushion
* @return {boolean}
*/
xports['inX'] = function(el, cushion) {
var r = rectangle(el, cushion);
return !!r && r.right >= 0 && r.left <= viewportW();
};
/**
* Test if an element is in the same y-axis section as the viewport.
* @since 1.0.0
* @param {Element|Object} el
* @param {number=} cushion
* @return {boolean}
*/
xports['inY'] = function(el, cushion) {
var r = rectangle(el, cushion);
return !!r && r.bottom >= 0 && r.top <= viewportH();
};
/**
* Test if an element is in the viewport.
* @since 1.0.0
* @param {Element|Object} el
* @param {number=} cushion
* @return {boolean}
*/
xports['inViewport'] = function(el, cushion) {
// Equiv to `inX(el, cushion) && inY(el, cushion)` but just manually do both
// to avoid calling rectangle() twice. It gzips just as small like this.
var r = rectangle(el, cushion);
return !!r && r.bottom >= 0 && r.right >= 0 && r.top <= viewportH() && r.left <= viewportW();
};
return xports;
});