PageSourceSearch

https://manodelfriki.com/modules/ets_superspeed/views/js/ets_lazysizes.js

js manodelfriki.com collected 2026-10-04 13:24:45 UTC 19,895 bytes, 757 lines download raw bytes

vendor: 5,886 bytes, lines 1-241
1/**
2 * 2007-2022 ETS-Soft
3 *
4 * NOTICE OF LICENSE
5 *
6 * This file is not open source! Each license that you purchased is only available for 1 wesite only.
7 * If you want to use this file on more websites (or projects), you need to purchase additional licenses.
8 * You are not allowed to redistribute, resell, lease, license, sub-license or offer our resources to any third party.
9 *
10 * DISCLAIMER
11 *
12 * Do not edit or add to this file if you wish to upgrade PrestaShop to newer
13 * versions in the future. If you wish to customize PrestaShop for your
14 * needs please contact us for extra customization service at an affordable price
15 *
16 *  @author ETS-Soft <[email protected]>
17 *  @copyright  2007-2022 ETS-Soft
18 *  @license    Valid for 1 website (or project) for each purchase of license
19 *  International Registered Trademark & Property of ETS-Soft
20 */
21(function(window, factory) {
22	var lazySizes = factory(window, window.document);
23	window.lazySizes = lazySizes;
24	if(typeof module == 'object' && module.exports){
25		module.exports = lazySizes;
26	}
27}(typeof window != 'undefined' ?
28      window : {}, function l(window, document) {
29	'use strict';
30	/*jshint eqnull:true */
31
32	var lazysizes, lazySizesCfg;
33
34	(function(){
35		var prop;
36
37		var lazySizesDefaults = {
38			lazyClass: 'lazyload',
39			loadedClass: 'lazyloaded',
40			loadingClass: 'lazyloading',
41			preloadClass: 'lazypreload',
42			errorClass: 'lazyerror',
43			//strictClass: 'lazystrict',
44			autosizesClass: 'lazyautosizes',
45			srcAttr: 'data-src',
46			srcsetAttr: 'data-srcset',
47			sizesAttr: 'data-sizes',
48			//preloadAfterLoad: false,
49			minSize: 40,
50			customMedia: {},
51			init: true,
52			expFactor: 1.5,
53			hFac: 0.8,
54			loadMode: 2,
55			loadHidden: true,
56			ricTimeout: 0,
57			throttleDelay: 125,
58		};
59
60		lazySizesCfg = window.lazySizesConfig || window.lazysizesConfig || {};
61
62		for(prop in lazySizesDefaults){
63			if(!(prop in lazySizesCfg)){
64				lazySizesCfg[prop] = lazySizesDefaults[prop];
65			}
66		}
67	})();
68
69	if (!document || !document.getElementsByClassName) {
70		return {
71			init: function () {},
72			cfg: lazySizesCfg,
73			noSupport: true,
74		};
75	}
76
77	var docElem = document.documentElement;
78
79	var Date = window.Date;
80
81	var supportPicture = window.HTMLPictureElement;
82
83	var _addEventListener = 'addEventListener';
84
85	var _getAttribute = 'getAttribute';
86
87	var addEventListener = window[_addEventListener];
88
89	var setTimeout = window.setTimeout;
90
91	var requestAnimationFrame = window.requestAnimationFrame || setTimeout;
92
93	var requestIdleCallback = window.requestIdleCallback;
94
95	var regPicture = /^picture$/i;
96	var regLoadElements = /^img|iframe$/i;
97
98	var loadEvents = ['load', 'error', 'lazyincluded', '_lazyloaded'];
99
100	var regClassCache = {};
101
102	var forEach = Array.prototype.forEach;
103
104	var hasClass = function(ele, cls) {
105		if(!regClassCache[cls]){
106			regClassCache[cls] = new RegExp('(\\s|^)'+cls+'(\\s|$)');
107		}
108		return regClassCache[cls].test(ele[_getAttribute]('class') || '') && regClassCache[cls];
109	};
110
111	var addClass = function(ele, cls) {
112		if (!hasClass(ele, cls)){
113			ele.setAttribute('class', (ele[_getAttribute]('class') || '').trim() + ' ' + cls);
114		}
115	};
116
117	var removeClass = function(ele, cls) {
118		var reg;
119		if ((reg = hasClass(ele,cls))) {
120			ele.setAttribute('class', (ele[_getAttribute]('class') || '').replace(reg, ' '));
121		}
122	};
123
124	var addRemoveLoadEvents = function(dom, fn, add){
125		var action = add ? _addEventListener : 'removeEventListener';
126		if(add){
127			addRemoveLoadEvents(dom, fn);
128		}
129		loadEvents.forEach(function(evt){
130			dom[action](evt, fn);
131		});
132	};
133
134	var triggerEvent = function(elem, name, detail, noBubbles, noCancelable){
135		var event = document.createEvent('Event');
136
137		if(!detail){
138			detail = {};
139		}
140
141		detail.instance = lazysizes;
142
143		event.initEvent(name, !noBubbles, !noCancelable);
144
145		event.detail = detail;
146
147		elem.dispatchEvent(event);
148		return event;
149	};
150
151	var updatePolyfill = function (el, full){
152		var polyfill;
153		if( !supportPicture && ( polyfill = (window.picturefill || lazySizesCfg.pf) ) ){
154			if(full && full.src && !el[_getAttribute]('srcset')){
155				el.setAttribute('srcset', full.src);
156			}
157			polyfill({reevaluate: true, elements: [el]});
158		} else if(full && full.src){
159			el.src = full.src;
160		}
161	};
162
163	var getCSS = function (elem, style){
164		return (getComputedStyle(elem, null) || {})[style];
165	};
166
167	var getWidth = function(elem, parent, width){
168		width = width || elem.offsetWidth;
169
170		while(width < lazySizesCfg.minSize && parent && !elem._lazysizesWidth){
171			width =  parent.offsetWidth;
172			parent = parent.parentNode;
173		}
174
175		return width;
176	};
177
178	var rAF = (function(){
179		var running, waiting;
180		var firstFns = [];
181		var secondFns = [];
182		var fns = firstFns;
183
184		var run = function(){
185			var runFns = fns;
186
187			fns = firstFns.length ? secondFns : firstFns;
188
189			running = true;
190			waiting = false;
191
192			while(runFns.length){
193				runFns.shift()();
194			}
195
196			running = false;
197		};
198
199		var rafBatch = function(fn, queue){
200			if(running && !queue){
201				fn.apply(this, arguments);
202			} else {
203				fns.push(fn);
204
205				if(!waiting){
206					waiting = true;
207					(document.hidden ? setTimeout : requestAnimationFrame)(run);
208				}
209			}
210		};
211
212		rafBatch._lsFlush = run;
213
214		return rafBatch;
215	})();
216
217	var rAFIt = function(fn, simple){
218		return simple ?
219			function() {
220				rAF(fn);
221			} :
222			function(){
223				var that = this;
224				var args = arguments;
225				rAF(function(){
226					fn.apply(that, args);
227				});
228			}
229		;
230	};
231
232	var throttle = function(fn){
233		var running;
234		var lastTime = 0;
235		var gDelay = lazySizesCfg.throttleDelay;
236		var rICTimeout = lazySizesCfg.ricTimeout;
237		var run = function(){
238			running = false;
239			lastTime = Date.now();
240			fn();
241		};
vendor: 14,009 bytes, lines 242-757
242		var idleCallback = requestIdleCallback && rICTimeout > 49 ?
243			function(){
244				requestIdleCallback(run, {timeout: rICTimeout});
245
246				if(rICTimeout !== lazySizesCfg.ricTimeout){
247					rICTimeout = lazySizesCfg.ricTimeout;
248				}
249			} :
250			rAFIt(function(){
251				setTimeout(run);
252			}, true)
253		;
254
255		return function(isPriority){
256			var delay;
257
258			if((isPriority = isPriority === true)){
259				rICTimeout = 33;
260			}
261
262			if(running){
263				return;
264			}
265
266			running =  true;
267
268			delay = gDelay - (Date.now() - lastTime);
269
270			if(delay < 0){
271				delay = 0;
272			}
273
274			if(isPriority || delay < 9){
275				idleCallback();
276			} else {
277				setTimeout(idleCallback, delay);
278			}
279		};
280	};
281
282	//based on http://modernjavascript.blogspot.de/2013/08/building-better-debounce.html
283	var debounce = function(func) {
284		var timeout, timestamp;
285		var wait = 99;
286		var run = function(){
287			timeout = null;
288			func();
289		};
290		var later = function() {
291			var last = Date.now() - timestamp;
292
293			if (last < wait) {
294				setTimeout(later, wait - last);
295			} else {
296				(requestIdleCallback || run)(run);
297			}
298		};
299
300		return function() {
301			timestamp = Date.now();
302
303			if (!timeout) {
304				timeout = setTimeout(later, wait);
305			}
306		};
307	};
308
309	var loader = (function(){
310		var preloadElems, isCompleted, resetPreloadingTimer, loadMode, started;
311
312		var eLvW, elvH, eLtop, eLleft, eLright, eLbottom, isBodyHidden;
313
314		var regImg = /^img$/i;
315		var regIframe = /^iframe$/i;
316
317		var supportScroll = ('onscroll' in window) && !(/(gle|ing)bot/.test(navigator.userAgent));
318
319		var shrinkExpand = 0;
320		var currentExpand = 0;
321
322		var isLoading = 0;
323		var lowRuns = -1;
324
325		var resetPreloading = function(e){
326			isLoading--;
327			if(!e || isLoading < 0 || !e.target){
328				isLoading = 0;
329			}
330		};
331
332		var isVisible = function (elem) {
333			if (isBodyHidden == null) {
334				isBodyHidden = getCSS(document.body, 'visibility') == 'hidden';
335			}
336
337			return isBodyHidden || (getCSS(elem.parentNode, 'visibility') != 'hidden' && getCSS(elem, 'visibility') != 'hidden');
338		};
339
340		var isNestedVisible = function(elem, elemExpand){
341			var outerRect;
342			var parent = elem;
343			var visible = isVisible(elem);
344
345			eLtop -= elemExpand;
346			eLbottom += elemExpand;
347			eLleft -= elemExpand;
348			eLright += elemExpand;
349
350			while(visible && (parent = parent.offsetParent) && parent != document.body && parent != docElem){
351				visible = ((getCSS(parent, 'opacity') || 1) > 0);
352
353				if(visible && getCSS(parent, 'overflow') != 'visible'){
354					outerRect = parent.getBoundingClientRect();
355					visible = eLright > outerRect.left &&
356						eLleft < outerRect.right &&
357						eLbottom > outerRect.top - 1 &&
358						eLtop < outerRect.bottom + 1
359					;
360				}
361			}
362
363			return visible;
364		};
365
366		var checkElements = function() {
367			var eLlen, i, rect, autoLoadElem, loadedSomething, elemExpand, elemNegativeExpand, elemExpandVal,
368				beforeExpandVal, defaultExpand, preloadExpand, hFac;
369			var lazyloadElems = lazysizes.elements;
370
371			if((loadMode = lazySizesCfg.loadMode) && isLoading < 8 && (eLlen = lazyloadElems.length)){
372
373				i = 0;
374
375				lowRuns++;
376
377				for(; i < eLlen; i++){
378
379					if(!lazyloadElems[i] || lazyloadElems[i]._lazyRace){continue;}
380
381					if(!supportScroll || (lazysizes.prematureUnveil && lazysizes.prematureUnveil(lazyloadElems[i]))){unveilElement(lazyloadElems[i]);continue;}
382
383					if(!(elemExpandVal = lazyloadElems[i][_getAttribute]('data-expand')) || !(elemExpand = elemExpandVal * 1)){
384						elemExpand = currentExpand;
385					}
386
387					if (!defaultExpand) {
388						defaultExpand = (!lazySizesCfg.expand || lazySizesCfg.expand < 1) ?
389							docElem.clientHeight > 500 && docElem.clientWidth > 500 ? 500 : 370 :
390							lazySizesCfg.expand;
391
392						lazysizes._defEx = defaultExpand;
393
394						preloadExpand = defaultExpand * lazySizesCfg.expFactor;
395						hFac = lazySizesCfg.hFac;
396						isBodyHidden = null;
397
398						if(currentExpand < preloadExpand && isLoading < 1 && lowRuns > 2 && loadMode > 2 && !document.hidden){
399							currentExpand = preloadExpand;
400							lowRuns = 0;
401						} else if(loadMode > 1 && lowRuns > 1 && isLoading < 6){
402							currentExpand = defaultExpand;
403						} else {
404							currentExpand = shrinkExpand;
405						}
406					}
407
408					if(beforeExpandVal !== elemExpand){
409						eLvW = innerWidth + (elemExpand * hFac);
410						elvH = innerHeight + elemExpand;
411						elemNegativeExpand = elemExpand * -1;
412						beforeExpandVal = elemExpand;
413					}
414
415					rect = lazyloadElems[i].getBoundingClientRect();
416
417					if ((eLbottom = rect.bottom) >= elemNegativeExpand &&
418						(eLtop = rect.top) <= elvH &&
419						(eLright = rect.right) >= elemNegativeExpand * hFac &&
420						(eLleft = rect.left) <= eLvW &&
421						(eLbottom || eLright || eLleft || eLtop) &&
422						(lazySizesCfg.loadHidden || isVisible(lazyloadElems[i])) &&
423						((isCompleted && isLoading < 3 && !elemExpandVal && (loadMode < 3 || lowRuns < 4)) || isNestedVisible(lazyloadElems[i], elemExpand))){
424						unveilElement(lazyloadElems[i]);
425						loadedSomething = true;
426						if(isLoading > 9){break;}
427					} else if(!loadedSomething && isCompleted && !autoLoadElem &&
428						isLoading < 4 && lowRuns < 4 && loadMode > 2 &&
429						(preloadElems[0] || lazySizesCfg.preloadAfterLoad) &&
430						(preloadElems[0] || (!elemExpandVal && ((eLbottom || eLright || eLleft || eLtop) || lazyloadElems[i][_getAttribute](lazySizesCfg.sizesAttr) != 'auto')))){
431						autoLoadElem = preloadElems[0] || lazyloadElems[i];
432					}
433				}
434
435				if(autoLoadElem && !loadedSomething){
436					unveilElement(autoLoadElem);
437				}
438			}
439		};
440
441		var throttledCheckElements = throttle(checkElements);
442
443		var switchLoadingClass = function(e){
444			var elem = e.target;
445
446			if (elem._lazyCache) {
447				delete elem._lazyCache;
448				return;
449			}
450
451			resetPreloading(e);
452			addClass(elem, lazySizesCfg.loadedClass);
453			removeClass(elem, lazySizesCfg.loadingClass);
454			addRemoveLoadEvents(elem, rafSwitchLoadingClass);
455			triggerEvent(elem, 'lazyloaded');
456		};
457		var rafedSwitchLoadingClass = rAFIt(switchLoadingClass);
458		var rafSwitchLoadingClass = function(e){
459			rafedSwitchLoadingClass({target: e.target});
460		};
461
462		var changeIframeSrc = function(elem, src){
463			try {
464				elem.contentWindow.location.replace(src);
465			} catch(e){
466				elem.src = src;
467			}
468		};
469
470		var handleSources = function(source){
471			var customMedia;
472
473			var sourceSrcset = source[_getAttribute](lazySizesCfg.srcsetAttr);
474
475			if( (customMedia = lazySizesCfg.customMedia[source[_getAttribute]('data-media') || source[_getAttribute]('media')]) ){
476				source.setAttribute('media', customMedia);
477			}
478
479			if(sourceSrcset){
480				source.setAttribute('srcset', sourceSrcset);
481			}
482		};
483
484		var lazyUnveil = rAFIt(function (elem, detail, isAuto, sizes, isImg){
485			var src, srcset, parent, isPicture, event, firesLoad;
486
487			if(!(event = triggerEvent(elem, 'lazybeforeunveil', detail)).defaultPrevented){
488
489				if(sizes){
490					if(isAuto){
491						addClass(elem, lazySizesCfg.autosizesClass);
492					} else {
493						elem.setAttribute('sizes', sizes);
494					}
495				}
496
497				srcset = elem[_getAttribute](lazySizesCfg.srcsetAttr);
498				src = elem[_getAttribute](lazySizesCfg.srcAttr);
499
500				if(isImg) {
501					parent = elem.parentNode;
502					isPicture = parent && regPicture.test(parent.nodeName || '');
503				}
504
505				firesLoad = detail.firesLoad || !!(('src' in elem && regLoadElements.test(elem.nodeName)) && (srcset || src || isPicture));
506
507				event = {target: elem};
508
509				addClass(elem, lazySizesCfg.loadingClass);
510
511				if(firesLoad){
512					clearTimeout(resetPreloadingTimer);
513					resetPreloadingTimer = setTimeout(resetPreloading, 2500);
514					addRemoveLoadEvents(elem, rafSwitchLoadingClass, true);
515				}
516
517				if(isPicture){
518					forEach.call(parent.getElementsByTagName('source'), handleSources);
519				}
520
521				if(srcset){
522					elem.setAttribute('srcset', srcset);
523				} else if(src && !isPicture){
524					if(regIframe.test(elem.nodeName)){
525						changeIframeSrc(elem, src);
526					} else {
527						elem.src = src;
528					}
529				}
530
531				if(isImg && (srcset || isPicture)){
532					updatePolyfill(elem, {src: src});
533				}
534			}
535
536			if(elem._lazyRace){
537				delete elem._lazyRace;
538			}
539			removeClass(elem, lazySizesCfg.lazyClass);
540
541			rAF(function(){
542				// Part of this can be removed as soon as this fix is older: https://bugs.chromium.org/p/chromium/issues/detail?id=7731 (2015)
543				var isLoaded = elem.complete && elem.naturalWidth > 1;
544
545				if( !firesLoad || isLoaded){
546					if (isLoaded) {
547						addClass(elem, 'ls-is-cached');
548					}
549					switchLoadingClass(event);
550					elem._lazyCache = true;
551					setTimeout(function(){
552						if ('_lazyCache' in elem) {
553							delete elem._lazyCache;
554						}
555					}, 9);
556				}
557				if (elem.loading == 'lazy') {
558					isLoading--;
559				}
560			}, true);
561		});
562
563		var unveilElement = function (elem){
564			if (elem._lazyRace) {return;}
565			var detail;
566
567			var isImg = regImg.test(elem.nodeName);
568
569			//allow using sizes="auto", but don't use. it's invalid. Use data-sizes="auto" or a valid value for sizes instead (i.e.: sizes="80vw")
570			var sizes = isImg && (elem[_getAttribute](lazySizesCfg.sizesAttr) || elem[_getAttribute]('sizes'));
571			var isAuto = sizes == 'auto';
572
573			if( (isAuto || !isCompleted) && isImg && (elem[_getAttribute]('src') || elem.srcset) && !elem.complete && !hasClass(elem, lazySizesCfg.errorClass) && hasClass(elem, lazySizesCfg.lazyClass)){return;}
574
575			detail = triggerEvent(elem, 'lazyunveilread').detail;
576
577			if(isAuto){
578				 autoSizer.updateElem(elem, true, elem.offsetWidth);
579			}
580
581			elem._lazyRace = true;
582			isLoading++;
583
584			lazyUnveil(elem, detail, isAuto, sizes, isImg);
585		};
586
587		var afterScroll = debounce(function(){
588			lazySizesCfg.loadMode = 3;
589			throttledCheckElements();
590		});
591
592		var altLoadmodeScrollListner = function(){
593			if(lazySizesCfg.loadMode == 3){
594				lazySizesCfg.loadMode = 2;
595			}
596			afterScroll();
597		};
598
599		var onload = function(){
600			if(isCompleted){return;}
601			if(Date.now() - started < 999){
602				setTimeout(onload, 999);
603				return;
604			}
605
606
607			isCompleted = true;
608
609			lazySizesCfg.loadMode = 3;
610
611			throttledCheckElements();
612
613			addEventListener('scroll', altLoadmodeScrollListner, true);
614		};
615
616		return {
617			_: function(){
618				started = Date.now();
619
620				lazysizes.elements = document.getElementsByClassName(lazySizesCfg.lazyClass);
621				preloadElems = document.getElementsByClassName(lazySizesCfg.lazyClass + ' ' + lazySizesCfg.preloadClass);
622
623				addEventListener('scroll', throttledCheckElements, true);
624
625				addEventListener('resize', throttledCheckElements, true);
626
627				if(window.MutationObserver){
628					new MutationObserver( throttledCheckElements ).observe( docElem, {childList: true, subtree: true, attributes: true} );
629				} else {
630					docElem[_addEventListener]('DOMNodeInserted', throttledCheckElements, true);
631					docElem[_addEventListener]('DOMAttrModified', throttledCheckElements, true);
632					setInterval(throttledCheckElements, 999);
633				}
634
635				addEventListener('hashchange', throttledCheckElements, true);
636
637				//, 'fullscreenchange'
638				['focus', 'mouseover', 'click', 'load', 'transitionend', 'animationend'].forEach(function(name){
639					document[_addEventListener](name, throttledCheckElements, true);
640				});
641
642				if((/d$|^c/.test(document.readyState))){
643					onload();
644				} else {
645					addEventListener('load', onload);
646					document[_addEventListener]('DOMContentLoaded', throttledCheckElements);
647					setTimeout(onload, 20000);
648				}
649
650				if(lazysizes.elements.length){
651					checkElements();
652					rAF._lsFlush();
653				} else {
654					throttledCheckElements();
655				}
656			},
657			checkElems: throttledCheckElements,
658			unveil: unveilElement,
659			_aLSL: altLoadmodeScrollListner,
660		};
661	})();
662
663
664	var autoSizer = (function(){
665		var autosizesElems;
666
667		var sizeElement = rAFIt(function(elem, parent, event, width){
668			var sources, i, len;
669			elem._lazysizesWidth = width;
670			width += 'px';
671
672			elem.setAttribute('sizes', width);
673
674			if(regPicture.test(parent.nodeName || '')){
675				sources = parent.getElementsByTagName('source');
676				for(i = 0, len = sources.length; i < len; i++){
677					sources[i].setAttribute('sizes', width);
678				}
679			}
680
681			if(!event.detail.dataAttr){
682				updatePolyfill(elem, event.detail);
683			}
684		});
685		var getSizeElement = function (elem, dataAttr, width){
686			var event;
687			var parent = elem.parentNode;
688
689			if(parent){
690				width = getWidth(elem, parent, width);
691				event = triggerEvent(elem, 'lazybeforesizes', {width: width, dataAttr: !!dataAttr});
692
693				if(!event.defaultPrevented){
694					width = event.detail.width;
695
696					if(width && width !== elem._lazysizesWidth){
697						sizeElement(elem, parent, event, width);
698					}
699				}
700			}
701		};
702
703		var updateElementsSizes = function(){
704			var i;
705			var len = autosizesElems.length;
706			if(len){
707				i = 0;
708
709				for(; i < len; i++){
710					getSizeElement(autosizesElems[i]);
711				}
712			}
713		};
714
715		var debouncedUpdateElementsSizes = debounce(updateElementsSizes);
716
717		return {
718			_: function(){
719				autosizesElems = document.getElementsByClassName(lazySizesCfg.autosizesClass);
720				addEventListener('resize', debouncedUpdateElementsSizes);
721			},
722			checkElems: debouncedUpdateElementsSizes,
723			updateElem: getSizeElement
724		};
725	})();
726
727	var init = function(){
728		if(!init.i && document.getElementsByClassName){
729			init.i = true;
730			autoSizer._();
731			loader._();
732		}
733	};
734
735	setTimeout(function(){
736		if(lazySizesCfg.init){
737			init();
738		}
739	});
740
741	lazysizes = {
742		cfg: lazySizesCfg,
743		autoSizer: autoSizer,
744		loader: loader,
745		init: init,
746		uP: updatePolyfill,
747		aC: addClass,
748		rC: removeClass,
749		hC: hasClass,
750		fire: triggerEvent,
751		gW: getWidth,
752		rAF: rAF,
753	};
754
755	return lazysizes;
756}
757));

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.