/* ags 92 – B2B: oprava odkazov na produkt v CZ a HU (súčasť hladaj8, 1. 11. 2026).
* Problém: /{trh}/buxus/generate_page.php?page_id=N presmeruje každý trh na slovenskú adresu produktu
* a CZ/HU partnera odhlási (zadanie ui42 zadanie-ui42-generate-page-cz-hu-odhlasenie).
* Riešenie: na /cz a /hu sa každý odkaz na produkt cez generate_page prepíše na vyhľadanie kódu v trhu
* (/cz/vysledky-vyhladavania?term=KÓD#agsp=PAGE_ID). Na stránke výsledkov skript nájde kartu s tým page_id
* a hneď otvorí jej adresu (detail v jazyku trhu). Bez JS alebo pri nenájdení ostane partner na výsledkoch – prihlásený.
* SK sa nemení. Servisné stránky (faktúry 257, reklamácie 652491) sa neprepisujú.
* Vypnutie: window.agsOdkazy = { off: true } pred include, alebo návrat na hladaj7. Meranie: ags_odkaz_fix.
*/
(function () {
'use strict';
if (window.__agsOdkazy) return; window.__agsOdkazy = 1;
if (window.agsOdkazy && window.agsOdkazy.off) return;
var mm = location.pathname.match(/^\/(cz|hu)(\/|$)/); if (!mm) return;
var M = mm[1];
var SRCH = M === 'hu' ? '/hu/keresesi-eredmenyek' : '/cz/vysledky-vyhladavania';
var SKIP = { '257': 1, '652491': 1 };
var RE = /\/buxus\/generate_page\.php\?(?:[^#]*&)?page_id=(\d+)/;
function track(o) { try { o.event = 'ags_odkaz_fix'; o.trh = M; (window.dataLayer = window.dataLayer || []).push(o); } catch (e) {} }
function txt(e) { return e ? String(e.textContent || '').replace(/\s+/g, ' ').trim() : ''; }
function attrUp(a, n) { var e = a.closest ? a.closest('[' + n + ']') : null; return e ? e.getAttribute(n) || '' : ''; }
function codeOf(a) {
var c = attrUp(a, 'data-code'); if (c) return c;
var dm = attrUp(a, 'data-m'); if (dm && dm.indexOf(':') > 0) return dm.slice(dm.indexOf(':') + 1);
var card = a.closest ? a.closest('.agn-card, .product-card, .agsbf-card, .cd, .pc, li, tr') : null;
if (card) {
var ac = card.querySelector('.agn-code'); if (ac && txt(ac)) return txt(ac);
var m = txt(card).match(/(?:Kód|Kod|Cikkszám|Termékkód)\s*:?\s*([A-Za-z0-9._\-\/]+)/i); if (m) return m[1];
}
return '';
}
/* page_id → kód z enginu akcií (dlaždice Black Friday nemajú kód v DOM) */
var PMAP = null, PN = 0;
function akReady() { var A = window.__agsAkcie, S = A && A.S; return !!(S && S.ready); }
function codeByPid(pid) {
try {
var S = window.__agsAkcie && window.__agsAkcie.S, bc = S && S.byCode; if (!bc) return '';
var ks = Object.keys(bc);
if (!PMAP || PN !== ks.length) { PMAP = {}; PN = ks.length; ks.forEach(function (k) { var e = bc[k]; if (e && e.pid) PMAP[String(e.pid)] = e.code || k; }); }
return PMAP[String(pid)] || '';
} catch (e) { return ''; }
}
function nameOf(a) {
var t = a.getAttribute('title') || txt(a);
if (!t || t.length < 4) { var card = a.closest ? a.closest('.agn-card, .agsbf-card, .cd, .pc') : null; var n = card && card.querySelector('h3, h4, .nm, .agn-name, .name'); t = txt(n); }
return t.replace(/^[\s−\-–+]*\d+\s*%\s*/, '').slice(0, 80);
}
function safeUrl(pid, term) { return SRCH + '?term=' + encodeURIComponent(term || '') + '#agsp=' + pid; }
window.agsOdkaz = { safeUrl: safeUrl, market: M };
/* 1. stránka výsledkov s #agsp= → otvoriť detail produktu v jazyku trhu */
var hm = location.hash.match(/agsp=(\d+)/);
if (hm) {
var pid = hm[1], done = false, tries = 0;
var find = function () {
if (done) return;
var cards = document.querySelectorAll('.product-card'), hit = null;
for (var i = 0; i < cards.length && !hit; i++) {
var c = cards[i];
if (String(c.getAttribute('data-lazy-product-id')) === pid || new RegExp('product_id=' + pid + '(?!\\d)').test(c.innerHTML)) hit = c;
}
if (hit) {
var a = hit.querySelector('a[href]'), u = a ? a.getAttribute('href') : '';
if (u && !RE.test(u) && u.indexOf('/' + M + '/') >= 0) { done = true; track({ akcia: 'presmer', pid: +pid }); location.replace(u); return; }
}
if (++tries < 40) setTimeout(find, 300); else { done = true; track({ akcia: 'nenajdene', pid: +pid }); } /* výsledky sa načítavajú dodatočne – max 12 s */
};
find();
}
/* 2. prepísať odkazy generate_page na bezpečné vyhľadanie v trhu */
var n = 0, t0 = Date.now(), ob = null, pend = 0, T_START = Date.now();
function fix(a) {
var h = a.getAttribute('href'); if (!h) return false;
var m = h.match(RE); if (!m || SKIP[m[1]]) return false;
var term = codeOf(a) || codeByPid(m[1]);
if (!term && !akReady() && Date.now() - T_START < 8000) return false; /* počkať na engine akcií (kód podľa page_id) */
term = term || nameOf(a); if (!term) return false;
a.setAttribute('href', safeUrl(m[1], term)); a.setAttribute('data-agsp', m[1]);
return true;
}
function scan() {
pend = 0;
if (Date.now() - t0 > 1000) { t0 = Date.now(); n = 0; }
if (++n > 20) { try { ob && ob.disconnect(); } catch (e) {} track({ akcia: 'stop' }); return; }
var k = 0, as = document.querySelectorAll('a[href*="generate_page.php"]');
for (var i = 0; i < as.length; i++) if (fix(as[i])) k++;
if (k) track({ akcia: 'prepis', n: k });
}
/* 3. poistka pri kliku (odkaz vznikol tesne pred klikom) */
function onClick(e) {
var a = e.target && e.target.closest ? e.target.closest('a[href]') : null; if (!a) return;
var m = (a.getAttribute('href') || '').match(RE); if (!m || SKIP[m[1]]) return;
var term = codeOf(a) || codeByPid(m[1]) || nameOf(a); if (!term) return;
e.preventDefault(); e.stopPropagation();
a.setAttribute('href', safeUrl(m[1], term));
track({ akcia: 'klik', pid: +m[1] });
location.href = safeUrl(m[1], term);
}
document.addEventListener('click', onClick, true);
document.addEventListener('auxclick', onClick, true);
var start = function () {
scan(); setTimeout(scan, 1500); setTimeout(scan, 4000); setTimeout(scan, 9000);
try { ob = new MutationObserver(function () { if (!pend) pend = setTimeout(scan, 250); }); ob.observe(document.body, { childList: true, subtree: true }); } catch (e) {}
};
if (document.body) start(); else document.addEventListener('DOMContentLoaded', start);
})();
/* ags 92 – B2B: inteligentné hľadanie (hladaj8.js.txt), verzia 2026-11-01a
* v8 (1. 11.): CZ/HU odkazy na produkt bez generate_page (presmeruje na /sk a partnera odhlási) – vyhľadanie kódu + otvorenie detailu; blok „oprava odkazov“ na začiatku súboru
* odkazy na výsledky hľadania podľa trhu (HU /hu/keresesi-eredmenyek – slovenská adresa na HU odhlási partnera)
* v7 (23. 10.): pridanie do košíka na HU cez /hu/kosar-tartalma (v6 volalo /hu/obsah-kosika = 404, na HU sa nepridalo nič);
* import na HU cez maďarskú adresu (slovenská adresa na HU odhlási partnera)
* v6 (23. 10.): ostrá prevádzka – na HU sa z indexu vyradia značky, ktoré partner nesmie vidieť (window.agsChicco.hide, rovnako ako chicco-hu3);
* texty pre partnerov vo vykaní, bez interných názvov systémov
* v5: v každom výsledku počet kusov (−/číslo/+) a tlačidlo košíka – pridanie bez otvárania produktu; Enter v počte alebo Shift+Enter na vybranom riadku
* v4: prekreslený prázdny stav (naposledy hľadané s vymazaním, dlaždice Novinky / Výpredaj / akcie, kategórie, klikateľné tipy z reálnych kódov)
* Lokálny index produktov (Apps Script „Index B2B“ → IndexedDB raz denne), hľadanie v prehliadači bez volaní na server.
* Kód, názov, EAN, značka, kategória · bez diakritiky · viac slov = všetky · % ako v Money (fus%ruk) ·
* „KÓD ks“ = rýchle pridanie do košíka (existujúci príkaz košíka) · EAN 13 číslic + Enter = 1 ks · viac riadkov = import.
* Zapína sa cez window.agsHladaj = { mode:'preview'|'live'|'off', allow:[firmy], markets:[...], api:'…/exec', fallback:'/buxus/docs/…{m}…' }.
* Núdzové vypnutie: mode:'off'. Enter bez výberu = pôvodné serverové hľadanie (formulár sa nemení).
*/
(function () {
'use strict';
var VER = '2026-11-01a';
var CFG = window.agsHladaj || {};
var MODE = CFG.mode || 'off';
if (MODE === 'off' || window.__agsHladajLoaded) return;
var mm = location.pathname.match(/^\/(sk|cz|hu)(\/|$)/);
if (!mm) return;
var M = mm[1];
if ((CFG.markets || ['sk', 'cz', 'hu']).indexOf(M) < 0) return;
var h3 = document.querySelector('#header .header-basic-info h3');
var firm = h3 ? h3.textContent.trim() : '';
if (MODE === 'preview' && (!firm || (CFG.allow || []).indexOf(firm) < 0)) return;
var input = document.querySelector('#search-text, input[name="term"]');
var form = input ? input.form : null;
if (!input || !form) return;
window.__agsHladajLoaded = VER;
var T = {
sk: { recent: 'Naposledy hľadané', quick: 'Rýchly vstup', tips: 'Tipy: fus%ruk nájde „Fusak s rukavicami“ · PM2607 6 pridá 6 ks do košíka · načítajte EAN skenerom · vložte viac kódov naraz a vznikne import.', nov: 'Novinky', vyp: 'Výpredaj', cats: 'Kategórie', brands: 'Značky', camp: 'Kampaň', res: '{n} výsledkov · {ms} ms', none: 'Nič sa nenašlo v katalógu – skúste hľadať na serveri', loading: 'Načítavam katalóg…', server: 'Hľadať na serveri ↗', serverAll: 'Všetkých {n} na serveri ↗', keys: '↑↓ výber · Enter otvoriť · Esc zavrieť', inStock: 'Skladom', term: 'Termín {d}', sellout: 'Dopredaj · {n} ks', no: 'Neobjednávať', newF: 'Novinka', outlet: 'Outlet', add: 'Pridať {n} ks', addSub: '{code} · do košíka hneď, bez otvárania produktu', addKey: 'Enter = do košíka', added: 'Pridané do košíka: {n} ks', addFail: 'Nepodarilo sa pridať – otvorte produkt', open: 'otvoriť detail produktu', imp: 'Rozpoznaných {n} riadkov · {ok} kódov nájdených · {bad} nenájdených', impSub: 'Skladom {s} · termín {t} · spolu {q} ks. Enter = otvoriť import do košíka (zoznam sa skopíruje).', impKey: 'Enter = import', noPid: 'Kód bez stránky – otvorí sa hľadanie', ean: 'EAN zo skenera = 1 ks do košíka' },
cz: { recent: 'Naposledy hledané', quick: 'Rychlý vstup', tips: 'Tipy: fus%ruk najde „Fusak s rukavicemi“ · PM2607 6 přidá 6 ks do košíku · načtěte EAN skenerem · vložte více kódů najednou a vznikne import.', nov: 'Novinky', vyp: 'Výprodej', cats: 'Kategorie', brands: 'Značky', camp: 'Kampaň', res: '{n} výsledků · {ms} ms', none: 'Nic se nenašlo v katalogu – zkuste hledat na serveru', loading: 'Načítám katalog…', server: 'Hledat na serveru ↗', serverAll: 'Všech {n} na serveru ↗', keys: '↑↓ výběr · Enter otevřít · Esc zavřít', inStock: 'Skladem', term: 'Termín {d}', sellout: 'Doprodej · {n} ks', no: 'Neobjednávat', newF: 'Novinka', outlet: 'Outlet', add: 'Přidat {n} ks', addSub: '{code} · do košíku hned, bez otevírání produktu', addKey: 'Enter = do košíku', added: 'Přidáno do košíku: {n} ks', addFail: 'Nepodařilo se přidat – otevřete produkt', open: 'otevřít detail produktu', imp: 'Rozpoznáno {n} řádků · {ok} kódů nalezeno · {bad} nenalezeno', impSub: 'Skladem {s} · termín {t} · celkem {q} ks. Enter = otevřít import do košíku (seznam se zkopíruje).', impKey: 'Enter = import', noPid: 'Kód bez stránky – otevře se hledání', ean: 'EAN ze skeneru = 1 ks do košíku' },
hu: { recent: 'Legutóbbi keresések', quick: 'Gyors belépés', tips: 'Tippek: bund%keszty megtalálja a „Bundazsák kesztyűvel“ terméket · PM2607 6 6 db-ot a kosárba tesz · EAN vonalkódolvasóval · több kód egyszerre = import.', nov: 'Újdonságok', vyp: 'Kiárusítás', cats: 'Kategóriák', brands: 'Márkák', camp: 'Kampány', res: '{n} találat · {ms} ms', none: 'Nincs találat a katalógusban – keressen a szerveren', loading: 'Katalógus betöltése…', server: 'Keresés a szerveren ↗', serverAll: 'Mind a(z) {n} a szerveren ↗', keys: '↑↓ választás · Enter megnyitás · Esc bezárás', inStock: 'Raktáron', term: 'Várható {d}', sellout: 'Kifutó · {n} db', no: 'Nem rendelhető', newF: 'Újdonság', outlet: 'Outlet', add: '{n} db hozzáadása', addSub: '{code} · azonnal a kosárba, a termék megnyitása nélkül', addKey: 'Enter = kosárba', added: 'Kosárba téve: {n} db', addFail: 'Nem sikerült – nyissa meg a terméket', open: 'termék megnyitása', imp: '{n} sor felismerve · {ok} kód megtalálva · {bad} nem található', impSub: 'Raktáron {s} · várható {t} · összesen {q} db. Enter = import a kosárba (a lista a vágólapra kerül).', impKey: 'Enter = import', noPid: 'Kód oldal nélkül – keresés nyílik meg', ean: 'EAN olvasóval = 1 db a kosárba' }
}[M];
var T2 = {
sk: { clear: 'Vymazať', novS: 'nové modely za 60 dní', vypS: 'dopredaj skladu', akS: 'akcia do {d}', akL: 'akcia – posledný deň', cats: 'Kategórie', tipsT: 'Hľadajte rýchlejšie', ex1: 'fus%ruk', t1: 'stačia časti slov', t2: 'kód + počet = rovno do košíka', t3: 'viac kódov naraz = import', t4: 'čítačka EAN = 1 ks do košíka', kod: 'KÓD', addT: 'Pridať do košíka', addOk: 'Pridané {n} ks', minus: 'menej', plus: 'viac', keyAdd: 'Shift+Enter do košíka' },
cz: { clear: 'Smazat', novS: 'nové modely za 60 dní', vypS: 'doprodej skladu', akS: 'akce do {d}', akL: 'akce – poslední den', cats: 'Kategorie', tipsT: 'Hledejte rychleji', ex1: 'fus%ruk', t1: 'stačí části slov', t2: 'kód + počet = rovnou do košíku', t3: 'více kódů najednou = import', t4: 'čtečka EAN = 1 ks do košíku', kod: 'KÓD', addT: 'Přidat do košíku', addOk: 'Přidáno {n} ks', minus: 'méně', plus: 'více', keyAdd: 'Shift+Enter do košíku' },
hu: { clear: 'Törlés', novS: 'új modellek az elmúlt 60 napban', vypS: 'készletkiárusítás', akS: 'akció {d}-ig', akL: 'akció – utolsó nap', cats: 'Kategóriák', tipsT: 'Keressen gyorsabban', ex1: 'bund%keszty', t1: 'elég a szórészlet', t2: 'cikkszám + darab = egyből a kosárba', t3: 'több cikkszám egyszerre = import', t4: 'EAN-olvasó = 1 db a kosárba', kod: 'CIKKSZÁM', addT: 'Kosárba', addOk: '{n} db kosárba téve', minus: 'kevesebb', plus: 'több', keyAdd: 'Shift+Enter kosárba' }
}[M];
var SVG = {
nov: '',
vyp: '',
ak: '',
clock: '',
cart: '',
check: '',
bolt: ''
};
var base = '/' + M;
var SRCH = (function () { try { var i = document.querySelector('form input[name="term"]'); var a = i && i.form && i.form.getAttribute('action'); if (a) return a.replace(/^https?:\/\/[^\/]+/, ''); } catch (e) {} return base + '/' + ({ hu: 'keresesi-eredmenyek' }[M] || 'vysledky-vyhladavania'); })();
var CART = base + '/' + ({ hu: 'kosar-tartalma' }[M] || 'obsah-kosika');
var IMPORT = base + '/' + ({ hu: 'fiokom/a-termekek-importalasa-a-kosarba' }[M] || 'moj-ucet/import-produktov-do-kosika');
var API = CFG.api || '';
var FALLBACK = (CFG.fallback || '').replace('{m}', M);
var TTL = (CFG.ttlHours || 24) * 3600 * 1000;
var MAX = CFG.max || 8;
function q(s, r) { return (r || document).querySelector(s); }
function qa(s, r) { return Array.prototype.slice.call((r || document).querySelectorAll(s)); }
function el(tag, cls, html) { var e = document.createElement(tag); if (cls) e.className = cls; if (html != null) e.innerHTML = html; return e; }
function esc(s) { return String(s == null ? '' : s).replace(/[&<>"]/g, function (c) { return { '&': '&', '<': '<', '>': '>', '"': '"' }[c]; }); }
function track(ev, d) { try { window.dataLayer = window.dataLayer || []; d = d || {}; d.event = ev; d.market = M; d.mode = MODE; window.dataLayer.push(d); } catch (e) {} }
var DIA = { 'ł': 'l', 'đ': 'd', 'ø': 'o', 'ß': 'ss', 'æ': 'ae', 'œ': 'oe' };
function norm(s) {
s = String(s || '').toLowerCase();
try { s = s.normalize('NFD').replace(/[\u0300-\u036f]/g, ''); } catch (e) {}
return s.replace(/[łđøßæœ]/g, function (c) { return DIA[c] || c; }).replace(/[\u00a0\s]+/g, ' ').trim();
}
function fmtDate(iso) { if (!iso) return ''; var p = iso.split('-'); return M === 'hu' ? (p[1] * 1) + '. ' + (p[2] * 1) + '.' : (p[2] * 1) + '. ' + (p[1] * 1) + '.'; }
function productUrl(r) { if (r.pid && M !== 'sk') return SRCH + '?term=' + encodeURIComponent(r.code) + '#agsp=' + r.pid; /* v8: CZ/HU generate_page odhlási partnera */ return r.pid ? base + '/buxus/generate_page.php?page_id=' + r.pid : SRCH + '?term=' + encodeURIComponent(r.code); }
function thumbUrl(r) { return (r.img && r.img !== '-') ? 'https://drive.google.com/thumbnail?id=' + encodeURIComponent(r.img) + '&sz=w96' : ''; }
function stock(r) {
if (r.qty > 0) return r.status === 'X' ? { c: 'x', t: T.sellout.replace('{n}', r.qty) } : { c: 'ok', t: T.inStock };
if (r.status !== 'X' && r.term) return { c: 't', t: T.term.replace('{d}', fmtDate(r.term)) };
return { c: 'n', t: T.no };
}
function stockRank(r) { var s = stock(r).c; return s === 'ok' ? 3 : s === 't' ? 2 : s === 'x' ? 1 : 0; }
/* ---------- CSS ---------- */
var css = ''
+ '.agq-wrap{position:relative}'
+ '.agq{position:absolute;left:0;top:calc(100% + 4px);width:820px;max-width:calc(100vw - 32px);background:#fff;color:#17202b;border-radius:12px;box-shadow:0 18px 50px rgba(15,42,74,.25);z-index:60;display:none;grid-template-columns:1fr 230px;overflow:hidden;font-family:"Figtree","Helvetica Neue",Helvetica,Arial,sans-serif;font-size:13px;line-height:1.3;text-align:left}'
+ '.agq.open{display:grid}.agq.one{grid-template-columns:1fr}'
+ '.agq *{box-sizing:border-box}.agq a{color:inherit;text-decoration:none}'
+ '.agq-res{padding:8px;min-width:0}'
+ '.agq-row{display:grid;grid-template-columns:48px 1fr auto;gap:12px;align-items:center;padding:7px 8px;border-radius:8px;cursor:pointer}'
+ '.agq-row.sel,.agq-row:hover{background:#eef3fa}.agq-row.sel{outline:2px solid #2364b8;outline-offset:-2px}'
+ '.agq-th{width:48px;height:48px;border-radius:8px;background:#f0f3f6;display:flex;align-items:center;justify-content:center;font-size:11px;color:#9aa5b3;font-weight:700;overflow:hidden}.agq-th img{width:48px;height:48px;object-fit:contain;display:block;background:#fff}'
+ '.agq-n{font-size:13.5px;line-height:1.3;color:#17202b}.agq-n mark{background:#fff2a8;color:inherit;border-radius:3px;padding:0 1px}'
+ '.agq-m{font-size:11.5px;color:#6b7684;margin-top:2px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.agq-m b{color:#17202b;font-weight:600}'
+ '.agq-st{font-size:11px;font-weight:700;border-radius:999px;padding:3px 9px;white-space:nowrap}.agq-st.ok{background:#e4f5ea;color:#1d8a4e}.agq-st.t{background:#fff4dd;color:#9a6300}.agq-st.x{background:#fde8e6;color:#c8322b}.agq-st.n{background:#e9eef4;color:#6b7684}'
+ '.agq-fl{display:inline-block;font-size:10px;font-weight:700;letter-spacing:.05em;text-transform:uppercase;background:#1fb6a6;color:#fff;border-radius:999px;padding:1px 6px;margin-left:6px;vertical-align:middle}.agq-fl.o{background:#c8322b}'
+ '.agq-side{background:#f7f9fc;border-left:1px solid #e3e8ee;padding:12px;font-size:12.5px;display:flex;flex-direction:column;gap:12px;min-width:0}'
+ '.agq-side h6,.agq-empty h6{margin:0 0 5px;font-size:10.5px;letter-spacing:.08em;text-transform:uppercase;color:#6b7684;font-weight:700}'
+ '.agq-side a{display:block;color:#2364b8;font-weight:600;padding:3px 0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.agq-side a span{color:#9aa5b3;font-weight:500}.agq-side a:hover{text-decoration:underline}'
+ '.agq-foot{grid-column:1/-1;display:flex;gap:16px;align-items:center;padding:8px 14px;border-top:1px solid #e3e8ee;font-size:11.5px;color:#6b7684;background:#fff;flex-wrap:wrap}.agq-foot kbd{border:1px solid #cfd8e3;border-radius:4px;padding:0 5px;font-family:inherit;font-size:10.5px;background:#f7f9fc;color:#4b5663;margin-right:2px}.agq-foot .agq-srv{margin-left:auto;color:#2364b8;font-weight:600;cursor:pointer}.agq-foot .agq-srv:hover{text-decoration:underline}'
+ '.agq-act{display:flex;align-items:center;gap:12px;padding:10px 12px;border-radius:10px;background:#0f2a4a;color:#fff;margin:4px 8px 8px;cursor:pointer}.agq-act.sel{outline:2px solid #3b82f6}.agq-act b{font-size:14px;display:block}.agq-act span{font-size:12px;opacity:.85}.agq-act .agq-btn{margin-left:auto;background:#fff;color:#0f2a4a;padding:7px 12px;font-size:12.5px;font-weight:700;border-radius:8px;white-space:nowrap}.agq-act .agq-th{background:#fff;color:#6b7684;flex:none}'
+ '.agq-empty{padding:14px 16px 12px;grid-column:1/-1;display:flex;flex-direction:column;gap:14px}.agq-empty h6{margin:0 0 7px}'
+ '.agq-hrow{display:flex;justify-content:space-between;align-items:baseline}.agq-hrow a{font-size:11.5px;color:#9aa5b3;cursor:pointer}.agq-hrow a:hover{color:#c8322b}'
+ '.agq-rec{display:flex;flex-wrap:wrap;gap:6px}.agq-rec a{display:inline-flex;align-items:center;gap:6px;background:#f2f5f9;border-radius:999px;padding:5px 12px 5px 9px;font-size:12.5px;color:#243242;font-weight:500;cursor:pointer}.agq-rec a:hover{background:#e3ecf7;color:#2364b8}.agq-rec svg{width:13px;height:13px;color:#9aa5b3}'
+ '.agq-tiles{display:grid;grid-template-columns:repeat(auto-fit,minmax(200px,1fr));gap:8px}'
+ '.agq-tile{display:flex;gap:11px;align-items:center;padding:10px 12px;border:1px solid #e3e8ee;border-radius:12px;background:#fff;min-width:0;cursor:pointer;transition:border-color .12s,box-shadow .12s}.agq-tile:hover{border-color:#2364b8;box-shadow:0 6px 18px rgba(15,42,74,.10)}'
+ '.agq-ic{width:36px;height:36px;border-radius:10px;display:flex;align-items:center;justify-content:center;flex:none;font-weight:800;font-size:11.5px;letter-spacing:-.02em}.agq-ic svg{width:19px;height:19px}'
+ '.agq-tile>span:last-child{min-width:0}.agq-tile b{display:block;font-size:13.5px;font-weight:700;color:#17202b;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.agq-tile b em{font-style:normal;background:#1fb6a6;color:#fff;border-radius:999px;padding:1px 7px;font-size:11px;font-weight:700;margin-left:6px;vertical-align:1px}'
+ '.agq-tile small{display:block;font-size:11.5px;color:#6b7684;margin-top:1px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}'
+ '.agq-cats{display:grid;grid-template-columns:repeat(3,1fr);gap:2px 10px}.agq-cats a{display:flex;justify-content:space-between;align-items:center;gap:8px;padding:6px 9px;border-radius:8px;font-size:13px;color:#243242;min-width:0}.agq-cats a span{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.agq-cats a:after{content:"\u203a";color:#b5c0cc;font-size:16px;line-height:1}.agq-cats a:hover{background:#eef3fa;color:#2364b8}.agq-cats a:hover:after{color:#2364b8}'
+ '.agq-tipbox{background:#f5f8fc;border:1px solid #e8eef5;border-radius:12px;padding:10px 12px;display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:7px 18px}'
+ '.agq-tt{grid-column:1/-1;display:flex;align-items:center;gap:6px;font-size:10.5px;letter-spacing:.08em;text-transform:uppercase;color:#6b7684;font-weight:700}.agq-tt svg{width:13px;height:13px;color:#f0a531}'
+ '.agq-tipbox a,.agq-tipbox span.agq-tp{display:flex;align-items:center;gap:8px;font-size:12.5px;color:#4b5663;min-width:0}.agq-tipbox a{cursor:pointer}.agq-tipbox a:hover{color:#2364b8}.agq-tipbox a:hover code{border-color:#2364b8}'
+ '.agq-tipbox code{background:#fff;border:1px solid #dbe1e8;border-radius:6px;padding:1px 7px;color:#0f2a4a;font-weight:700;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:11.5px;white-space:nowrap;flex:none}'
+ '.agq-chips{display:flex;flex-wrap:wrap;gap:6px}.agq-chips a{border:1px solid #dbe1e8;border-radius:999px;padding:4px 11px;font-size:12.5px;color:#2364b8;font-weight:500;background:#fff;cursor:pointer}.agq-chips a:hover{border-color:#2364b8}'
+ '.agq-tip{font-size:12px;color:#6b7684;margin-top:12px;line-height:1.5}.agq-tip code{background:#f0f3f6;border-radius:4px;padding:0 5px;color:#17202b}'
+ '.agq-msg{padding:14px 16px;color:#6b7684;grid-column:1/-1}.agq-msg.ok{color:#1d8a4e;font-weight:600}.agq-msg.bad{color:#c8322b}'
+ '.agq-r{display:flex;flex-direction:column;align-items:flex-end;gap:6px}.agq-buy{display:flex;align-items:center;gap:3px;cursor:default}'
+ '.agq-q{width:24px;height:28px;border:1px solid #dbe1e8;background:#fff;border-radius:7px;font-size:16px;line-height:1;color:#243242;cursor:pointer;padding:0;font-family:inherit}.agq-q:hover{border-color:#2364b8;color:#2364b8}'
+ '.agq-qi{width:46px;height:28px;border:1px solid #dbe1e8;border-radius:7px;text-align:center;font:inherit;font-size:13px;font-weight:700;color:#17202b;-moz-appearance:textfield;padding:0;background:#fff}.agq-qi::-webkit-inner-spin-button,.agq-qi::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}.agq-qi:focus{outline:2px solid #2364b8;outline-offset:-1px;border-color:#2364b8}'
+ '.agq-add{height:28px;min-width:38px;padding:0 9px;margin-left:3px;border:0;border-radius:7px;background:#0f2a4a;color:#fff;cursor:pointer;display:inline-flex;align-items:center;justify-content:center;gap:5px;font:inherit;font-size:12px;font-weight:700;transition:background .12s}.agq-add svg{width:16px;height:16px}.agq-add:hover{background:#1457a8}.agq-add.ok{background:#1d8a4e}.agq-add.bad{background:#c8322b}.agq-add[disabled]{opacity:.65;cursor:wait}'
+ '.agq-row.agq-done{background:#effaf3}.agq-okt{font-size:11px;font-weight:700;color:#1d8a4e;white-space:nowrap}'
+ '.agq-hint:empty{display:none}.agq-hint{position:absolute;right:84px;top:50%;transform:translateY(-50%);font-size:11px;color:#9aa5b3;background:#f3f6fa;border-radius:6px;padding:2px 7px;pointer-events:none;white-space:nowrap}'
+ '@media (max-width:991px){.agq-cats{grid-template-columns:repeat(2,1fr)}.agq-tipbox{grid-template-columns:1fr}.agq{grid-template-columns:1fr;width:calc(100vw - 32px)}.agq-side{display:none}.agq-hint{display:none}}';
var st = el('style'); st.id = 'agq-css'; st.textContent = css; document.head.appendChild(st);
/* ---------- index: IndexedDB cache + stiahnutie ---------- */
var IDX = null, loading = null, rows = [];
function idb() {
return new Promise(function (res, rej) {
try { var r = indexedDB.open('ags-hladaj', 1); r.onupgradeneeded = function () { r.result.createObjectStore('idx'); }; r.onsuccess = function () { res(r.result); }; r.onerror = function () { rej(r.error); }; } catch (e) { rej(e); }
});
}
function idbGet(k) { return idb().then(function (db) { return new Promise(function (res) { var t = db.transaction('idx').objectStore('idx').get(k); t.onsuccess = function () { res(t.result); }; t.onerror = function () { res(null); }; }); }).catch(function () { return null; }); }
function idbSet(k, v) { return idb().then(function (db) { return new Promise(function (res) { var t = db.transaction('idx', 'readwrite'); t.objectStore('idx').put(v, k); t.oncomplete = function () { res(true); }; t.onerror = function () { res(false); }; }); }).catch(function () { return false; }); }
function fetchT(url, ms) {
var ctl = ('AbortController' in window) ? new AbortController() : null;
var timer = ctl ? setTimeout(function () { ctl.abort(); }, ms) : null;
return fetch(url, { signal: ctl ? ctl.signal : undefined, credentials: 'omit', cache: 'no-store' }).then(function (r) { if (timer) clearTimeout(timer); if (!r.ok) throw new Error('HTTP ' + r.status); return r.json(); });
}
function prepare(data) {
var f = data.f || ['code', 'name', 'ean', 'brand', 'cat', 'status', 'qty', 'term', 'flags', 'pid', 'img'];
var ix = {}; f.forEach(function (n, i) { ix[n] = i; });
rows = (data.r || []).map(function (a) {
var r = { code: a[ix.code], name: a[ix.name], ean: a[ix.ean], brand: a[ix.brand], cat: a[ix.cat], status: a[ix.status], qty: a[ix.qty] | 0, term: a[ix.term], flags: a[ix.flags] | 0, pid: a[ix.pid] | 0, img: a[ix.img] };
r.nc = norm(r.code); r.nn = norm(r.name); r.ne = String(r.ean || ''); r.nb = norm(r.brand); r.nk = norm(r.cat); r.nw = ' ' + r.nn + ' ';
return r;
});
try {
var CH = window.agsChicco;
if (M === 'hu' && CH && CH.on) {
var hb = (CH.hide || CH.brands || []).map(function (b) { return String(b).toUpperCase().replace(/[^A-Z0-9 &]/g, ''); }).filter(Boolean);
if (hb.length) {
var hre = new RegExp('^\\s*(\\d+\\s*x\\s*)?(' + hb.join('|') + ')\\b', 'i');
rows = rows.filter(function (r) { return hb.indexOf(String(r.brand || '').toUpperCase().replace(/[^A-Z0-9 &]/g, '')) < 0 && !hre.test(r.name || ''); });
}
}
} catch (e) {}
IDX = { t: data.t, n: rows.length, v: data.v };
byCode = {}; byEan = {};
rows.forEach(function (r) { byCode[r.nc] = r; if (r.ne && r.ne.length >= 8) byEan[r.ne] = r; });
window.agsHladajInfo = { ver: VER, market: M, mode: MODE, index: IDX };
}
var byCode = {}, byEan = {};
function load(force) {
if (IDX && !force) return Promise.resolve(IDX);
if (loading) return loading;
loading = idbGet('idx-' + M).then(function (c) {
var fresh = c && c.saved && (Date.now() - c.saved) < TTL && c.data && c.data.r;
if (fresh) { prepare(c.data); return IDX; }
var p = API ? fetchT(API + (API.indexOf('?') > -1 ? '&' : '?') + 'm=' + M, 8000) : Promise.reject(new Error('no api'));
return p.catch(function (e1) {
if (FALLBACK) return fetchT(FALLBACK, 8000);
throw e1;
}).then(function (data) {
if (!data || !data.r || data.r.length < 100) throw new Error('bad index');
prepare(data); idbSet('idx-' + M, { saved: Date.now(), data: data });
track('ags_hs_index', { n: rows.length, src: 'net' });
return IDX;
}).catch(function (e) {
if (c && c.data && c.data.r) { prepare(c.data); track('ags_hs_index', { n: rows.length, src: 'stale' }); return IDX; }
throw e;
});
}).then(function (r) { loading = null; return r; }, function (e) { loading = null; throw e; });
return loading;
}
// načítanie v pozadí po načítaní stránky (v nečinnosti), aby bol prvý klik okamžitý
function idle(fn) { if ('requestIdleCallback' in window) requestIdleCallback(fn, { timeout: 4000 }); else setTimeout(fn, 2500); }
if (document.readyState === 'complete') idle(function () { load().catch(function () {}); });
else window.addEventListener('load', function () { idle(function () { load().catch(function () {}); }); });
/* ---------- UI ---------- */
var box = input.parentNode;
var wrap = input.closest ? (input.closest('.agh-search') || input.closest('form')) : form;
// ak má obal hľadania overflow:hidden (zaoblený box v hlavičke), panel ide o úroveň vyššie a umiestni sa výpočtom
var host = wrap;
try { if (getComputedStyle(wrap).overflow !== 'visible' && wrap.parentNode && wrap.parentNode !== document.body) { host = wrap.parentNode; if (getComputedStyle(host).position === 'static') host.style.position = 'relative'; } } catch (e) {}
// v3: počítadlo výsledkov (hint) sa umiestňuje v boxe hľadania – box musí ostať positioned, inak hint skočí na košík
try { if (getComputedStyle(wrap).position === 'static') wrap.style.position = 'relative'; } catch (e) {}
host.classList.add('agq-wrap');
var panel = el('div', 'agq'); panel.setAttribute('role', 'listbox'); host.appendChild(panel);
function place() { if (host === wrap) return; var a = wrap.getBoundingClientRect(), b = host.getBoundingClientRect(); panel.style.left = Math.round(a.left - b.left) + 'px'; panel.style.top = Math.round(a.bottom - b.top + 4) + 'px'; }
var hint = el('span', 'agq-hint'); if (input.closest && input.closest('.agh-search')) { wrap.appendChild(hint); } else { hint = null; }
var state = { open: false, items: [], sel: -1, mode: 'empty', q: '' };
function setHint(t) { if (hint) hint.textContent = t || ''; }
function recent() { try { return JSON.parse(localStorage.getItem('ags_hs_recent') || '[]'); } catch (e) { return []; } }
function remember(qv) { try { qv = String(qv || '').trim(); if (!qv || qv.length > 40) return; var r = recent().filter(function (x) { return x !== qv; }); r.unshift(qv); localStorage.setItem('ags_hs_recent', JSON.stringify(r.slice(0, 8))); } catch (e) {} }
function openPanel() { if (!state.open) { state.open = true; place(); panel.classList.add('open'); track('ags_hs_open'); } }
window.addEventListener('resize', function () { if (state.open) place(); });
function closePanel() { state.open = false; panel.classList.remove('open'); state.sel = -1; setHint(''); }
function fmtDay(d) { return M === 'hu' ? (d.getMonth() + 1) + '. ' + d.getDate() + '.' : d.getDate() + '. ' + (d.getMonth() + 1) + '.'; }
// príklady do tipov z reálneho katalógu (skladom, so stránkou) – aby klik naozaj niečo našiel
function examples() {
var ok = rows.filter(function (r) { return r.qty > 0 && r.pid && r.code && !/\s/.test(r.code); });
var pm = ok.filter(function (r) { return /PETITE/i.test(r.brand || ''); });
var a = (pm[0] || ok[0]), b = (pm[1] || ok[1]);
return { one: a ? a.code : '', two: a && b ? a.code + ' 2, ' + b.code + ' 1' : '' };
}
function renderEmpty() {
state.mode = 'empty'; state.items = []; state.sel = -1;
panel.classList.add('one');
var r = recent(), now = new Date();
var html = '
' + esc(T2.ex1) + '' + esc(T2.t1) + ''
+ (ex.one ? '' + esc(ex.one) + ' 6' + esc(T2.t2) + '' : '' + esc(T2.kod) + ' 6' + esc(T2.t2) + '')
+ (ex.two ? '' + esc(ex.one) + ' 2, …' + esc(T2.t3) + '' : '' + esc(T2.kod) + ' 2, …' + esc(T2.t3) + '')
+ 'EAN' + esc(T2.t4) + '