1const zzscroll = (() => { 2 const alreadyRegister = []; 3 function zzscroll(id, config){ 4 if (alreadyRegister.includes(id)) { 5 return; 6 } 7 const target = $(id); 8 if (!target.length) { 9 return; 10 } 11 const { duration = 500, interval = 3000, autoplay = true } = config || {} 12 13 alreadyRegister.push(id); 14 const box = target.find('.wrapbox'); 15 const leftBtn = target.siblings('span[class="prev-btn"]'); 16 const rightBtn = target.siblings('span[class="next-btn"]'); 17 18 let firstChild = box.children().first(); 19 let lastChild = box.children().last(); 20 let firstClone; 21 let lastClone; 22 let isRunning = false; 23 let isPaused = false; 24 let pauseTimestamp = 0; 25 let delayTime = null; 26 27 function _animation(to, cb) { 28 isRunning = true; 29 box.css('transition', `transform ${duration}ms ease`); 30 box.css('transform', `translateX(${(box._position || 0) + to}px)`); 31 setTimeout(() => { 32 box.css('transition', 'none'); 33 box.css('transform', `translateX(0px)`); 34 isRunning = false; 35 cb && cb(); 36 }, duration); 37 } 38 39 /** @param {JQuery} el */ 40 function _getSize(el) { 41 const marginLeft = parseInt(el.css('margin-left')); 42 const marginRight = parseInt(el.css('margin-right')); 43 const { width } = el.get(0).getBoundingClientRect(); 44 return { 45 width: width + (parseFloat(marginLeft) || 0) + (parseFloat(marginRight) || 0), 46 }; 47 } 48 49 function _cloneClear() { 50 if (firstClone) { 51 firstClone.remove(); 52 } 53 if (lastClone) { 54 lastClone.remove(); 55 } 56 } 57 58 function _clone() { 59 firstClone = firstChild.clone(true, true); 60 firstClone.get(0).clone = true; 61 lastClone = lastChild.clone(true, true); 62 lastClone.get(0).clone = true; 63 box.append(firstClone); 64 box.prepend(lastClone); 65 const { width } = _getSize(firstClone); 66 const posi = -1 * width; 67 box.css('transition', `none`); 68 box.css('transform', `translateX(${posi}px)`); 69 box._position = posi; 70 } 71 72 /** @param {JQuery} el */ 73 function _move(el, direction, cb) { 74 const { width } = _getSize(el); 75 _animation(direction * width, () => { 76 cb && cb(); 77 }); 78 } 79 80 function _toLeft(cb) { 81 if (isRunning) { 82 return; 83 } 84 _move(lastChild, 1, () => { 85 _cloneClear(); 86 const _lastChild = lastChild.prev(); 87 box.get(0).insertBefore(lastChild.get(0), firstChild.get(0)); 88 firstChild = lastChild; 89 lastChild = _lastChild; 90 _clone(); 91 cb && cb(); 92 }); 93 } 94 95 function _toRight(cb) { 96 if (isRunning) { 97 return; 98 } 99 _move(firstChild, -1, () => { 100 _cloneClear(); 101 const _firstChild = firstChild.next(); 102 box.get(0).appendChild(firstChild.get(0)); 103 lastChild = firstChild; 104 firstChild = _firstChild; 105 _clone(); 106 cb && cb(); 107 }); 108 } 109 110 function _clearDelayTime() { 111 if (delayTime) { 112 clearTimeout(delayTime); 113 } 114 } 115 116 function _autoplay() { 117 if (!autoplay || isRunning || isPaused) { 118 return; 119 } 120 _clearDelayTime(); 121 _toRight(() => { 122 delayTime = setTimeout(_autoplay, interval); 123 }); 124 } 125 126 function _animationState(state) { 127 if (state) { 128 _clearDelayTime(); 129 if (isPaused && !isRunning) { 130 const time = Date.now() - pauseTimestamp; 131 delayTime = setTimeout(_autoplay, time > interval ? 0 : interval - time); 132 pauseTimestamp = 0; 133 } 134 isPaused = false; 135 } else { 136 pauseTimestamp = Date.now(); 137 isPaused = true; 138 } 139 } 140 141 function btnEnter(e) { 142 e.stopPropagation(); 143 _animationState(false); 144 } 145 function btnLeave(e) { 146 e.stopPropagation(); 147 _animationState(true); 148 } 149 150 function _delay(e) { 151 e.stopPropagation(); 152 if (leftBtn) { 153 leftBtn.off('mouseover', _delay); 154 leftBtn.off('click', _delay); 155 } 156 if (rightBtn) { 157 rightBtn.off('mouseover', _delay); 158 rightBtn.off('click', _delay); 159 } 160 if (autoplay) { 161 target.off('mouseover', _delay); 162 } 163 _confirm(); 164 } 165 166 function _confirm() { 167 let widthTotal = 0; 168 box.children().each((i, el) => { 169 const { width } = el.getBoundingClientRect(); 170 widthTotal += width; 171 }); 172 box.css('width', Math.max(widthTotal, window.innerWidth * 1.5) + 'px'); 173 if (widthTotal > target.innerWidth()) { 174 _clone(); 175 if (leftBtn) { 176 leftBtn.on('mouseover', btnEnter); 177 leftBtn.on('mouseout', btnLeave); 178 leftBtn.on('click', () => { 179 _toLeft(() => { 180 _clearDelayTime(); 181 delayTime = setTimeout(_autoplay, interval); 182 }); 183 }); 184 } 185 if (rightBtn) { 186 rightBtn.on('mouseover', btnEnter); 187 rightBtn.on('mouseout', btnLeave); 188 rightBtn.on('click',() => { 189 _toRight(() => { 190 _clearDelayTime(); 191 delayTime = setTimeout(_autoplay, interval); 192 }); 193 }); 194 } 195 if (autoplay) { 196 target.on('mouseover', (e) => { 197 e.stopPropagation(); 198 _animationState(false); 199 }); 200 target.on('mouseout', (e) => { 201 e.stopPropagation(); 202 _animationState(true); 203 }); 204 _clearDelayTime(); 205 delayTime = setTimeout(_autoplay, interval); 206 } 207 } else { 208 if (leftBtn) { 209 leftBtn.on('mouseover', _delay); 210 leftBtn.on('click', _delay); 211 } 212 if (rightBtn) { 213 rightBtn.on('mouseover', _delay); 214 rightBtn.on('click', _delay); 215 } 216 if (autoplay) { 217 target.on('mouseover', _delay); 218 } 219 } 220 } 221 222 _confirm(); 223 } 224 225 return zzscroll; 226})(); 227
228zzscroll("#zzscroll"); 229zzscroll("#zzscroll1"); 230zzscroll("#zzscroll2"); 231zzscroll("#zzscroll3"); 232zzscroll("#zzscroll4"); 233zzscroll("#zzscroll5"); 234zzscroll("#zzscroll6"); 235zzscroll("#zzscroll_cart", { 236 autoplay: false, 237});
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.