1// hires-lightbox.js â пÑоÑмоÑÑÑик Ñ Ð°Ð¹Ñезов и галеÑей Ð´Ð»Ñ Ð¿ÑбликаÑий 3dnews (PhotoSwipe v5, Ð»ÐµÐ½Ð¸Ð²Ð°Ñ Ð·Ð°Ð³ÑÑзка). 2// ÐÑогÑеÑÑивное ÑлÑÑÑение: без модÑÐ»Ñ / пÑи Ñбое v5 â <a href> оÑкÑÑÐ²Ð°ÐµÑ Ð¸ÑÑ Ð¾Ð´Ð½Ð¸Ðº как ÑанÑÑе. 3// ÐалеÑеи (.adaptive-gallery, ÑоÑÐ¼Ð°Ñ get_hgallery_new): data-size Ñже в ÑазмеÑке â пÑелоад не нÑжен. 4// ÐегаÑи-ÑоÑмаÑÑ .gallery-am-block (montage) и .gallery-box (2013) ÐРпеÑÐµÑ Ð²Ð°ÑÑваем â Ñам Ñвои вÑÑеÑÑ. 5(function () { 6 var IMG_RE = /\.(jpe?g|png|gif|webp|avif)(\?|#|$)/i; 7 var BASE = '/assets/js/photoswipe5/'; 8 var BODY_SEL = '.entry-body, [itemprop="articleBody"]'; 9 var pswPromise = null, cssPromise = null, busy = false; 10 11 function ensureCss() { // гÑÑзим css и ÑезолвимÑÑ Ð¿Ð¾ его onload 12 if (cssPromise) return cssPromise; 13 var st = document.createElement('style'); // ТÐ: одиноÑнÑе без кнопок â зÑм ÑкÑÑÑ; Ñ Ð³Ð°Ð»ÐµÑей (ÑеÑение DesT 2026-08-27) зÑм/капÑен/ÑÑÑÑÑик оÑÑаÑÑÑÑ 14 st.textContent = 15 '.pswp.pswp--hires .pswp__button--zoom{display:none}' + 16 '.pswp.pswp--hires.pswp--gal .pswp__button--zoom{display:block}' + 17 '.pswp__gal-caption{position:absolute;left:0;right:0;bottom:0;padding:12px 20px;color:#fff;font-size:15px;line-height:1.35;text-align:center;text-shadow:0 1px 2px #000;pointer-events:none}'; 18 document.head.appendChild(st); 19 cssPromise = new Promise(function (res) { 20 var l = document.createElement('link'); l.rel = 'stylesheet'; l.href = BASE + 'photoswipe.css'; 21 l.onload = l.onerror = function () { res(); }; // не блокиÑÑем даже еÑли css не долеÑел 22 document.head.appendChild(l); 23 }); 24 return cssPromise; 25 } 26 function loadPsw() { 27 if (!pswPromise) pswPromise = import(BASE + 'photoswipe.esm.min.js').then(function (m) { return m.default; }) 28 ['catch'](function (e) { pswPromise = null; throw e; }); // не кеÑиÑÑем пÑовал импоÑÑа â ÑÑанзиенÑнÑй Ñбой не ÑÐ±Ð¸Ð²Ð°ÐµÑ Ð»Ð°Ð¹ÑÐ±Ð¾ÐºÑ Ð½Ð° ÑеÑÑÐ¸Ñ 29 return pswPromise; 30 } 31 // fallbackHref: еÑли v5/css не загÑÑзÑÑÑÑ Ð¸Ð»Ð¸ init ÐºÐ¸Ð½ÐµÑ â ÑÑ Ð¾Ð´Ð¸Ð¼ на иÑÑ Ð¾Ð´Ð½Ð¸Ðº (не мÑÑÑвÑй клик) 32 function openSingle(item, fallbackHref) { 33 Promise.all([ ensureCss(), loadPsw() ]).then(function (r) { // ÐÐÐÐ CSS до init â инаÑе пеÑвÑй показ без ÑÑилей: каÑÑинки вÑваливаÑÑÑÑ Ð² поÑок ÑÑаÑÑи 34 new r[1]({ 35 dataSource: [item], index: 0, mainClass: 'pswp--hires', 36 bgOpacity: 0.9, showHideAnimationType: 'fade', clickToCloseNonZoomable: true 37 }).init(); 38 busy = false; 39 })['catch'](function () { busy = false; if (fallbackHref) window.location.href = fallbackHref; }); 40 } 41 // ÐалеÑеÑ: items = [{src,width,height,msrc,title}], ÑÑÑелки/зÑм из коÑобки, капÑен и ÑÑÑÑÑик â Ñвои ÑлеменÑÑ 42 function openGallery(items, index, fallbackHref) { 43 Promise.all([ ensureCss(), loadPsw() ]).then(function (r) { 44 var PhotoSwipe = r[1]; 45 var pswp = new PhotoSwipe({ 46 dataSource: items, index: index, mainClass: 'pswp--hires pswp--gal', 47 bgOpacity: 0.9, showHideAnimationType: 'fade', clickToCloseNonZoomable: true 48 }); 49 var captionEl = null; // ÑÑÑÑÑик â ÐСТРÐÐÐÐЫРv5 (.pswp__counter), Ñвой ÐРдобавлÑÑÑ (2026-08-27: двоилоÑÑ) 50 function updateMeta() { 51 if (captionEl) { 52 var t = items[pswp.currIndex] && items[pswp.currIndex].title || ''; 53 captionEl.textContent = t; 54 captionEl.style.display = t ? '' : 'none'; 55 } 56 } 57 pswp.on('uiRegister', function () { 58 pswp.ui.registerElement({ 59 name: 'gal-caption', className: 'pswp__gal-caption', appendTo: 'root', 60 onInit: function (el) { captionEl = el; updateMeta(); } 61 }); 62 }); 63 pswp.on('change', updateMeta); 64 pswp.init(); 65 busy = false;
66 })['catch'](function () { busy = false; if (fallbackHref) window.location.href = fallbackHref; }); 67 } 68 function preloadOpen(src, msrc, fallbackHref) { 69 document.body.style.cursor = 'progress'; 70 var full = new Image(); 71 full.onload = function () { document.body.style.cursor = ''; openSingle({ src: src, width: full.naturalWidth, height: full.naturalHeight, msrc: msrc }, fallbackHref); }; 72 full.onerror = function () { document.body.style.cursor = ''; busy = false; if (fallbackHref) window.location.href = fallbackHref; }; 73 full.src = src; 74 } 75 // СобÑаÑÑ items галеÑеи из ÑазмеÑки: вÑе <a data-size> (вклÑÑÐ°Ñ ÑкÑÑÑÑе пÑевÑÑ n>3) 76 function galleryItems(gal) { 77 var anchors = gal.querySelectorAll('a[data-size]'), items = []; 78 for (var i = 0; i < anchors.length; i++) { 79 var a = anchors[i], m = /(\d+)\s*x\s*(\d+)/i.exec(a.getAttribute('data-size') || ''); 80 if (!m) continue; 81 var img = a.querySelector('img'), fig = a.querySelector('figure'); 82 items.push({ 83 src: a.href, width: +m[1], height: +m[2], 84 msrc: img ? (img.currentSrc || img.src) : undefined, 85 title: fig ? fig.textContent.replace(/^\s+|\s+$/g, '') : '' 86 }); 87 } 88 return items; 89 } 90 function onClick(e) { 91 if (busy) return; 92 var t = e.target; 93 if (!t || !t.closest) return; 94 if (!t.closest(BODY_SEL)) return; // ÑолÑко Ñело пÑбликаÑии (3dnews/download .entry-body, servernews .pubtext[itemprop=articleBody]) 95 if (t.closest('.gallery-am-block, .gallery-box')) return; // легаÑи-ÑоÑмаÑÑ: Ñвои вÑÑеÑÑ, не пеÑÐµÑ Ð²Ð°ÑÑваем 96 97 // --- галеÑÐµÑ ÑоÑмаÑа A --- 98 var gal = t.closest('.adaptive-gallery'); 99 if (gal) { 100 var items = galleryItems(gal); 101 if (!items.length) return; 102 var index = 0, fallback = items[0].src; 103 if (!t.closest('.openGallery')) { // "СмоÑÑеÑÑ Ð²Ñе изобÑажениÑ" â вÑегда Ñ Ð¿ÐµÑвого 104 var a = t.closest('a[data-size]'); 105 if (a) { 106 var anchors = gal.querySelectorAll('a[data-size]'); 107 for (var i = 0; i < anchors.length; i++) if (anchors[i] === a) { index = i; break; } 108 fallback = a.href; 109 } 110 } 111 e.preventDefault(); busy = true; openGallery(items, index, fallback); return; 112 } 113 114 // --- одиноÑÐ½Ð°Ñ ÐºÐ°ÑÑинка --- 115 var img = t.closest('img'); 116 if (!img) return; 117 var msrc = img.currentSrc || img.src; 118 var a = img.closest('a'); 119 if (a) { 120 var href = a.getAttribute('href') || ''; 121 if (!IMG_RE.test(href)) return; // ÑÑÑлка не на каÑÑÐ¸Ð½ÐºÑ â не меÑаем навигаÑии 122 e.preventDefault(); busy = true; preloadOpen(a.href, msrc, a.href); return; 123 } 124 e.preventDefault(); busy = true; // Ð³Ð¾Ð»Ð°Ñ <img> 125 if (img.complete && img.naturalWidth) openSingle({ src: img.src, width: img.naturalWidth, height: img.naturalHeight, msrc: msrc }, null); 126 else preloadOpen(img.src, msrc, null); 127 } 128 // document-level делегиÑование: покÑÑÐ²Ð°ÐµÑ AJAX-подгÑÑÐ·ÐºÑ (uncut/infinity) без пеÑепÑивÑзки 129 document.addEventListener('click', onClick); 130})();
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.