1/* 2 * PRS Video Spots â lightbox + lazy player init. 3 */ 4(function () { 5 'use strict'; 6 7 function buildPlayer(host) { 8 if (host.dataset.prsBuilt === '1') { return; } 9 var type = host.dataset.type; 10 var src = host.dataset.src; 11 var attrs = host.dataset.attrs || ''; 12 if (!src) { return; } 13 14 var el; 15 if (type === 'iframe') { 16 el = document.createElement('iframe'); 17 // append autoplay=1 if not present, since the user clicked 18 var sep = src.indexOf('?') === -1 ? '?' : '&'; 19 if (!/[?&]autoplay=1/.test(src)) { 20 src = src.replace(/([?&])autoplay=0/, '$1autoplay=1'); 21 if (!/[?&]autoplay=/.test(src)) { src += sep + 'autoplay=1'; } 22 } 23 el.src = src; 24 el.setAttribute('frameborder', '0'); 25 el.setAttribute('allow', 'accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture'); 26 el.setAttribute('allowfullscreen', 'allowfullscreen'); 27 } else { 28 el = document.createElement('video'); 29 el.src = src; 30 el.setAttribute('autoplay', 'autoplay'); 31 el.setAttribute('playsinline', 'playsinline'); 32 el.setAttribute('preload', 'auto'); 33 if (/\bmuted\b/.test(attrs)) { el.setAttribute('muted', 'muted'); } 34 if (/\bloop\b/.test(attrs)) { el.setAttribute('loop', 'loop'); } 35 var posterMatch = attrs.match(/poster="([^"]+)"/); 36 if (posterMatch) { el.setAttribute('poster', posterMatch[1]); } 37 } 38 host.innerHTML = ''; 39 host.appendChild(el); 40 host.dataset.prsBuilt = '1'; 41 } 42 43 function tearDown(modal) { 44 var host = modal.querySelector('.prs-vs-modal__player'); 45 if (host) { 46 host.innerHTML = ''; 47 host.dataset.prsBuilt = '0'; 48 } 49 } 50 51 function openModal(id) { 52 var modal = document.getElementById(id); 53 if (!modal) { return; } 54 var host = modal.querySelector('.prs-vs-modal__player'); 55 if (host) { buildPlayer(host); } 56 modal.classList.add('is-open'); 57 modal.setAttribute('aria-hidden', 'false'); 58 document.body.classList.add('prs-vs-modal-open'); 59 } 60 61 function closeModal(modal) { 62 modal.classList.remove('is-open'); 63 modal.setAttribute('aria-hidden', 'true'); 64 document.body.classList.remove('prs-vs-modal-open'); 65 tearDown(modal); 66 } 67 68 document.addEventListener('click', function (e) { 69 var opener = e.target.closest('.js-prs-vs-open'); 70 if (opener) { 71 e.preventDefault(); 72 openModal(opener.dataset.prsVsTarget); 73 return; 74 } 75 var closer = e.target.closest('.js-prs-vs-close'); 76 if (closer) { 77 e.preventDefault(); 78 var modal = closer.closest('.prs-vs-modal'); 79 if (modal) { closeModal(modal); } 80 } 81 }); 82 83 document.addEventListener('keydown', function (e) { 84 if (e.key === 'Escape') { 85 var open = document.querySelector('.prs-vs-modal.is-open'); 86 if (open) { closeModal(open); } 87 } 88 }); 89 90 /* Move "tab" position videos above the recommended-products block, 91 because PRS051 renders displayFooterProduct AFTER accessories. */ 92 function reorderTabSpots() { 93 var tabs = document.querySelectorAll('.prs-vs-wrapper.prs-vs-ctx-product_tab'); 94 if (!tabs.length) { return false; } 95 var anchor = document.querySelector('.product-accessories-block') 96 || document.querySelector('.product-video-section'); 97 if (!anchor || !anchor.parentNode) { return false; } 98 var moved = false;
99 tabs.forEach(function (node) { 100 if (node === anchor || anchor.contains(node)) { return; } 101 if (node.nextElementSibling === anchor && node.parentNode === anchor.parentNode) { return; } 102 anchor.parentNode.insertBefore(node, anchor); 103 moved = true; 104 }); 105 return moved; 106 } 107 function initReorder() { 108 reorderTabSpots(); 109 var tries = 0; 110 var iv = setInterval(function () { 111 tries++; 112 reorderTabSpots(); 113 if (tries >= 10) { clearInterval(iv); } 114 }, 300); 115 if (typeof MutationObserver !== 'undefined') { 116 var mo = new MutationObserver(function () { reorderTabSpots(); }); 117 mo.observe(document.body, { childList: true, subtree: true }); 118 setTimeout(function () { mo.disconnect(); }, 6000); 119 } 120 } 121 function stripVideoControls() { 122 document.querySelectorAll('.prs-vs video').forEach(function (video) { 123 video.removeAttribute('controls'); 124 video.controls = false; 125 }); 126 } 127 128 if (document.readyState === 'loading') { 129 document.addEventListener('DOMContentLoaded', function () { 130 stripVideoControls(); 131 initReorder(); 132 }); 133 } else { 134 stripVideoControls(); 135 initReorder(); 136 } 137 /* Inject "between products" videos into the category product grid. */ 138 function injectBetweenSpots() { 139 var spots = document.querySelectorAll('.prs-vs-wrapper.prs-vs-ctx-category_between .prs-vs--between'); 140 if (!spots.length) { return; } 141 var list = document.querySelector('#js-product-list .products') 142 || document.querySelector('.products.product_list') 143 || document.querySelector('#js-product-list'); 144 if (!list) { return; } 145 var items = list.querySelectorAll(':scope > .product, :scope > li, :scope > .js-product, :scope > article'); 146 if (!items.length) { 147 items = list.querySelectorAll('.product-miniature, .js-product-miniature, article.product-miniature'); 148 } 149 if (!items.length) { return; } 150 spots.forEach(function (spot) { 151 var after = parseInt(spot.getAttribute('data-between-after') || '4', 10); 152 if (!after || after < 1) { after = 4; } 153 var idx = Math.min(after, items.length) - 1; 154 var anchor = items[idx]; 155 if (!anchor || !anchor.parentNode) { return; } 156 // Wrap to occupy a full row in the grid 157 var wrap = document.createElement('div'); 158 wrap.className = 'prs-vs-between-row'; 159 wrap.appendChild(spot); 160 if (anchor.nextSibling) { 161 anchor.parentNode.insertBefore(wrap, anchor.nextSibling); 162 } else { 163 anchor.parentNode.appendChild(wrap); 164 } 165 }); 166 } 167 if (document.readyState === 'loading') { 168 document.addEventListener('DOMContentLoaded', injectBetweenSpots); 169 } else { 170 injectBetweenSpots(); 171 } 172 // Re-run after AJAX product list updates (PrestaShop "updateProductList" event) 173 if (typeof window.prestashop !== 'undefined' && window.prestashop.on) { 174 window.prestashop.on('updateProductList', function () { setTimeout(injectBetweenSpots, 50); }); 175 } 176})();
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.