1// Member Products Homepage Slider 2document.querySelectorAll('[data-shop-carousel]').forEach((carousel) => { 3 const track = carousel.querySelector('[data-shop-track]'); 4 const controls = carousel.querySelector('[data-shop-controls]'); 5 const previousButton = carousel.querySelector('[data-shop-prev]'); 6 const nextButton = carousel.querySelector('[data-shop-next]'); 7 8 if (!track || !controls || !previousButton || !nextButton) { 9 return; 10 } 11 12 const prefersReducedMotion = window.matchMedia('(prefers-reduced-motion: reduce)').matches; 13 const scrollStep = () => { 14 const card = track.querySelector('.hpv3-product-card'); 15 const gap = parseFloat(window.getComputedStyle(track).columnGap) || 0; 16 17 return card ? card.getBoundingClientRect().width + gap : track.clientWidth; 18 }; 19 const updateControls = () => { 20 const maxScrollLeft = track.scrollWidth - track.clientWidth; 21 22 controls.hidden = maxScrollLeft <= 1; 23 previousButton.disabled = track.scrollLeft <= 1; 24 nextButton.disabled = track.scrollLeft >= maxScrollLeft - 1; 25 }; 26 27 previousButton.addEventListener('click', () => { 28 track.scrollBy({left: -scrollStep(), behavior: prefersReducedMotion ? 'auto' : 'smooth'}); 29 }); 30 nextButton.addEventListener('click', () => { 31 track.scrollBy({left: scrollStep(), behavior: prefersReducedMotion ? 'auto' : 'smooth'}); 32 }); 33 track.addEventListener('scroll', updateControls, {passive: true}); 34 window.addEventListener('resize', updateControls); 35 updateControls(); 36});
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.