ratchet_design 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/LICENSE.txt +21 -0
- data/README.md +41 -0
- data/app/assets/images/ratchet/favicon.ico +0 -0
- data/app/assets/javascripts/ratchet/_svg.js +55 -0
- data/app/assets/javascripts/ratchet/base/form.js +220 -0
- data/app/assets/javascripts/ratchet/base/mobilemenu.js +62 -0
- data/app/assets/javascripts/ratchet/base/validation.js +230 -0
- data/app/assets/javascripts/ratchet/core.js +92 -0
- data/app/assets/javascripts/ratchet/enhancement/_collapse.js +96 -0
- data/app/assets/javascripts/ratchet/enhancement/_lightbox.js +93 -0
- data/app/assets/javascripts/ratchet/enhancement/_swap.js +120 -0
- data/app/assets/javascripts/ratchet/enhancement/_switcheroo.js +28 -0
- data/app/assets/javascripts/ratchet/enhancement/_textcounter.js +92 -0
- data/app/assets/javascripts/ratchet/enhancement/loader.js +77 -0
- data/app/assets/javascripts/ratchet/enhancement/notice.js +70 -0
- data/app/assets/javascripts/ratchet/enhancement/sticky.js +128 -0
- data/app/assets/javascripts/ratchet/enhancement/waypoints.js +328 -0
- data/app/assets/javascripts/ratchet/shim/classlist.js +234 -0
- data/app/assets/javascripts/ratchet/shim/object.assign.js +30 -0
- data/app/assets/javascripts/ratchet/utility/compile_data.js +32 -0
- data/app/assets/javascripts/ratchet/utility/from_top.js +14 -0
- data/app/assets/javascripts/ratchet/utility/full_stop.js +55 -0
- data/app/assets/javascripts/ratchet/utility/get_closest.js +20 -0
- data/app/assets/javascripts/ratchet/utility/get_next.js +17 -0
- data/app/assets/javascripts/ratchet/utility/load_font.js +72 -0
- data/app/assets/javascripts/ratchet/utility/load_script.js +34 -0
- data/app/assets/javascripts/ratchet/utility/matches.js +15 -0
- data/app/assets/javascripts/ratchet/utility/scroll_to.js +74 -0
- data/app/assets/javascripts/ratchet/utility/throttle.js +25 -0
- data/app/assets/javascripts/ratchet/utility/timeout.js +45 -0
- data/app/assets/javascripts/ratchet/utility/unhover.js +56 -0
- data/app/assets/javascripts/ratchet/utility/word_count.js +15 -0
- data/app/assets/stylesheets/ratchet/_core.scss +20 -0
- data/app/assets/stylesheets/ratchet/base/_button.scss +101 -0
- data/app/assets/stylesheets/ratchet/base/_document.scss +306 -0
- data/app/assets/stylesheets/ratchet/base/_form.scss +614 -0
- data/app/assets/stylesheets/ratchet/base/_list.scss +114 -0
- data/app/assets/stylesheets/ratchet/base/_media.scss +41 -0
- data/app/assets/stylesheets/ratchet/base/_table.scss +81 -0
- data/app/assets/stylesheets/ratchet/base/_text.scss +411 -0
- data/app/assets/stylesheets/ratchet/enhancement/_contrast-section.scss +22 -0
- data/app/assets/stylesheets/ratchet/enhancement/_feature.scss +49 -0
- data/app/assets/stylesheets/ratchet/enhancement/_hero.scss +44 -0
- data/app/assets/stylesheets/ratchet/enhancement/_loader.scss +109 -0
- data/app/assets/stylesheets/ratchet/enhancement/_notice.scss +74 -0
- data/app/assets/stylesheets/ratchet/enhancement/_signup.scss +206 -0
- data/app/assets/stylesheets/ratchet/enhancement/_sticky-sidebar.scss +36 -0
- data/app/assets/stylesheets/ratchet/fonts-woff.css +55 -0
- data/app/assets/stylesheets/ratchet/fonts-woff2.css +55 -0
- data/app/assets/stylesheets/ratchet/utility/_global.scss +255 -0
- data/app/assets/stylesheets/ratchet/utility/_grid.scss +102 -0
- data/app/assets/svgs/ratchet/facebook.svg +1 -0
- data/app/assets/svgs/ratchet/github.svg +1 -0
- data/app/assets/svgs/ratchet/google-plus.svg +1 -0
- data/app/assets/svgs/ratchet/ibm.svg +1 -0
- data/app/assets/svgs/ratchet/inbox.svg +1 -0
- data/app/assets/svgs/ratchet/linkedin.svg +1 -0
- data/app/assets/svgs/ratchet/ratchet.svg +1 -0
- data/app/assets/svgs/ratchet/search.svg +1 -0
- data/app/assets/svgs/ratchet/subscribe.svg +1 -0
- data/app/assets/svgs/ratchet/twitter.svg +1 -0
- data/app/assets/svgs/ratchet/y-combinator.svg +1 -0
- data/app/helpers/ratchet/application_helper.rb +51 -0
- data/app/views/layouts/ratchet/default.html.slim +61 -0
- data/app/views/shared/ratchet/_footer.html.slim +2 -0
- data/app/views/shared/ratchet/_header.html.slim +17 -0
- data/app/views/shared/ratchet/_icons.html.slim +89 -0
- data/lib/ratchet_design.rb +12 -0
- data/lib/ratchet_design/version.rb +3 -0
- data/public/assets/ratchet/core-0.1.0.js +103 -0
- data/public/assets/ratchet/core-0.1.0.js.gz +0 -0
- data/public/assets/ratchet/core-0.1.0.map.json +1 -0
- data/public/assets/ratchet/fonts-woff-0.1.0.css +55 -0
- data/public/assets/ratchet/fonts-woff-0.1.0.css.gz +0 -0
- data/public/assets/ratchet/fonts-woff2-0.1.0.css +55 -0
- data/public/assets/ratchet/fonts-woff2-0.1.0.css.gz +0 -0
- metadata +177 -0
@@ -0,0 +1,234 @@
|
|
1
|
+
/**
|
2
|
+
* ClassList
|
3
|
+
* Cross-browser full element.classList implementation
|
4
|
+
* @source http://purl.eligrey.com/github/classList.js/blob/master/classList.js
|
5
|
+
* @author Eli Grey - http://eligrey.com
|
6
|
+
* @license MIT
|
7
|
+
**/
|
8
|
+
|
9
|
+
if ( 'document' in self ) {
|
10
|
+
|
11
|
+
// Full polyfill for browsers with no classList support
|
12
|
+
if ( !( 'classList' in document.createElement( '_' ) ) ) {
|
13
|
+
|
14
|
+
( function( view ) {
|
15
|
+
|
16
|
+
'use strict';
|
17
|
+
|
18
|
+
if ( !( 'Element' in view ) ) return;
|
19
|
+
|
20
|
+
var
|
21
|
+
classListProp = 'classList',
|
22
|
+
protoProp = 'prototype',
|
23
|
+
elemCtrProto = view.Element[ protoProp ],
|
24
|
+
objCtr = Object,
|
25
|
+
|
26
|
+
strTrim = String[ protoProp ].trim || function() {
|
27
|
+
return this.replace( /^\s+|\s+$/g, '' );
|
28
|
+
},
|
29
|
+
|
30
|
+
arrIndexOf = Array[ protoProp ].indexOf || function( item ) {
|
31
|
+
for ( var i = 0; i < this.length; i++ ) {
|
32
|
+
if ( i in this && this[ i ] === item ) {
|
33
|
+
return i;
|
34
|
+
}
|
35
|
+
}
|
36
|
+
return -1;
|
37
|
+
},
|
38
|
+
|
39
|
+
DOMEx = function( type, message ) {
|
40
|
+
this.name = type;
|
41
|
+
this.code = DOMException[ type ];
|
42
|
+
this.message = message;
|
43
|
+
},
|
44
|
+
|
45
|
+
checkTokenAndGetIndex = function( classList, token ) {
|
46
|
+
if ( token === '' ) {
|
47
|
+
throw new DOMEx(
|
48
|
+
'SYNTAX_ERR',
|
49
|
+
'An invalid or illegal string was specified'
|
50
|
+
);
|
51
|
+
}
|
52
|
+
if ( /\s/.test( token ) ) {
|
53
|
+
throw new DOMEx(
|
54
|
+
'INVALID_CHARACTER_ERR',
|
55
|
+
'String contains an invalid character'
|
56
|
+
);
|
57
|
+
}
|
58
|
+
return arrIndexOf.call( classList, token );
|
59
|
+
},
|
60
|
+
|
61
|
+
ClassList = function( elem ) {
|
62
|
+
var trimmedClasses = strTrim.call( elem.getAttribute( 'class' ) || '' ),
|
63
|
+
classes = trimmedClasses ? trimmedClasses.split( /\s+/ ) : [];
|
64
|
+
|
65
|
+
for ( var i = 0; i < classes.length; i++ ) {
|
66
|
+
this.push( classes[ i ] );
|
67
|
+
}
|
68
|
+
|
69
|
+
this._updateClassName = function() {
|
70
|
+
elem.setAttribute( 'class', this.toString() );
|
71
|
+
};
|
72
|
+
},
|
73
|
+
|
74
|
+
classListProto = ClassList[ protoProp ] = [],
|
75
|
+
|
76
|
+
classListGetter = function() {
|
77
|
+
return new ClassList( this );
|
78
|
+
};
|
79
|
+
|
80
|
+
DOMEx[ protoProp ] = Error[ protoProp ];
|
81
|
+
|
82
|
+
classListProto.item = function( i ) {
|
83
|
+
return this[ i ] || null;
|
84
|
+
};
|
85
|
+
|
86
|
+
classListProto.contains = function( token ) {
|
87
|
+
token += '';
|
88
|
+
return checkTokenAndGetIndex( this, token ) !== -1;
|
89
|
+
};
|
90
|
+
|
91
|
+
classListProto.add = function() {
|
92
|
+
var
|
93
|
+
tokens = arguments,
|
94
|
+
iter = 0,
|
95
|
+
len = tokens.length,
|
96
|
+
updated = false,
|
97
|
+
token;
|
98
|
+
|
99
|
+
do {
|
100
|
+
token = tokens[ iter ] + '';
|
101
|
+
if ( checkTokenAndGetIndex( this, token ) === -1 ) {
|
102
|
+
this.push( token );
|
103
|
+
updated = true;
|
104
|
+
}
|
105
|
+
}
|
106
|
+
|
107
|
+
while ( ++iter < len );
|
108
|
+
|
109
|
+
if ( updated ) {
|
110
|
+
this._updateClassName();
|
111
|
+
}
|
112
|
+
};
|
113
|
+
|
114
|
+
classListProto.remove = function() {
|
115
|
+
var
|
116
|
+
tokens = arguments,
|
117
|
+
iter = 0,
|
118
|
+
len = tokens.length,
|
119
|
+
updated = false,
|
120
|
+
token,
|
121
|
+
index;
|
122
|
+
|
123
|
+
do {
|
124
|
+
token = tokens[ iter ] + '';
|
125
|
+
index = checkTokenAndGetIndex( this, token );
|
126
|
+
|
127
|
+
while ( index !== -1 ) {
|
128
|
+
this.splice( index, 1 );
|
129
|
+
updated = true;
|
130
|
+
index = checkTokenAndGetIndex( this, token );
|
131
|
+
}
|
132
|
+
}
|
133
|
+
|
134
|
+
while ( ++iter < len );
|
135
|
+
|
136
|
+
if ( updated ) {
|
137
|
+
this._updateClassName();
|
138
|
+
}
|
139
|
+
};
|
140
|
+
|
141
|
+
classListProto.toggle = function( token, force ) {
|
142
|
+
token += '';
|
143
|
+
|
144
|
+
var
|
145
|
+
result = this.contains( token ),
|
146
|
+
method = result ? force !== true && 'remove' : force !== false && 'add';
|
147
|
+
|
148
|
+
if ( method ) {
|
149
|
+
this[ method ]( token );
|
150
|
+
}
|
151
|
+
|
152
|
+
if ( force === true || force === false ) {
|
153
|
+
return force;
|
154
|
+
} else {
|
155
|
+
return !result;
|
156
|
+
}
|
157
|
+
};
|
158
|
+
|
159
|
+
classListProto.toString = function() {
|
160
|
+
return this.join( ' ' );
|
161
|
+
};
|
162
|
+
|
163
|
+
if ( objCtr.defineProperty ) {
|
164
|
+
var classListPropDesc = {
|
165
|
+
get : classListGetter,
|
166
|
+
enumerable : true,
|
167
|
+
configurable : true
|
168
|
+
};
|
169
|
+
|
170
|
+
try {
|
171
|
+
objCtr.defineProperty( elemCtrProto, classListProp, classListPropDesc );
|
172
|
+
}
|
173
|
+
|
174
|
+
catch ( ex ) {
|
175
|
+
if ( ex.number === -0x7FF5EC54 ) {
|
176
|
+
classListPropDesc.enumerable = false;
|
177
|
+
objCtr.defineProperty( elemCtrProto, classListProp, classListPropDesc );
|
178
|
+
}
|
179
|
+
}
|
180
|
+
|
181
|
+
} else if ( objCtr[ protoProp ].__defineGetter__ ) {
|
182
|
+
elemCtrProto.__defineGetter__( classListProp, classListGetter );
|
183
|
+
}
|
184
|
+
|
185
|
+
}( self ));
|
186
|
+
|
187
|
+
} else {
|
188
|
+
|
189
|
+
( function() {
|
190
|
+
|
191
|
+
'use strict';
|
192
|
+
|
193
|
+
var testElement = document.createElement( '_' );
|
194
|
+
|
195
|
+
testElement.classList.add( 'c1', 'c2' );
|
196
|
+
|
197
|
+
if ( !testElement.classList.contains( 'c2' ) ) {
|
198
|
+
var createMethod = function( method ) {
|
199
|
+
var original = DOMTokenList.prototype[ method ];
|
200
|
+
|
201
|
+
DOMTokenList.prototype[ method ] = function( token ) {
|
202
|
+
var i, len = arguments.length;
|
203
|
+
|
204
|
+
for ( i = 0; i < len; i++ ) {
|
205
|
+
token = arguments[ i ];
|
206
|
+
original.call( this, token );
|
207
|
+
}
|
208
|
+
};
|
209
|
+
};
|
210
|
+
createMethod( 'add' );
|
211
|
+
createMethod( 'remove' );
|
212
|
+
}
|
213
|
+
|
214
|
+
testElement.classList.toggle( 'c3', false );
|
215
|
+
|
216
|
+
if ( testElement.classList.contains( 'c3' ) ) {
|
217
|
+
var _toggle = DOMTokenList.prototype.toggle;
|
218
|
+
|
219
|
+
DOMTokenList.prototype.toggle = function( token, force ) {
|
220
|
+
if ( 1 in arguments && !this.contains( token ) === !force ) {
|
221
|
+
return force;
|
222
|
+
} else {
|
223
|
+
return _toggle.call( this, token );
|
224
|
+
}
|
225
|
+
};
|
226
|
+
|
227
|
+
}
|
228
|
+
|
229
|
+
testElement = null;
|
230
|
+
|
231
|
+
}());
|
232
|
+
|
233
|
+
}
|
234
|
+
}
|
@@ -0,0 +1,30 @@
|
|
1
|
+
/**
|
2
|
+
* Object.assign polyfill
|
3
|
+
* Cross-browser full Object.assign implementation
|
4
|
+
* @source https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/assign#Polyfill
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
if ( typeof Object.assign != 'function' ) {
|
9
|
+
( function() {
|
10
|
+
Object.assign = function( target ) {
|
11
|
+
'use strict';
|
12
|
+
if ( target === undefined || target === null ) {
|
13
|
+
throw new TypeError( 'Cannot convert undefined or null to object' );
|
14
|
+
}
|
15
|
+
|
16
|
+
var output = Object( target );
|
17
|
+
for ( var index = 1; index < arguments.length; index++ ) {
|
18
|
+
var source = arguments[ index ];
|
19
|
+
if ( source !== undefined && source !== null ) {
|
20
|
+
for ( var nextKey in source ) {
|
21
|
+
if ( Object.prototype.hasOwnProperty.call( source, nextKey ) ) {
|
22
|
+
output[ nextKey ] = source[ nextKey ];
|
23
|
+
}
|
24
|
+
}
|
25
|
+
}
|
26
|
+
}
|
27
|
+
return output;
|
28
|
+
};
|
29
|
+
})();
|
30
|
+
}
|
@@ -0,0 +1,32 @@
|
|
1
|
+
/**
|
2
|
+
* CompileData 0.0.1
|
3
|
+
* Compile input data from a given parent element
|
4
|
+
* @author Kyle Foster (@hkfoster)
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
// Public API function
|
9
|
+
var compileData = function( parent ) {
|
10
|
+
|
11
|
+
// Scoped variables
|
12
|
+
var formData = new FormData(),
|
13
|
+
allFields = parent.querySelectorAll( 'input:not([type=submit])' );
|
14
|
+
|
15
|
+
// Loop over fields
|
16
|
+
for ( var i = 0; i < allFields.length; i++ ) {
|
17
|
+
|
18
|
+
// Uncomment for testing
|
19
|
+
// console.log( 'Name: ' + allFields[ i ].name + '\n' + 'Value: ' + allFields[ i ].value );
|
20
|
+
|
21
|
+
// And append their name/value to new formData object
|
22
|
+
formData.append( allFields[ i ].name, allFields[ i ].value );
|
23
|
+
|
24
|
+
}
|
25
|
+
|
26
|
+
// Then return said formData object
|
27
|
+
return formData;
|
28
|
+
|
29
|
+
};
|
30
|
+
|
31
|
+
// Public API
|
32
|
+
module.exports = compileData;
|
@@ -0,0 +1,14 @@
|
|
1
|
+
/**
|
2
|
+
* FromTop 0.0.1
|
3
|
+
* Find element’s distance from top of document
|
4
|
+
* @author Kyle Foster (@hkfoster)
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
// Public API function
|
9
|
+
var fromTop = function( elem ) {
|
10
|
+
return Math.round( elem.getBoundingClientRect().top + window.pageYOffset );
|
11
|
+
};
|
12
|
+
|
13
|
+
// Public API
|
14
|
+
module.exports = fromTop;
|
@@ -0,0 +1,55 @@
|
|
1
|
+
/**
|
2
|
+
* FullStop 0.0.2
|
3
|
+
* Prevent CSS transitions from occurring during a window resize
|
4
|
+
* @author Kyle Foster (@hkfoster)
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
// Dependencies
|
9
|
+
var throttle = require( '../utility/throttle' ),
|
10
|
+
timeout = require( '../utility/timeout' );
|
11
|
+
|
12
|
+
// Public API function
|
13
|
+
var fullStop = function( settings ) {
|
14
|
+
|
15
|
+
// Overridable defaults
|
16
|
+
var defaults = {
|
17
|
+
resizeDelay : 250,
|
18
|
+
resizeClass : 'no-transitions'
|
19
|
+
};
|
20
|
+
|
21
|
+
// Scoped variables
|
22
|
+
var options = Object.assign( {}, defaults, settings ),
|
23
|
+
docBody = document.body,
|
24
|
+
resizeTimer;
|
25
|
+
|
26
|
+
// Resize handler function
|
27
|
+
function resizeHandler() {
|
28
|
+
|
29
|
+
// Clear timer (if it exists)
|
30
|
+
if ( resizeTimer ) timeout.clear( resizeTimer );
|
31
|
+
|
32
|
+
// Add body class while resizing
|
33
|
+
docBody.classList.add( options.resizeClass );
|
34
|
+
|
35
|
+
// Check to see if resize is over
|
36
|
+
resizeTimer = timeout.set( function() {
|
37
|
+
|
38
|
+
// And remove body class upon completion
|
39
|
+
docBody.classList.remove( options.resizeClass );
|
40
|
+
|
41
|
+
// Delay firing function based on argument passed
|
42
|
+
}, options.resizeDelay );
|
43
|
+
|
44
|
+
}
|
45
|
+
|
46
|
+
// Resize throttle function init
|
47
|
+
throttle( 'resize', 'optimizedResize' );
|
48
|
+
|
49
|
+
// Resize function listener
|
50
|
+
window.addEventListener( 'optimizedResize', resizeHandler, false );
|
51
|
+
|
52
|
+
};
|
53
|
+
|
54
|
+
// Public API
|
55
|
+
module.exports = fullStop;
|
@@ -0,0 +1,20 @@
|
|
1
|
+
/**
|
2
|
+
* GetClosest 0.0.1
|
3
|
+
* Get closest DOM element up the tree that matches a given selector
|
4
|
+
* @author Kyle Foster (@hkfoster)
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
// Dependencies
|
9
|
+
var matches = require( './matches' );
|
10
|
+
|
11
|
+
// Public API function
|
12
|
+
var getClosest = function ( elem, selector ) {
|
13
|
+
for ( ; elem && elem !== document; elem = elem.parentNode ) {
|
14
|
+
if ( matches( elem, selector ) ) return elem;
|
15
|
+
}
|
16
|
+
return false;
|
17
|
+
};
|
18
|
+
|
19
|
+
// Public API
|
20
|
+
module.exports = getClosest;
|
@@ -0,0 +1,17 @@
|
|
1
|
+
/**
|
2
|
+
* GetNext 0.0.1
|
3
|
+
* Get next DOM element that matches a given selector
|
4
|
+
* @author Kyle Foster (@hkfoster)
|
5
|
+
* @license MIT
|
6
|
+
**/
|
7
|
+
|
8
|
+
// Public API function
|
9
|
+
var getNext = function( elem, selector ) {
|
10
|
+
for ( ; elem && elem !== document; elem = elem.parentNode ) {
|
11
|
+
if ( elem.querySelector( selector ) ) return elem.querySelector( selector );
|
12
|
+
}
|
13
|
+
return false;
|
14
|
+
};
|
15
|
+
|
16
|
+
// Public API
|
17
|
+
module.exports = getNext;
|
@@ -0,0 +1,72 @@
|
|
1
|
+
/**
|
2
|
+
* LoadFont 0.0.1
|
3
|
+
* A font loader that leverages LocalStorage
|
4
|
+
* @author Adam Beres-Deak (@bdadam) & Kyle Foster (@hkfoster)
|
5
|
+
* @source https://github.com/bdadam/OptimizedWebfontLoading
|
6
|
+
* @license MIT
|
7
|
+
**/
|
8
|
+
|
9
|
+
// Dependencies - https://github.com/filamentgroup/woff2-feature-test
|
10
|
+
var supportsWoff2 = ( function( win ) {
|
11
|
+
if ( !( "FontFace" in win ) ) return false;
|
12
|
+
var f = new FontFace( 't', 'url( "data:application/font-woff2;base64,d09GMgABAAAAAAIkAAoAAAAABVwAAAHcAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAABlYAgloKLEoBNgIkAxgLDgAEIAWDcgc1G7IEyB6SJAFID5YA3nAHC6h4+H7s27nP1kTyOoQkGuJWtNGIJKYznRI3VEL7IaHq985ZUuKryZKcAtJsi5eULwUybm9KzajBBhywZ5ZwoJNuwDX5C/xBjvz5DbsoNsvG1NGQiqp0NMLZ7JlnW+5MaM3HwcHheUQeiVokekHkn/FRdefvJaTp2PczN+I1Sc3k9VuX51Tb0Tqqf1deVXGdJsDOhz0/EffMOPOzHNH06pYkDDjs+P8fb/z/8n9Iq8ITzWywkP6PBMMN9L/O7vY2FNoTAkp5PpD6g1nV9WmyQnM5uPpAMHR2fe06jbfvzPriekVTQxC6lpKr43oDtRZfCATl5OVAUKykqwm9o8R/kg37cxa6eZikS7cjK4aIwoyh6jOFplhFrz2b833G3Jii9AjDUiAZ9AxZtxdEYV6imvRF0+0Nej3wu6nPZrTLh81AVcV3kmMVdQj6Qbe9qetzbuDZ7vXOlRrqooFSxCv6SfrDICA6rnHZXQPVcUHJYGcoqa3jVH7ATrjWBNYYkEqF3RFpVIl0q2JvMOJd7/TyjXHw2NyAuJpNaEbz8RTEVtCbSH7JrwQQOqwGl7sTUOtdBZIY2DKqKlvOmPvUxJaURAZZcviTT0SKHCXqzwc=" ) format( "woff2" )', {} );
|
13
|
+
f.load()[ 'catch' ]( function() {} );
|
14
|
+
return f.status == 'loading' || f.status == 'loaded';
|
15
|
+
})( window );
|
16
|
+
|
17
|
+
// Public API function -
|
18
|
+
var loadFont = function( fontName, woffUrl, woff2Url, onlyLoadFontOnSecondPageload ){
|
19
|
+
|
20
|
+
// Many unsupported browsers should stop here
|
21
|
+
var nua = navigator.userAgent,
|
22
|
+
nope = !window.addEventListener || ( nua.match( /(Android (2|3|4.0|4.1|4.2|4.3))|(Opera (Mini|Mobi))/ ) && !nua.match( /Chrome/ ) );
|
23
|
+
|
24
|
+
if ( nope ) return;
|
25
|
+
|
26
|
+
// Set up LocalStorage
|
27
|
+
var loSto = {};
|
28
|
+
|
29
|
+
// Set up a proxy variable to help with LocalStorage
|
30
|
+
try { loSto = localStorage || {}; }
|
31
|
+
catch( ex ) {}
|
32
|
+
|
33
|
+
var loStoPrefix = 'x-font-' + fontName,
|
34
|
+
loStoUrlKey = loStoPrefix + 'url',
|
35
|
+
loStoCssKey = loStoPrefix + 'css',
|
36
|
+
storedFontUrl = loSto[ loStoUrlKey ],
|
37
|
+
storedFontCss = loSto[ loStoCssKey ],
|
38
|
+
styleElement = document.createElement( 'style' );
|
39
|
+
|
40
|
+
// Make <style> element & apply base64 encoded font data
|
41
|
+
styleElement.rel = 'stylesheet';
|
42
|
+
document.head.appendChild( styleElement );
|
43
|
+
|
44
|
+
// CSS in LocalStorage & loaded from one of the current URLs
|
45
|
+
if ( storedFontCss && ( storedFontUrl === woffUrl || storedFontUrl === woff2Url ) ) {
|
46
|
+
|
47
|
+
styleElement.textContent = storedFontCss;
|
48
|
+
|
49
|
+
// Data not present or loaded from an obsolete URL
|
50
|
+
} else {
|
51
|
+
|
52
|
+
// Check for WOFF2 support
|
53
|
+
var cssUrl = ( woff2Url && supportsWoff2 ) ? woff2Url : woffUrl,
|
54
|
+
request = new XMLHttpRequest();
|
55
|
+
|
56
|
+
// Fetch font data from the server
|
57
|
+
request.open( 'GET', cssUrl );
|
58
|
+
request.onload = function() {
|
59
|
+
if ( request.status >= 200 && request.status < 400 ) {
|
60
|
+
|
61
|
+
// Update LocalStorage with fresh data & apply
|
62
|
+
loSto[ loStoUrlKey ] = cssUrl;
|
63
|
+
loSto[ loStoCssKey ] = request.responseText;
|
64
|
+
if ( !onlyLoadFontOnSecondPageload ) styleElement.textContent = request.responseText;
|
65
|
+
}
|
66
|
+
};
|
67
|
+
request.send();
|
68
|
+
}
|
69
|
+
};
|
70
|
+
|
71
|
+
// Public API
|
72
|
+
module.exports = loadFont;
|