PluginProbe
Elementor Website Builder – more than just a page builder / 3.7.0
Elementor Website Builder – more than just a page builder v3.7.0
4.3.0-beta2 4.3.0-beta1 4.2.4 4.2.3 4.2.2 4.2.1 4.2.0 4.1.5 4.2.0-beta2 4.2.0-dev2 4.2.0-beta1 4.1.4 4.1.3 4.1.2 4.1.1 4.1.0 4.1.0-beta3 4.1.0-dev3 4.0.9 4.1.0-beta2 4.1.0-dev2 4.0.8 4.1.0-beta1 4.1.0-dev1 4.0.7 All 451 releases
elementor / assets / lib / waypoints / waypoints.js

waypoints.js in Elementor Website Builder – more than just a page builder 3.7.0, at assets/lib/waypoints/waypoints.js

662 lines 17.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 /*!
2 Waypoints - 4.0.1
3 Copyright © 2011-2016 Caleb Troughton
4 Licensed under the MIT license.
5 https://github.com/imakewebthings/waypoints/blob/master/licenses.txt
6 */
7 (function() {
8 'use strict'
9
10 var keyCounter = 0
11 var allWaypoints = {}
12
13 /* http://imakewebthings.com/waypoints/api/waypoint */
14 function Waypoint(options) {
15 if (!options) {
16 throw new Error('No options passed to Waypoint constructor')
17 }
18 if (!options.element) {
19 throw new Error('No element option passed to Waypoint constructor')
20 }
21 if (!options.handler) {
22 throw new Error('No handler option passed to Waypoint constructor')
23 }
24
25 this.key = 'waypoint-' + keyCounter
26 this.options = Waypoint.Adapter.extend({}, Waypoint.defaults, options)
27 this.element = this.options.element
28 this.adapter = new Waypoint.Adapter(this.element)
29 this.callback = options.handler
30 this.axis = this.options.horizontal ? 'horizontal' : 'vertical'
31 this.enabled = this.options.enabled
32 this.triggerPoint = null
33 this.group = Waypoint.Group.findOrCreate({
34 name: this.options.group,
35 axis: this.axis
36 })
37 this.context = Waypoint.Context.findOrCreateByElement(this.options.context)
38
39 if (Waypoint.offsetAliases[this.options.offset]) {
40 this.options.offset = Waypoint.offsetAliases[this.options.offset]
41 }
42 this.group.add(this)
43 this.context.add(this)
44 allWaypoints[this.key] = this
45 keyCounter += 1
46 }
47
48 /* Private */
49 Waypoint.prototype.queueTrigger = function(direction) {
50 this.group.queueTrigger(this, direction)
51 }
52
53 /* Private */
54 Waypoint.prototype.trigger = function(args) {
55 if (!this.enabled) {
56 return
57 }
58 if (this.callback) {
59 this.callback.apply(this, args)
60 }
61 }
62
63 /* Public */
64 /* http://imakewebthings.com/waypoints/api/destroy */
65 Waypoint.prototype.destroy = function() {
66 this.context.remove(this)
67 this.group.remove(this)
68 delete allWaypoints[this.key]
69 }
70
71 /* Public */
72 /* http://imakewebthings.com/waypoints/api/disable */
73 Waypoint.prototype.disable = function() {
74 this.enabled = false
75 return this
76 }
77
78 /* Public */
79 /* http://imakewebthings.com/waypoints/api/enable */
80 Waypoint.prototype.enable = function() {
81 this.context.refresh()
82 this.enabled = true
83 return this
84 }
85
86 /* Public */
87 /* http://imakewebthings.com/waypoints/api/next */
88 Waypoint.prototype.next = function() {
89 return this.group.next(this)
90 }
91
92 /* Public */
93 /* http://imakewebthings.com/waypoints/api/previous */
94 Waypoint.prototype.previous = function() {
95 return this.group.previous(this)
96 }
97
98 /* Private */
99 Waypoint.invokeAll = function(method) {
100 var allWaypointsArray = []
101 for (var waypointKey in allWaypoints) {
102 allWaypointsArray.push(allWaypoints[waypointKey])
103 }
104 for (var i = 0, end = allWaypointsArray.length; i < end; i++) {
105 allWaypointsArray[i][method]()
106 }
107 }
108
109 /* Public */
110 /* http://imakewebthings.com/waypoints/api/destroy-all */
111 Waypoint.destroyAll = function() {
112 Waypoint.invokeAll('destroy')
113 }
114
115 /* Public */
116 /* http://imakewebthings.com/waypoints/api/disable-all */
117 Waypoint.disableAll = function() {
118 Waypoint.invokeAll('disable')
119 }
120
121 /* Public */
122 /* http://imakewebthings.com/waypoints/api/enable-all */
123 Waypoint.enableAll = function() {
124 Waypoint.Context.refreshAll()
125 for (var waypointKey in allWaypoints) {
126 allWaypoints[waypointKey].enabled = true
127 }
128 return this
129 }
130
131 /* Public */
132 /* http://imakewebthings.com/waypoints/api/refresh-all */
133 Waypoint.refreshAll = function() {
134 Waypoint.Context.refreshAll()
135 }
136
137 /* Public */
138 /* http://imakewebthings.com/waypoints/api/viewport-height */
139 Waypoint.viewportHeight = function() {
140 return window.innerHeight || document.documentElement.clientHeight
141 }
142
143 /* Public */
144 /* http://imakewebthings.com/waypoints/api/viewport-width */
145 Waypoint.viewportWidth = function() {
146 return document.documentElement.clientWidth
147 }
148
149 Waypoint.adapters = []
150
151 Waypoint.defaults = {
152 context: window,
153 continuous: true,
154 enabled: true,
155 group: 'default',
156 horizontal: false,
157 offset: 0
158 }
159
160 Waypoint.offsetAliases = {
161 'bottom-in-view': function() {
162 return this.context.innerHeight() - this.adapter.outerHeight()
163 },
164 'right-in-view': function() {
165 return this.context.innerWidth() - this.adapter.outerWidth()
166 }
167 }
168
169 window.Waypoint = Waypoint
170 }())
171 ;(function() {
172 'use strict'
173
174 function requestAnimationFrameShim(callback) {
175 window.setTimeout(callback, 1000 / 60)
176 }
177
178 var keyCounter = 0
179 var contexts = {}
180 var Waypoint = window.Waypoint
181 var oldWindowLoad = window.onload
182
183 /* http://imakewebthings.com/waypoints/api/context */
184 function Context(element) {
185 this.element = element
186 this.Adapter = Waypoint.Adapter
187 this.adapter = new this.Adapter(element)
188 this.key = 'waypoint-context-' + keyCounter
189 this.didScroll = false
190 this.didResize = false
191 this.oldScroll = {
192 x: this.adapter.scrollLeft(),
193 y: this.adapter.scrollTop()
194 }
195 this.waypoints = {
196 vertical: {},
197 horizontal: {}
198 }
199
200 element.waypointContextKey = this.key
201 contexts[element.waypointContextKey] = this
202 keyCounter += 1
203 if (!Waypoint.windowContext) {
204 Waypoint.windowContext = true
205 Waypoint.windowContext = new Context(window)
206 }
207
208 this.createThrottledScrollHandler()
209 this.createThrottledResizeHandler()
210 }
211
212 /* Private */
213 Context.prototype.add = function(waypoint) {
214 var axis = waypoint.options.horizontal ? 'horizontal' : 'vertical'
215 this.waypoints[axis][waypoint.key] = waypoint
216 this.refresh()
217 }
218
219 /* Private */
220 Context.prototype.checkEmpty = function() {
221 var horizontalEmpty = this.Adapter.isEmptyObject(this.waypoints.horizontal)
222 var verticalEmpty = this.Adapter.isEmptyObject(this.waypoints.vertical)
223 var isWindow = this.element == this.element.window
224 if (horizontalEmpty && verticalEmpty && !isWindow) {
225 this.adapter.off('.waypoints')
226 delete contexts[this.key]
227 }
228 }
229
230 /* Private */
231 Context.prototype.createThrottledResizeHandler = function() {
232 var self = this
233
234 function resizeHandler() {
235 self.handleResize()
236 self.didResize = false
237 }
238
239 this.adapter.on('resize.waypoints', function() {
240 if (!self.didResize) {
241 self.didResize = true
242 Waypoint.requestAnimationFrame(resizeHandler)
243 }
244 })
245 }
246
247 /* Private */
248 Context.prototype.createThrottledScrollHandler = function() {
249 var self = this
250 function scrollHandler() {
251 self.handleScroll()
252 self.didScroll = false
253 }
254
255 this.adapter.on('scroll.waypoints', function() {
256 if (!self.didScroll || Waypoint.isTouch) {
257 self.didScroll = true
258 Waypoint.requestAnimationFrame(scrollHandler)
259 }
260 })
261 }
262
263 /* Private */
264 Context.prototype.handleResize = function() {
265 Waypoint.Context.refreshAll()
266 }
267
268 /* Private */
269 Context.prototype.handleScroll = function() {
270 var triggeredGroups = {}
271 var axes = {
272 horizontal: {
273 newScroll: this.adapter.scrollLeft(),
274 oldScroll: this.oldScroll.x,
275 forward: 'right',
276 backward: 'left'
277 },
278 vertical: {
279 newScroll: this.adapter.scrollTop(),
280 oldScroll: this.oldScroll.y,
281 forward: 'down',
282 backward: 'up'
283 }
284 }
285
286 for (var axisKey in axes) {
287 var axis = axes[axisKey]
288 var isForward = axis.newScroll > axis.oldScroll
289 var direction = isForward ? axis.forward : axis.backward
290
291 for (var waypointKey in this.waypoints[axisKey]) {
292 var waypoint = this.waypoints[axisKey][waypointKey]
293 if (waypoint.triggerPoint === null) {
294 continue
295 }
296 var wasBeforeTriggerPoint = axis.oldScroll < waypoint.triggerPoint
297 var nowAfterTriggerPoint = axis.newScroll >= waypoint.triggerPoint
298 var crossedForward = wasBeforeTriggerPoint && nowAfterTriggerPoint
299 var crossedBackward = !wasBeforeTriggerPoint && !nowAfterTriggerPoint
300 if (crossedForward || crossedBackward) {
301 waypoint.queueTrigger(direction)
302 triggeredGroups[waypoint.group.id] = waypoint.group
303 }
304 }
305 }
306
307 for (var groupKey in triggeredGroups) {
308 triggeredGroups[groupKey].flushTriggers()
309 }
310
311 this.oldScroll = {
312 x: axes.horizontal.newScroll,
313 y: axes.vertical.newScroll
314 }
315 }
316
317 /* Private */
318 Context.prototype.innerHeight = function() {
319 /*eslint-disable eqeqeq */
320 if (this.element == this.element.window) {
321 return Waypoint.viewportHeight()
322 }
323 /*eslint-enable eqeqeq */
324 return this.adapter.innerHeight()
325 }
326
327 /* Private */
328 Context.prototype.remove = function(waypoint) {
329 delete this.waypoints[waypoint.axis][waypoint.key]
330 this.checkEmpty()
331 }
332
333 /* Private */
334 Context.prototype.innerWidth = function() {
335 /*eslint-disable eqeqeq */
336 if (this.element == this.element.window) {
337 return Waypoint.viewportWidth()
338 }
339 /*eslint-enable eqeqeq */
340 return this.adapter.innerWidth()
341 }
342
343 /* Public */
344 /* http://imakewebthings.com/waypoints/api/context-destroy */
345 Context.prototype.destroy = function() {
346 var allWaypoints = []
347 for (var axis in this.waypoints) {
348 for (var waypointKey in this.waypoints[axis]) {
349 allWaypoints.push(this.waypoints[axis][waypointKey])
350 }
351 }
352 for (var i = 0, end = allWaypoints.length; i < end; i++) {
353 allWaypoints[i].destroy()
354 }
355 }
356
357 /* Public */
358 /* http://imakewebthings.com/waypoints/api/context-refresh */
359 Context.prototype.refresh = function() {
360 /*eslint-disable eqeqeq */
361 var isWindow = this.element == this.element.window
362 /*eslint-enable eqeqeq */
363 var contextOffset = isWindow ? undefined : this.adapter.offset()
364 var triggeredGroups = {}
365 var axes
366
367 this.handleScroll()
368 axes = {
369 horizontal: {
370 contextOffset: isWindow ? 0 : contextOffset.left,
371 contextScroll: isWindow ? 0 : this.oldScroll.x,
372 contextDimension: this.innerWidth(),
373 oldScroll: this.oldScroll.x,
374 forward: 'right',
375 backward: 'left',
376 offsetProp: 'left'
377 },
378 vertical: {
379 contextOffset: isWindow ? 0 : contextOffset.top,
380 contextScroll: isWindow ? 0 : this.oldScroll.y,
381 contextDimension: this.innerHeight(),
382 oldScroll: this.oldScroll.y,
383 forward: 'down',
384 backward: 'up',
385 offsetProp: 'top'
386 }
387 }
388
389 for (var axisKey in axes) {
390 var axis = axes[axisKey]
391 for (var waypointKey in this.waypoints[axisKey]) {
392 var waypoint = this.waypoints[axisKey][waypointKey]
393 var adjustment = waypoint.options.offset
394 var oldTriggerPoint = waypoint.triggerPoint
395 var elementOffset = 0
396 var freshWaypoint = oldTriggerPoint == null
397 var contextModifier, wasBeforeScroll, nowAfterScroll
398 var triggeredBackward, triggeredForward
399
400 if (waypoint.element !== waypoint.element.window) {
401 elementOffset = waypoint.adapter.offset()[axis.offsetProp]
402 }
403
404 if (typeof adjustment === 'function') {
405 adjustment = adjustment.apply(waypoint)
406 }
407 else if (typeof adjustment === 'string') {
408 adjustment = parseFloat(adjustment)
409 if (waypoint.options.offset.indexOf('%') > - 1) {
410 adjustment = Math.ceil(axis.contextDimension * adjustment / 100)
411 }
412 }
413
414 contextModifier = axis.contextScroll - axis.contextOffset
415 waypoint.triggerPoint = Math.floor(elementOffset + contextModifier - adjustment)
416 wasBeforeScroll = oldTriggerPoint < axis.oldScroll
417 nowAfterScroll = waypoint.triggerPoint >= axis.oldScroll
418 triggeredBackward = wasBeforeScroll && nowAfterScroll
419 triggeredForward = !wasBeforeScroll && !nowAfterScroll
420
421 if (!freshWaypoint && triggeredBackward) {
422 waypoint.queueTrigger(axis.backward)
423 triggeredGroups[waypoint.group.id] = waypoint.group
424 }
425 else if (!freshWaypoint && triggeredForward) {
426 waypoint.queueTrigger(axis.forward)
427 triggeredGroups[waypoint.group.id] = waypoint.group
428 }
429 else if (freshWaypoint && axis.oldScroll >= waypoint.triggerPoint) {
430 waypoint.queueTrigger(axis.forward)
431 triggeredGroups[waypoint.group.id] = waypoint.group
432 }
433 }
434 }
435
436 Waypoint.requestAnimationFrame(function() {
437 for (var groupKey in triggeredGroups) {
438 triggeredGroups[groupKey].flushTriggers()
439 }
440 })
441
442 return this
443 }
444
445 /* Private */
446 Context.findOrCreateByElement = function(element) {
447 return Context.findByElement(element) || new Context(element)
448 }
449
450 /* Private */
451 Context.refreshAll = function() {
452 for (var contextId in contexts) {
453 contexts[contextId].refresh()
454 }
455 }
456
457 /* Public */
458 /* http://imakewebthings.com/waypoints/api/context-find-by-element */
459 Context.findByElement = function(element) {
460 return contexts[element.waypointContextKey]
461 }
462
463 window.onload = function() {
464 if (oldWindowLoad) {
465 oldWindowLoad()
466 }
467 Context.refreshAll()
468 }
469
470
471 Waypoint.requestAnimationFrame = function(callback) {
472 var requestFn = window.requestAnimationFrame ||
473 window.mozRequestAnimationFrame ||
474 window.webkitRequestAnimationFrame ||
475 requestAnimationFrameShim
476 requestFn.call(window, callback)
477 }
478 Waypoint.Context = Context
479 }())
480 ;(function() {
481 'use strict'
482
483 function byTriggerPoint(a, b) {
484 return a.triggerPoint - b.triggerPoint
485 }
486
487 function byReverseTriggerPoint(a, b) {
488 return b.triggerPoint - a.triggerPoint
489 }
490
491 var groups = {
492 vertical: {},
493 horizontal: {}
494 }
495 var Waypoint = window.Waypoint
496
497 /* http://imakewebthings.com/waypoints/api/group */
498 function Group(options) {
499 this.name = options.name
500 this.axis = options.axis
501 this.id = this.name + '-' + this.axis
502 this.waypoints = []
503 this.clearTriggerQueues()
504 groups[this.axis][this.name] = this
505 }
506
507 /* Private */
508 Group.prototype.add = function(waypoint) {
509 this.waypoints.push(waypoint)
510 }
511
512 /* Private */
513 Group.prototype.clearTriggerQueues = function() {
514 this.triggerQueues = {
515 up: [],
516 down: [],
517 left: [],
518 right: []
519 }
520 }
521
522 /* Private */
523 Group.prototype.flushTriggers = function() {
524 for (var direction in this.triggerQueues) {
525 var waypoints = this.triggerQueues[direction]
526 var reverse = direction === 'up' || direction === 'left'
527 waypoints.sort(reverse ? byReverseTriggerPoint : byTriggerPoint)
528 for (var i = 0, end = waypoints.length; i < end; i += 1) {
529 var waypoint = waypoints[i]
530 if (waypoint.options.continuous || i === waypoints.length - 1) {
531 waypoint.trigger([direction])
532 }
533 }
534 }
535 this.clearTriggerQueues()
536 }
537
538 /* Private */
539 Group.prototype.next = function(waypoint) {
540 this.waypoints.sort(byTriggerPoint)
541 var index = Waypoint.Adapter.inArray(waypoint, this.waypoints)
542 var isLast = index === this.waypoints.length - 1
543 return isLast ? null : this.waypoints[index + 1]
544 }
545
546 /* Private */
547 Group.prototype.previous = function(waypoint) {
548 this.waypoints.sort(byTriggerPoint)
549 var index = Waypoint.Adapter.inArray(waypoint, this.waypoints)
550 return index ? this.waypoints[index - 1] : null
551 }
552
553 /* Private */
554 Group.prototype.queueTrigger = function(waypoint, direction) {
555 this.triggerQueues[direction].push(waypoint)
556 }
557
558 /* Private */
559 Group.prototype.remove = function(waypoint) {
560 var index = Waypoint.Adapter.inArray(waypoint, this.waypoints)
561 if (index > -1) {
562 this.waypoints.splice(index, 1)
563 }
564 }
565
566 /* Public */
567 /* http://imakewebthings.com/waypoints/api/first */
568 Group.prototype.first = function() {
569 return this.waypoints[0]
570 }
571
572 /* Public */
573 /* http://imakewebthings.com/waypoints/api/last */
574 Group.prototype.last = function() {
575 return this.waypoints[this.waypoints.length - 1]
576 }
577
578 /* Private */
579 Group.findOrCreate = function(options) {
580 return groups[options.axis][options.name] || new Group(options)
581 }
582
583 Waypoint.Group = Group
584 }())
585 ;(function() {
586 'use strict'
587
588 var $ = window.jQuery
589 var Waypoint = window.Waypoint
590
591 function JQueryAdapter(element) {
592 this.$element = $(element)
593 }
594
595 $.each([
596 'innerHeight',
597 'innerWidth',
598 'off',
599 'offset',
600 'on',
601 'outerHeight',
602 'outerWidth',
603 'scrollLeft',
604 'scrollTop'
605 ], function(i, method) {
606 JQueryAdapter.prototype[method] = function() {
607 var args = Array.prototype.slice.call(arguments)
608 return this.$element[method].apply(this.$element, args)
609 }
610 })
611
612 $.each([
613 'extend',
614 'inArray',
615 'isEmptyObject'
616 ], function(i, method) {
617 JQueryAdapter[method] = $[method]
618 })
619
620 Waypoint.adapters.push({
621 name: 'jquery',
622 Adapter: JQueryAdapter
623 })
624 Waypoint.Adapter = JQueryAdapter
625 }())
626 ;(function() {
627 'use strict'
628
629 var Waypoint = window.Waypoint
630
631 function createExtension(framework) {
632 return function() {
633 var waypoints = []
634 var overrides = arguments[0]
635
636 if (framework.isFunction(arguments[0])) {
637 overrides = framework.extend({}, arguments[1])
638 overrides.handler = arguments[0]
639 }
640
641 this.each(function() {
642 var options = framework.extend({}, overrides, {
643 element: this
644 })
645 if (typeof options.context === 'string') {
646 options.context = framework(this).closest(options.context)[0]
647 }
648 waypoints.push(new Waypoint(options))
649 })
650
651 return waypoints
652 }
653 }
654
655 if (window.jQuery) {
656 window.jQuery.fn.elementorWaypoint = createExtension(window.jQuery)
657 }
658 if (window.Zepto) {
659 window.Zepto.fn.elementorWaypoint = createExtension(window.Zepto)
660 }
661 }())
662 ;