{
  "version": 3,
  "sources": ["/cdn/shop/t/3/assets/js-vision.js?cbx=1791111608956"],
  "sourcesContent": ["/* ==========================================================================\n   Vision Attire \u2014 shared behaviour\n   No framework. Everything here is either progressive enhancement or a\n   feature the audit identified as revenue-critical.\n   ========================================================================== */\n(() => {\n  'use strict';\n\n  const $  = (s, c = document) => c.querySelector(s);\n  const $$ = (s, c = document) => [...c.querySelectorAll(s)];\n  const DAY = 86400000;\n\n  /* --- analytics ----------------------------------------------------------\n     vaTrack() is defined in the page head by build.py and only sends on the\n     client's own domain. settle() waits until someone stops typing, so a hip\n     measurement or a show date isn't sent a keystroke at a time.\n     ---------------------------------------------------------------------- */\n  const vaSend = (n, p) => { if (window.vaTrack) window.vaTrack(n, p || {}); };\n  const settled = {};\n  const settle = (n, p) => {\n    const key = JSON.stringify(p), last = settled[n] || {};\n    clearTimeout(last.t);\n    settled[n] = { key: last.key, t: setTimeout(() => {\n      if (settled[n].key === key) return;\n      settled[n].key = key; vaSend(n, p);\n    }, 1200) };\n  };\n  document.addEventListener('click', e => {\n    const a = e.target.closest('a[href]');\n    if (!a) return;\n    const href = a.getAttribute('href');\n    const where = a.closest('.nav') ? 'nav' : a.closest('.drawer') ? 'menu' : a.closest('.foot') ? 'footer' : 'page';\n    if (href.startsWith('mailto:')) vaSend('contact_click', { method: 'email', location: where });\n    else if (href.startsWith('tel:')) vaSend('contact_click', { method: 'phone', location: where });\n    else if (/^(\\/pages\\/)?custom(\\.html|$|[?#])/.test(href)) vaSend('cta_click', { cta: 'build_custom', location: where });\n    else if (/^(product-[a-z-]+\\.html|\\/collections\\/[a-z-]+$|\\/collections\\/[a-z-]+#)/.test(href) && where === 'page' && !a.closest('[data-product]'))\n      vaSend('select_item', { item_list_name: location.pathname.replace(/^\\/|\\.html$/g, '') || 'index',\n        items: [{ item_id: href.split('#')[1] || href.replace('.html', ''), item_name: a.textContent.trim().replace(/\\s+/g, ' ').slice(0, 80) }] });\n  });\n\n  /* --- mobile drawer ---------------------------------------------------- */\n  const burger = $('.burger');\n  const drawer = $('#drawer');\n  const nav = $('.nav');\n  if (nav) new ResizeObserver(() => document.documentElement.style.setProperty('--site-nav-h', nav.offsetHeight + 'px')).observe(nav);\n  const helpMenu = $('.nav__group');\n  if (helpMenu) {\n    document.addEventListener('click', e => {if (!helpMenu.contains(e.target)) helpMenu.open = false;});\n    document.addEventListener('keydown', e => {if (e.key === 'Escape' && helpMenu.open) {helpMenu.open = false; $('summary', helpMenu).focus();}});\n    helpMenu.addEventListener('focusout', () => requestAnimationFrame(() => {if (!helpMenu.contains(document.activeElement)) helpMenu.open = false;}));\n  }\n  if (burger && drawer) {\n    burger.addEventListener('click', () => {\n      const open = burger.getAttribute('aria-expanded') === 'true';\n      burger.setAttribute('aria-expanded', String(!open));\n      drawer.toggleAttribute('data-open', !open);\n      if (!open) {\n        document.documentElement.style.setProperty('--site-nav-bottom', nav.getBoundingClientRect().bottom + 'px');\n        drawer.scrollTop = 0;\n        $('a', drawer).focus({preventScroll:true});\n      } else burger.focus();\n      document.body.style.overflow = open ? '' : 'hidden';\n    });\n    drawer.addEventListener('click', e => {\n      if (e.target.tagName === 'A') burger.click();\n    });\n    addEventListener('keydown', e => {\n      if (e.key === 'Escape' && burger.getAttribute('aria-expanded') === 'true') burger.click();\n      if (e.key === 'Tab' && burger.getAttribute('aria-expanded') === 'true') {\n        const links = $$('a', drawer), first = links[0], last = links[links.length - 1];\n        if (e.shiftKey && (document.activeElement === first || document.activeElement === burger)) {e.preventDefault();last.focus();}\n        else if (!e.shiftKey && document.activeElement === last) {e.preventDefault();burger.focus();}\n        else if (!e.shiftKey && document.activeElement === burger) {e.preventDefault();first.focus();}\n      }\n    });\n    matchMedia('(min-width:1060px)').addEventListener('change', e => {if(e.matches && burger.getAttribute('aria-expanded')==='true')burger.click();});\n  }\n\n  /* --- reveal on scroll ------------------------------------------------- */\n  const reveals = $$('[data-reveal]');\n  if (reveals.length && !matchMedia('(prefers-reduced-motion: reduce)').matches) {\n    const io = new IntersectionObserver((entries) => {\n      entries.forEach(en => {\n        if (!en.isIntersecting) return;\n        const d = en.target.dataset.revealDelay || 0;\n        setTimeout(() => en.target.classList.add('is-in'), +d);\n        io.unobserve(en.target);\n      });\n    }, { rootMargin: '0px 0px -8% 0px', threshold: 0.05 });\n    reveals.forEach(el => io.observe(el));\n  } else {\n    reveals.forEach(el => el.classList.add('is-in'));\n  }\n\n  /* --- accent switcher --------------------------------------------------\n     Andy asked whether to add a colour to the black/white/grey and said the\n     red was too harsh. Rather than answer in an email, the options are live\n     against the real product. Choice persists across pages.\n     ---------------------------------------------------------------------- */\n  const bar = $('#accbar');\n  if (bar) {\n    const KEY = 'va-accent-2';  // bumped 5 Oct 2026 so saved bronze picks don't hide the new teal\n    const HIDE = 'va-accent-hidden';\n    const set = (v) => {\n      document.documentElement.dataset.accent = v;\n      try { localStorage.setItem(KEY, v); } catch {}\n      $$('button[data-acc]', bar).forEach(b =>\n        b.setAttribute('aria-pressed', String(b.dataset.acc === v)));\n    };\n    // A ?accent= in the URL wins over the saved choice, so a single link can\n    // open the site in one specific colour. Used for the bronze/blue decision.\n    const VALID = ['teal','bronze','deepblue','electric','oxblood','orange','red','none'];\n    let saved = 'teal';\n    try { saved = localStorage.getItem(KEY) || 'teal'; } catch {}\n    const fromUrl = new URLSearchParams(location.search).get('accent');\n    if (fromUrl && VALID.includes(fromUrl)) saved = fromUrl;\n    set(saved);\n    let hidden = false;\n    try { hidden = localStorage.getItem(HIDE) === '1'; } catch {}\n    if (!hidden) bar.hidden = false;\n    $$('button[data-acc]', bar).forEach(b =>\n      b.addEventListener('click', () => set(b.dataset.acc)));\n    $('[data-close]', bar).addEventListener('click', () => {\n      bar.hidden = true;\n      try { localStorage.setItem(HIDE, '1'); } catch {}\n    });\n  }\n\n  /* --- data ------------------------------------------------------------- */\n  let SITE = null;\n  const siteReady = fetch(VA_DATA('assets/data/site.json'))\n    .then(r => r.json()).then(VA_FIX)\n    .then(d => (SITE = d))\n    .catch(() => null);\n\n  /* --- business-day helpers --------------------------------------------- */\n  const addBusinessDays = (from, n) => {\n    const d = new Date(from);\n    let left = n;\n    while (left > 0) {\n      d.setDate(d.getDate() + 1);\n      if (d.getDay() !== 0 && d.getDay() !== 6) left--;\n    }\n    return d;\n  };\n  const fmt = (d) => d.toLocaleDateString('en-AU', { weekday: 'short', day: 'numeric', month: 'short', year: 'numeric' });\n  const startOfDay = (d) => { const x = new Date(d); x.setHours(0, 0, 0, 0); return x; };\n\n  /* --- delivery calculator ----------------------------------------------\n     The single highest-value thing in the build. Three of the sixteen DMs\n     Andy sent were a competitor asking whether shorts land before their show.\n     Answers with an estimate and a stated buffer \u2014 never a guaranteed date.\n     ---------------------------------------------------------------------- */\n  async function initCalc(form) {\n    await siteReady;\n    if (!SITE) return;\n    const T = SITE.turnaround, S = SITE.shipping;\n    const out = $('[data-calc-out]', form) || $(form.dataset.calcOut);\n    if (!out) return;\n\n    // Every region select is filled from site.json rather than its own markup,\n    // so adding a country is a data edit in one place instead of five pages.\n    const sel = $('[name=region]', form);\n    if (sel && !sel.dataset.filled) {\n      const au = [...sel.options].filter(o => o.value.startsWith('AU-'));\n      sel.innerHTML = '';\n      au.forEach(o => sel.add(o));\n      S.international.regions.forEach(r => sel.add(new Option(r.name, r.name)));\n      sel.dataset.filled = '1';\n    }\n\n    const regionDays = (region) => {\n      if (region === 'AU-standard') return [S.standardDaysMin, S.standardDaysMax];\n      if (region === 'AU-express')  return [S.expressDaysMin, S.expressDaysMax];\n      const r = S.international.regions.find(x => x.name === region);\n      return r ? [r.daysMin, r.daysMax] : [S.standardDaysMin, S.standardDaysMax];\n    };\n\n    function run() {\n      const showVal = $('[name=showDate]', form).value;\n      const type    = $('[name=orderType]', form).value;\n      const region  = $('[name=region]', form).value;\n      if (!showVal) { out.hidden = true; return; }\n\n      const today = startOfDay(new Date());\n      const show  = startOfDay(new Date(showVal + 'T00:00:00'));\n      const daysAvailable = Math.round((show - today) / DAY);\n\n      if (daysAvailable < 0) {\n        out.hidden = false;\n        out.dataset.verdict = 'no';\n        out.innerHTML = `<div class=\"calc__verdict\">That date has already passed</div>\n          <p class=\"small muted\">Pick your show date and we'll work back from it.</p>`;\n        return;\n      }\n\n      const [shipMin, shipMax] = regionDays(region);\n      let leadMin, leadMax, leadLabel, readyFrom;\n\n      if (type === 'instock') {\n        leadMin = T.inStockDispatchDaysMin;\n        leadMax = T.inStockDispatchDaysMax;\n        leadLabel = `Dispatched in ${leadMin}\u2013${leadMax} business days`;\n        readyFrom = 'the day you order';\n      } else if (type === 'rush') {\n        leadMin = T.mockupTurnaroundDays + T.rushWeeksMin * 7;\n        leadMax = T.mockupTurnaroundDays + 3 + T.rushWeeksMax * 7;\n        leadLabel = `Mockup in ~${T.mockupTurnaroundDays} business days, then ${T.rushWeeksMin}\u2013${T.rushWeeksMax} weeks from your approval`;\n        readyFrom = 'mockup approval';\n      } else {\n        leadMin = T.mockupTurnaroundDays + T.customWeeksMin * 7;\n        leadMax = T.mockupTurnaroundDays + 3 + T.customWeeksMax * 7;\n        leadLabel = `Mockup in ~${T.mockupTurnaroundDays} business days, then ${T.customWeeksMin}\u2013${T.customWeeksMax} weeks from your approval`;\n        readyFrom = 'mockup approval';\n      }\n\n      const totalMax = leadMax + shipMax;\n      // Buffer scales with the job. A week of contingency is right on a six-week\n      // custom build and absurd on a two-day dispatch \u2014 a flat week would tell\n      // someone ten days out that an in-stock order is risky, which it isn't.\n      const buffer   = Math.min(T.bufferDays, Math.max(3, Math.ceil(totalMax * 0.25)));\n      const required = totalMax + buffer;\n      const arriveMin = addBusinessDays(today, leadMin + shipMin);\n      const arriveMax = addBusinessDays(today, leadMax + shipMax);\n\n      let verdict, head, note;\n      if (type !== 'instock' && daysAvailable < T.cutoffWeeks * 7 && type === 'custom') {\n        verdict = 'no';\n        head = \"Too close for a standard custom order\";\n        note = `Our cut-off for custom is ${T.cutoffWeeks} weeks out, and your show is ${daysAvailable} days away. `\n             + `A rush order may still work, or take a look at what's in stock \u2014 that ships in ${T.inStockDispatchDaysMin}\u2013${T.inStockDispatchDaysMax} business days.`;\n      } else if (daysAvailable >= required) {\n        verdict = 'yes';\n        head = 'Yes \u2014 that works';\n        note = `You've got ${daysAvailable} days. We estimate ${totalMax} days end to end, which leaves about ${daysAvailable - totalMax} days spare.`;\n      } else if (daysAvailable >= totalMax) {\n        verdict = 'tight';\n        head = \"It should make it, but it's tight\";\n        note = `You've got ${daysAvailable} days and we estimate ${totalMax}. That's inside our estimate but there's no room if anything slips. `\n             + `Call us before you order and we'll tell you honestly.`;\n      } else {\n        verdict = 'no';\n        head = \"Not in time, going by our estimates\";\n        note = `You've got ${daysAvailable} days and we estimate ${totalMax}. We'd rather say so now than take the order. `\n             + (type === 'custom' ? 'Try a rush order, or something in stock.' : 'Have a look at what we hold in stock.');\n      }\n\n      out.hidden = false;\n      out.dataset.verdict = verdict;\n      settle('delivery_check', { order_type: type, verdict, days_to_show: daysAvailable });\n      out.innerHTML = `\n        <div class=\"calc__verdict\">${head}</div>\n        <p class=\"small\" style=\"color:var(--ink-2)\">${note}</p>\n        <div class=\"calc__rows\">\n          <div><span>Estimated arrival</span><b>${fmt(arriveMin)} \u2013 ${fmt(arriveMax)}</b></div>\n          <div><span>Your show</span><b>${fmt(show)}</b></div>\n          <div><span>Production</span><b>${leadLabel}</b></div>\n          <div><span>Shipping</span><b>${shipMin}\u2013${shipMax} business days</b></div>\n        </div>\n        <p class=\"hint mt-1\">These are estimates with a ${buffer}-day buffer built in, counted from ${readyFrom}. They are not guaranteed arrival dates.</p>`;\n    }\n\n    $$('input, select', form).forEach(el => el.addEventListener('change', run));\n    $$('input[type=date]', form).forEach(el => el.addEventListener('input', run));\n    form.addEventListener('submit', e => { e.preventDefault(); run(); });\n\n    // Can't order for a show in the past.\n    const dateEl = $('[name=showDate]', form);\n    if (dateEl && !dateEl.min) dateEl.min = new Date().toISOString().slice(0, 10);\n    run();\n  }\n  $$('[data-calc]').forEach(initCalc);\n  // The custom builder injects its own calculator after this has already run,\n  // so it needs a way back in. Without this the show-date check inside the\n  // builder never binds \u2014 three of the sixteen DMs were that exact question.\n  window.__vaInitCalc = (el) => { if (el) initCalc(el); };\n\n  /* --- size finder -------------------------------------------------------\n     Andy's division advice was trapped in the DMs. Three of the sixteen were\n     a first-timer asking what size they are.\n     ---------------------------------------------------------------------- */\n  async function initSizer(form) {\n    await siteReady;\n    if (!SITE) return;\n    const Z = SITE.sizing;\n    const out = $('[data-size-out]', form);\n    if (!out) return;\n\n    function run() {\n      const raw  = parseFloat($('[name=hip]', form).value);\n      const unit = ($('[name=unit]:checked', form) || {}).value || 'in';\n      const div  = $('[name=division]', form).value;\n      const isTrunk = !!(Z.trunkChart && Z.trunkChart.ranges[div]);\n      const lbl = $('[data-measure-lbl]', form);\n      if (lbl) lbl.textContent = isTrunk ? 'Measurement around your waist' : 'Measurement around your hips';\n      if (!raw || raw <= 0) { out.hidden = true; $$('tbody tr', document).forEach(r => r.classList.remove('is-match')); return; }\n\n      const inches = unit === 'cm' ? raw / 2.54 : raw;\n      $$('tbody tr', document).forEach(r => r.classList.remove('is-match'));\n      if (isTrunk) return trunks(raw, unit, inches, div);\n      let band = Z.hipToSize.find(b => inches >= b.min && inches < b.max);\n      let straddles = false;\n      if (!band) {\n        band = inches < Z.hipToSize[0].min ? Z.hipToSize[0] : Z.hipToSize[Z.hipToSize.length - 1];\n      } else {\n        // The bands deliberately overlap at the edges. Between two sizes,\n        // the client's rule is take the smaller one.\n        const overlap = Z.hipToSize.find(b => b !== band && inches >= b.min && inches < b.max);\n        if (overlap) { straddles = true; band = overlap.size < band.size ? overlap : band; }\n      }\n\n      const advice = Z.divisionAdvice.find(a =>\n        a.division.toLowerCase().includes(div.toLowerCase().split(' ')[0]));\n\n      let size = band.size;\n      let adjNote = '';\n      if (advice) {\n        if (advice.advice === 'down' && size > Z.waistSizes[0]) {\n          adjNote = `For ${advice.division.toLowerCase()}, we'd size you down to <b>${size - 2}&Prime;</b>. ${advice.why}`;\n        } else if (advice.advice === 'up' && size < Z.waistSizes[Z.waistSizes.length - 1]) {\n          adjNote = `For ${advice.division.toLowerCase()}, we'd size you up to <b>${size + 2}&Prime;</b>. ${advice.why}`;\n        } else if (advice.advice === 'preference') {\n          adjNote = `For ${advice.division.toLowerCase()}: ${advice.why}`;\n        }\n      }\n\n      out.hidden = false;\n      settle('size_finder', { size, division: div });\n      out.innerHTML = `\n        <div class=\"calc__verdict\">Start at ${size}&Prime;</div>\n        <p class=\"small\" style=\"color:var(--ink-2)\">\n          A ${unit === 'cm' ? raw + 'cm' : raw + '&Prime;'} hip measurement${unit === 'cm' ? ` (${inches.toFixed(1)}&Prime;)` : ''} puts you in the ${size}&Prime; band.\n          ${straddles ? `You're between two sizes, so we've taken the smaller one \u2014 that's our rule and it's the right call in a stretch fabric.` : ''}\n        </p>\n        ${adjNote ? `<p class=\"small mt-1\" style=\"color:var(--ink-2)\">${adjNote}</p>` : ''}\n        <p class=\"hint mt-1\">Not sure? Send us your measurements before you order. We'd rather check than have you exchange.</p>`;\n\n      $$('tbody tr[data-size]').forEach(r =>\n        r.classList.toggle('is-match', +r.dataset.size === size));\n    }\n\n    // Trunks sell in letter sizes off Andy's own trunk chart, which leaves a gap between bands\n    // (30 to 31 and so on). A measurement in a gap is between two sizes, and her rule there is the larger one.\n    // Trunks size off the waist; the Classic Taper has its own single-figure waist chart (Andy, 5 Oct 2026).\n    function trunks(raw, unit, inches, div) {\n      const T = Z.trunkChart, range = T.ranges[div];\n      const name = div === 'Classic' ? 'Classic trunks' : 'Bodybuilding trunks';\n      const top = T.bands[T.bands.length - 1];\n      let band = T.bands.find(b => inches >= b.min && inches <= b.max);\n      const between = !band && inches > T.bands[0].min && inches < top.max;\n      if (!band) band = T.bands.find(b => inches < b.min);\n      let verdict, why = '';\n      if (!band) {\n        verdict = range.includes('2XL') ? 'Talk to us about 2XL or 3XL' : 'Talk to us before you order';\n        why = `That's above our chart, which tops out at ${top.max}&Prime;. Send us your measurement and we'll tell you which size.`;\n      } else if (!range.includes(band.size)) {\n        verdict = `Start at ${T.bands.find(b => b.size === range[0]).name}`;\n        why = `${name} start at ${T.bands.find(b => b.size === range[0]).name}, so that's the closest fit. Send us your measurement if you're unsure.`;\n      } else {\n        verdict = `Start at ${band.name}`;\n        why = between ? `You're between two sizes, so we've taken the larger one. Trunks are cut smaller than the shorts.` : '';\n      }\n      const advice = div === 'Classic' && Z.divisionAdvice.find(a => a.advice === 'preference');\n      const TP = div === 'Classic' && T.taper;\n      let taperNote = '';\n      if (TP) {\n        const fit = TP.sizes.find(t => inches <= t.waist);\n        taperNote = fit\n          ? `In the Classic Taper, which has its own chart, start at <b>${fit.name}</b> (${fit.waist}&Prime; waist).`\n          : `The Classic Taper tops out at ${TP.sizes[TP.sizes.length - 1].waist}&Prime;. Send us your measurement before you order one.`;\n        $$('tbody tr[data-taper]').forEach(r => r.classList.toggle('is-match', !!fit && r.dataset.taper === fit.size));\n      }\n      out.hidden = false;\n      settle('size_finder', { size: band ? band.size : 'above chart', division: div });\n      out.innerHTML = `\n        <div class=\"calc__verdict\">${verdict}</div>\n        <p class=\"small\" style=\"color:var(--ink-2)\">\n          A ${unit === 'cm' ? raw + 'cm' : raw + '&Prime;'} waist measurement${unit === 'cm' ? ` (${inches.toFixed(1)}&Prime;)` : ''} on our trunk chart. ${why}\n        </p>\n        ${taperNote ? `<p class=\"small mt-1\" style=\"color:var(--ink-2)\">${taperNote}</p>` : ''}\n        ${advice ? `<p class=\"small mt-1\" style=\"color:var(--ink-2)\">For classic physique: ${advice.why}</p>` : ''}\n        <p class=\"hint mt-1\">Not sure? Send us your measurements before you order. We'd rather check than have you exchange.</p>`;\n      if (band && range.includes(band.size)) $$(`tbody tr[data-trunk=\"${band.size}\"]`).forEach(r => r.classList.add('is-match'));\n    }\n\n    $$('input, select', form).forEach(el => {\n      el.addEventListener('change', run);\n      el.addEventListener('input', run);\n    });\n    form.addEventListener('submit', e => { e.preventDefault(); run(); });\n  }\n  $$('[data-sizer]').forEach(initSizer);\n\n  /* --- product page ------------------------------------------------------\n     Builds its own controls from the catalogue so a colourway is data, not a\n     hand-written block of HTML per product.\n     ---------------------------------------------------------------------- */\n  $$('[data-product]').forEach(async (root) => {\n    const [cat, site] = await Promise.all([\n      fetch(VA_DATA('assets/data/catalogue.json')).then(r => r.json()).then(VA_FIX)\n        .then(c => window.VA_SHOP ? VA_SHOP.live(c) : c),\n      siteReady,\n    ]).catch(() => [null, null]);\n    if (!cat || !SITE) return;\n    const coll = cat.collections.find(c => c.handle === root.dataset.product);\n    if (!coll) return;\n\n    const esc = (s) => String(s).replace(/[&<>\"]/g, c => ({ '&': '&amp;', '<': '&lt;', '>': '&gt;', '\"': '&quot;' }[c]));\n    // Only the shorts come in lengths; trunks have none, so no picker and no length on the variant.\n    const lengths = coll.lengths || [];\n    const advice = SITE.sizing.divisionAdvice.find(a =>\n      (coll.sizeAdvice === 'down' && a.advice === 'down') ||\n      (coll.sizeAdvice === 'up' && a.advice === 'up') ||\n      (coll.sizeAdvice === 'preference' && a.advice === 'preference'));\n\n    const optionLabel = coll.optionLabel || 'Colourway';\n    // Live store sizes win: trunks sell in letters (S to 3XL), shorts by waist.\n    const live = window.VA_SHOP && VA_SHOP.sizes ? VA_SHOP.sizes(coll) : [];\n    const sizeList = live.length ? live : SITE.sizing.waistSizes;\n    const lettered = sizeList.some(s => typeof s === 'string');\n    const sizeName = (s) => lettered ? `Size ${s}` : `${s}&Prime; waist`;\n    const inch = lettered ? '' : '&Prime;';\n    // A shop card links to page.html#<handle>, which opens on that colourway.\n    // On Shopify a /products/<handle> URL arrives with the colourway in VA_PICK instead,\n    // and a bag line or order email adds ?variant=<id>, which also picks the size and length.\n    const hashPick = decodeURIComponent(location.hash.slice(1));\n    const fromPick = coll.products.findIndex(p => p.handle === (hashPick || window.VA_PICK));\n    const vid = +new URLSearchParams(location.search).get('variant') || 0;\n    const fromVariant = vid ? coll.products.findIndex(p => (p.variants || []).some(v => +v.id === vid)) : -1;\n    const byVariant = fromVariant >= 0 && !(hashPick && fromPick >= 0);\n    const state = { i: Math.max(0, byVariant ? fromVariant : fromPick), length: lengths[0] ?? null, size: null, shot: 0 };\n    if (byVariant) {\n      const v0 = coll.products[fromVariant].variants.find(v => +v.id === vid);\n      if (v0.size != null && sizeList.some(s => String(s) === String(v0.size))) state.size = v0.size;\n      if (v0.length != null && lengths.includes(v0.length)) state.length = v0.length;\n    }\n    const item = () => ({ currency: 'AUD', value: coll.price, items: [{\n      item_id: coll.products[state.i].handle, item_name: coll.title, item_variant: coll.products[state.i].title,\n      item_category: coll.handle, price: coll.price, quantity: 1 }] });\n    const viewItem = () => vaSend('view_item', item());\n\n    root.innerHTML = `\n      <div class=\"split split--wide\">\n        <div class=\"cfg__preview\">\n          <div class=\"cfg__stage pgal\" data-stage>\n            <div class=\"pgal__track\" data-track tabindex=\"0\" aria-roledescription=\"carousel\"\n                 aria-label=\"${esc(coll.title)} photographs. Arrow keys change the view.\"></div>\n            <p class=\"pgal__call\" data-call aria-live=\"polite\"></p>\n            <button class=\"pgal__step pgal__step--prev\" type=\"button\" data-step=\"-1\" aria-label=\"Previous photograph\"></button>\n            <button class=\"pgal__step pgal__step--next\" type=\"button\" data-step=\"1\" aria-label=\"Next photograph\"></button>\n          </div>\n          <div class=\"pgal__calls\" data-calls></div>\n          <div class=\"cfg__meta\" data-meta></div>\n        </div>\n        <div>\n          <p class=\"eyebrow\" data-pname></p>\n          <h1 class=\"t2\">${esc(coll.title)}</h1>\n          <p class=\"lede mt-2\">${esc(coll.blurb)}</p>\n          <p style=\"font-family:var(--f-d);font-size:2.2rem;margin-top:18px\" data-price>$${coll.price}</p>\n\n          <div class=\"field mt-2\">\n            <span class=\"lbl\">${esc(optionLabel)}</span>\n            <div class=\"choices\">\n              ${coll.products.map((p, i) => `\n                <label class=\"choice\">\n                  <input type=\"radio\" name=\"colourway\" value=\"${i}\" ${i === state.i ? 'checked' : ''}>\n                  <span><i class=\"swatch\" style=\"background:${p.swatch}\"></i>${esc(p.title)}</span>\n                </label>`).join('')}\n            </div>\n          </div>\n\n          <div class=\"field\">\n            <span class=\"lbl\">${lettered ? 'Size' : 'Waist size'}</span>\n            <div class=\"choices\">\n              ${sizeList.map(w => `\n                <label class=\"choice\">\n                  <input type=\"radio\" name=\"psize\" value=\"${esc(w)}\" ${String(w) === String(state.size) ? 'checked' : ''}>\n                  <span>${esc(w)}${inch}</span>\n                </label>`).join('')}\n            </div>\n            <p class=\"hint mt-1\">\n              ${advice ? `<b style=\"color:var(--acc-tx)\">${advice.advice === 'down' ? 'Size down' : advice.advice === 'up' ? 'Size up' : 'Your call'}</b> for this one. ${esc(advice.why)} ` : ''}\n              <a href=\"${VA_PAGE('sizing.html')}\" style=\"color:var(--acc-tx)\">Work out your size</a>.\n            </p>\n          </div>\n\n          ${lengths.length > 1 ? `\n          <div class=\"field\">\n            <span class=\"lbl\">Length</span>\n            <div class=\"choices\">\n              ${lengths.map((l, i) => `\n                <label class=\"choice\">\n                  <input type=\"radio\" name=\"plength\" value=\"${l}\" ${l === state.length ? 'checked' : ''}>\n                  <span>${l}&Prime;</span>\n                </label>`).join('')}\n            </div>\n          </div>` : ''}\n\n          <div data-buy hidden>\n            <button class=\"btn btn--wide\" type=\"button\">Add to bag</button>\n            <p class=\"hint mt-1\">Dispatched in ${SITE.turnaround.inStockDispatchDaysMin}\u2013${SITE.turnaround.inStockDispatchDaysMax} business days. Free shipping over $${SITE.shipping.freeThreshold}.</p>\n          </div>\n\n          <form data-notify hidden data-confirm=\"You're on the list. We'll email you the moment this exact size and colour is back.\"\n                name=\"back-in-stock\" method=\"POST\" data-netlify=\"true\" netlify-honeypot=\"bot-field\">\n            <input type=\"hidden\" name=\"form-name\" value=\"back-in-stock\">\n            <p hidden><label>Leave blank <input name=\"bot-field\" tabindex=\"-1\" autocomplete=\"off\"></label></p>\n            <input type=\"hidden\" name=\"referralCode\"><input type=\"hidden\" name=\"referralSource\"><input type=\"hidden\" name=\"referralLanding\">\n            <input type=\"hidden\" name=\"variant\" data-variant>\n            <div class=\"card card--acc\">\n              <h3>Sold out \u2014 want to know when it's back?</h3>\n              <p class=\"mb-2\">We're restocking most of the range. Tell us your email and we'll let you know when\n              this exact size and colour lands. Not a newsletter.</p>\n              <div class=\"field\" style=\"margin-bottom:12px\">\n                <label class=\"sr-only\" for=\"notify-email\">Email</label>\n                <input class=\"input\" type=\"email\" id=\"notify-email\" name=\"email\" placeholder=\"you@email.com\" required>\n              </div>\n              <button class=\"btn btn--wide\" type=\"submit\">Notify me</button>\n            </div>\n          </form>\n\n          <div class=\"pills mt-2\">\n            <span class=\"pill\">Sizes ${esc(sizeList[0])}${inch}\u2013${esc(sizeList[sizeList.length - 1])}${inch}</span>\n            <span class=\"pill\">4-way stretch</span>\n            <span class=\"pill\">Made for the stage</span>\n          </div>\n          <p class=\"hint mt-2\">\n            Legal in IFBB, ICN, NABBA, WNBF and INBA. Not ANB or NBA \u2014 they require their own stagewear.\n            <a href=\"${VA_PAGE('federations.html')}\" style=\"color:var(--acc-tx)\">The detail</a>.\n          </p>\n        </div>\n      </div>`;\n\n    /* The gallery runs like a judging round: the panel's calls (front, the\n       quarter turns, back), then the close-ups. One swipe track on phones; the\n       same track with the numbered calls under it on desktop. */\n    const track = $('[data-track]', root);\n    const pad = n => String(n).padStart(2, '0');\n    const shots = () => {\n      const p = coll.products[state.i];\n      return p.gallery?.length ? p.gallery\n        : [{ src: p.imgLarge || p.img, thumb: p.img, label: p.title, kind: 'view' }];\n    };\n    const reduced = matchMedia('(prefers-reduced-motion: reduce)');\n\n    const seenKinds = new Set();\n    const mark = () => {\n      const list = shots(), s = list[state.shot];\n      // Which photos people actually open, the on-stage ones above all. Shot 0\n      // is shown on load, so only a move away from it counts.\n      const kindKey = coll.products[state.i].handle + ':' + (s.kind || 'view');\n      if (state.shot > 0 && !seenKinds.has(kindKey)) {\n        seenKinds.add(kindKey);\n        vaSend('gallery_view', { photo_kind: s.kind || 'view', ...item() });\n      }\n      $('[data-call]', root).innerHTML =\n        `<b>${pad(state.shot + 1)}</b><span>/${pad(list.length)}</span> ${esc(s.label)}`;\n      $$('[data-shot]', root).forEach(b =>\n        b.setAttribute('aria-current', +b.dataset.shot === state.shot ? 'true' : 'false'));\n      // Load the neighbours early so a swipe never lands on a blank frame.\n      $$('.pgal__slide img', track).forEach((img, k) => {\n        if (Math.abs(k - state.shot) <= 1) img.loading = 'eager';\n      });\n    };\n    const showShot = (n, smooth) => {\n      const len = shots().length;\n      state.shot = (n + len) % len;\n      // Slide positions, not index \u00D7 width: the track's width can be fractional.\n      track.scrollTo({ left: track.children[state.shot].offsetLeft,\n                       behavior: smooth && !reduced.matches ? 'smooth' : 'auto' });\n      mark();\n    };\n\n    const paintGallery = () => {\n      const p = coll.products[state.i], list = shots();\n      track.innerHTML = list.map((s, k) => `\n        <figure class=\"pgal__slide pgal__slide--${s.kind || 'view'}\" aria-roledescription=\"slide\"\n                aria-label=\"${k + 1} of ${list.length}: ${esc(s.label)}\">\n          <img class=\"pstage__img\" src=\"${s.src}\" alt=\"${esc(coll.title)}, ${esc(p.title)}, ${s.kind === 'stage' ? 'worn on stage' : esc(s.label.toLowerCase())}\"\n               width=\"${s.w || 1200}\" height=\"${s.h || 1200}\" decoding=\"async\" ${k > 1 ? 'loading=\"lazy\"' : ''}>\n        </figure>`).join('');\n      // One row per kind, in the order the kinds first appear. The first on-stage\n      // shot sits second in the track, so its row follows the studio views' row.\n      const views = list.filter(s => (s.kind || 'view') === 'view').length;\n      const names = { view: views === 4 ? 'Quarter turns' : 'Front and back', stage: 'On stage', detail: 'Close-ups' };\n      const kinds = [...new Set(list.map(s => s.kind || 'view'))];\n      const group = kind => `\n        <div class=\"pgal__group\">\n          <span class=\"pgal__gname\">${names[kind] || kind}</span>\n          <div class=\"pgal__row\">\n            ${list.map((s, k) => [s, k]).filter(([s]) => (s.kind || 'view') === kind).map(([s, k]) => `\n              <button type=\"button\" class=\"pgal__pick\" data-shot=\"${k}\" title=\"${esc(s.label)}\"\n                      aria-label=\"${pad(k + 1)}, ${esc(s.label)}\">\n                <img src=\"${s.thumb}\" alt=\"\" width=\"180\" height=\"180\" loading=\"lazy\" decoding=\"async\">\n                <b>${pad(k + 1)}</b>\n              </button>`).join('')}\n          </div>\n        </div>`;\n      $('[data-calls]', root).innerHTML = list.length > 1 ? kinds.map(group).join('') : '';\n      $$('[data-shot]', root).forEach(b => b.addEventListener('click', () => showShot(+b.dataset.shot, true)));\n      $('.pgal', root).classList.toggle('is-single', list.length < 2);\n      state.shot = 0;\n      track.scrollLeft = 0;\n      mark();\n    };\n\n    // Swipes and trackpad scrolls move the track directly; follow them.\n    let settle;\n    track.addEventListener('scroll', () => {\n      cancelAnimationFrame(settle);\n      settle = requestAnimationFrame(() => {\n        const n = Math.round(track.scrollLeft / Math.max(1, track.children[0]?.getBoundingClientRect().width || 1));\n        if (n !== state.shot && n < shots().length) { state.shot = n; mark(); }\n      });\n    }, { passive: true });\n    $$('[data-step]', root).forEach(b =>\n      b.addEventListener('click', () => showShot(state.shot + +b.dataset.step, true)));\n    $('.pgal', root).addEventListener('keydown', e => {\n      if (e.key !== 'ArrowLeft' && e.key !== 'ArrowRight') return;\n      e.preventDefault();\n      showShot(state.shot + (e.key === 'ArrowRight' ? 1 : -1), true);\n    });\n    // The track is sized by the viewport; keep the current shot in frame on resize.\n    addEventListener('resize', () => { track.scrollLeft = track.children[state.shot]?.offsetLeft || 0; });\n\n    const paint = () => {\n      const p = coll.products[state.i];\n      $('[data-pname]', root).textContent = p.note ? `${p.title} \u00B7 ${p.note}` : p.title;\n\n      const map = { in: ['In stock', 'pill--in'], low: ['Low stock', 'pill--low'], out: ['Sold out', 'pill--out'] };\n      // Live store: the chosen size and length decide stock and price. Sizes with nothing\n      // left are struck through (still selectable, so the notify form can open); sizes this\n      // colourway was never made in are hidden, because the size list covers the whole collection.\n      const shop = window.VA_SHOP && p.variants;\n      if (shop) {\n        $$('[name=psize]', root).forEach(el => {\n          const x = VA_SHOP.variant(p, el.value, state.length), made = !!x || !p.variants.length;\n          el.closest('.choice').style.display = made ? '' : 'none';\n          el.closest('.choice').toggleAttribute('data-gone', !(x && x.available));\n          if (!made && el.checked) { el.checked = false; state.size = null; }\n        });\n      }\n      const v = shop ? VA_SHOP.variant(p, state.size, state.length) : null;\n      const stock = shop && state.size ? (v && v.available ? 'in' : 'out') : p.stock;\n      if (shop) $('[data-price]', root).textContent = '$' + (v ? v.price : p.price ?? coll.price);\n      const [txt, cls] = map[stock] || map.out;\n      $('[data-meta]', root).innerHTML =\n        `<span class=\"pill ${cls}\">${txt}</span>` +\n        `<span class=\"pill\">${state.size ? sizeName(state.size) : 'Pick a size'}</span>` +\n        (lengths.length > 1 ? `<span class=\"pill\">${state.length}&Prime; length</span>` : '');\n\n      const out = stock === 'out';\n      $('[data-notify]', root).hidden = !out;\n      $('[data-buy]', root).hidden = out;\n      const vf = $('[data-variant]', root);\n      if (vf) vf.value = `${coll.title} / ${p.title} / ${state.size ? state.size + (/^\\d+$/.test(state.size) ? 'in' : '') : 'size not chosen'}${lengths.length > 1 ? ` / ${state.length}in` : ''}`;\n    };\n\n    $$('[name=colourway]', root).forEach(el =>\n      el.addEventListener('change', () => {\n        state.i = +el.value; paint(); paintGallery(); viewItem();\n        history.replaceState(null, '', '#' + coll.products[state.i].handle);\n      }));\n    // A #handle link to the page you are already on (the footer, a shared link\n    // pasted into the same tab) changes only the hash; follow it.\n    addEventListener('hashchange', () => {\n      const i = coll.products.findIndex(p => p.handle === decodeURIComponent(location.hash.slice(1)));\n      const el = $(`[name=colourway][value=\"${i}\"]`, root);\n      if (i < 0 || i === state.i || !el) return;\n      el.checked = true; state.i = i; paint(); paintGallery(); viewItem();\n    });\n    $$('[name=plength]', root).forEach(el =>\n      el.addEventListener('change', () => { state.length = +el.value; paint(); }));\n    $$('[name=psize]', root).forEach(el =>\n      el.addEventListener('change', () => { state.size = lettered ? el.value : +el.value; paint(); }));\n\n    paint();\n    paintGallery();\n    viewItem();\n    // On Netlify there is no cart: the click still tells us which size and colour people\n    // wanted. On Shopify it adds the exact variant to the real bag.\n    const buy = $('[data-buy] button', root), buyNote = $('[data-buy] .hint', root), buyText = buy.textContent;\n    buy.addEventListener('click', async () => {\n      const p = coll.products[state.i];\n      const track = () => vaSend('add_to_cart', { currency: 'AUD', value: p.price ?? coll.price,\n        items: [{ ...item().items[0], item_variant: `${p.title} / ${state.size || 'no size'}${state.length ? ` / ${state.length}in` : ''}` }] });\n      if (!window.VA_SHOP || !p.variants) return track();\n      if (!state.size) {\n        buyNote.textContent = lettered ? 'Pick a size first.' : 'Pick a waist size first.';\n        $('[name=psize]', root).focus();\n        return;\n      }\n      const v = VA_SHOP.variant(p, state.size, state.length);\n      if (!v || !v.available) return paint();\n      buy.disabled = true; buy.textContent = 'Adding\u2026';\n      try {\n        await VA_SHOP.add([{ id: v.id, quantity: 1 }]);\n        track();\n        buy.textContent = 'Added to your bag';\n        buyNote.innerHTML = `<a href=\"${VA_SHOP.cartUrl}\" style=\"color:var(--acc-tx)\">View your bag and check out</a>, or keep shopping.`;\n      } catch (e) {\n        buy.textContent = buyText;\n        // Shopify's stock refusals (\"All 1 ... are in your cart.\") say why; retrying won't help those.\n        const msg = String(e.message || '').trim().replace(/[.!]+$/, '').replace(/\\bcart\\b/gi, 'bag');\n        buyNote.textContent = /quantity|in your bag|more|sold out|stock/i.test(msg)\n          ? `${msg}. That's all we have in this size right now.`\n          : `${msg || \"That didn't go through\"}. Please try again, or email info@visionattire.com.au.`;\n      } finally {\n        buy.disabled = false;\n        setTimeout(() => { if (buy.textContent === 'Added to your bag') buy.textContent = buyText; }, 2500);\n      }\n    });\n    $$('form[data-confirm]', root).forEach(f => { shopifyPrep(f); f.addEventListener('submit', confirmHandler); });\n  });\n\n  /* --- attribution ---------------------------------------------------------\n     Partner referral codes and the expo QR source. Captured once from the\n     URL, kept for 30 days, and carried through to whichever enquiry form the\n     visitor eventually fills in \u2014 the click and the form are rarely the same\n     visit.\n     ---------------------------------------------------------------------- */\n  const ATTR_KEY = 'va-attribution-v1';\n  const ATTR_DAYS = 30;\n  const ATTR_LABELS = { 'cbr-expo-2026': 'CBR Fitness Expo 2026' };\n\n  function attrRead() {\n    try {\n      const raw = localStorage.getItem(ATTR_KEY);\n      if (!raw) return null;\n      const rec = JSON.parse(raw);\n      if (!rec || typeof rec !== 'object' || typeof rec.expires !== 'number') return null;\n      if (Date.now() > rec.expires) {\n        try { localStorage.removeItem(ATTR_KEY); } catch {}\n        return null;\n      }\n      return rec;\n    } catch { return null; }\n  }\n\n  function attrWrite(rec) {\n    try { localStorage.setItem(ATTR_KEY, JSON.stringify(rec)); } catch {}\n  }\n\n  function attrLabel(rec) {\n    if (!rec || !rec.source) return '';\n    return ATTR_LABELS[rec.source] || rec.source;\n  }\n\n  (function initAttribution() {\n    const cleanRef = (v) => (v || '').replace(/[^A-Za-z0-9_-]/g, '').slice(0, 40).toUpperCase();\n    const cleanSrc = (v) => (v || '').toLowerCase().replace(/[^a-z0-9-]/g, '').slice(0, 60);\n    const params = new URLSearchParams(location.search);\n    const ref = cleanRef(params.get('ref'));\n    const src = cleanSrc(params.get('src') || params.get('utm_source'));\n    const campaign = cleanSrc(params.get('utm_campaign'));\n\n    if (ref || src) {\n      // Last touch wins: a fresh ref/source in the URL replaces whatever was\n      // stored before, rather than merging with it.\n      const now = Date.now();\n      attrWrite({\n        ref: ref || null,\n        source: src || null,\n        campaign: campaign || null,\n        landing: (location.pathname + location.search).slice(0, 200),\n        firstSeen: new Date(now).toISOString(),\n        expires: now + ATTR_DAYS * DAY,\n      });\n    } else {\n      // No new ref/source on this load: leave any existing record alone,\n      // except that reading it here clears it out once it's past 30 days.\n      attrRead();\n    }\n  })();\n\n  window.VA_ATTRIBUTION = {\n    get: attrRead,\n    sourceLabel: () => attrLabel(attrRead()),\n    apply(form) {\n      if (!form) return;\n      const rec = attrRead();\n      const label = attrLabel(rec);\n      const set = (name, value) => {\n        const el = $(`[name=${name}]`, form);\n        if (el) el.value = value || '';\n      };\n      set('referralCode', rec && rec.ref);\n      set('referralSource', rec && rec.campaign ? `${label} / ${rec.campaign}` : label);\n      set('referralLanding', rec && rec.landing);\n    },\n  };\n\n  $$('form[data-netlify]').forEach(f => window.VA_ATTRIBUTION.apply(f));\n\n  const attrNote = $('[data-attribution-note]');\n  if (attrNote) {\n    const noteLabel = window.VA_ATTRIBUTION.sourceLabel();\n    if (noteLabel) {\n      attrNote.hidden = false;\n      attrNote.textContent = `You found us through ${ATTR_LABELS[window.VA_ATTRIBUTION.get()?.source] ? 'the ' : ''}${noteLabel}. We\u2019ll note that on your application.`;\n    }\n  }\n\n  /* --- forms -------------------------------------------------------------\n     Netlify Forms handles these on deploy with no backend. On Shopify\n     (VA_FORMS 'shopify') they post to the store's own contact form instead,\n     which emails the store and can't carry files. Locally there is nothing\n     to post to, so confirm in the UI rather than throwing an error at\n     someone reviewing the build.\n     ---------------------------------------------------------------------- */\n  const SHOPIFY_FORMS = window.VA_FORMS === 'shopify';\n  const SENT_KEY = 'va-contact-sent';\n  const LABELS = { okFederation: 'Federation note confirmed', okCopyright: 'Artwork confirmed as their own',\n    photoConsent: 'Photo consent', spec: 'Design specification' };\n  const SKIP = new Set(['form-name', 'bot-field', 'form_type', 'utf8', 'h-captcha-response', 'g-recaptcha-response']);\n  // Declarations rather than consts: the product page draws its back-in-stock form before this part of the file runs.\n  function hiddenInput(name, value) { return Object.assign(document.createElement('input'), { type: 'hidden', name, value }); }\n  const isLocal = () => ['localhost', '127.0.0.1'].includes(location.hostname) || location.protocol === 'file:';\n\n  // Turns a site form into a Shopify contact form. The store's captcha guards any form that posts to /contact\n  // with form_type=contact, checked when it is submitted, so forms drawn later by JS are covered too.\n  function shopifyPrep(form) {\n    if (window.VA_FORMS !== 'shopify' || form.dataset.shopify) return;\n    form.dataset.shopify = 'true';\n    form.setAttribute('action', '/contact');\n    form.setAttribute('method', 'post');\n    form.setAttribute('accept-charset', 'UTF-8');\n    form.enctype = 'application/x-www-form-urlencoded';\n    form.prepend(hiddenInput('form_type', 'contact'), hiddenInput('utf8', '\u2713'));\n    const fileFields = [...new Set([...form.querySelectorAll('input[type=file]')].map(i => i.closest('.field') || i))];\n    if (!fileFields.length) return;\n    form.dataset.hadFiles = 'true';\n    const note = document.createElement('p');\n    note.className = 'small muted';\n    note.dataset.filesNote = '';\n    const what = { 'size-help': 'photos', 'custom-order': 'artwork, logos or reference images' }[form.getAttribute('name')] || 'files';\n    note.innerHTML = `Email your ${what} to ` +\n      '<a href=\"mailto:info@visionattire.com.au\">info@visionattire.com.au</a> once you\\'ve sent this, and we\\'ll match them to your request.';\n    fileFields[0].replaceWith(note);\n    fileFields.slice(1).forEach(f => f.remove());\n  }\n\n  // Writes every answer into contact[Label] fields, the only ones Shopify puts in the email.\n  function contactFields(form) {\n    form.querySelectorAll('[data-contact]').forEach(i => i.remove());\n    const name = form.getAttribute('name') || 'contact';\n    const fields = new Map([['Form', name.charAt(0).toUpperCase() + name.slice(1).replace(/-/g, ' ')]]);\n    for (const [k, v] of new FormData(form)) {\n      if (SKIP.has(k) || k.startsWith('contact[') || typeof v !== 'string' || !v.trim()) continue;\n      const label = k === 'email' ? 'email' : LABELS[k] ||\n        k.replace(/([a-z])([A-Z])/g, '$1 $2').replace(/[-_]/g, ' ').toLowerCase().replace(/^./, c => c.toUpperCase());\n      const value = v === 'on' ? 'yes' : v.trim();\n      fields.set(label, fields.has(label) ? fields.get(label) + ', ' + value : value);\n    }\n    if (form.dataset.hadFiles) fields.set('Files', 'Asked to email any files to info@visionattire.com.au');\n    for (const [label, value] of fields) {\n      const input = hiddenInput(`contact[${label}]`, value);\n      input.dataset.contact = '';\n      form.append(input);\n    }\n  }\n\n  // No preventDefault on the way out: the browser posts to /contact, the store's captcha may step in first, and\n  // Shopify sends the shopper back to this page with ?contact_posted=true, where the banner below picks it up.\n  function shopifySubmit(e, form) {\n    if (form.dataset.sending === 'true') return;   // the captcha re-submitting once it has a token\n    if (form.dataset.sent === 'true' || form.elements['bot-field']?.value) { e.preventDefault(); return; }\n    shopifyPrep(form);\n    if (window.VA_ATTRIBUTION) window.VA_ATTRIBUTION.apply(form);\n    contactFields(form);\n    form.querySelectorAll('.note[role=status]').forEach(n => n.remove());\n    const box = Object.assign(document.createElement('div'), { className: 'note mt-2' });\n    box.setAttribute('role', 'status');\n    form.appendChild(box);\n    if (isLocal()) { e.preventDefault(); box.textContent = 'Local preview: nothing has been sent. Your details are still here.'; return; }\n    try { sessionStorage.setItem(SENT_KEY, JSON.stringify({ form: form.getAttribute('name'), confirm: form.dataset.confirm, at: Date.now() })); } catch {}\n    form.dataset.sending = 'true';\n    const button = form.querySelector('[type=submit]');\n    if (button) button.textContent = 'Sending\u2026';\n    box.textContent = 'Sending your request. Please keep this page open.';\n  }\n\n  if (SHOPIFY_FORMS) {\n    let sent = null;\n    try { sent = JSON.parse(sessionStorage.getItem(SENT_KEY) || 'null'); sessionStorage.removeItem(SENT_KEY); } catch {}\n    const url = new URL(location.href);\n    const posted = url.searchParams.get('contact_posted') === 'true';\n    const main = $('main');\n    if (main && (posted || (sent && Date.now() - sent.at < 15 * 60 * 1000))) {\n      const box = Object.assign(document.createElement('div'), { className: 'note' });\n      box.setAttribute('role', 'status');\n      if (posted) {\n        box.textContent = sent?.confirm || \"Thanks, your message is with the Vision Attire team. We'll reply by email.\";\n        vaSend('generate_lead', { form_name: sent?.form || 'contact', referral_source: window.VA_ATTRIBUTION?.get()?.source || '(none)' });\n      } else {\n        box.className = 'note note--warn';\n        box.append('Your request was not confirmed as received. Please send it again, or email ',\n          Object.assign(document.createElement('a'), { href: 'mailto:info@visionattire.com.au', textContent: 'info@visionattire.com.au' }), '.');\n        vaSend('form_error', { form_name: sent.form });\n      }\n      const wrap = Object.assign(document.createElement('div'), { className: 'wrap' });\n      wrap.style.paddingTop = '24px';\n      wrap.append(box);\n      main.prepend(wrap);\n      url.searchParams.delete('contact_posted');\n      history.replaceState(history.state, '', url.pathname + url.search);\n    }\n  }\n\n  async function confirmHandler(e) {\n    const form = e.currentTarget;\n    if (e.defaultPrevented || !form.checkValidity()) return;\n    if (SHOPIFY_FORMS) return shopifySubmit(e, form);\n    e.preventDefault();\n    if (form.dataset.sending === 'true' || form.dataset.sent === 'true') return;\n    const fileBytes = [...form.querySelectorAll('input[type=file]')]\n      .reduce((t, i) => t + [...i.files].reduce((s, f) => s + f.size, 0), 0);\n    if (fileBytes > 5 * 1024 * 1024) {\n      form.querySelectorAll('.note[role=status]').forEach(n => n.remove());\n      const warn = Object.assign(document.createElement('div'), { className: 'note mt-2',\n        textContent: `Your files come to ${(fileBytes / 1048576).toFixed(1)} MB and the limit is 5 MB in total. ` +\n          'Please send smaller files, or send the form without them and email them to info@visionattire.com.au.' });\n      warn.setAttribute('role', 'status');\n      form.appendChild(warn);\n      return;\n    }\n    if (window.VA_ATTRIBUTION) window.VA_ATTRIBUTION.apply(form);\n    const local = ['localhost', '127.0.0.1'].includes(location.hostname) || location.protocol === 'file:';\n    const box = document.createElement('div');\n    box.className = 'note mt-2';\n    box.setAttribute('role', 'status');\n    form.querySelectorAll('.note[role=status]').forEach(n => n.remove());\n    form.appendChild(box);\n    if (local) { box.textContent = 'Local preview: nothing has been sent. Your details are still here.'; return; }\n    const button = form.querySelector('[type=submit]'), label = button?.textContent;\n    const data = new FormData(form);\n    data.set('form-name', form.getAttribute('name'));\n    form.dataset.sending = 'true';\n    if (button) { button.disabled = true; button.textContent = 'Sending\u2026'; }\n    box.textContent = 'Sending your request. Please keep this page open.';\n    const controller = new AbortController(), timeout = setTimeout(() => controller.abort(), 30000);\n    try {\n      const multipart = form.enctype === 'multipart/form-data';\n      // On Shopify the theme points VA_FORMS at the Netlify relay; forms still land in Netlify.\n      const response = await fetch(window.VA_FORMS || '/', {\n        method: 'POST',\n        headers: multipart ? {} : {'Content-Type': 'application/x-www-form-urlencoded'},\n        body: multipart ? data : new URLSearchParams(data), signal: controller.signal,\n      });\n      if (!response.ok) throw new Error(response.status === 413 ? 'too large' : 'Submission failed');\n      form.dataset.sent = 'true';\n      box.textContent = form.dataset.confirm;\n      vaSend('generate_lead', { form_name: form.getAttribute('name'),\n        referral_source: window.VA_ATTRIBUTION?.get()?.source || '(none)' });\n      if (button) button.textContent = 'Request sent';\n    } catch (err) {\n      vaSend('form_error', { form_name: form.getAttribute('name') });\n      box.textContent = err && err.message === 'too large'\n        ? 'Your files are too large to send. Please send smaller versions, or send this without them and email them to us. '\n        : 'Your request was not confirmed as received. Your details are still here. Please try again, or email us. ';\n      if (button) { button.disabled = false; button.textContent = label; }\n      const custom = form.getAttribute('name') === 'custom-order';\n      const email = document.createElement('a');\n      email.textContent = custom ? 'Email this design request' : 'Email info@visionattire.com.au';\n      email.href = 'mailto:info@visionattire.com.au?subject=' + encodeURIComponent(custom ? 'Custom shorts design request' : 'Website enquiry') +\n        (custom ? '&body=' + encodeURIComponent(data.get('spec') || '') : '');\n      box.append(email);\n    } finally { clearTimeout(timeout); delete form.dataset.sending; }\n  }\n  window.__vaConfirm = confirmHandler;\n  // Forms drawn later (the builder, back-in-stock, drop waitlist) wire themselves through this.\n  window.__vaWire = form => { shopifyPrep(form); form.addEventListener('submit', confirmHandler); };\n  $$('form[data-confirm]').forEach(window.__vaWire);\n\n  /* --- year --------------------------------------------------------------- */\n  $$('[data-year]').forEach(el => el.textContent = new Date().getFullYear());\n})();\n"],
  "mappings": "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",
  "names": ["settle", "track"]
}
