/*! waypoints - 4.0.1 copyright © 2011-2016 caleb troughton licensed under the mit license. https://github.com/imakewebthings/waypoints/blob/master/licenses.txt */ (function() { 'use strict' var keycounter = 0 var allwaypoints = {} /* http://imakewebthings.com/waypoints/api/waypoint */ function waypoint(options) { if (!options) { throw new error('no options passed to waypoint constructor') } if (!options.element) { throw new error('no element option passed to waypoint constructor') } if (!options.handler) { throw new error('no handler option passed to waypoint constructor') } this.key = 'waypoint-' + keycounter this.options = waypoint.adapter.extend({}, waypoint.defaults, options) this.element = this.options.element this.adapter = new waypoint.adapter(this.element) this.callback = options.handler this.axis = this.options.horizontal ? 'horizontal' : 'vertical' this.enabled = this.options.enabled this.triggerpoint = null this.group = waypoint.group.findorcreate({ name: this.options.group, axis: this.axis }) this.context = waypoint.context.findorcreatebyelement(this.options.context) if (waypoint.offsetaliases[this.options.offset]) { this.options.offset = waypoint.offsetaliases[this.options.offset] } this.group.add(this) this.context.add(this) allwaypoints[this.key] = this keycounter += 1 } /* private */ waypoint.prototype.queuetrigger = function(direction) { this.group.queuetrigger(this, direction) } /* private */ waypoint.prototype.trigger = function(args) { if (!this.enabled) { return } if (this.callback) { this.callback.apply(this, args) } } /* public */ /* http://imakewebthings.com/waypoints/api/destroy */ waypoint.prototype.destroy = function() { this.context.remove(this) this.group.remove(this) delete allwaypoints[this.key] } /* public */ /* http://imakewebthings.com/waypoints/api/disable */ waypoint.prototype.disable = function() { this.enabled = false return this } /* public */ /* http://imakewebthings.com/waypoints/api/enable */ waypoint.prototype.enable = function() { this.context.refresh() this.enabled = true return this } /* public */ /* http://imakewebthings.com/waypoints/api/next */ waypoint.prototype.next = function() { return this.group.next(this) } /* public */ /* http://imakewebthings.com/waypoints/api/previous */ waypoint.prototype.previous = function() { return this.group.previous(this) } /* private */ waypoint.invokeall = function(method) { var allwaypointsarray = [] for (var waypointkey in allwaypoints) { allwaypointsarray.push(allwaypoints[waypointkey]) } for (var i = 0, end = allwaypointsarray.length; i < end; i++) { allwaypointsarray[i][method]() } } /* public */ /* http://imakewebthings.com/waypoints/api/destroy-all */ waypoint.destroyall = function() { waypoint.invokeall('destroy') } /* public */ /* http://imakewebthings.com/waypoints/api/disable-all */ waypoint.disableall = function() { waypoint.invokeall('disable') } /* public */ /* http://imakewebthings.com/waypoints/api/enable-all */ waypoint.enableall = function() { waypoint.context.refreshall() for (var waypointkey in allwaypoints) { allwaypoints[waypointkey].enabled = true } return this } /* public */ /* http://imakewebthings.com/waypoints/api/refresh-all */ waypoint.refreshall = function() { waypoint.context.refreshall() } /* public */ /* http://imakewebthings.com/waypoints/api/viewport-height */ waypoint.viewportheight = function() { return window.innerheight || document.documentelement.clientheight } /* public */ /* http://imakewebthings.com/waypoints/api/viewport-width */ waypoint.viewportwidth = function() { return document.documentelement.clientwidth } waypoint.adapters = [] waypoint.defaults = { context: window, continuous: true, enabled: true, group: 'default', horizontal: false, offset: 0 } waypoint.offsetaliases = { 'bottom-in-view': function() { return this.context.innerheight() - this.adapter.outerheight() }, 'right-in-view': function() { return this.context.innerwidth() - this.adapter.outerwidth() } } window.waypoint = waypoint }()) ;(function() { 'use strict' function requestanimationframeshim(callback) { window.settimeout(callback, 1000 / 60) } var keycounter = 0 var contexts = {} var waypoint = window.waypoint var oldwindowload = window.onload /* http://imakewebthings.com/waypoints/api/context */ function context(element) { this.element = element this.adapter = waypoint.adapter this.adapter = new this.adapter(element) this.key = 'waypoint-context-' + keycounter this.didscroll = false this.didresize = false this.oldscroll = { x: this.adapter.scrollleft(), y: this.adapter.scrolltop() } this.waypoints = { vertical: {}, horizontal: {} } element.waypointcontextkey = this.key contexts[element.waypointcontextkey] = this keycounter += 1 if (!waypoint.windowcontext) { waypoint.windowcontext = true waypoint.windowcontext = new context(window) } this.createthrottledscrollhandler() this.createthrottledresizehandler() } /* private */ context.prototype.add = function(waypoint) { var axis = waypoint.options.horizontal ? 'horizontal' : 'vertical' this.waypoints[axis][waypoint.key] = waypoint this.refresh() } /* private */ context.prototype.checkempty = function() { var horizontalempty = this.adapter.isemptyobject(this.waypoints.horizontal) var verticalempty = this.adapter.isemptyobject(this.waypoints.vertical) var iswindow = this.element == this.element.window if (horizontalempty && verticalempty && !iswindow) { this.adapter.off('.waypoints') delete contexts[this.key] } } /* private */ context.prototype.createthrottledresizehandler = function() { var self = this function resizehandler() { self.handleresize() self.didresize = false } this.adapter.on('resize.waypoints', function() { if (!self.didresize) { self.didresize = true waypoint.requestanimationframe(resizehandler) } }) } /* private */ context.prototype.createthrottledscrollhandler = function() { var self = this function scrollhandler() { self.handlescroll() self.didscroll = false } this.adapter.on('scroll.waypoints', function() { if (!self.didscroll || waypoint.istouch) { self.didscroll = true waypoint.requestanimationframe(scrollhandler) } }) } /* private */ context.prototype.handleresize = function() { waypoint.context.refreshall() } /* private */ context.prototype.handlescroll = function() { var triggeredgroups = {} var axes = { horizontal: { newscroll: this.adapter.scrollleft(), oldscroll: this.oldscroll.x, forward: 'right', backward: 'left' }, vertical: { newscroll: this.adapter.scrolltop(), oldscroll: this.oldscroll.y, forward: 'down', backward: 'up' } } for (var axiskey in axes) { var axis = axes[axiskey] var isforward = axis.newscroll > axis.oldscroll var direction = isforward ? axis.forward : axis.backward for (var waypointkey in this.waypoints[axiskey]) { var waypoint = this.waypoints[axiskey][waypointkey] if (waypoint.triggerpoint === null) { continue } var wasbeforetriggerpoint = axis.oldscroll < waypoint.triggerpoint var nowaftertriggerpoint = axis.newscroll >= waypoint.triggerpoint var crossedforward = wasbeforetriggerpoint && nowaftertriggerpoint var crossedbackward = !wasbeforetriggerpoint && !nowaftertriggerpoint if (crossedforward || crossedbackward) { waypoint.queuetrigger(direction) triggeredgroups[waypoint.group.id] = waypoint.group } } } for (var groupkey in triggeredgroups) { triggeredgroups[groupkey].flushtriggers() } this.oldscroll = { x: axes.horizontal.newscroll, y: axes.vertical.newscroll } } /* private */ context.prototype.innerheight = function() { /*eslint-disable eqeqeq */ if (this.element == this.element.window) { return waypoint.viewportheight() } /*eslint-enable eqeqeq */ return this.adapter.innerheight() } /* private */ context.prototype.remove = function(waypoint) { delete this.waypoints[waypoint.axis][waypoint.key] this.checkempty() } /* private */ context.prototype.innerwidth = function() { /*eslint-disable eqeqeq */ if (this.element == this.element.window) { return waypoint.viewportwidth() } /*eslint-enable eqeqeq */ return this.adapter.innerwidth() } /* public */ /* http://imakewebthings.com/waypoints/api/context-destroy */ context.prototype.destroy = function() { var allwaypoints = [] for (var axis in this.waypoints) { for (var waypointkey in this.waypoints[axis]) { allwaypoints.push(this.waypoints[axis][waypointkey]) } } for (var i = 0, end = allwaypoints.length; i < end; i++) { allwaypoints[i].destroy() } } /* public */ /* http://imakewebthings.com/waypoints/api/context-refresh */ context.prototype.refresh = function() { /*eslint-disable eqeqeq */ var iswindow = this.element == this.element.window /*eslint-enable eqeqeq */ var contextoffset = iswindow ? undefined : this.adapter.offset() var triggeredgroups = {} var axes this.handlescroll() axes = { horizontal: { contextoffset: iswindow ? 0 : contextoffset.left, contextscroll: iswindow ? 0 : this.oldscroll.x, contextdimension: this.innerwidth(), oldscroll: this.oldscroll.x, forward: 'right', backward: 'left', offsetprop: 'left' }, vertical: { contextoffset: iswindow ? 0 : contextoffset.top, contextscroll: iswindow ? 0 : this.oldscroll.y, contextdimension: this.innerheight(), oldscroll: this.oldscroll.y, forward: 'down', backward: 'up', offsetprop: 'top' } } for (var axiskey in axes) { var axis = axes[axiskey] for (var waypointkey in this.waypoints[axiskey]) { var waypoint = this.waypoints[axiskey][waypointkey] var adjustment = waypoint.options.offset var oldtriggerpoint = waypoint.triggerpoint var elementoffset = 0 var freshwaypoint = oldtriggerpoint == null var contextmodifier, wasbeforescroll, nowafterscroll var triggeredbackward, triggeredforward if (waypoint.element !== waypoint.element.window) { elementoffset = waypoint.adapter.offset()[axis.offsetprop] } if (typeof adjustment === 'function') { adjustment = adjustment.apply(waypoint) } else if (typeof adjustment === 'string') { adjustment = parsefloat(adjustment) if (waypoint.options.offset.indexof('%') > - 1) { adjustment = math.ceil(axis.contextdimension * adjustment / 100) } } contextmodifier = axis.contextscroll - axis.contextoffset waypoint.triggerpoint = math.floor(elementoffset + contextmodifier - adjustment) wasbeforescroll = oldtriggerpoint < axis.oldscroll nowafterscroll = waypoint.triggerpoint >= axis.oldscroll triggeredbackward = wasbeforescroll && nowafterscroll triggeredforward = !wasbeforescroll && !nowafterscroll if (!freshwaypoint && triggeredbackward) { waypoint.queuetrigger(axis.backward) triggeredgroups[waypoint.group.id] = waypoint.group } else if (!freshwaypoint && triggeredforward) { waypoint.queuetrigger(axis.forward) triggeredgroups[waypoint.group.id] = waypoint.group } else if (freshwaypoint && axis.oldscroll >= waypoint.triggerpoint) { waypoint.queuetrigger(axis.forward) triggeredgroups[waypoint.group.id] = waypoint.group } } } waypoint.requestanimationframe(function() { for (var groupkey in triggeredgroups) { triggeredgroups[groupkey].flushtriggers() } }) return this } /* private */ context.findorcreatebyelement = function(element) { return context.findbyelement(element) || new context(element) } /* private */ context.refreshall = function() { for (var contextid in contexts) { contexts[contextid].refresh() } } /* public */ /* http://imakewebthings.com/waypoints/api/context-find-by-element */ context.findbyelement = function(element) { return contexts[element.waypointcontextkey] } window.onload = function() { if (oldwindowload) { oldwindowload() } context.refreshall() } waypoint.requestanimationframe = function(callback) { var requestfn = window.requestanimationframe || window.mozrequestanimationframe || window.webkitrequestanimationframe || requestanimationframeshim requestfn.call(window, callback) } waypoint.context = context }()) ;(function() { 'use strict' function bytriggerpoint(a, b) { return a.triggerpoint - b.triggerpoint } function byreversetriggerpoint(a, b) { return b.triggerpoint - a.triggerpoint } var groups = { vertical: {}, horizontal: {} } var waypoint = window.waypoint /* http://imakewebthings.com/waypoints/api/group */ function group(options) { this.name = options.name this.axis = options.axis this.id = this.name + '-' + this.axis this.waypoints = [] this.cleartriggerqueues() groups[this.axis][this.name] = this } /* private */ group.prototype.add = function(waypoint) { this.waypoints.push(waypoint) } /* private */ group.prototype.cleartriggerqueues = function() { this.triggerqueues = { up: [], down: [], left: [], right: [] } } /* private */ group.prototype.flushtriggers = function() { for (var direction in this.triggerqueues) { var waypoints = this.triggerqueues[direction] var reverse = direction === 'up' || direction === 'left' waypoints.sort(reverse ? byreversetriggerpoint : bytriggerpoint) for (var i = 0, end = waypoints.length; i < end; i += 1) { var waypoint = waypoints[i] if (waypoint.options.continuous || i === waypoints.length - 1) { waypoint.trigger([direction]) } } } this.cleartriggerqueues() } /* private */ group.prototype.next = function(waypoint) { this.waypoints.sort(bytriggerpoint) var index = waypoint.adapter.inarray(waypoint, this.waypoints) var islast = index === this.waypoints.length - 1 return islast ? null : this.waypoints[index + 1] } /* private */ group.prototype.previous = function(waypoint) { this.waypoints.sort(bytriggerpoint) var index = waypoint.adapter.inarray(waypoint, this.waypoints) return index ? this.waypoints[index - 1] : null } /* private */ group.prototype.queuetrigger = function(waypoint, direction) { this.triggerqueues[direction].push(waypoint) } /* private */ group.prototype.remove = function(waypoint) { var index = waypoint.adapter.inarray(waypoint, this.waypoints) if (index > -1) { this.waypoints.splice(index, 1) } } /* public */ /* http://imakewebthings.com/waypoints/api/first */ group.prototype.first = function() { return this.waypoints[0] } /* public */ /* http://imakewebthings.com/waypoints/api/last */ group.prototype.last = function() { return this.waypoints[this.waypoints.length - 1] } /* private */ group.findorcreate = function(options) { return groups[options.axis][options.name] || new group(options) } waypoint.group = group }()) ;(function() { 'use strict' var $ = window.jquery var waypoint = window.waypoint function jqueryadapter(element) { this.$element = $(element) } $.each([ 'innerheight', 'innerwidth', 'off', 'offset', 'on', 'outerheight', 'outerwidth', 'scrollleft', 'scrolltop' ], function(i, method) { jqueryadapter.prototype[method] = function() { var args = array.prototype.slice.call(arguments) return this.$element[method].apply(this.$element, args) } }) $.each([ 'extend', 'inarray', 'isemptyobject' ], function(i, method) { jqueryadapter[method] = $[method] }) waypoint.adapters.push({ name: 'jquery', adapter: jqueryadapter }) waypoint.adapter = jqueryadapter }()) ;(function() { 'use strict' var waypoint = window.waypoint function createextension(framework) { return function() { var waypoints = [] var overrides = arguments[0] if (framework.isfunction(arguments[0])) { overrides = framework.extend({}, arguments[1]) overrides.handler = arguments[0] } this.each(function() { var options = framework.extend({}, overrides, { element: this }) if (typeof options.context === 'string') { options.context = framework(this).closest(options.context)[0] } waypoints.push(new waypoint(options)) }) return waypoints } } if (window.jquery) { window.jquery.fn.waypoint = createextension(window.jquery) } if (window.zepto) { window.zepto.fn.waypoint = createextension(window.zepto) } }()) ;