1/*! 2 * Webflow: Front-end site library 3 * @license MIT 4 * Inline scripts may access the api using an async handler: 5 * var Webflow = Webflow || []; 6 * Webflow.push(readyFunction); 7 */ 8(function () { 9 'use strict'; 10 11 function __commonjs(fn, module) { return module = { exports: {} }, fn(module, module.exports), module.exports; } 12 13 var webflowEnv = __commonjs(function (module, exports) { 14 /** 15 * Returns a Boolean representing whether or not the client is a mobile browser. 16 * 17 * NOTE: Many thanks to detectmobilebrowsers.com for this user agent detection 18 * regex, without which the mobile internet probably wouldn't exist. 19 */ 20 exports.isMobile = function() { 21 var userAgent = navigator.userAgent || navigator.vendor || window.opera; 22 return /(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows ce|xda|xiino/i 23 .test(userAgent) || 24 /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i 25 .test(userAgent.substr(0, 4)); 26 }; 27 }); 28 29 var require$$0 = (webflowEnv && typeof webflowEnv === 'object' && 'default' in webflowEnv ? webflowEnv['default'] : webflowEnv); 30 31 /*! 32 * tram.js v0.8.2-global 33 * Cross-browser CSS3 transitions in JavaScript 34 * https://github.com/bkwld/tram 35 * MIT License 36 */ 37 window.tram=function(a){function b(a,b){var c=new M.Bare;return c.init(a,b)}function c(a){return a.replace(/[A-Z]/g,function(a){return"-"+a.toLowerCase()})}function d(a){var b=parseInt(a.slice(1),16),c=b>>16&255,d=b>>8&255,e=255&b;return[c,d,e]}function e(a,b,c){return"#"+(1<<24|a<<16|b<<8|c).toString(16).slice(1)}function f(){}function g(a,b){j("Type warning: Expected: ["+a+"] Got: ["+typeof b+"] "+b)}function h(a,b,c){j("Units do not match ["+a+"]: "+b+", "+c)}function i(a,b,c){if(void 0!==b&&(c=b),void 0===a)return c;var d=c;return $.test(a)||!_.test(a)?d=parseInt(a,10):_.test(a)&&(d=1e3*parseFloat(a)),0>d&&(d=0),d===d?d:c}function j(a){U.debug&&window&&window.console.warn(a)}function k(a){for(var b=-1,c=a?a.length:0,d=[];++b<c;){var e=a[b];e&&d.push(e)}return d}var l=function(a,b,c){function d(a){return"object"==typeof a}function e(a){return"function"==typeof a}function f(){}function g(h,i){function j(){var a=new k;return e(a.init)&&a.init.apply(a,arguments),a}function k(){}i===c&&(i=h,h=Object),j.Bare=k;var l,m=f[a]=h[a],n=k[a]=j[a]=new f;return n.constructor=j,j.mixin=function(b){return k[a]=j[a]=g(j,b)[a],j}
37,j.open=function(a){if(l={},e(a)?l=a.call(j,n,m,j,h):d(a)&&(l=a),d(l))for(var c in l)b.call(l,c)&&(n[c]=l[c]);return e(n.init)||(n.init=h),j},j.open(i)}return g}("prototype",{}.hasOwnProperty),m={ease:["ease",function(a,b,c,d){var e=(a/=d)*a,f=e*a;return b+c*(-2.75*f*e+11*e*e+-15.5*f+8*e+.25*a)}],"ease-in":["ease-in",function(a,b,c,d){var e=(a/=d)*a,f=e*a;return b+c*(-1*f*e+3*e*e+-3*f+2*e)}],"ease-out":["ease-out",function(a,b,c,d){var e=(a/=d)*a,f=e*a;return b+c*(.3*f*e+-1.6*e*e+2.2*f+-1.8*e+1.9*a)}],"ease-in-out":["ease-in-out",function(a,b,c,d){var e=(a/=d)*a,f=e*a;return b+c*(2*f*e+-5*e*e+2*f+2*e)}],linear:["linear",function(a,b,c,d){return c*a/d+b}],"ease-in-quad":["cubic-bezier(0.550, 0.085, 0.680, 0.530)",function(a,b,c,d){return c*(a/=d)*a+b}],"ease-out-quad":["cubic-bezier(0.250, 0.460, 0.450, 0.940)",function(a,b,c,d){return-c*(a/=d)*(a-2)+b}],"ease-in-out-quad":["cubic-bezier(0.455, 0.030, 0.515, 0.955)",function(a,b,c,d){return(a/=d/2)<1?c/2*a*a+b:-c/2*(--a*(a-2)-1)+b}],"ease-in-cubic":["cubic-bezier(0.550, 0.055, 0.675, 0.190)",function(a,b,c,d){return c*(a/=d)*a*a+b}],"ease-out-cubic":["cubic-bezier(0.215, 0.610, 0.355, 1)",function(a,b,c,d){return c*((a=a/d-1)*a*a+1)+b}],"ease-in-out-cubic":["cubic-bezier(0.645, 0.045, 0.355, 1)",function(a,b,c,d){return(a/=d/2)<1?c/2*a*a*a+b:c/2*((a-=2)*a*a+2)+b}],"ease-in-quart":["cubic-bezier(0.895, 0.030, 0.685, 0.220)",function(a,b,c,d){return c*(a/=d)*a*a*a+b}],"ease-out-quart":["cubic-bezier(0.165, 0.840, 0.440, 1)",function(a,b,c,d){return-c*((a=a/d-1)*a*a*a-1)+b}],"ease-in-out-quart":["cubic-bezier(0.770, 0, 0.175, 1)",function(a,b,c,d){return(a/=d/2)<1?c/2*a*a*a*a+b:-c/2*((a-=2)*a*a*a-2)+b}],"ease-in-quint":["cubic-bezier(0.755, 0.050, 0.855, 0.060)",function(a,b,c,d){return c*(a/=d)*a*a*a*a+b}],"ease-out-quint":["cubic-bezier(0.230, 1, 0.320, 1)",function(a,b,c,d){return c*((a=a/d-1)*a*a*a*a+1)+b}],"ease-in-out-quint":["cubic-bezier(0.860, 0, 0.070, 1)",function(a,b,c,d){return(a/=d/2)<1?c/2*a*a*a*a*a+b:c/2*((a-=2)*a*a*a*a+2)+b}],"ease-in-sine":["cubic-bezier(0.470, 0, 0.745, 0.715)",function(a,b,c,d){return-c*Math.cos(a/d*(Math.PI/2))+c+b}],"ease-out-sine":["cubic-bezier(0.390, 0.575, 0.565, 1)",function(a,b,c,d){return c*Math.sin(a/d*(Math.PI/2))+b}],"ease-in-out-sine":["cubic-bezier(0.445, 0.050, 0.550, 0.950)",function(a,b,c,d){return-c/2*(Math.cos(Math.PI*a/d)-1)+b}],"ease-in-expo":["cubic-bezier(0.950, 0.050, 0.795, 0.035)",function(a,b,c,d){return 0===a?b:c*Math.pow(2,10*(a/d-1))+b}],"ease-out-expo":["cubic-bezier(0.190, 1, 0.220, 1)",function(a,b,c,d){return a===d?b+c:c*(-Math.pow(2,-10*a/d)+1)+b}],"ease-in-out-expo":["cubic-bezier(1, 0, 0, 1)",function(a,b,c,d){return 0===a?b:a===d?b+c:(a/=d/2)<1?c/2*Math.pow(2,10*(a-1))+b:c/2*(-Math.pow(2,-10*--a)+2)+b}],"ease-in-circ":["cubic-bezier(0.600, 0.040, 0.980, 0.335)",function(a,b,c,d){return-c*(Math.sqrt(1-(a/=d)*a)-1)+b}],"ease-out-circ":["cubic-bezier(0.075, 0.820, 0.165, 1)",function(a,b,c,d){return c*Math.sqrt(1-(a=a/d-1)*a)+b}],"ease-in-out-circ":["cubic-bezier(0.785, 0.135, 0.150, 0.860)",function(a,b,c,d){return(a/=d/2)<1?-c/2*(Math.sqrt(1-a*a)-1)+b:c/2*(Math.sqrt(1-(a-=2)*a)+1)+b}],"ease-in-back":["cubic-bezier(0.600, -0.280, 0.735, 0.045)",function(a,b,c,d,e){return void 0===e&&(e=1.70158),c*(a/=d)*a*((e+1)*a-e)+b}],"ease-out-back":["cubic-bezier(0.175, 0.885, 0.320, 1.275)",function(a,b,c,d,e){return void 0===e&&(e=1.70158),c*((a=a/d-1)*a*((e+1)*a+e)+1)+b}],"ease-in-out-back":["cubic-bezier(0.680, -0.550, 0.265, 1.550)",function(a,b,c,d,e){return void 0===e&&(e=1.70158),(a/=d/2)<1?c/2*a*a*(((e*=1.525)+1)*a-e)+b:c/2*((a-=2)*a*(((e*=1.525)+1)*a+e)+2)+b}]},n={"ease-in-back":"cubic-bezier(0.600, 0, 0.735, 0.045)","ease-out-back":"cubic-bezier(0.175, 0.885, 0.320, 1)","ease-in-out-back":"cubic-bezier(0.680, 0, 0.265, 1)"},o=document,p=window,q="bkwld-tram",r=/[\-\.0-9]/g,s=/[A-Z]/,t="number",u=/^(rgb|#)/,v=/(em|cm|mm|in|pt|pc|px)$/,w=/(em|cm|mm|in|pt|pc|px|%)$/,x=/(deg|rad|turn)$/,y="unitless",z=/(all|none) 0s ease 0s/,A=/^(width|height)$/,B=" ",C=o.createElement("a"),D=["Webkit","Moz","O","ms"],E=["-webkit-","-moz-","-o-","-ms-"],F=function(a){if
37(a in C.style)return{dom:a,css:a};var b,c,d="",e=a.split("-");for(b=0;b<e.length;b++)d+=e[b].charAt(0).toUpperCase()+e[b].slice(1);for(b=0;b<D.length;b++)if(c=D[b]+d,c in C.style)return{dom:c,css:E[b]+a}},G=b.support={bind:Function.prototype.bind,transform:F("transform"),transition:F("transition"),backface:F("backface-visibility"),timing:F("transition-timing-function")};if(G.transition){var H=G.timing.dom;if(C.style[H]=m["ease-in-back"][0],!C.style[H])for(var I in n)m[I][0]=n[I]}var J=b.frame=function(){var a=p.requestAnimationFrame||p.webkitRequestAnimationFrame||p.mozRequestAnimationFrame||p.oRequestAnimationFrame||p.msRequestAnimationFrame;return a&&G.bind?a.bind(p):function(a){p.setTimeout(a,16)}}(),K=b.now=function(){var a=p.performance,b=a&&(a.now||a.webkitNow||a.msNow||a.mozNow);return b&&G.bind?b.bind(a):Date.now||function(){return+new Date}}(),L=l(function(b){function d(a,b){var c=k((""+a).split(B)),d=c[0];b=b||{};var e=Y[d];if(!e)return j("Unsupported property: "+d);if(!b.weak||!this.props[d]){var f=e[0],g=this.props[d];return g||(g=this.props[d]=new f.Bare),g.init(this.$el,c,e,b),g}}function e(a,b,c){if(a){var e=typeof a;if(b||(this.timer&&this.timer.destroy(),this.queue=[],this.active=!1),"number"==e&&b)return this.timer=new S({duration:a,context:this,complete:h}),void(this.active=!0);if("string"==e&&b){switch(a){case"hide":o.call(this);break;case"stop":l.call(this);break;case"redraw":p.call(this);break;default:d.call(this,a,c&&c[1])}return h.call(this)}if("function"==e)return void a.call(this,this);if("object"==e){var f=0;u.call(this,a,function(a,b){a.span>f&&(f=a.span),a.stop(),a.animate(b)},function(a){"wait"in a&&(f=i(a.wait,0))}),t.call(this),f>0&&(this.timer=new S({duration:f,context:this}),this.active=!0,b&&(this.timer.complete=h));var g=this,j=!1,k={};J(function(){u.call(g,a,function(a){a.active&&(j=!0,k[a.name]=a.nextStyle)}),j&&g.$el.css(k)})}}}function f(a){a=i(a,0),this.active?this.queue.push({options:a}):(this.timer=new S({duration:a,context:this,complete:h}),this.active=!0)}function g(a){return this.active?(this.queue.push({options:a,args:arguments}),void(this.timer.complete=h)):j("No active transition timer. Use start() or wait() before then().")}function h(){if(this.timer&&this.timer.destroy(),this.active=!1,this.queue.length){var a=this.queue.shift();e.call(this,a.options,!0,a.args)}}function l(a){this.timer&&this.timer.destroy(),this.queue=[],this.active=!1;var b;"string"==typeof a?(b={},b[a]=1):b="object"==typeof a&&null!=a?a:this.props,u.call(this,b,v),t.call(this)}function m(a){l.call(this,a),u.call(this,a,w,x)}function n(a){"string"!=typeof a&&(a="block"),this.el.style.display=a}function o(){l.call(this),this.el.style.display="none"}function p(){this.el.offsetHeight}function r(){l.call(this),a.removeData(this.el,q),this.$el=this.el=null}function t(){var a,b,c=[];this.upstream&&c.push(this.upstream);for(a in this.props)b=this.props[a],b.active&&c.push(b.string);c=c.join(","),this.style!==c&&(this.style=c,this.el.style[G.transition.dom]=c)}function u(a,b,e){var f,g,h,i,j=b!==v,k={};for(f in a)h=a[f],f in Z?(k.transform||(k.transform={}),k.transform[f]=h):(s.test(f)&&(f=c(f)),f in Y?k[f]=h:(i||(i={}),i[f]=h));for(f in k){if(h=k[f],g=this.props[f],!g){if(!j)continue;g=d.call(this,f)}b.call(this,g,h)}e&&i&&e.call(this,i)}function v(a){a.stop()}function w(a,b){a.set(b)}function x(a){this.$el.css(a)}function y(a,c){b[a]=function(){return this.children?A.call(this,c,arguments):(this.el&&c.apply(this,arguments),this)}}function A(a,b){var c,d=this.children.length;for(c=0;d>c;c++)a.apply(this.children[c],b);return this}b.init=function(b){if(this.$el=a(b),this.el=this.$el[0],this.props={},this.queue=[],this.style="",this.active=!1,U.keepInherited&&!U.fallback){var c=W(this.el,"transition");c&&!z.test(c)&&(this.upstream=c)}G.backface&&U.hideBackface&&V(this.el,G.backface.css,"hidden")},y("add",d),y("start",e),y("wait",f),y("then",g),y("next",h),y("stop",l),y("set",m),y("show",n),y("hide",o),y("redraw",p),y("destroy",r)}),M=l(L,function(b){function c(b,c){var d=a.data(b,q)||a.data(b,q,new L.Bare);return d.el||d.init(b),c?d.start(c):d}b.init=function(b,d){var e=a(b);if(!e.length)return this;if(1===e.length)return c(e[0],d);var f=[];return e.each(function(a,b){f.push(c(b,d))}),this.children=f,this}}),N=l(function(a){function b(){var a=this.get();this.update("auto");var b=this.get();return this.update(a),b}function c(a,b,c){return void 0!==b&&(c=b),a in m?a:c}function d(a){var b=/rgba?\((\d+),\s*(\d+),\s*(\d+)/.exec(a);return(b?e(b[1],b[2],b[3]):a).replace(/#(\w)(\w)(\w)$/,"#$1$1$2$2$3$3")}var f={duration:500,ease:"ease",delay:0};a.init=function(a,b,d,e){this.$el=a,this.el=a[0];var g=b[0];d[2]&&(g=d[2]),X[g]&&(g=X[g]),this.name=g,this.type=d[1],this.duration=i(b[1],this.duration,f.duration),this.ease=c(b[2],this.ease,f.ease),this.delay=i(b[3],this.delay,f.delay),this.span=this.duration+this.delay,this.active=!1,this.nextStyle=null,this.auto=A.test(this.name),this.unit=e.unit||this.unit||U.defaultUnit,this.angle=e.angle||this.angle||U.defaultAngle,U.fallback||e.fallback?this.animate=this.fallback:(this.animate=this.transition,this.string=this.name+B+this.duration+"ms"+("ease"!=this.ease?B+m[this.ease][0]:"")+(this.delay?B+this.delay+"ms":""))},a.set=function(a){a=this.convert(a,this.type),this.update(a),this.redraw()},a.transition=function(a){this.active=!0,a=this.convert(a,this.type),this.auto&&("auto"==this.el.style[this.name]&&(this.update(this.get()),this.redraw()),"auto"==a&&(a=b.call(this))),this.nextStyle=a},a.fallback=function(a){var c=this.el.style[this.name]||this.convert(this.get(),this.type);a=this.convert(a,this.type),this.auto&&("auto"==c&&(c=this.convert(this.get(),this.type)),"auto"==a&&(a=b.call(this))),this.tween=new R({from:c,to:a,duration:this.duration,delay:this.delay,ease:this.ease,update:this.update,context:this})},a.get=function(){return W(this.el,this.name)},a.update=function(a){V(this.el,this.name,a)},a.stop=function(){(this.active||this.nextStyle)&&(this.active=!1,this.nextStyle=null,V(this.el,this.name,this.get()));var a=this.tween;a&&a.context&&a.destroy()},a.convert=function(a,b){if("auto"==a&&this.auto)return a;var c,e="number"==typeof a,f="string"==typeof a;switch(b){case t:if(e)return a;
37if(f&&""===a.replace(r,""))return+a;c="number(unitless)";break;case u:if(f){if(""===a&&this.original)return this.original;if(b.test(a))return"#"==a.charAt(0)&&7==a.length?a:d(a)}c="hex or rgb string";break;case v:if(e)return a+this.unit;if(f&&b.test(a))return a;c="number(px) or string(unit)";break;case w:if(e)return a+this.unit;if(f&&b.test(a))return a;c="number(px) or string(unit or %)";break;case x:if(e)return a+this.angle;if(f&&b.test(a))return a;c="number(deg) or string(angle)";break;case y:if(e)return a;if(f&&w.test(a))return a;c="number(unitless) or string(unit or %)"}return g(c,a),a},a.redraw=function(){this.el.offsetHeight}}),O=l(N,function(a,b){a.init=function(){b.init.apply(this,arguments),this.original||(this.original=this.convert(this.get(),u))}}),P=l(N,function(a,b){a.init=function(){b.init.apply(this,arguments),this.animate=this.fallback},a.get=function(){return this.$el[this.name]()},a.update=function(a){this.$el[this.name](a)}}),Q=l(N,function(a,b){function c(a,b){var c,d,e,f,g;for(c in a)f=Z[c],e=f[0],d=f[1]||c,g=this.convert(a[c],e),b.call(this,d,g,e)}a.init=function(){b.init.apply(this,arguments),this.current||(this.current={},Z.perspective&&U.perspective&&(this.current.perspective=U.perspective,V(this.el,this.name,this.style(this.current)),this.redraw()))},a.set=function(a){c.call(this,a,function(a,b){this.current[a]=b}),V(this.el,this.name,this.style(this.current)),this.redraw()},a.transition=function(a){var b=this.values(a);this.tween=new T({current:this.current,values:b,duration:this.duration,delay:this.delay,ease:this.ease});var c,d={};for(c in this.current)d[c]=c in b?b[c]:this.current[c];this.active=!0,this.nextStyle=this.style(d)},a.fallback=function(a){var b=this.values(a);this.tween=new T({current:this.current,values:b,duration:this.duration,delay:this.delay,ease:this.ease,update:this.update,context:this})},a.update=function(){V(this.el,this.name,this.style(this.current))},a.style=function(a){var b,c="";for(b in a)c+=b+"("+a[b]+") ";return c},a.values=function(a){var b,d={};return c.call(this,a,function(a,c,e){d[a]=c,void 0===this.current[a]&&(b=0,~a.indexOf("scale")&&(b=1),this.current[a]=this.convert(b,e))}),d}}),R=l(function(b){function c(a){1===n.push(a)&&J(g)}function g(){var a,b,c,d=n.length;if(d)for(J(g),b=K(),a=d;a--;)c=n[a],c&&c.render(b)}function i(b){var c,d=a.inArray(b,n);d>=0&&(c=n.slice(d+1),n.length=d,c.length&&(n=n.concat(c)))}function j(a){return Math.round(a*o)/o}function k(a,b,c){return e(a[0]+c*(b[0]-a[0]),a[1]+c*(b[1]-a[1]),a[2]+c*(b[2]-a[2]))}var l={ease:m.ease[1],from:0,to:1};b.init=function(a){this.duration=a.duration||0,this.delay=a.delay||0;var b=a.ease||l.ease;m[b]&&(b=m[b][1]),"function"!=typeof b&&(b=l.ease),this.ease=b,this.update=a.update||f,this.complete=a.complete||f,this.context=a.context||this,this.name=a.name;var c=a.from,d=a.to;void 0===c&&(c=l.from),void 0===d&&(d=l.to),this.unit=a.unit||"","number"==typeof c&&"number"==typeof d?(this.begin=c,this.change=d-c):this.format(d,c),this.value=this.begin+this.unit,this.start=K(),a.autoplay!==!1&&this.play()},b.play=function(){this.active||(this.start||(this.start=K()),this.active=!0,c(this))},b.stop=function(){this.active&&(this.active=!1,i(this))},b.render=function(a){var b,c=a-this.start;if(this.delay){if(c<=this.delay)return;c-=this.delay}if(c<this.duration){var d=this.ease(c,0,1,this.duration);return b=this.startRGB?k(this.startRGB,this.endRGB,d):j(this.begin+d*this.change),this.value=b+this.unit,void this.update.call(this.context,this.value)}b=this.endHex||this.begin+this.change,this.value=b+this.unit,this.update.call(this.context,this.value),this.complete.call(this.context),this.destroy()},b.format=function(a,b){if(b+="",a+="","#"==a.charAt(0))return this.startRGB=d(b),this.endRGB=d(a),this.endHex=a,this.begin=0,void(this.change=1);if(!this.unit){var c=b.replace(r,""),e=a.replace(r,"");c!==e&&h("tween",b,a),this.unit=c}b=parseFloat(b),a=parseFloat(a),this.begin=this.value=b,this.change=a-b},b.destroy=function(){this.stop(),this.context=null,this.ease=this.update=this.complete=f};var n=[],o=1e3}),S=l(R,function(a){a.init=function(a){this.duration=a.duration||0,this.complete=a.complete||f,this.context=a.context,this.play()},a.render=function(a){var b=a-this.start;b<this.duration||(this.complete.call(this.context),this.destroy())}}),T=l(R,function(a,b){a.init=function(a){this.context=a.context,this.update=a.update,this.tweens=[],this.current=a.current;var b,c;for(b in a.values)c=a.values[b],this.current[b]!==c&&this.tweens.push(new R({n
37ame:b,from:this.current[b],to:c,duration:a.duration,delay:a.delay,ease:a.ease,autoplay:!1}));this.play()},a.render=function(a){var b,c,d=this.tweens.length,e=!1;for(b=d;b--;)c=this.tweens[b],c.context&&(c.render(a),this.current[c.name]=c.value,e=!0);return e?void(this.update&&this.update.call(this.context)):this.destroy()},a.destroy=function(){if(b.destroy.call(this),this.tweens){var a,c=this.tweens.length;for(a=c;a--;)this.tweens[a].destroy();this.tweens=null,this.current=null}}}),U=b.config={debug:!1,defaultUnit:"px",defaultAngle:"deg",keepInherited:!1,hideBackface:!1,perspective:"",fallback:!G.transition,agentTests:[]};b.fallback=function(a){if(!G.transition)return U.fallback=!0;U.agentTests.push("("+a+")");var b=new RegExp(U.agentTests.join("|"),"i");U.fallback=b.test(navigator.userAgent)},b.fallback("6.0.[2-5] Safari"),b.tween=function(a){return new R(a)},b.delay=function(a,b,c){return new S({complete:b,duration:a,context:c})},a.fn.tram=function(a){return b.call(null,this,a)};var V=a.style,W=a.css,X={transform:G.transform&&G.transform.css},Y={color:[O,u],background:[O,u,"background-color"],"outline-color":[O,u],"border-color":[O,u],"border-top-color":[O,u],"border-right-color":[O,u],"border-bottom-color":[O,u],"border-left-color":[O,u],"border-width":[N,v],"border-top-width":[N,v],"border-right-width":[N,v],"border-bottom-width":[N,v],"border-left-width":[N,v],"border-spacing":[N,v],"letter-spacing":[N,v],margin:[N,v],"margin-top":[N,v],"margin-right":[N,v],"margin-bottom":[N,v],"margin-left":[N,v],padding:[N,v],"padding-top":[N,v],"padding-right":[N,v],"padding-bottom":[N,v],"padding-left":[N,v],"outline-width":[N,v],opacity:[N,t],top:[N,w],right:[N,w],bottom:[N,w],left:[N,w],"font-size":[N,w],"text-indent":[N,w],"word-spacing":[N,w],width:[N,w],"min-width":[N,w],"max-width":[N,w],height:[N,w],"min-height":[N,w],"max-height":[N,w],"line-height":[N,y],"scroll-top":[P,t,"scrollTop"],"scroll-left":[P,t,"scrollLeft"]},Z={};G.transform&&(Y.transform=[Q],Z={x:[w,"translateX"],y:[w,"translateY"],rotate:[x],rotateX:[x],rotateY:[x],scale:[t],scaleX:[t],scaleY:[t],skew:[x],skewX:[x],skewY:[x]}),G.transform&&G.backface&&(Z.z=[w,"translateZ"],Z.rotateZ=[x],Z.scaleZ=[t],Z.perspective=[v]);var $=/ms/,_=/s|\./;return a.tram=b}(window.jQuery); 38 39 var require$$0$2 = {}; 40 41 var underscoreCustom = __commonjs(function (module) { 42 // Include tram for frame-throttling 43 var $ = window.$; 44 var tram = require$$0$2 && $.tram; 45 46 /*eslint-disable */ 47 48 /*! 49 * Webflow._ (aka) Underscore.js 1.6.0 (custom build) 50 * _.each 51 * _.map 52 * _.find 53 * _.filter 54 * _.any 55 * _.contains 56 * _.delay 57 * _.defer 58 * _.throttle (webflow) 59 * _.debounce 60 * _.keys 61 * _.has 62 * _.now 63 * 64 * http://underscorejs.org 65 * (c) 2009-2013 Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors 66 * Underscore may be freely distributed under the MIT license. 67 * @license MIT 68 */ 69 module.exports = (function() { 70 var _ = {}; 71 72 // Current version. 73 _.VERSION = '1.6.0-Webflow'; 74 75 // Establish the object that gets returned to break out of a loop iteration. 76 var breaker = {}; 77 78 // Save bytes in the minified (but not gzipped) version: 79 var ArrayProto = Array.prototype, ObjProto = Object.prototype, FuncProto = Function.prototype; 80 81 // Create quick reference variables for speed access to core prototypes. 82 var 83 push = ArrayProto.push, 84 slice = ArrayProto.slice, 85 concat = ArrayProto.concat, 86 toString = ObjProto.toString, 87 hasOwnProperty = ObjProto.hasOwnProperty; 88 89 // All **ECMAScript 5** native function implementations that we hope to use 90 // are declared here. 91 var 92 nativeForEach = ArrayProto.forEach, 93 nativeMap = ArrayProto.map, 94 nativeReduce = ArrayProto.reduce, 95 nativeReduceRight = ArrayProto.reduceRight, 96 nativeFilter = ArrayProto.filter, 97 nativeEvery = ArrayProto.every, 98 nativeSome = ArrayProto.some, 99 nativeIndexOf = ArrayProto.indexOf, 100 nativeLastIndexOf = ArrayProto.lastIndexOf, 101 nativeIsArray = Array.isArray, 102 nativeKeys = Object.keys, 103 nativeBind = FuncProto.bind; 104 105 // Collection Functions 106 // -------------------- 107 108 // The cornerstone, an `each` implementation, aka `forEach`. 109 // Handles objects with the built-in `forEach`, arrays, and raw objects.
110 // Delegates to **ECMAScript 5**'s native `forEach` if available. 111 var each = _.each = _.forEach = function(obj, iterator, context) { 112 /* jshint shadow:true */ 113 if (obj == null) return obj; 114 if (nativeForEach && obj.forEach === nativeForEach) { 115 obj.forEach(iterator, context); 116 } else if (obj.length === +obj.length) { 117 for (var i = 0, length = obj.length; i < length; i++) { 118 if (iterator.call(context, obj[i], i, obj) === breaker) return; 119 } 120 } else { 121 var keys = _.keys(obj); 122 for (var i = 0, length = keys.length; i < length; i++) { 123 if (iterator.call(context, obj[keys[i]], keys[i], obj) === breaker) return; 124 } 125 } 126 return obj; 127 }; 128 129 // Return the results of applying the iterator to each element. 130 // Delegates to **ECMAScript 5**'s native `map` if available. 131 _.map = _.collect = function(obj, iterator, context) { 132 var results = []; 133 if (obj == null) return results; 134 if (nativeMap && obj.map === nativeMap) return obj.map(iterator, context); 135 each(obj, function(value, index, list) { 136 results.push(iterator.call(context, value, index, list)); 137 }); 138 return results; 139 }; 140 141 // Return the first value which passes a truth test. Aliased as `detect`. 142 _.find = _.detect = function(obj, predicate, context) { 143 var result; 144 any(obj, function(value, index, list) { 145 if (predicate.call(context, value, index, list)) { 146 result = value; 147 return true; 148 } 149 }); 150 return result; 151 }; 152 153 // Return all the elements that pass a truth test. 154 // Delegates to **ECMAScript 5**'s native `filter` if available. 155 // Aliased as `select`. 156 _.filter = _.select = function(obj, predicate, context) { 157 var results = []; 158 if (obj == null) return results; 159 if (nativeFilter && obj.filter === nativeFilter) return obj.filter(predicate, context); 160 each(obj, function(value, index, list) { 161 if (predicate.call(context, value, index, list)) results.push(value); 162 }); 163 return results; 164 }; 165 166 // Determine if at least one element in the object matches a truth test. 167 // Delegates to **ECMAScript 5**'s native `some` if available. 168 // Aliased as `any`. 169 var any = _.some = _.any = function(obj, predicate, context) { 170 predicate || (predicate = _.identity); 171 var result = false;
172 if (obj == null) return result; 173 if (nativeSome && obj.some === nativeSome) return obj.some(predicate, context); 174 each(obj, function(value, index, list) { 175 if (result || (result = predicate.call(context, value, index, list))) return breaker; 176 }); 177 return !!result; 178 }; 179 180 // Determine if the array or object contains a given value (using `===`). 181 // Aliased as `include`. 182 _.contains = _.include = function(obj, target) { 183 if (obj == null) return false; 184 if (nativeIndexOf && obj.indexOf === nativeIndexOf) return obj.indexOf(target) != -1; 185 return any(obj, function(value) { 186 return value === target; 187 }); 188 }; 189 190 // Function (ahem) Functions 191 // -------------------- 192 193 // Delays a function for the given number of milliseconds, and then calls 194 // it with the arguments supplied. 195 _.delay = function(func, wait) { 196 var args = slice.call(arguments, 2); 197 return setTimeout(function(){ return func.apply(null, args); }, wait); 198 }; 199 200 // Defers a function, scheduling it to run after the current call stack has 201 // cleared. 202 _.defer = function(func) { 203 return _.delay.apply(_, [func, 1].concat(slice.call(arguments, 1))); 204 }; 205 206 // Returns a function, that, when invoked, will only be triggered once every 207 // browser animation frame - using tram's requestAnimationFrame polyfill. 208 _.throttle = function(func) { 209 var wait, args, context; 210 return function() { 211 if (wait) return; 212 wait = true; 213 args = arguments; 214 context = this; 215 tram.frame(function() { 216 wait = false; 217 func.apply(context, args); 218 }); 219 }; 220 }; 221 222 // Returns a function, that, as long as it continues to be invoked, will not 223 // be triggered. The function will be called after it stops being called for 224 // N milliseconds. If `immediate` is passed, trigger the function on the 225 // leading edge, instead of the trailing. 226 _.debounce = function(func, wait, immediate) { 227 var timeout, args, context, timestamp, result; 228 229 var later = function() { 230 var last = _.now() - timestamp; 231 if (last < wait) { 232 timeout = setTimeout(later, wait - last); 233 } else { 234 timeout = null; 235 if (!immediate) { 236 result = func.apply(context, args); 237 context = args = null; 238 } 239 } 240 }; 241 242 return function() { 243 context = this; 244 args = arguments; 245 timestamp = _.now(); 246 var callNow = immediate && !timeout; 247 if (!timeout) { 248 timeout = setTimeout(later, wait); 249 } 250 if (callNow) { 251 result = func.apply(context, args); 252 context = args = null; 253 } 254 255 return result; 256 }; 257 }; 258 259 // Object Functions 260 // ---------------- 261 262 // Fill in a given object with default properties. 263 _.defaults = function(obj) { 264 if (!_.isObject(obj)) return obj; 265 for (var i = 1, length = arguments.length; i < length; i++) { 266 var source = arguments[i]; 267 for (var prop in source) { 268 if (obj[prop] === void 0) obj[prop] = source[prop]; 269 } 270 } 271 return obj; 272 }; 273 274 // Retrieve the names of an object's properties. 275 // Delegates to **ECMAScript 5**'s native `Object.keys` 276 _.keys = function(obj) { 277 if (!_.isObject(obj)) return []; 278 if (nativeKeys) return nativeKeys(obj); 279 var keys = []; 280 for (var key in obj) if (_.has(obj, key)) keys.push(key); 281 return keys; 282 }; 283 284 // Shortcut function for checking if an object has a given property directly 285 // on itself (in other words, not on a prototype). 286 _.has = function(obj, key) { 287 return hasOwnProperty.call(obj, key); 288 }; 289 290 // Is a given variable an object? 291 _.isObject = function(obj) { 292 return obj === Object(obj); 293 }; 294 295 // Utility Functions 296 // ----------------- 297 298 // A (possibly faster) way to get the current timestamp as an integer. 299 _.now = Date.now || function() { return new Date().getTime(); }; 300 301 // By default, Underscore uses ERB-style template delimiters, change the 302 // following template settings to use alternative delimiters. 303 _.templateSettings = { 304 evaluate : /<%([\s\S]+?)%>/g, 305 interpolate : /<%=([\s\S]+?)%>/g, 306 escape : /<%-([\s\S]+?)%>/g 307 }; 308 309 // When customizing `templateSettings`, if you don't want to define an 310 // interpolation, evaluation or escaping regex, we need one that is 311 // guaranteed not to match. 312 var noMatch = /(.)^/; 313 314 // Certain characters need to be escaped so that they can be put into a 315 // string literal. 316 var escapes = { 317 "'": "'", 318 '\\': '\\', 319 '\r': 'r', 320 '\n': 'n', 321 '\u2028': 'u2028', 322 '\u2029': 'u2029' 323 }; 324 325 var escaper = /\\|'|\r|\n|\u2028|\u2029/g; 326 327 var escapeChar = function(match) { 328 return '\\' + escapes[match]; 329 }; 330 331 // JavaScript micro-templating, similar to John Resig's implementation. 332 // Underscore templating handles arbitrary delimiters, preserves whitespace, 333 // and correctly escapes quotes within interpolated code. 334 // NB: `oldSettings` only exists for backwards compatibility. 335 _.template = function(text, settings, oldSettings) { 336 if (!settings && oldSettings) settings = oldSettings; 337 settings = _.defaults({}, settings, _.templateSettings); 338 339 // Combine delimiters into one regular expression via alternation. 340 var matcher = RegExp([
341 (settings.escape || noMatch).source, 342 (settings.interpolate || noMatch).source, 343 (settings.evaluate || noMatch).source 344 ].join('|') + '|$', 'g'); 345 346 // Compile the template source, escaping string literals appropriately. 347 var index = 0; 348 var source = "__p+='"; 349 text.replace(matcher, function(match, escape, interpolate, evaluate, offset) { 350 source += text.slice(index, offset).replace(escaper, escapeChar); 351 index = offset + match.length; 352 353 if (escape) { 354 source += "'+\n((__t=(" + escape + "))==null?'':_.escape(__t))+\n'"; 355 } else if (interpolate) { 356 source += "'+\n((__t=(" + interpolate + "))==null?'':__t)+\n'"; 357 } else if (evaluate) { 358 source += "';\n" + evaluate + "\n__p+='"; 359 } 360 361 // Adobe VMs need the match returned to produce the correct offest. 362 return match; 363 }); 364 source += "';\n"; 365 366 // If a variable is not specified, place data values in local scope. 367 if (!settings.variable) source = 'with(obj||{}){\n' + source + '}\n'; 368 369 source = "var __t,__p='',__j=Array.prototype.join," + 370 "print=function(){__p+=__j.call(arguments,'');};\n" + 371 source + 'return __p;\n'; 372 373 try { 374 var render = new Function(settings.variable || 'obj', '_', source); 375 } catch (e) { 376 e.source = source; 377 throw e; 378 } 379 380 var template = function(data) { 381 return render.call(this, data, _); 382 }; 383 384 // Provide the compiled source as a convenience for precompilation. 385 var argument = settings.variable || 'obj'; 386 template.source = 'function(' + argument + '){\n' + source + '}'; 387 388 return template; 389 }; 390 391 // Export underscore 392 return _; 393 }()); 394 395 /* eslint-enable */ 396 }); 397 398 var require$$1 = (underscoreCustom && typeof underscoreCustom === 'object' && 'default' in underscoreCustom ? underscoreCustom['default'] : underscoreCustom); 399 400 var webflowLib = __commonjs(function (module) { 401 /** 402 * Webflow: Core site library 403 */ 404 405 var Webflow = {}; 406 var modules = {}; 407 var primary = []; 408 var secondary = window.Webflow || []; 409 var $ = window.jQuery; 410 var $win = $(window); 411 var $doc = $(document); 412 var isFunction = $.isFunction; 413 var _ = Webflow._ = require$$1; 414 var tram = require$$0$2 && $.tram; 415 var domready = false; 416 var destroyed = false; 417 var Modernizr = window.Modernizr; 418 tram.config.hideBackface = false; 419 tram.config.keepInherited = true; 420 421 /** 422 * Webflow.define - Define a named module 423 * @param {string} name 424 * @param {function} factory 425 * @param {object} options 426 * @return {object} 427 */ 428 Webflow.define = function(name, factory, options) { 429 if (modules[name]) unbindModule(modules[name]); 430 var instance = modules[name] = factory($, _, options) || {}; 431 bindModule(instance); 432 return instance; 433 }; 434 435 /** 436 * Webflow.require - Require a named module 437 * @param {string} name 438 * @return {object} 439 */ 440 Webflow.require = function(name) { 441 return modules[name]; 442 }; 443 444 function bindModule(module) { 445 // If running in Webflow app, subscribe to design/preview events 446 if (Webflow.env()) { 447 isFunction(module.design) && $win.on('__wf_design', module.design); 448 isFunction(module.preview) && $win.on('__wf_preview', module.preview); 449 } 450 // Subscribe to front-end destroy event 451 isFunction(module.destroy) && $win.on('__wf_destroy', module.destroy); 452 // Look for ready method on module 453 if (module.ready && isFunction(module.ready)) { 454 addReady(module); 455 } 456 } 457 458 function addReady(module) { 459 // If domready has already happened, run ready method 460 if (domready) { 461 module.ready(); 462 return; 463 } 464 // Otherwise add ready method to the primary queue (only once) 465 if (_.contains(primary, module.ready)) return; 466 primary.push(module.ready); 467 } 468 469 function unbindModule(module) { 470 // Unsubscribe module from window events 471 isFunction(module.design) && $win.off('__wf_design', module.design); 472 isFunction(module.preview) && $win.off('__wf_preview', module.preview); 473 isFunction(module.destroy) && $win.off('__wf_destroy', module.destroy); 474 // Remove ready method from primary queue 475 if (module.ready && isFunction(module.ready)) { 476 removeReady(module); 477 } 478 } 479 480 function removeReady(module) { 481 primary = _.filter(primary, function(readyFn) { 482 return readyFn !== module.ready; 483 }); 484 } 485 486 /** 487 * Webflow.push - Add a ready handler into secondary queue 488 * @param {function} ready Callback to invoke on domready 489 */ 490 Webflow.push = function(ready) { 491 // If domready has already happened, invoke handler 492 if (domready) { 493 isFunction(ready) && ready(); 494 return; 495 } 496 // Otherwise push into secondary queue 497 secondary.push(ready); 498 }; 499 500 /** 501 * Webflow.env - Get the state of the Webflow app 502 * @param {string} mode [optional] 503 * @return {boolean} 504 */ 505 Webflow.env = function(mode) { 506 var designFlag = window.__wf_design; 507 var inApp = typeof designFlag !== 'undefined'; 508 if (!mode) return inApp; 509 if (mode === 'design') return inApp && designFlag; 510 if (mode === 'preview') return inApp && !designFlag; 511 if (mode === 'slug') return inApp && window.__wf_slug; 512 if (mode === 'editor') return window.WebflowEditor; 513 if (mode === 'test') return false || window.__wf_test; 514 if (mode === 'frame') return window !== window.top; 515 }; 516 517 // Feature detects + browser sniffs ಠ_ಠ518 var userAgent = navigator.userAgent.toLowerCase(); 519 var appVersion = navigator.appVersion.toLowerCase(); 520 var touch = Webflow.env.touch = ('ontouchstart' in window) || window.DocumentTouch && document instanceof window.DocumentTouch; 521 var chrome = Webflow.env.chrome = /chrome/.test(userAgent) && /Google/.test(navigator.vendor) && parseInt(appVersion.match(/chrome\/(\d+)\./)[1], 10); 522 var ios = Webflow.env.ios = Modernizr && Modernizr.ios; 523 Webflow.env.safari = /safari/.test(userAgent) && !chrome && !ios; 524 525 // Maintain current touch target to prevent late clicks on touch devices 526 var touchTarget; 527 // Listen for both events to support touch/mouse hybrid devices 528 touch && $doc.on('touchstart mousedown', function(evt) { 529 touchTarget = evt.target; 530 }); 531 532 /** 533 * Webflow.validClick - validate click target against current touch target 534 * @param {HTMLElement} clickTarget Element being clicked 535 * @return {Boolean} True if click target is valid (always true on non-touch) 536 */ 537 Webflow.validClick = touch ? function(clickTarget) { 538 return clickTarget === touchTarget || $.contains(clickTarget, touchTarget); 539 } : function() { return true; }; 540 541 /** 542 * Webflow.resize, Webflow.scroll - throttled event proxies 543 */ 544 var resizeEvents = 'resize.webflow orientationchange.webflow load.webflow';
545 var scrollEvents = 'scroll.webflow ' + resizeEvents; 546 Webflow.resize = eventProxy($win, resizeEvents); 547 Webflow.scroll = eventProxy($win, scrollEvents); 548 Webflow.redraw = eventProxy(); 549 550 // Create a proxy instance for throttled events 551 function eventProxy(target, types) { 552 553 // Set up throttled method (using custom frame-based _.throttle) 554 var handlers = []; 555 var proxy = {}; 556 proxy.up = _.throttle(function(evt) { 557 _.each(handlers, function(h) { h(evt); }); 558 }); 559 560 // Bind events to target 561 if (target && types) target.on(types, proxy.up); 562 563 /** 564 * Add an event handler 565 * @param {function} handler 566 */ 567 proxy.on = function(handler) { 568 if (typeof handler !== 'function') return; 569 if (_.contains(handlers, handler)) return; 570 handlers.push(handler); 571 }; 572 573 /** 574 * Remove an event handler 575 * @param {function} handler 576 */ 577 proxy.off = function(handler) { 578 // If no arguments supplied, clear all handlers 579 if (!arguments.length) { 580 handlers = []; 581 return; 582 } 583 // Otherwise, remove handler from the list 584 handlers = _.filter(handlers, function(h) { 585 return h !== handler; 586 }); 587 }; 588 589 return proxy; 590 } 591 592 // Webflow.location - Wrap window.location in api 593 Webflow.location = function(url) { 594 window.location = url; 595 }; 596 597 // Webflow.app - Designer-specific methods 598 Webflow.app = Webflow.env() ? {} : null; 599 if (Webflow.app) { 600 601 // Trigger redraw for specific elements 602 var redraw = new Event('__wf_redraw'); 603 Webflow.app.redrawElement = function(i, el) { el.dispatchEvent(redraw); }; 604 605 // Webflow.location - Re-route location change to trigger an event 606 Webflow.location = function(url) { 607 window.dispatchEvent(new CustomEvent('__wf_location', { detail: url })); 608 }; 609 } 610 611 // Webflow.ready - Call primary and secondary handlers 612 Webflow.ready = function() { 613 domready = true; 614 615 // Restore modules after destroy 616 if (destroyed) { 617 restoreModules(); 618 619 // Otherwise run primary ready methods 620 } else { 621 _.each(primary, callReady); 622 } 623 624 // Run secondary ready methods 625 _.each(secondary, callReady); 626 627 // Trigger resize 628 Webflow.resize.up(); 629 }; 630 631 function callReady(readyFn) { 632 isFunction(readyFn) && readyFn(); 633 } 634 635 function restoreModules() { 636 destroyed = false; 637 _.each(modules, bindModule); 638 } 639 640 /** 641 * Webflow.load - Add a window load handler that will run even if load event has already happened 642 * @param {function} handler 643 */ 644 var deferLoad; 645 Webflow.load = function(handler) { 646 deferLoad.then(handler); 647 }; 648 649 function bindLoad() { 650 // Reject any previous deferred (to support destroy) 651 if (deferLoad) { 652 deferLoad.reject(); 653 $win.off('load', deferLoad.resolve); 654 } 655 // Create deferred and bind window load event 656 deferLoad = new $.Deferred(); 657 $win.on('load', deferLoad.resolve); 658 } 659 660 // Webflow.destroy - Trigger a destroy event for all modules 661 Webflow.destroy = function(options) { 662 options = options || {}; 663 destroyed = true; 664 $win.triggerHandler('__wf_destroy'); 665 666 // Allow domready reset for tests 667 if (options.domready != null) { 668 domready = options.domready; 669 } 670 671 // Unbind modules 672 _.each(modules, unbindModule); 673 674 // Clear any proxy event handlers 675 Webflow.resize.off(); 676 Webflow.scroll.off(); 677 Webflow.redraw.off(); 678 679 // Clear any queued ready methods 680 primary = []; 681 secondary = []; 682 683 // If load event has not yet fired, replace the deferred 684 if (deferLoad.state() === 'pending') bindLoad(); 685 }; 686 687 // Listen for domready 688 $(Webflow.ready); 689 690 // Listen for window.onload and resolve deferred 691 bindLoad(); 692 693 // Export commonjs module 694 module.exports = window.Webflow = Webflow; 695 }); 696 697 var require$$0$1 = (webflowLib && typeof webflowLib === 'object' && 'default' in webflowLib ? webflowLib['default'] : webflowLib); 698 699 var webflowBackgroundVideo = __commonjs(function (module) { 700 /** 701 * Webflow: Background Video component 702 */ 703 704 var Webflow = require$$0$1; 705 var WebflowEnv = require$$0; 706 707 Webflow.define('backgroundVideo', module.exports = function ($) { 708 709 function ready () { 710 // Prevent default render while in-app 711 if (Webflow.env()) { 712 return; 713 } 714 715 var backgroundVideoNodes = $(document).find('.w-background-video').not('.w-background-video-atom'); 716 717 if (backgroundVideoNodes.length === 0) { 718 return; 719 } 720 721 backgroundVideoNodes.each(function (_, node) { 722 $(node).prepend(createVideoNode(node)); 723 }); 724 } 725 726 function createVideoNode (nativeNode) { 727 var nodeData = $(nativeNode).data(); 728 729 if (!nodeData.videoUrls) { 730 return $('<video />
730'); 731 } 732 733 // Prevent loading the videos on mobile browsers as its likely that they 734 // are on low-bandwidth connections. 735 if (WebflowEnv.isMobile()) { 736 return $('<video />').css('background-image', 'url(' + nodeData.posterUrl + ')'); 737 } 738 739 var videoURLs = nodeData.videoUrls.split(','); 740 var sourceNodes = videoURLs.map(function (url) { 741 return $('<source />').attr({ 742 src: url, 743 'data-wf-ignore': '', 744 }); 745 }); 746 747 var videoNode = $('<video />').attr({ 748 autoplay: nodeData.autoplay, 749 loop: nodeData.loop, 750 }) 751 .css('background-image', 'url(' + nodeData.posterUrl + ')'); 752 753 videoNode.append(sourceNodes); 754 755 return videoNode; 756 } 757 758 return { ready: ready }; 759 }); 760 }); 761 762 var webflowBrand = __commonjs(function (module) { 763 /** 764 * Webflow: Brand pages on the subdomain 765 */ 766 767 var Webflow = require$$0$1; 768 769 Webflow.define('brand', module.exports = function($) { 770 var api = {}; 771 var $html = $('html'); 772 var $body = $('body'); 773 var namespace = '.w-webflow-badge'; 774 var location = window.location; 775 var isPhantom = /PhantomJS/i.test(navigator.userAgent); 776 var brandElement; 777 778 // ----------------------------------- 779 // Module methods 780 781 api.ready = function() { 782 var shouldBrand = $html.attr('data-wf-status'); 783 var publishedDomain = $html.attr('data-wf-domain') || ''; 784 if (/\.webflow\.io$/i.test(publishedDomain) && location.hostname !== publishedDomain) { 785 shouldBrand = true; 786 } 787 if (shouldBrand && !isPhantom) { 788 brandElement = brandElement || createBadge(); 789 ensureBrand(); 790 setTimeout(ensureBrand, 500); 791 } 792 }; 793 794 function createBadge() { 795 var $brand = $('<a class="w-webflow-badge"></a>') 796 .attr('href', 'https://webflow.com?utm_campaign=brandjs'); 797 798 var $logoArt = $('<img>') 799 .attr('src', 'https://d1otoma47x30pg.cloudfront.net/img/webflow-badge-icon.60efbf6ec9.svg') 800 .css({ 801 marginRight: '8px', 802 width: '16px', 803 }); 804 805 var $logoText = $('<img>') 806 .attr('src', 'https://d1otoma47x30pg.cloudfront.net/img/webflow-badge-text.6faa6a38cd.svg'); 807 808 $brand.append($logoArt, $logoText); 809 return $brand[0]; 810 } 811 812 function ensureBrand() { 813 var found = $body.children(namespace); 814 var match = found.length && found.get(0) === brandElement; 815 var inEditor = Webflow.env('editor'); 816 if (match) { 817 // Remove brand when Editor is active 818 if (inEditor) { 819 found.remove(); 820 } 821 // Exit early, brand is in place 822 return; 823 } 824 // Remove any invalid brand elements 825 if (found.length) { 826 found.remove(); 827 } 828 // Append the brand (unless Editor is active) 829 if (!inEditor) { 830 $body.append(brandElement); 831 } 832 } 833 834 // Export module 835 return api; 836 }); 837 }); 838 839 var webflowEdit = __commonjs(function (module) { 840 /** 841 * Webflow: Editor loader 842 */ 843 844 var Webflow = require$$0$1; 845 846 Webflow.define('edit', module.exports = function($, _, options) { 847 options = options || {}; 848 849 // Exit early in test env or when inside an iframe 850 if (Webflow.env('test') || Webflow.env('frame')) { 851 // Allow test fixtures to continue 852 if (!options.fixture) { 853 return {exit: 1}; 854 } 855 } 856 857 var api = {}; 858 var $win = $(window); 859 var $html = $(document.documentElement); 860 var location = document.location; 861 var hashchange = 'hashchange'; 862 var loaded; 863 var loadEditor = options.load || load; 864 var hasLocalStorage = false; 865 866 try { 867 // Check localStorage for editor data 868 hasLocalStorage = localStorage && localStorage.getItem && localStorage.getItem('WebflowEditor'); 869 } catch (e) { 870 // SecurityError: browser storage has been disabled 871 } 872 873 if (hasLocalStorage) { 874 loadEditor(); 875 876 } else if (location.search) { 877 // Check url query for `edit` parameter or any url ending in `?edit` 878 if (/[?&](edit)(?:[=&?]|$)/.test(location.search) || /\?edit$/.test(location.href)) { 879 loadEditor(); 880 } 881 882 } else {
883 // Check hash fragment to support `#hash?edit` 884 $win.on(hashchange, checkHash).triggerHandler(hashchange); 885 } 886 887 function checkHash() { 888 if (loaded) return; 889 // Load editor when hash contains `?edit` 890 if (/\?edit/.test(location.hash)) loadEditor(); 891 } 892 893 function load() { 894 loaded = true; 895 // Predefine global immediately to benefit Webflow.env 896 window.WebflowEditor = true; 897 $win.off(hashchange, checkHash); 898 $.ajax({ 899 url: cleanSlashes("https://editor-api.webflow.com" + '/api/editor/view'), 900 data: { siteId: $html.attr('data-wf-site') }, 901 xhrFields: { withCredentials: true }, 902 dataType: 'json', 903 crossDomain: true, 904 success: success 905 }); 906 } 907 908 function success(data) { 909 if (!data) { 910 console.error('Could not load editor data'); 911 return; 912 } 913 getScript(prefix(data.scriptPath), function () { 914 window.WebflowEditor(data); 915 }); 916 } 917 918 function getScript(url, done) { 919 $.ajax({ type: 'GET', url: url, dataType: 'script', cache: true }).then(done, error); 920 } 921 922 function error(jqXHR, textStatus, errorThrown) { 923 console.error('Could not load editor script: ' + textStatus); 924 throw errorThrown; 925 } 926 927 function prefix(url) { 928 return (url.indexOf('//') >= 0) ? url : cleanSlashes("https://editor-api.webflow.com" + url); 929 } 930 931 function cleanSlashes(url) { 932 return url.replace(/([^:])\/\//g, '$1/'); 933 } 934 935 // Export module 936 return api; 937 }); 938 }); 939 940 var xdomainMin = __commonjs(function (module) { 941 /*! 942 * jQuery-ajaxTransport-XDomainRequest - v1.0.3 943 * 2014-12-16 WEBFLOW - Removed UMD wrapper 944 * https://github.com/MoonScript/jQuery-ajaxTransport-XDomainRequest 945 * Copyright (c) 2014 Jason Moon (@JSONMOON) 946 * @license MIT (/blob/master/LICENSE.txt) 947 */ 948 module.exports=function($){if($.support.cors||!$.ajaxTransport||!window.XDomainRequest){return}var httpRegEx=/^https?:\/\//i;var getOrPostRegEx=/^get|post$/i;var sameSchemeRegEx=new RegExp("^"+location.protocol,"i");$.ajaxTransport("* text html xml json",function(options,userOptions,jqXHR){if(!options.crossDomain||!options.async||!getOrPostRegEx.test(options.type)||!httpRegEx.test(options.url)||!sameSchemeRegEx.test(options.url)){return}var xdr=null;return{send:function(headers,complete){var postData="";var userType=(userOptions.dataType||"").toLowerCase();xdr=new XDomainRequest;if(/^\d+$/.test(userOptions.timeout)){xdr.timeout=userOptions.timeout}xdr.ontimeout=function(){complete(500,"timeout")};xdr.onload=function(){var allResponseHeaders="Content-Length: "+xdr.responseText.length+"\r\nContent-Type: "+xdr.contentType;var status={code:200,message:"success"};var responses={text:xdr.responseText};try{if(userType==="html"||/text\/html/i.test(xdr.contentType)){responses.html=xdr.responseText}else if(userType==="json"||userType!=="text"&&/\/json/i.test(xdr.contentType)){try{responses.json=$.parseJSON(xdr.responseText)}catch(e){status.code=500;status.message="parseerror"}}else if(userType==="xml"||userType!=="text"&&/\/xml/i.test(xdr.contentType)){var doc=new ActiveXObject("Microsoft.XMLDOM");doc.async=false;try{doc.loadXML(xdr.responseText)}catch(e){doc=undefined}if(!doc||!doc.documentElement||doc.getElementsByTagName("parsererror").length){status.code=500;status.message="parseerror";throw"Invalid XML: "+xdr.responseText}responses.xml=doc}}catch(parseMessage){throw parseMessage}finally{complete(status.code,status.message,responses,allResponseHeaders)}};xdr.onprogress=function(){};xdr.onerror=function(){complete(500,"error",{text:xdr.responseText})};if(userOptions.data){postData=$.type(userOptions.data)==="string"?userOptions.data:$.param(userOptions.data)}xdr.open(options.type,options.url);xdr.send(postData)},abort:function(){if(xdr){xdr.abort()}}}})}(window.jQuery); 949 }); 950 951 var webflowForms = __commonjs(function (module) { 952 /** 953 * Webflow: Forms 954 */ 955 956 var Webflow = require$$0$1; 957 958 Webflow.define('forms', module.exports = function($, _) { 959 var api = {}; 960 961 // Cross-Domain AJAX for IE8 962 963 964 var $doc = $(document); 965 var $forms; 966 var loc = window.location; 967 var retro = window.XDomainRequest && !window.atob; 968 var namespace = '.w-form'; 969 var siteId; 970 var emailField = /e(-)?mail/i; 971 var emailValue = /^\S+@\S+$/; 972 var alert = window.alert; 973 var inApp = Webflow.env(); 974 var listening; 975 976 // MailChimp domains: list-manage.com + mirrors 977 var chimpRegex = /list-manage[1-9]?.com/i; 978 979 var disconnected = _.debounce(function() { 980 alert('Oops! This page has improperly configured forms. Please contact your website administrator to fix this issue.'); 981 }, 100); 982 983 api.ready = api.design = api.preview = function() { 984 // Init forms 985 init(); 986
987 // Wire document events on published site only once 988 if (!inApp && !listening) { 989 addListeners(); 990 } 991 }; 992 993 function init() { 994 siteId = $('html').attr('data-wf-site'); 995 996 $forms = $(namespace + ' form'); 997 if (!$forms.length) return; 998 $forms.each(build); 999 } 1000 1001 function build(i, el) { 1002 // Store form state using namespace 1003 var $el = $(el); 1004 var data = $.data(el, namespace); 1005 if (!data) data = $.data(el, namespace, { form: $el }); // data.form 1006 1007 reset(data); 1008 var wrap = $el.closest('div.w-form'); 1009 data.done = wrap.find('> .w-form-done'); 1010 data.fail = wrap.find('> .w-form-fail'); 1011 1012 var action = data.action = $el.attr('action'); 1013 data.handler = null; 1014 data.redirect = $el.attr('data-redirect'); 1015 1016 // MailChimp form 1017 if (chimpRegex.test(action)) { data.handler = submitMailChimp; return; } 1018 1019 // Custom form action 1020 if (action) return; 1021 1022 // Webflow form 1023 if (siteId) { data.handler = submitWebflow; return; } 1024 1025 // Alert for disconnected Webflow forms 1026 disconnected(); 1027 } 1028 1029 function addListeners() { 1030 listening = true; 1031 1032 // Handle form submission for Webflow forms 1033 $doc.on('submit', namespace + ' form', function(evt) { 1034 var data = $.data(this, namespace); 1035 if (data.handler) { 1036 data.evt = evt; 1037 data.handler(data); 1038 } 1039 }); 1040 } 1041 1042 // Reset data common to all submit handlers 1043 function reset(data) { 1044 var btn = data.btn = data.form.find(':input[type="submit"]'); 1045 data.wait = data.btn.attr('data-wait') || null; 1046 data.success = false; 1047 btn.prop('disabled', false); 1048 data.label && btn.val(data.label); 1049 } 1050 1051 // Disable submit button 1052 function disableBtn(data) { 1053 var btn = data.btn; 1054 var wait = data.wait; 1055 btn.prop('disabled', true); 1056 // Show wait text and store previous label 1057 if (wait) { 1058 data.label = btn.val(); 1059 btn.val(wait); 1060 } 1061 } 1062 1063 // Find form fields, validate, and set value pairs 1064 function findFields(form, result) { 1065 var status = null; 1066 result = result || {}; 1067 1068 // The ":input" selector is a jQuery shortcut to select all inputs, selects, textareas 1069 form.find(':input:not([type="submit"])').each(function(i, el) { 1070 var field = $(el); 1071 var type = field.attr('type'); 1072 var name = field.attr('data-name') || field.attr('name') || ('Field ' + (i + 1)); 1073 var value = field.val(); 1074 1075 if (type === 'checkbox') { 1076 value = field.is(':checked'); 1077 } if (type === 'radio') { 1078 // Radio group value already processed 1079 if (result[name] === null || typeof result[name] === 'string') { 1080 return; 1081 } 1082 1083 value = form.find('input[name="' + field.attr('name') + '"]:checked').val() || null; 1084 } 1085 1086 if (typeof value === 'string') value = $.trim(value); 1087 result[name] = value; 1088 status = status || getStatus(field, type, name, value); 1089 }); 1090 1091 return status; 1092 } 1093 1094 function getStatus(field, type, name, value) { 1095 var status = null; 1096 1097 if (type === 'password') { 1098 status = 'Passwords cannot be submitted.'; 1099 } else if (field.attr('required')) { 1100 if (!value) { 1101 status = 'Please fill out the required field: ' + name; 1102 } else if (emailField.test(name) || emailField.test(field.attr('type'))) { 1103 if (!emailValue.test(value)) status = 'Please enter a valid email address for: ' + name; 1104 } 1105 } 1106 1107 return status; 1108 } 1109 1110 // Submit form to Webflow 1111 function submitWebflow(data) { 1112 reset(data); 1113 1114 var form = data.form; 1115 var payload = { 1116 name: form.attr('data-name') || form.attr('name') || 'Untitled Form', 1117 source: loc.href, 1118 test: Webflow.env(), 1119 fields: {}, 1120 dolphin: /pass[\s-_]?(word|code)|secret|login|credentials/i.test(form.html()) 1121 }; 1122 1123 preventDefault(data); 1124 1125 // Find & populate all fields 1126 var status = findFields(form, payload.fields); 1127 if (status) return alert(status); 1128 1129 // Disable submit button 1130 disableBtn(data); 1131 1132 // Read site ID 1133 // NOTE: If this site is exported, the HTML tag must retain the data-wf-site attribute for forms to work 1134 if (!siteId) { afterSubmit(data); return; } 1135 var url = "https://webflow.com" + '/api/v1/form/' + siteId; 1136 1137 // Work around same-protocol IE XDR limitation - without this IE9 and below forms won't submit 1138 if (retro && url.indexOf("https://webflow.com") >= 0) { 1139 url = url.replace("https://webflow.com", "http://formdata.webflow.com"); 1140 } 1141 1142 $.ajax({ 1143 url: url, 1144 type: 'POST', 1145 data: payload, 1146 dataType: 'json', 1147 crossDomain: true 1148 }).done(function() { 1149 data.success = true; 1150 afterSubmit(data); 1151 }).fail(function() { 1152 afterSubmit(data); 1153 }); 1154 } 1155 1156 // Submit form to MailChimp 1157 function submitMailChimp(data) { 1158 reset(data); 1159 1160 var form = data.form; 1161 var payload = {}; 1162 1163 // Skip Ajax submission if http/s mismatch, fallback to POST instead 1164 if (/^https/.test(loc.href) && !/^https/.test(data.action)) { 1165 form.attr('method', 'post'); 1166 return; 1167 } 1168 1169 preventDefault(data); 1170 1171 // Find & populate all fields 1172 var status = findFields(form, payload); 1173 if (status) return alert(status); 1174 1175 // Disable submit button 1176 disableBtn(data); 1177 1178 // Use special format for MailChimp params 1179 var fullName; 1180 _.each(payload, function(value, key) { 1181 if (emailField.test(key)) payload.EMAIL = value; 1182 if (/^((full[ _-]?)?name)$/i.test(key)) fullName = value; 1183 if (/^(first[ _-]?name)$/i.test(key)) payload.FNAME = value; 1184 if (/^(last[ _-]?name)$/i.test(key)) payload.LNAME = value; 1185 }); 1186 1187 if (fullName && !payload.FNAME) { 1188 fullName = fullName.split(' '); 1189 payload.FNAME = fullName[0]; 1190 payload.LNAME = payload.LNAME || fullName[1]; 1191 } 1192 1193 // Use the (undocumented) MailChimp jsonp api 1194 var url = data.action.replace('/post?', '/post-json?') + '&c=?'; 1195 // Add special param to prevent bot signups 1196 var userId = url.indexOf('u=') + 2; 1197 userId = url.substring(userId, url.indexOf('&', userId)); 1198 var listId = url.indexOf('id=') + 3; 1199 listId = url.substring(listId, url.indexOf('&', listId)); 1200 payload['b_' + userId + '_' + listId] = ''; 1201 1202 $.ajax({ 1203 url: url, 1204 data: payload, 1205 dataType: 'jsonp' 1206 }).done(function(resp) { 1207 data.success = (resp.result === 'success' || /already/.test(resp.msg)); 1208 if (!data.success) console.info('MailChimp error: ' + resp.msg); 1209 afterSubmit(data); 1210 }).fail(function() { 1211 afterSubmit(data); 1212 }); 1213 } 1214 1215 // Common callback which runs after all Ajax submissions 1216 function afterSubmit(data) { 1217 var form = data.form; 1218 var redirect = data.redirect; 1219 var success = data.success; 1220 1221 // Redirect to a success url if defined 1222 if (success && redirect) { 1223 Webflow.location(redirect); 1224 return; 1225 } 1226 1227 // Show or hide status divs 1228 data.done.toggle(success); 1229 data.fail.toggle(!success); 1230 1231 // Hide form on success 1232 form.toggle(!success); 1233 1234 // Reset data and enable submit button 1235 reset(data); 1236 } 1237 1238 function preventDefault(data) { 1239 data.evt && data.evt.preventDefault(); 1240 data.evt = null; 1241 } 1242 1243 // Export module 1244 return api; 1245 }); 1246 }); 1247 1248 var webflowIxEvents = __commonjs(function (module) { 1249 'use strict'; 1250 1251 /** 1252 * Webflow: IX Event triggers for other modules 1253 */ 1254 1255 var $ = window.jQuery; 1256 var api = {}; 1257 var eventQueue = []; 1258 var namespace = '.w-ix'; 1259 1260 var eventTriggers = { 1261 reset: function(i, el) { 1262 el.__wf_intro = null; 1263 }, 1264 intro: function(i, el) { 1265 if (el.__wf_intro) return; 1266 el.__wf_intro = true; 1267 $(el).triggerHandler(api.types.INTRO); 1268 }, 1269 outro: function(i, el) { 1270 if (!el.__wf_intro) return; 1271 el.__wf_intro = null; 1272 $(el).triggerHandler(api.types.OUTRO); 1273 } 1274 }; 1275 1276 api.triggers = {}; 1277 1278 api.types = { 1279 INTRO: 'w-ix-intro' + namespace, 1280 OUTRO: 'w-ix-outro' + namespace 1281 }; 1282 1283 // Trigger any events in queue + restore trigger methods 1284 api.init = function() { 1285 var count = eventQueue.length; 1286 for (var i = 0; i < count; i++) { 1287 var memo = eventQueue[i]; 1288 memo[0](0, memo[1]); 1289 } 1290 eventQueue = []; 1291 $.extend(api.triggers, eventTriggers); 1292 }; 1293 1294 // Replace all triggers with async wrapper to queue events until init 1295 api.async = function() { 1296 for (var key in eventTriggers) { 1297 var func = eventTriggers[key]; 1298 if (!eventTriggers.hasOwnProperty(key)) continue; 1299 1300 // Replace trigger method with async wrapper 1301 api.triggers[key] = function(i, el) { 1302 eventQueue.push([func, el]); 1303 }; 1304 } 1305 }; 1306 1307 // Default triggers to async queue 1308 api.async(); 1309 1310 module.exports = api; 1311 }); 1312 1313 var require$$0$3 = (webflowIxEvents && typeof webflowIxEvents === 'object' && 'default' in webflowIxEvents ? webflowIxEvents['default'] : webflowIxEvents); 1314 1315 var webflowIx = __commonjs(function (module) { 1316 /** 1317 * Webflow: Interactions 1318 */ 1319 1320 var Webflow = require$$0$1; 1321 var IXEvents = require$$0$3; 1322 1323 Webflow.define('ix', module.exports = function($, _) { 1324 var api = {}; 1325 var designer; 1326 var $win = $(window); 1327 var namespace = '.w-ix'; 1328 var tram = $.tram; 1329 var env = Webflow.env; 1330 var inApp = env(); 1331 var emptyFix = env.chrome && env.chrome < 35; 1332 var transNone = 'none 0s ease 0s'; 1333 var $subs = $(); 1334 var config = {}; 1335 var anchors = []; 1336 var loads = []; 1337 var readys = []; 1338 var destroyed; 1339 var readyDelay = 1; 1340 1341 // Component types and proxy selectors 1342 var components = { 1343 tabs: '.w-tab-link, .w-tab-pane', 1344 dropdown: '.w-dropdown', 1345 slider: '.w-slide', 1346 navbar: '.w-nav' 1347 }; 1348 1349 // ----------------------------------- 1350 // Module methods 1351 1352 api.init = function(list) { 1353 setTimeout(function() { configure(list); }, 1); 1354 }; 1355 1356 api.preview = function() { 1357 designer = false;
1358 readyDelay = 100; 1359 setTimeout(function() { configure(window.__wf_ix); }, 1); 1360 }; 1361 1362 api.design = function() { 1363 designer = true; 1364 api.destroy(); 1365 }; 1366 1367 api.destroy = function() { 1368 destroyed = true; 1369 $subs.each(teardown); 1370 Webflow.scroll.off(scroll); 1371 IXEvents.async(); 1372 anchors = []; 1373 loads = []; 1374 readys = []; 1375 }; 1376 1377 api.ready = function() { 1378 // Redirect IX init while in design/preview modes 1379 if (inApp) return env('design') ? api.design() : api.preview(); 1380 1381 // Ready should only be used after destroy, as a way to re-init 1382 if (config && destroyed) { 1383 destroyed = false; 1384 init(); 1385 } 1386 }; 1387 1388 api.run = run; 1389 api.style = inApp ? styleApp : stylePub; 1390 1391 // ----------------------------------- 1392 // Private methods 1393 1394 function configure(list) { 1395 if (!list) return; 1396 1397 // Map all interactions by slug 1398 config = {}; 1399 _.each(list, function(item) { 1400 config[item.slug] = item.value; 1401 }); 1402 1403 // Init ix after config 1404 init(); 1405 } 1406 1407 function init() { 1408 // Build each element's interaction keying from data attribute 1409 var els = $('[data-ix]'); 1410 if (!els.length) return; 1411 els.each(teardown); 1412 els.each(build); 1413 1414 // Listen for scroll events if any anchors exist 1415 if (anchors.length) { 1416 Webflow.scroll.on(scroll); 1417 setTimeout(scroll, 1); 1418 } 1419 1420 // Handle loads or readys if they exist 1421 if (loads.length) Webflow.load(runLoads); 1422 if (readys.length) setTimeout(runReadys, readyDelay); 1423 1424 // Trigger queued events, must happen after init 1425 IXEvents.init(); 1426 1427 // Trigger a redraw to ensure all IX intros play 1428 Webflow.redraw.up(); 1429 } 1430 1431 function build(i, el) { 1432 var $el = $(el); 1433 var id = $el.attr('data-ix'); 1434 var ix = config[id]; 1435 if (!ix) return; 1436 var triggers = ix.triggers; 1437 if (!triggers) return; 1438 1439 // Set styles immediately to provide tram with starting transform values 1440 api.style($el, ix.style); 1441 1442 _.each(triggers, function(trigger) { 1443 var state = {}; 1444 var type = trigger.type; 1445 var stepsB = trigger.stepsB && trigger.stepsB.length; 1446 1447 function runA() { run(trigger, $el, { group: 'A' }); } 1448 function runB() { run(trigger, $el, { group: 'B' }); } 1449 1450 if (type === 'load') { 1451 (trigger.preload && !inApp) ? loads.push(runA) : readys.push(runA); 1452 return; 1453 } 1454 1455 if (type === 'click') { 1456 $el.on('click' + namespace, function(evt) { 1457 // Avoid late clicks on touch devices 1458 if (!Webflow.validClick(evt.currentTarget)) return; 1459 1460 // Prevent default on empty hash urls 1461 if ($el.attr('href') === '#') evt.preventDefault(); 1462 1463 run(trigger, $el, { group: state.clicked ? 'B' : 'A' }); 1464 if (stepsB) state.clicked = !state.clicked; 1465 }); 1466 $subs = $subs.add($el); 1467 return; 1468 } 1469 1470 if (type === 'hover') { 1471 $el.on('mouseenter' + namespace, runA); 1472 $el.on('mouseleave' + namespace, runB); 1473 $subs = $subs.add($el); 1474 return; 1475 } 1476 1477 if (type === 'scroll') { 1478 anchors.push({ 1479 el: $el, trigger: trigger, state: { active: false }, 1480 offsetTop: convert(trigger.offsetTop), 1481 offsetBot: convert(trigger.offsetBot) 1482 }); 1483 return; 1484 } 1485 1486 // Check for a proxy component selector 1487 // type == [tabs, dropdown, slider, navbar] 1488 var proxy = components[type]; 1489 if (proxy) { 1490 var $proxy = $el.closest(proxy); 1491 $proxy.on(IXEvents.types.INTRO, runA).on(IXEvents.types.OUTRO, runB); 1492 $subs = $subs.add($proxy); 1493 return; 1494 } 1495 }); 1496 } 1497 1498 function convert(offset) { 1499 if (!offset) return 0; 1500 offset = String(offset); 1501 var result = parseInt(offset, 10); 1502 if (result !== result) return 0; 1503 if (offset.indexOf('%') > 0) { 1504 result /= 100; 1505 if (result >= 1) result = 0.999; 1506 } 1507 return result; 1508 } 1509 1510 function teardown(i, el) { 1511 $(el).off(namespace); 1512 } 1513 1514 function scroll() { 1515 var viewTop = $win.scrollTop(); 1516 var viewHeight = $win.height(); 1517 1518 // Check each anchor for a valid scroll trigger 1519 var count = anchors.length; 1520 for (var i = 0; i < count; i++) { 1521 var anchor = anchors[i]; 1522 var $el = anchor.el; 1523 var trigger = anchor.trigger; 1524 var stepsB = trigger.stepsB && trigger.stepsB.length; 1525 var state = anchor.state; 1526 var top = $el.offset().top; 1527 var height = $el.outerHeight(); 1528 var offsetTop = anchor.offsetTop; 1529 var offsetBot = anchor.offsetBot; 1530 if (offsetTop < 1 && offsetTop > 0) offsetTop *= viewHeight; 1531 if (offsetBot < 1 && offsetBot > 0) offsetBot *= viewHeight; 1532 var active = (top + height - offsetTop >= viewTop && top + offsetBot <= viewTop + viewHeight); 1533 if (active === state.active) continue; 1534 if (active === false && !stepsB) continue; 1535 state.active = active; 1536 run(trigger, $el, { group: active ? 'A' : 'B' }); 1537 } 1538 } 1539 1540 function runLoads() { 1541 var count = loads.length; 1542 for (var i = 0; i < count; i++) { 1543 loads[i](); 1544 } 1545 } 1546 1547 function runReadys() { 1548 var count = readys.length; 1549 for (var i = 0; i < count; i++) { 1550 readys[i](); 1551 } 1552 } 1553 1554 function run(trigger, $el, opts, replay) { 1555 opts = opts || {}; 1556 var done = opts.done; 1557 var preserve3d = trigger.preserve3d; 1558
1559 // Do not run in designer unless forced 1560 if (designer && !opts.force) return; 1561 1562 // Operate on a set of grouped steps 1563 var group = opts.group || 'A'; 1564 var loop = trigger['loop' + group]; 1565 var steps = trigger['steps' + group]; 1566 if (!steps || !steps.length) return; 1567 if (steps.length < 2) loop = false; 1568 1569 // One-time init before any loops 1570 if (!replay) { 1571 1572 // Find selector within element descendants, siblings, or query whole document 1573 var selector = trigger.selector; 1574 if (selector) { 1575 if (trigger.descend) { 1576 $el = $el.find(selector); 1577 } else if (trigger.siblings) { 1578 $el = $el.siblings(selector); 1579 } else { 1580 $el = $(selector); 1581 } 1582 if (inApp) $el.attr('data-ix-affect', 1); 1583 } 1584 1585 // Apply empty fix for certain Chrome versions 1586 if (emptyFix) $el.addClass('w-ix-emptyfix'); 1587 1588 // Set preserve3d for triggers with 3d transforms 1589 if (preserve3d) $el.css('transform-style', 'preserve-3d'); 1590 } 1591 1592 var _tram = tram($el); 1593 1594 // Add steps 1595 var meta = {omit3d: !preserve3d}; 1596 for (var i = 0; i < steps.length; i++) { 1597 addStep(_tram, steps[i], meta); 1598 } 1599 1600 function fin() { 1601 // Run trigger again if looped 1602 if (loop) return run(trigger, $el, opts, true); 1603 1604 // Reset any 'auto' values 1605 if (meta.width === 'auto') _tram.set({ width: 'auto' }); 1606 if (meta.height === 'auto') _tram.set({ height: 'auto' }); 1607 1608 // Run callback 1609 done && done(); 1610 } 1611 1612 // Add final step to queue if tram has started 1613 meta.start ? _tram.then(fin) : fin(); 1614 } 1615 1616 function addStep(_tram, step, meta) { 1617 var addMethod = 'add'; 1618 var startMethod = 'start'; 1619 1620 // Once the transition has started, we will always use then() to add to the queue. 1621 if (meta.start) addMethod = startMethod = 'then'; 1622 1623 // Parse transitions string on the current step 1624 var transitions = step.transition; 1625 if (transitions) { 1626 transitions = transitions.split(','); 1627 for (var i = 0; i < transitions.length; i++) { 1628 var transition = transitions[i]; 1629 _tram[addMethod](transition); 1630 } 1631 } 1632 1633 // Build a clean object to pass to the tram method 1634 var clean = tramify(step, meta) || {}; 1635 1636 // Store last width and height values 1637 if (clean.width != null) meta.width = clean.width; 1638 if (clean.height != null) meta.height = clean.height; 1639 1640 // When transitions are not present, set values immediately and continue queue. 1641 if (transitions == null) { 1642 1643 // If we have started, wrap set() in then() and reset queue 1644 if (meta.start) { 1645 _tram.then(function() { 1646 var queue = this.queue; 1647 this.set(clean); 1648 if (clean.display) { 1649 _tram.redraw(); 1650 Webflow.redraw.up(); 1651 } 1652 this.queue = queue; 1653 this.next(); 1654 }); 1655 } else { 1656 _tram.set(clean); 1657 1658 // Always redraw after setting display 1659 if (clean.display) { 1660 _tram.redraw(); 1661 Webflow.redraw.up(); 1662 } 1663 } 1664 1665 // Use the wait() method to kick off queue in absence of transitions. 1666 var wait = clean.wait; 1667 if (wait != null) { 1668 _tram.wait(wait); 1669 meta.start = true; 1670 } 1671 1672 // Otherwise, when transitions are present 1673 } else { 1674 1675 // If display is present, handle it separately 1676 if (clean.display) { 1677 var display = clean.display; 1678 delete clean.display; 1679 1680 // If we've already started, we need to wrap it in a then() 1681 if (meta.start) { 1682 _tram.then(function() { 1683 var queue = this.queue; 1684 this.set({ display: display }).redraw(); 1685 Webflow.redraw.up(); 1686 this.queue = queue; 1687 this.next(); 1688 }); 1689 } else { 1690 _tram.set({ display: display }).redraw(); 1691 Webflow.redraw.up(); 1692 } 1693 } 1694 1695 // Otherwise, start a transition using the current start method. 1696 _tram[startMethod](clean); 1697 meta.start = true; 1698 } 1699 } 1700 1701 // (In app) Set styles immediately and manage upstream transition
1702 function styleApp(el, data) { 1703 var _tram = tram(el); 1704 1705 // Exit early when data is empty to avoid clearing upstream 1706 if ($.isEmptyObject(data)) return; 1707 1708 // Get computed transition value 1709 el.css('transition', ''); 1710 var computed = el.css('transition'); 1711 1712 // If computed is set to none, clear upstream 1713 if (computed === transNone) computed = _tram.upstream = null; 1714 1715 // Set upstream transition to none temporarily 1716 _tram.upstream = transNone; 1717 1718 // Set values immediately 1719 _tram.set(tramify(data)); 1720 1721 // Only restore upstream in preview mode 1722 _tram.upstream = computed; 1723 } 1724 1725 // (Published) Set styles immediately on specified jquery element 1726 function stylePub(el, data) { 1727 tram(el).set(tramify(data)); 1728 } 1729 1730 // Build a clean object for tram 1731 function tramify(obj, meta) { 1732 var omit3d = meta && meta.omit3d; 1733 var result = {}; 1734 var found = false; 1735 for (var key in obj) { 1736 if (key === 'transition') continue; 1737 if (key === 'keysort') continue; 1738 if (omit3d) { 1739 if (key === 'z' || key === 'rotateX' || key === 'rotateY' || key === 'scaleZ') { 1740 continue; 1741 } 1742 } 1743 result[key] = obj[key]; 1744 found = true; 1745 } 1746 // If empty, return null for tram.set/stop compliance 1747 return found ? result : null; 1748 } 1749 1750 // Export module 1751 return api; 1752 }); 1753 }); 1754 1755 var webflowLinks = __commonjs(function (module) { 1756 /** 1757 * Webflow: Auto-select links to current page or section 1758 */ 1759 1760 var Webflow = require$$0$1; 1761 1762 Webflow.define('links', module.exports = function($, _) { 1763 var api = {}; 1764 var $win = $(window); 1765 var designer; 1766 var inApp = Webflow.env(); 1767 var location = window.location; 1768 var tempLink = document.createElement('a'); 1769 var linkCurrent = 'w--current'; 1770 var validHash = /^#[a-zA-Z][\w:.-]*$/; 1771 var indexPage = /index\.(html|php)$/; 1772 var dirList = /\/$/; 1773 var anchors; 1774 var slug; 1775 1776 // ----------------------------------- 1777 // Module methods 1778 1779 api.ready = api.design = api.preview = init; 1780 1781 // ----------------------------------- 1782 // Private methods 1783 1784 function init() { 1785 designer = inApp && Webflow.env('design'); 1786 slug = Webflow.env('slug') || location.pathname || ''; 1787 1788 // Reset scroll listener, init anchors 1789 Webflow.scroll.off(scroll); 1790 anchors = []; 1791 1792 // Test all links for a selectable href 1793 var links = document.links; 1794 for (var i = 0; i < links.length; ++i) { 1795 select(links[i]); 1796 } 1797 1798 // Listen for scroll if any anchors exist 1799 if (anchors.length) { 1800 Webflow.scroll.on(scroll); 1801 scroll(); 1802 } 1803 } 1804 1805 function select(link) { 1806 var href = (designer && link.getAttribute('href-disabled')) || link.getAttribute('href'); 1807 tempLink.href = href; 1808 1809 // Ignore any hrefs with a colon to safely avoid all uri schemes 1810 if (href.indexOf(':') >= 0) return; 1811 1812 var $link = $(link); 1813 1814 // Check for valid hash links w/ sections and use scroll anchor 1815 if (href.indexOf('#') === 0 && validHash.test(href)) { 1816 var $section = $(href); 1817 $section.length && anchors.push({ link: $link, sec: $section, active: false }); 1818 return; 1819 } 1820 1821 // Ignore empty # links 1822 if (href === '#') return; 1823 1824 // Determine whether the link should be selected 1825 var match = (tempLink.href === location.href) || (href === slug) || (indexPage.test(href) && dirList.test(slug)); 1826 setClass($link, linkCurrent, match); 1827 } 1828 1829 function scroll() { 1830 var viewTop = $win.scrollTop(); 1831 var viewHeight = $win.height(); 1832 1833 // Check each anchor for a section in view 1834 _.each(anchors, function(anchor) { 1835 var $link = anchor.link; 1836 var $section = anchor.sec; 1837 var top = $section.offset().top; 1838 var height = $section.outerHeight(); 1839 var offset = viewHeight * 0.5; 1840 var active = ($section.is(':visible') && 1841 top + height - offset >= viewTop && 1842 top + offset <= viewTop + viewHeight); 1843 if (anchor.active === active) return; 1844 anchor.active = active; 1845 setClass($link, linkCurrent, active); 1846 if (designer) $link[0].__wf_current = active; 1847 }); 1848 } 1849 1850 function setClass($elem, className, add) { 1851 var exists = $elem.hasClass(className); 1852 if (add && exists) return; 1853 if (!add && !exists) return; 1854 add ? $elem.addClass(className) : $elem.removeClass(className); 1855 } 1856 1857 // Export module 1858 return api; 1859 }); 1860 }); 1861 1862 var webflowScroll = __commonjs(function (module) { 1863 /** 1864 * Webflow: Smooth scroll 1865 */ 1866 1867 var Webflow = require$$0$1; 1868 1869 Webflow.define('scroll', module.exports = function($) { 1870 var $doc = $(document); 1871 var win = window; 1872 var loc = win.location; 1873 var history = inIframe() ? null : win.history;
1874 var validHash = /^[a-zA-Z0-9][\w:.-]*$/; 1875 1876 function inIframe() { 1877 try { 1878 return Boolean(win.frameElement); 1879 } catch (e) { 1880 return true; 1881 } 1882 } 1883 1884 function ready() { 1885 // If hash is already present on page load, scroll to it right away 1886 if (loc.hash) { 1887 findEl(loc.hash.substring(1)); 1888 } 1889 1890 // The current page url without the hash part. 1891 var locHref = loc.href.split('#')[0]; 1892 1893 // When clicking on a link, check if it links to another part of the page 1894 $doc.on('click', 'a', function(e) { 1895 if (Webflow.env('design')) { 1896 return; 1897 } 1898 1899 // Ignore links being used by jQuery mobile 1900 if (window.$.mobile && $(e.currentTarget).hasClass('ui-link')) return; 1901 1902 // Ignore empty # links 1903 if (this.getAttribute('href') === '#') { 1904 e.preventDefault(); 1905 return; 1906 } 1907 1908 // The href property always contains the full url so we can compare 1909 // with the documentâs location to only target links on this page. 1910 var parts = this.href.split('#'); 1911 var hash = parts[0] === locHref ? parts[1] : null; 1912 if (hash) { 1913 findEl(hash, e); 1914 } 1915 }); 1916 } 1917 1918 function findEl(hash, e) { 1919 if (!validHash.test(hash)) return; 1920 1921 var el = $('#' + hash); 1922 if (!el.length) { 1923 return; 1924 } 1925 1926 if (e) { 1927 e.preventDefault(); 1928 e.stopPropagation(); 1929 } 1930 1931 // Push new history state 1932 if ( 1933 loc.hash !== hash && 1934 history && history.pushState && 1935 // Navigation breaks Chrome when the protocol is `file:`. 1936 !(Webflow.env.chrome && loc.protocol === 'file:') 1937 ) { 1938 var oldHash = history.state && history.state.hash; 1939 if (oldHash !== hash) { 1940 history.pushState({ hash: hash }, '', '#' + hash); 1941 } 1942 } 1943 1944 // If a fixed header exists, offset for the height 1945 var rootTag = Webflow.env('editor') ? '.w-editor-body' : 'body'; 1946 var header = $('header, ' + rootTag + ' > .header, ' + rootTag + ' > .w-nav:not([data-no-scroll])'); 1947 var offset = header.css('position') === 'fixed' ? header.outerHeight() : 0; 1948 1949 win.setTimeout(function() { 1950 scroll(el, offset); 1951 }, e ? 0 : 300); 1952 } 1953 1954 function scroll(el, offset){ 1955 var start = $(win).scrollTop(); 1956 var end = el.offset().top - offset; 1957 1958 // If specified, scroll so that the element ends up in the middle of the viewport 1959 if (el.data('scroll') === 'mid') { 1960 var available = $(win).height() - offset; 1961 var elHeight = el.outerHeight(); 1962 if (elHeight < available) { 1963 end -= Math.round((available - elHeight) / 2); 1964 } 1965 } 1966 1967 var mult = 1; 1968 1969 // Check for custom time multiplier on the body and the element 1970 $('body').add(el).each(function() { 1971 var time = parseFloat($(this).attr('data-scroll-time'), 10); 1972 if (!isNaN(time) && (time === 0 || time > 0)) { 1973 mult = time; 1974 } 1975 }); 1976 1977 // Shim for IE8 and below 1978 if (!Date.now) { 1979 Date.now = function() { return new Date().getTime(); }; 1980 } 1981 1982 var clock = Date.now(); 1983 var animate = win.requestAnimationFrame || win.mozRequestAnimationFrame || win.webkitRequestAnimationFrame || function(fn) { win.setTimeout(fn, 15); }; 1984 var duration = (472.143 * Math.log(Math.abs(start - end) +125) - 2000) * mult; 1985 1986 var step = function() { 1987 var elapsed = Date.now() - clock; 1988 win.scroll(0, getY(start, end, elapsed, duration)); 1989 1990 if (elapsed <= duration) { 1991 animate(step); 1992 } 1993 }; 1994 1995 step(); 1996 } 1997 1998 function getY(start, end, elapsed, duration) { 1999 if (elapsed > duration) { 2000 return end; 2001 } 2002 2003 return start + (end - start) * ease(elapsed / duration); 2004 } 2005 2006 function ease(t) { 2007 return t<0.5 ? 4 * t * t * t : (t-1) * (2 * t-2) * (2 * t-2)+1; 2008 } 2009 2010 // Export module 2011 return { ready: ready }; 2012 }); 2013 }); 2014 2015 var webflowTouch = __commonjs(function (module) { 2016 /** 2017 * Webflow: Touch events 2018 */ 2019 2020 var Webflow = require$$0$1; 2021 2022 Webflow.define('touch', module.exports = function($) { 2023 var api = {}; 2024 var fallback = !document.addEventListener; 2025 var getSelection = window.getSelection; 2026 2027 // Fallback to click events in old IE 2028 if (fallback) { 2029 $.event.special.tap = { bindType: 'click', delegateType: 'click' }; 2030 } 2031 2032 api.init = function(el) { 2033 if (fallback) return null; 2034 el = typeof el === 'string' ? $(el).get(0) : el; 2035 return el ? new Touch(el) : null; 2036 }; 2037 2038 function Touch(el) { 2039 var active = false;
2040 var dirty = false; 2041 var useTouch = false; 2042 var thresholdX = Math.min(Math.round(window.innerWidth * 0.04), 40); 2043 var startX; 2044 var startY; 2045 var lastX; 2046 2047 el.addEventListener('touchstart', start, false); 2048 el.addEventListener('touchmove', move, false); 2049 el.addEventListener('touchend', end, false); 2050 el.addEventListener('touchcancel', cancel, false); 2051 el.addEventListener('mousedown', start, false); 2052 el.addEventListener('mousemove', move, false); 2053 el.addEventListener('mouseup', end, false); 2054 el.addEventListener('mouseout', cancel, false); 2055 2056 function start(evt) { 2057 // We donât handle multi-touch events yet. 2058 var touches = evt.touches; 2059 if (touches && touches.length > 1) { 2060 return; 2061 } 2062 2063 active = true; 2064 dirty = false; 2065 2066 if (touches) { 2067 useTouch = true; 2068 startX = touches[0].clientX; 2069 startY = touches[0].clientY; 2070 } else { 2071 startX = evt.clientX; 2072 startY = evt.clientY; 2073 } 2074 2075 lastX = startX; 2076 } 2077 2078 function move(evt) { 2079 if (!active) return; 2080 2081 if (useTouch && evt.type === 'mousemove') { 2082 evt.preventDefault(); 2083 evt.stopPropagation(); 2084 return; 2085 } 2086 2087 var touches = evt.touches; 2088 var x = touches ? touches[0].clientX : evt.clientX; 2089 var y = touches ? touches[0].clientY : evt.clientY; 2090 2091 var velocityX = x - lastX; 2092 lastX = x; 2093 2094 // Allow swipes while pointer is down, but prevent them during text selection 2095 if (Math.abs(velocityX) > thresholdX && getSelection && String(getSelection()) === '') { 2096 triggerEvent('swipe', evt, { direction: velocityX > 0 ? 'right' : 'left' }); 2097 cancel(); 2098 } 2099 2100 // If pointer moves more than 10px flag to cancel tap 2101 if (Math.abs(x - startX) > 10 || Math.abs(y - startY) > 10) { 2102 dirty = true; 2103 } 2104 } 2105 2106 function end(evt) { 2107 if (!active) return; 2108 active = false; 2109 2110 if (useTouch && evt.type === 'mouseup') { 2111 evt.preventDefault(); 2112 evt.stopPropagation(); 2113 useTouch = false; 2114 return; 2115 } 2116 2117 if (!dirty) triggerEvent('tap', evt); 2118 } 2119 2120 function cancel() { 2121 active = false; 2122 } 2123 2124 function destroy() { 2125 el.removeEventListener('touchstart', start, false); 2126 el.removeEventListener('touchmove', move, false); 2127 el.removeEventListener('touchend', end, false); 2128 el.removeEventListener('touchcancel', cancel, false); 2129 el.removeEventListener('mousedown', start, false); 2130 el.removeEventListener('mousemove', move, false); 2131 el.removeEventListener('mouseup', end, false); 2132 el.removeEventListener('mouseout', cancel, false); 2133 el = null; 2134 } 2135 2136 // Public instance methods 2137 this.destroy = destroy; 2138 } 2139 2140 // Wrap native event to supoprt preventdefault + stopPropagation 2141 function triggerEvent(type, evt, data) { 2142 var newEvent = $.Event(type, { originalEvent: evt }); 2143 $(evt.target).trigger(newEvent, data); 2144 } 2145 2146 // Listen for touch events on all nodes by default. 2147 api.instance = api.init(document); 2148 2149 // Export module 2150 return api; 2151 }); 2152 }); 2153 2154}()); 2155 2156/** 2157 * ---------------------------------------------------------------------- 2158 * Webflow: Interactions: Init 2159 */ 2160Webflow.require('ix').init([ 2161 {"slug":"new-interaction","name":"New Interaction","value":{"style":{},"triggers":[{"type":"hover","stepsA":[],"stepsB":[]}]}} 2162]);
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.