/* ========================================================= LGT Campaign Bar (BALK 3) โ€” v2 (STICKY FIXED) Loaded as So this file MUST be valid JavaScript (even if extension is .html). Behaviour: - Height 30px, mobile-only - Inserted AFTER black USP bar (.lgt-uspbar-top) - Sticky logic: * If USP clone (.lgt-uspbar-clone) is visible (opacity > 0.02) -> show fixed bar under it * Else if scrollY >= 49 -> show fixed bar under white header * Else -> show flow bar in-page - Close: hides for 30 minutes (sessionStorage) - If no active campaign -> bar does not exist (display none + css var 0) ========================================================= */ (function(){ "use strict"; var MQ = window.matchMedia && window.matchMedia("(max-width: 768px)"); function isMobile(){ return MQ ? MQ.matches : (window.innerWidth <= 768); } // Some themes scroll inside a container (overflow:auto) instead of window. // We detect the real scroller so sticky logic works everywhere. var scroller = null; var scrollIsWindow = true; function pickScroller(){ var candidates = [ document.querySelector("main#maincontent"), document.querySelector("main.page-main"), document.querySelector(".page-wrapper"), document.scrollingElement || document.documentElement ].filter(Boolean); for (var i=0;i el.clientHeight + 2); if (canScroll && tall){ scroller = el; scrollIsWindow = false; return; } } scroller = window; scrollIsWindow = true; } function getScrollTop(){ if (scrollIsWindow) return window.pageYOffset || 0; return scroller ? (scroller.scrollTop || 0) : 0; } var CLOSE_KEY_UNTIL = "lgt_campaignbar_closed_until"; var CLOSE_MS = 30 * 60 * 1000; // --------- Campaign data (edit here) ---------- // All CTAs go to /cadeautips as requested // textHtml can contain emoji + simple inline SVG. var campaigns = [ // TEST (today -> 1 June 2026) { id: "test", start: "2026-02-27T00:00:00+01:00", end: "2026-06-01T23:59:59+02:00", bg: "#ffd1dc", fg: "#333", textHtml: '๐Ÿงช Testbalk (' + (new Date()).toLocaleDateString("nl-NL") + '): ' + 'naar cadeautips' }, // VALENTIJN (yearly) { id:"valentijn-2026", start:"2026-01-25T00:00:00+01:00", end:"2026-02-14T23:59:59+01:00", bg:"#ffd1dc", fg:"#333", textHtml:'โค๏ธ Valentijnsactie โ€” cadeautips' }, { id:"valentijn-2027", start:"2027-01-25T00:00:00+01:00", end:"2027-02-14T23:59:59+01:00", bg:"#ffd1dc", fg:"#333", textHtml:'โค๏ธ Valentijnsactie โ€” cadeautips' }, { id:"valentijn-2028", start:"2028-01-25T00:00:00+01:00", end:"2028-02-14T23:59:59+01:00", bg:"#ffd1dc", fg:"#333", textHtml:'โค๏ธ Valentijnsactie โ€” cadeautips' }, // MOEDERDAG (NL: 2e zondag mei) โ€” show 3 weeks before through that day { id:"moederdag-2026", start:"2026-04-19T00:00:00+02:00", end:"2026-05-10T23:59:59+02:00", bg:"#ffe6f2", fg:"#333", textHtml:'๐ŸŒท Moederdag cadeautips โ€” shop nu' }, { id:"moederdag-2027", start:"2027-04-18T00:00:00+02:00", end:"2027-05-09T23:59:59+02:00", bg:"#ffe6f2", fg:"#333", textHtml:'๐ŸŒท Moederdag cadeautips โ€” shop nu' }, { id:"moederdag-2028", start:"2028-04-23T00:00:00+02:00", end:"2028-05-14T23:59:59+02:00", bg:"#ffe6f2", fg:"#333", textHtml:'๐ŸŒท Moederdag cadeautips โ€” shop nu' }, // VADERDAG (NL: 3e zondag juni) โ€” show 3 weeks before through that day { id:"vaderdag-2026", start:"2026-05-24T00:00:00+02:00", end:"2026-06-21T23:59:59+02:00", bg:"#d9ecff", fg:"#0b2545", textHtml:'๐Ÿ‘” Vaderdag cadeautips โ€” shop nu' }, { id:"vaderdag-2027", start:"2027-05-30T00:00:00+02:00", end:"2027-06-20T23:59:59+02:00", bg:"#d9ecff", fg:"#0b2545", textHtml:'๐Ÿ‘” Vaderdag cadeautips โ€” shop nu' }, { id:"vaderdag-2028", start:"2028-05-28T00:00:00+02:00", end:"2028-06-18T23:59:59+02:00", bg:"#d9ecff", fg:"#0b2545", textHtml:'๐Ÿ‘” Vaderdag cadeautips โ€” shop nu' }, // BLACK FRIDAY (show 10 days up to BF, plus weekend through Cyber Monday) { id:"bf-2026", start:"2026-11-16T00:00:00+01:00", end:"2026-11-30T23:59:59+01:00", bg:"#111", fg:"#fff", textHtml:'๐Ÿ”ฅ Black Friday deals โ€” bekijk acties' }, { id:"bf-2027", start:"2027-11-15T00:00:00+01:00", end:"2027-11-29T23:59:59+01:00", bg:"#111", fg:"#fff", textHtml:'๐Ÿ”ฅ Black Friday deals โ€” bekijk acties' }, { id:"bf-2028", start:"2028-11-13T00:00:00+01:00", end:"2028-11-27T23:59:59+01:00", bg:"#111", fg:"#fff", textHtml:'๐Ÿ”ฅ Black Friday deals โ€” bekijk acties' }, // SINTERKLAAS (but do NOT show during BF windows) { id:"sint-2026", start:"2026-11-12T00:00:00+01:00", end:"2026-12-05T23:59:59+01:00", bg:"#ffefc7", fg:"#5a2a00", textHtml:'๐ŸŽ Sinterklaas cadeautips โ€” bekijk tips' }, { id:"sint-2027", start:"2027-11-10T00:00:00+01:00", end:"2027-12-05T23:59:59+01:00", bg:"#ffefc7", fg:"#5a2a00", textHtml:'๐ŸŽ Sinterklaas cadeautips โ€” bekijk tips' }, { id:"sint-2028", start:"2028-11-10T00:00:00+01:00", end:"2028-12-05T23:59:59+01:00", bg:"#ffefc7", fg:"#5a2a00", textHtml:'๐ŸŽ Sinterklaas cadeautips โ€” bekijk tips' }, // KERST (starts Dec 6, ends Dec 31) { id:"kerst-2026", start:"2026-12-06T00:00:00+01:00", end:"2026-12-31T23:59:59+01:00", bg:"#0f3d2e", fg:"#fff", textHtml:'๐ŸŽ„ Kerst cadeautips โ€” shop kerst' }, { id:"kerst-2027", start:"2027-12-06T00:00:00+01:00", end:"2027-12-31T23:59:59+01:00", bg:"#0f3d2e", fg:"#fff", textHtml:'๐ŸŽ„ Kerst cadeautips โ€” shop kerst' }, { id:"kerst-2028", start:"2028-12-06T00:00:00+01:00", end:"2028-12-31T23:59:59+01:00", bg:"#0f3d2e", fg:"#fff", textHtml:'๐ŸŽ„ Kerst cadeautips โ€” shop kerst' }, // HAPPY NEW YEAR (Jan 1 - Jan 7) { id:"hny-2027", start:"2027-01-01T00:00:00+01:00", end:"2027-01-07T23:59:59+01:00", bg:"#e6f3ff", fg:"#0b2545", textHtml:'โœจ Happy New Year โ€” cadeautips' }, { id:"hny-2028", start:"2028-01-01T00:00:00+01:00", end:"2028-01-07T23:59:59+01:00", bg:"#e6f3ff", fg:"#0b2545", textHtml:'โœจ Happy New Year โ€” cadeautips' }, { id:"hny-2029", start:"2029-01-01T00:00:00+01:00", end:"2029-01-07T23:59:59+01:00", bg:"#e6f3ff", fg:"#0b2545", textHtml:'โœจ Happy New Year โ€” cadeautips' } ]; // Black Friday windows used to suppress Sinterklaas var bfWindows = [ ["2026-11-16T00:00:00+01:00","2026-11-30T23:59:59+01:00"], ["2027-11-15T00:00:00+01:00","2027-11-29T23:59:59+01:00"], ["2028-11-13T00:00:00+01:00","2028-11-27T23:59:59+01:00"] ]; // --------- helpers ---------- function nowMs(){ return Date.now(); } function setCssVarHeight(px){ try{ document.documentElement.style.setProperty("--lgt-campaignbar-h", px + "px"); }catch(e){} } function getClosedUntil(){ try{ var v = sessionStorage.getItem(CLOSE_KEY_UNTIL); return v ? parseInt(v,10) : 0; }catch(e){ return 0; } } function isClosed(){ var until = getClosedUntil(); return until && nowMs() < until; } function closeFor30Min(){ try{ sessionStorage.setItem(CLOSE_KEY_UNTIL, String(nowMs() + CLOSE_MS)); }catch(e){} } function inWindow(startIso, endIso){ var t = nowMs(); var s = new Date(startIso).getTime(); var e = new Date(endIso).getTime(); return (t >= s && t <= e); } function isInBlackFridayWindow(){ for (var i=0;i 0 ? h : 56; } function getUspStickyOffset(){ // If the black sticky clone is visible, campaign bar must sit UNDER it. var uspClone = document.querySelector(".lgt-uspbar-clone"); if (!uspClone) return 0; var cs = window.getComputedStyle(uspClone); var op = parseFloat(cs.opacity || "0") || 0; if (op > 0.02) return 49; return 0; } function uspCloneVisible(){ var uspClone = document.querySelector(".lgt-uspbar-clone"); if (!uspClone) return false; var cs = getComputedStyle(uspClone); var op = parseFloat(cs.opacity || "0") || 0; return op > 0.02; } function buildBar(id){ var el = document.createElement("div"); el.id = id; el.innerHTML = '' + '
'; return el; } var flowBar = null; var fixedBar = null; var active = null; var raf = 0; function ensureBars(){ ensureStyle(); if (!flowBar) flowBar = document.getElementById("header-specialday-bar") || buildBar("header-specialday-bar"); if (!fixedBar) { fixedBar = document.getElementById("header-specialday-bar-fixed") || buildBar("header-specialday-bar-fixed"); if (!fixedBar.isConnected) document.body.appendChild(fixedBar); } } function applyCampaign(c){ ensureBars(); if (!c){ active = null; setCssVarHeight(0); flowBar.style.display = "none"; fixedBar.style.display = "none"; return; } active = c; setCssVarHeight(30); flowBar.style.background = c.bg || "#ffd1dc"; flowBar.style.color = c.fg || "#333"; fixedBar.style.background = c.bg || "#ffd1dc"; fixedBar.style.color = c.fg || "#333"; flowBar.querySelector(".lgt-specialday-text").innerHTML = c.textHtml || ""; fixedBar.querySelector(".lgt-specialday-text").innerHTML = c.textHtml || ""; // insert flowBar after usp top if possible var uspTop = document.querySelector(".lgt-uspbar-top"); if (uspTop && uspTop.parentNode){ uspTop.insertAdjacentElement("afterend", flowBar); } else { var header = document.querySelector("header.page-header") || document.querySelector(".page-header") || document.querySelector("header"); if (header) header.insertAdjacentElement("afterend", flowBar); } // reset display states; updatePosition() decides fixed/flow flowBar.style.display = "flex"; fixedBar.style.display = "none"; if (isClosed()){ flowBar.classList.add("is-hidden"); fixedBar.classList.add("is-hidden"); } else { flowBar.classList.remove("is-hidden"); fixedBar.classList.remove("is-hidden"); } } function updatePosition(){ if (!active) return; if (!isMobile()){ fixedBar.style.display = "none"; return; } if (isClosed()){ flowBar.classList.add("is-hidden"); fixedBar.classList.add("is-hidden"); } else { flowBar.classList.remove("is-hidden"); fixedBar.classList.remove("is-hidden"); } var y = getScrollTop(); var headerH = getHeaderH(); if (uspCloneVisible()){ fixedBar.style.top = "calc(" + headerH + "px + 49px)"; fixedBar.style.display = "flex"; flowBar.classList.add("is-hidden"); // no layout shift return; } if (y >= 49){ fixedBar.style.top = (headerH + getUspStickyOffset()) + "px"; fixedBar.style.display = "flex"; flowBar.classList.add("is-hidden"); return; } fixedBar.style.display = "none"; flowBar.classList.remove("is-hidden"); } function onScroll(){ if (raf) return; raf = requestAnimationFrame(function(){ raf = 0; updatePosition(); }); } function bindClose(){ document.addEventListener("click", function(e){ var btn = e.target.closest && e.target.closest("#header-specialday-bar .lgt-specialday-close, #header-specialday-bar-fixed .lgt-specialday-close"); if (!btn) return; e.preventDefault(); e.stopPropagation(); closeFor30Min(); if (flowBar) flowBar.classList.add("is-hidden"); if (fixedBar) fixedBar.classList.add("is-hidden"); // if user stays on page, auto-restore after 30m setTimeout(function(){ if (!isClosed()) updatePosition(); }, CLOSE_MS + 50); }, true); } function boot(){ pickScroller(); // Desktop: show the flow bar (no fixed/sticky needed) if (!isMobile()){ ensureBars(); bindClose(); activeCampaignInit(); return; } ensureBars(); bindClose(); // Wait a bit for USP bar injection script to run (it creates .lgt-uspbar-top) var stopAt = Date.now() + 4000; (function waitForUsp(){ var uspTop = document.querySelector(".lgt-uspbar-top"); if (uspTop || Date.now() > stopAt){ activeCampaignInit(); return; } setTimeout(waitForUsp, 60); })(); } function activeCampaignInit(){ var c = pickActiveCampaign(); applyCampaign(c); updatePosition(); if (scrollIsWindow) if (scrollIsWindow) window.addEventListener("scroll", onScroll, {passive:true}); else if (scroller) scroller.addEventListener("scroll", onScroll, {passive:true}); else if (scroller) scroller.addEventListener("scroll", onScroll, {passive:true}); window.addEventListener("resize", onScroll, {passive:true}); } if (document.readyState === "loading") document.addEventListener("DOMContentLoaded", boot); else boot(); } )();