{
  "version": 3,
  "sources": ["/cdn/shop/t/3/assets/spark-configurator.js?rev=20260726-configurator-glide"],
  "sourcesContent": ["const R2_ARTWORK_FILE_LIMIT_BYTES = 50 * 1024 * 1024;\r\nconst R2_ARTWORK_TOTAL_LIMIT_BYTES = 500 * 1024 * 1024;\r\nconst ARTWORK_FILE_HELP = 'PDF, AI, EPS, PNG, JPG, JPEG, TIF, TIFF or SVG \u00B7 Maximum 50 MB per file';\r\nconst SHEET_SAFE_MARGIN_INCHES = 8 / 25.4;\r\nconst SHEET_LABEL_GAP_INCHES = 2 / 25.4;\r\nconst LEGACY_PRICING_SHEET_GAP_INCHES = 0.1;\r\nconst DEFAULT_LABELS_PER_SHEET = 15;\r\n// Configurator price tables and price-point variants are priced in the shop's\r\n// base currency. Other markets (for example USD with duties, taxes and fees\r\n// included) must display Shopify's own presentment price for the exact variant\r\n// that checkout will charge, never the base-currency number.\r\nconst SHOP_BASE_CURRENCY = 'CAD';\r\nconst PRESENTMENT_PRICE_PENDING = '\u2026';\r\nconst PRESENTMENT_PRICE_UNAVAILABLE = 'Price shown in cart';\r\n\r\nclass SparkProductConfigurator extends HTMLElement {\r\n  connectedCallback() {\r\n    if (this.productionBenefitsMarkup === undefined) {\r\n      this.productionBenefitsMarkup = this.querySelector('[data-configurator-production-benefits]')?.innerHTML.trim() || '';\r\n      this.checkoutBenefitsMarkup = this.querySelector('[data-configurator-checkout-benefits]')?.innerHTML.trim() || '';\r\n    }\r\n    this.apiBase = (this.dataset.apiBase || '').replace(/\\/$/, '');\r\n    this.configUrl = this.dataset.configUrl || '';\r\n    this.allowApiFallback = this.dataset.allowApiFallback === 'true';\r\n    this.productHandle = this.dataset.productHandle || '';\r\n    this.productTitle = this.dataset.productTitle || 'Custom product';\r\n    this.currency = this.dataset.currency || 'CAD';\r\n    this.country = String(this.dataset.country || '').toUpperCase();\r\n    this.presentmentPrices = new Map();\r\n    this.presentmentPriceRequests = new Map();\r\n    this.profile = null;\r\n    this.localMatrix = null;\r\n    this.currentPriceRow = null;\r\n    this.state = {};\r\n    this.price = null;\r\n    this.lastRenderedPriceTotal = null;\r\n    this.loading = false;\r\n    this.step = 'options';\r\n    this.statusMessage = '';\r\n    this.statusType = '';\r\n    this.artworkFileSelectionKey = '';\r\n    this.artworkFiles = [];\r\n    this.artworkPreviewUrls = new Map();\r\n    this.artworkManifestToken = '';\r\n    this.artworkAccessUrl = '';\r\n    this.artworkManifestSelectionKey = '';\r\n    this.artworkUploadProgress = 0;\r\n    this.uploadApiBase = this.apiBase || 'https://configurator.sparkstickers.com';\r\n    this.showAllFixedQuantities = false;\r\n    this.versionsDropdownOpen = false;\r\n    this.preparedVariantCache = new Map();\r\n    this.preparedVariantTimer = null;\r\n    this.activePreparedVariantKey = '';\r\n    this.stickyObserver = null;\r\n    this.stickyScrollController = null;\r\n    this.stickyReachedOptions = false;\r\n    this.handleDocumentPointerDown = this.handleDocumentPointerDown || ((event) => {\r\n      const dropdown = this.querySelector('.spark-config__versions-dropdown[open]');\r\n      if (dropdown && !dropdown.contains(event.target)) {\r\n        this.versionsDropdownOpen = false;\r\n        dropdown.removeAttribute('open');\r\n      }\r\n    });\r\n    document.removeEventListener('pointerdown', this.handleDocumentPointerDown);\r\n    document.addEventListener('pointerdown', this.handleDocumentPointerDown);\r\n    this.restoreTopScrollOnReload();\r\n    this.load();\r\n  }\r\n\r\n  disconnectedCallback() {\r\n    if (this.stickyObserver) {\r\n      this.stickyObserver.disconnect();\r\n      this.stickyObserver = null;\r\n    }\r\n    if (this.stickyScrollController) {\r\n      this.stickyScrollController.abort();\r\n      this.stickyScrollController = null;\r\n    }\r\n    this.clearPreparedVariantTimer();\r\n    this.cancelPreparedVariantRequestsExcept('');\r\n    this.clearArtworkPreviewUrls();\r\n    document.removeEventListener('pointerdown', this.handleDocumentPointerDown);\r\n  }\r\n\r\n  restoreTopScrollOnReload() {\r\n    try {\r\n      const navEntry = performance.getEntriesByType?.('navigation')?.[0];\r\n      const previousScrollY = Number(sessionStorage.getItem('spark-product-scroll-y') || 0);\r\n      const shouldForceTop = navEntry?.type === 'reload' && previousScrollY <= 24 && !window.location.hash;\r\n\r\n      if (shouldForceTop) {\r\n        if ('scrollRestoration' in history) history.scrollRestoration = 'manual';\r\n        const forceTop = () => window.scrollTo({ top: 0, left: 0, behavior: 'auto' });\r\n        [0, 80, 240, 520, 900, 1400, 2200].forEach((delay) => window.setTimeout(forceTop, delay));\r\n        window.addEventListener('load', () => {\r\n          [0, 120, 420].forEach((delay) => window.setTimeout(forceTop, delay));\r\n        }, { once: true });\r\n      }\r\n\r\n      window.addEventListener('pagehide', () => {\r\n        sessionStorage.setItem('spark-product-scroll-y', String(Math.max(0, Math.round(window.scrollY || 0))));\r\n      });\r\n    } catch (error) {\r\n      // Scroll restoration is a progressive enhancement only.\r\n    }\r\n  }\r\n\r\n  async load() {\r\n    if (!this.productHandle) {\r\n      this.renderShell('Configurator is not connected for this product.');\r\n      return;\r\n    }\r\n\r\n    this.renderShell('Loading configurator...');\r\n\r\n    try {\r\n      const payload = await this.loadConfiguratorPayload();\r\n      this.localMatrix = payload.localMatrix || null;\r\n      this.profile = payload.profile;\r\n      this.state = this.restoreConfigurationState(this.defaultState(this.profile));\r\n      this.normalizeVisibleShapeSelection();\r\n      if (this.profile.engine === 'sheets') {\r\n        this.state.finish = this.normalizedSheetFinish(this.state.finish);\r\n      }\r\n      this.render();\r\n      await this.updatePrice();\r\n    } catch (error) {\r\n      this.renderShell(error.message || 'Configurator is not available.');\r\n    }\r\n  }\r\n\r\n  async loadConfiguratorPayload() {\r\n    if (this.configUrl) {\r\n      const response = await fetch(this.configUrl, { headers: { Accept: 'application/json' } });\r\n      if (response.ok) {\r\n        const matrix = await response.json();\r\n        if (matrix?.profile) {\r\n          normalizePricingMatrix(matrix);\r\n          return { profile: matrix.profile, localMatrix: matrix };\r\n        }\r\n      }\r\n    }\r\n\r\n    if (this.apiBase && this.allowApiFallback) {\r\n      const response = await fetch(`${this.apiBase}/api/configurator/profile/${encodeURIComponent(this.productHandle)}`, {\r\n        headers: { Accept: 'application/json', 'bypass-tunnel-reminder': 'true' },\r\n      });\r\n      if (!response.ok) throw new Error('Configurator profile is not available.');\r\n      const payload = await response.json();\r\n      return { profile: payload.profile, localMatrix: null };\r\n    }\r\n\r\n    throw new Error('Local pricing data is not published for this product yet.');\r\n  }\r\n\r\n  defaultState(profile) {\r\n    const engine = profile.engine;\r\n    const state = {\r\n      shape: profile.lockedShape ? (profile.defaultShape || 'diecut') : 'diecut',\r\n      material: profile.defaultMaterial || '',\r\n      finish: profile.defaultFinish || 'none',\r\n      lamination: 'none',\r\n      unwindDirection: 'Right of Copy',\r\n      artworkMode: 'upload',\r\n      artworkNotes: '',\r\n      artworkReminderEmail: '',\r\n      customSize: false,\r\n      customQuantity: false,\r\n      customArtworkVersions: false,\r\n    };\r\n\r\n    if (engine === 'stickers' || engine === 'sheets') {\r\n      const defaultSize = engine === 'stickers' && ['rectangle', 'oval'].includes(state.shape)\r\n        ? '2\" x 1\"'\r\n        : '2\" x 2\"';\r\n      const parsedDefaultSize = parseSize(defaultSize);\r\n      Object.assign(state, {\r\n        material: engine === 'sheets' ? (profile.defaultMaterial || 'paper') : (profile.defaultMaterial || 'vinylmatte'),\r\n        width: parsedDefaultSize.width,\r\n        height: parsedDefaultSize.height,\r\n        size: defaultSize,\r\n        sizeLabel: defaultSize,\r\n        quantity: 100,\r\n        labelQuantity: engine === 'sheets' ? 100 : undefined,\r\n        artworkVersions: 1,\r\n      });\r\n    }\r\n\r\n    if (engine === 'vista-roll-labels') {\r\n      const model = profile.settings?.rollLabels || {};\r\n      const rollShapeValues = this.orderedRollShapeValues(model.shapes);\r\n      const shape = rollShapeValues[0] || profile.defaultShape || 'Circle';\r\n      const compatibleSizes = model.compatible_sizes_by_shape?.[shape] || model.fixed_sizes || [];\r\n      const material = profile.defaultMaterial || profile.materialOrder?.[0] || model.materials?.[0] || 'White Paper';\r\n      const compatibleFinishes = this.rollFinishes(material);\r\n      Object.assign(state, {\r\n        shape,\r\n        size: this.preferredTwoByTwoValue(compatibleSizes),\r\n        material,\r\n        finish: compatibleFinishes[0]?.value || profile.defaultFinish || model.finishes?.[0] || 'Gloss',\r\n        quantity: model.quantities?.includes(100) ? 100 : model.quantities?.[0] || 50,\r\n      });\r\n    }\r\n\r\n    if (engine === 'vista-magnets') {\r\n      const model = profile.settings?.magnets || {};\r\n      const shape = profile.defaultShape || model.shapes?.[0] || 'Circle';\r\n      const compatibleSizes = model.compatible_sizes_by_shape?.[shape] || model.sizes || [];\r\n      const compatibleOrientations = model.compatible_orientations_by_shape?.[shape] || model.orientations || [];\r\n      Object.assign(state, {\r\n        shape,\r\n        size: this.preferredTwoByTwoValue(compatibleSizes) || '2\" x 2\"',\r\n        orientation: compatibleOrientations[0] || 'Vertical',\r\n        finish: profile.defaultFinish || model.finishes?.[0] || 'None',\r\n        quantity: model.quantities?.includes(100) ? 100 : model.quantities?.[0] || 10,\r\n      });\r\n    }\r\n\r\n    if (engine === 'jukebox-magnets') {\r\n      const model = profile.settings?.magnets || {};\r\n      const shape = profile.defaultShape || model.shapes?.[0] || 'diecut';\r\n      const compatibleSizes = model.compatible_sizes_by_shape?.[shape] || [];\r\n      const size = this.preferredTwoByTwoValue(compatibleSizes) || compatibleSizes[0] || '2\" x 2\"';\r\n      const parsedSize = parseSize(size);\r\n      Object.assign(state, {\r\n        shape,\r\n        size,\r\n        sizeLabel: size,\r\n        width: parsedSize.width,\r\n        height: parsedSize.height,\r\n        quantity: model.quantities?.includes(100) ? 100 : model.quantities?.[0] || 50,\r\n      });\r\n    }\r\n\r\n    return state;\r\n  }\r\n\r\n  configurationSnapshot() {\r\n    const allowedKeys = [\r\n      'shape', 'material', 'finish', 'lamination', 'unwindDirection', 'width', 'height', 'size', 'sizeLabel',\r\n      'quantity', 'labelQuantity', 'orientation', 'artworkVersions',\r\n      'customSize', 'customQuantity', 'customArtworkVersions', 'artworkMode', 'artworkNotes', 'artworkReminderEmail',\r\n    ];\r\n    const state = {};\r\n    allowedKeys.forEach((key) => {\r\n      const value = this.state[key];\r\n      if (value !== undefined && value !== null && value !== '') state[key] = value;\r\n    });\r\n    return { version: 1, productHandle: this.productHandle, state };\r\n  }\r\n\r\n  configurationToken() {\r\n    const bytes = new TextEncoder().encode(JSON.stringify(this.configurationSnapshot()));\r\n    let binary = '';\r\n    bytes.forEach((byte) => { binary += String.fromCharCode(byte); });\r\n    return window.btoa(binary).replace(/\\+/g, '-').replace(/\\//g, '_').replace(/=+$/g, '');\r\n  }\r\n\r\n  parseConfigurationSnapshot(value) {\r\n    if (!value) return null;\r\n    if (value.startsWith('{')) return JSON.parse(value);\r\n    const base64 = value.replace(/-/g, '+').replace(/_/g, '/');\r\n    const padded = base64.padEnd(Math.ceil(base64.length / 4) * 4, '=');\r\n    const binary = window.atob(padded);\r\n    const bytes = Uint8Array.from(binary, (character) => character.charCodeAt(0));\r\n    return JSON.parse(new TextDecoder().decode(bytes));\r\n  }\r\n\r\n  restoreConfigurationState(defaultState) {\r\n    const params = new URLSearchParams(window.location.search);\r\n    const variantId = params.get('variant') || '';\r\n    const encodedConfiguration = params.get('spark_config');\r\n    const restoreArtworkPreference = Boolean(encodedConfiguration);\r\n    let snapshot = null;\r\n\r\n    try {\r\n      if (encodedConfiguration) snapshot = this.parseConfigurationSnapshot(encodedConfiguration);\r\n      if (!snapshot && variantId) {\r\n        snapshot = JSON.parse(window.localStorage.getItem(this.configurationStorageKey(variantId)) || 'null');\r\n      }\r\n      if (!snapshot && variantId) {\r\n        snapshot = JSON.parse(window.localStorage.getItem(this.configurationStorageKey('latest')) || 'null');\r\n      }\r\n    } catch (_error) {\r\n      snapshot = null;\r\n    }\r\n\r\n    if (!snapshot || snapshot.productHandle !== this.productHandle || !snapshot.state || typeof snapshot.state !== 'object') {\r\n      return defaultState;\r\n    }\r\n\r\n    const allowedKeys = new Set([\r\n      'shape', 'material', 'finish', 'lamination', 'unwindDirection', 'width', 'height', 'size', 'sizeLabel',\r\n      'quantity', 'labelQuantity', 'orientation', 'artworkVersions',\r\n      'customSize', 'customQuantity', 'customArtworkVersions', 'artworkMode', 'artworkNotes', 'artworkReminderEmail',\r\n    ]);\r\n    const restored = { ...defaultState };\r\n    Object.entries(snapshot.state).forEach(([key, value]) => {\r\n      if (!allowedKeys.has(key)) return;\r\n      // A normal product visit should always begin with the uploader selected.\r\n      // Only an explicit cart-edit configuration may restore \"email later\".\r\n      if (key === 'artworkMode' && !restoreArtworkPreference) return;\r\n      if (!['string', 'number', 'boolean'].includes(typeof value)) return;\r\n      restored[key] = value;\r\n    });\r\n    return restored;\r\n  }\r\n\r\n  configurationStorageKey(variantId) {\r\n    const schemaVersions = {\r\n      stickers: 'v3:',\r\n      sheets: 'v2:',\r\n      'vista-roll-labels': 'v2:',\r\n      'vista-magnets': 'v2:',\r\n      'jukebox-magnets': 'v1:',\r\n    };\r\n    const schemaVersion = schemaVersions[this.profile?.engine] || '';\r\n    return `spark-config:${schemaVersion}${this.productHandle}:${variantId}`;\r\n  }\r\n\r\n  persistConfigurationSnapshot(variantId) {\r\n    try {\r\n      const serialized = JSON.stringify(this.configurationSnapshot());\r\n      window.localStorage.setItem(this.configurationStorageKey(String(variantId)), serialized);\r\n      window.localStorage.setItem(this.configurationStorageKey('latest'), serialized);\r\n    } catch (_error) {\r\n      // Cart links still carry the exact snapshot when local storage is unavailable.\r\n    }\r\n  }\r\n\r\n  renderShell(message) {\r\n    this.innerHTML = `\r\n      <div class=\"spark-config\">\r\n        <div class=\"spark-config__empty\">\r\n          <strong>Choose options for instant pricing</strong>\r\n          <span>${escapeHtml(message)}</span>\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  renderFlowHeader(isArtworkStep) {\r\n    const optionsStep = isArtworkStep\r\n      ? `\r\n        <button class=\"spark-config__flow-step is-complete\" type=\"button\" data-back-to-options aria-label=\"Return to product options\">\r\n          <span class=\"spark-config__flow-number\" aria-hidden=\"true\">1</span>\r\n          <span>\r\n            <strong>Choose options</strong>\r\n            <small>Size, finish, quantity</small>\r\n          </span>\r\n        </button>\r\n      `\r\n      : `\r\n        <div class=\"spark-config__flow-step is-active\" aria-current=\"step\">\r\n          <span class=\"spark-config__flow-number\" aria-hidden=\"true\">1</span>\r\n          <span>\r\n            <strong>Choose options</strong>\r\n            <small>Size, finish, quantity</small>\r\n          </span>\r\n        </div>\r\n      `;\r\n\r\n    return `\r\n      <div class=\"spark-config__flow\" aria-label=\"Order progress\">\r\n        ${optionsStep}\r\n        <div class=\"spark-config__flow-step${isArtworkStep ? ' is-active' : ''}\" aria-current=\"${isArtworkStep ? 'step' : 'false'}\">\r\n          <span class=\"spark-config__flow-number\" aria-hidden=\"true\">2</span>\r\n          <span>\r\n            <strong>Upload artwork</strong>\r\n            <small>Then add to cart</small>\r\n          </span>\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  defaultStatusMarkup(isArtworkStep = this.step === 'artwork') {\r\n    return '';\r\n  }\r\n\r\n  render() {\r\n    const stickyWasVisible = this.querySelector('[data-sticky-actions]')?.classList.contains('is-visible') === true;\r\n    const profile = this.profile;\r\n    const sections = [];\r\n\r\n    if (profile.engine === 'stickers' || profile.engine === 'sheets') {\r\n      if (!profile.lockedShape) sections.push(this.renderShapeSection());\r\n      sections.push(this.renderSizeSection());\r\n      if (profile.engine === 'sheets') sections.push(this.renderSheetInfo());\r\n      if (!profile.lockedMaterial) sections.push(this.renderMaterialSection());\r\n      if (profile.engine === 'sheets' && !profile.lockedFinish) sections.push(this.renderFinishSection());\r\n      if (profile.engine === 'stickers') sections.push(this.renderLaminationSection());\r\n      if (profile.engine === 'sheets') sections.push(this.renderArtworkVersionsSection());\r\n      sections.push(this.renderQuantitySection(profile.engine === 'sheets' ? 'Labels quantity' : 'Quantity'));\r\n    }\r\n\r\n    if (profile.engine === 'vista-roll-labels') {\r\n      sections.push(this.renderChoiceSection('Shape', 'shape', this.rollShapes()));\r\n      sections.push(this.renderSizeChoiceSection('Size', this.rollSizes()));\r\n      if (!profile.lockedMaterial) sections.push(this.renderMaterialSection());\r\n      sections.push(this.renderRollFinishSection());\r\n      sections.push(this.renderRollDirectionSection());\r\n      sections.push(this.renderQuantitySection('Quantity'));\r\n    }\r\n\r\n    if (profile.engine === 'vista-magnets') {\r\n      sections.push(this.renderChoiceSection('Shape', 'shape', this.magnetShapes()));\r\n      sections.push(this.renderChoiceSection('Size', 'size', this.magnetSizes()));\r\n      sections.push(this.renderChoiceSection('Finish', 'finish', this.magnetFinishes()));\r\n      sections.push(this.renderQuantitySection('Quantity'));\r\n    }\r\n\r\n    if (profile.engine === 'jukebox-magnets') {\r\n      sections.push(this.renderShapeSection());\r\n      sections.push(this.renderSizeSection());\r\n      sections.push(this.renderQuantitySection('Quantity'));\r\n    }\r\n\r\n    const isArtworkStep = this.step === 'artwork';\r\n    const visibleSections = isArtworkStep ? [this.renderArtworkSection()] : sections;\r\n    const canContinueOptions = isArtworkStep || this.canContinueOptions();\r\n    const canAddConfiguredItem = !isArtworkStep || this.canSubmitArtwork();\r\n    const priceBlockMarkup = isArtworkStep\r\n      ? ''\r\n      : this.renderPriceBlock(this.consumePriceAnimationState());\r\n\r\n    this.innerHTML = `\r\n      <div class=\"spark-config spark-config--${isArtworkStep ? 'artwork' : 'options'}\">\r\n        ${this.renderFlowHeader(isArtworkStep)}\r\n        <div class=\"spark-config__body\">\r\n          ${visibleSections.join('')}\r\n        </div>\r\n        <div class=\"spark-config__actions\">\r\n          ${isArtworkStep ? this.renderArtworkTotal() : priceBlockMarkup}\r\n          ${this.productionBenefitsMarkup}\r\n          ${isArtworkStep ? `\r\n            <div class=\"spark-config__action-row\">\r\n              <button class=\"spark-config__add\" type=\"button\" data-add-to-cart aria-busy=\"${this.loading}\" ${(!canAddConfiguredItem || this.loading) ? 'disabled aria-disabled=\"true\"' : ''}>\r\n                <span class=\"spark-config__spinner\" aria-hidden=\"true\"></span>\r\n                <span data-add-to-cart-label>${escapeHtml(this.addToCartLabel())}</span>\r\n                <svg class=\"spark-config__cart-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\" aria-hidden=\"true\"><path d=\"M3 4h2l2.1 10.2a2 2 0 0 0 2 1.6h7.8a2 2 0 0 0 2-1.6L20 7H6\"/><circle cx=\"10\" cy=\"19\" r=\"1.2\"/><circle cx=\"17\" cy=\"19\" r=\"1.2\"/></svg>\r\n              </button>\r\n            </div>\r\n          ` : `\r\n            <button class=\"spark-config__add\" type=\"button\" data-next-step ${canContinueOptions ? '' : 'disabled aria-disabled=\"true\"'}>\r\n              <span>Continue to upload artwork</span>\r\n              <span aria-hidden=\"true\">\u2192</span>\r\n            </button>\r\n          `}\r\n          <p class=\"spark-config__status${this.statusType ? ` is-${this.statusType}` : ''}\" data-status role=\"status\" aria-live=\"polite\">\r\n            ${this.statusMessage ? escapeHtml(this.statusMessage) : this.defaultStatusMarkup(isArtworkStep)}\r\n          </p>\r\n          ${this.checkoutBenefitsMarkup}\r\n        </div>\r\n        ${!isArtworkStep ? `\r\n          <div class=\"spark-config__sticky-actions${stickyWasVisible ? ' is-visible' : ''}\" data-sticky-actions aria-hidden=\"${stickyWasVisible ? 'false' : 'true'}\">\r\n            ${priceBlockMarkup}\r\n            <button class=\"spark-config__add\" type=\"button\" data-next-step ${canContinueOptions ? '' : 'disabled aria-disabled=\"true\"'}>\r\n              <span>Continue to upload artwork</span>\r\n              <span aria-hidden=\"true\">\u2192</span>\r\n            </button>\r\n          </div>\r\n        ` : ''}\r\n      </div>\r\n    `;\r\n\r\n    this.bindEvents();\r\n    this.setupStickyActions();\r\n    if (isArtworkStep) this.updateArtworkFileState();\r\n  }\r\n\r\n  bindEvents() {\r\n    if (!this.inputFocusHandlersBound) {\r\n      this.inputFocusHandlersBound = true;\r\n      const activateIfTextInput = (event) => {\r\n        if (this.contains(event.target) && isTextEntryControl(event.target)) {\r\n          this.setInputActive(true);\r\n        }\r\n      };\r\n      const releaseIfNoTextInput = () => {\r\n        window.setTimeout(() => {\r\n          this.setInputActive(this.isTextInputFocused());\r\n        }, 80);\r\n      };\r\n\r\n      this.addEventListener('focusin', activateIfTextInput);\r\n      this.addEventListener('focusout', releaseIfNoTextInput);\r\n      document.addEventListener('focusin', activateIfTextInput, true);\r\n      document.addEventListener('focusout', releaseIfNoTextInput, true);\r\n    }\r\n\r\n    this.bindOptionEvents(this);\r\n\r\n    const helpOpen = this.querySelector('[data-lamination-help-open]');\r\n    const helpDialog = this.querySelector('[data-lamination-help-dialog]');\r\n    const helpClose = this.querySelector('[data-lamination-help-close]');\r\n    if (helpOpen && helpDialog) {\r\n      helpOpen.addEventListener('click', () => helpDialog.showModal());\r\n      helpClose?.addEventListener('click', () => helpDialog.close());\r\n      helpDialog.addEventListener('click', (event) => {\r\n        if (event.target === helpDialog) helpDialog.close();\r\n      });\r\n    }\r\n\r\n    const versionsHelpOpen = this.querySelector('[data-versions-help-open]');\r\n    const versionsHelpDialog = this.querySelector('[data-versions-help-dialog]');\r\n    const versionsHelpClose = this.querySelector('[data-versions-help-close]');\r\n    if (versionsHelpOpen && versionsHelpDialog) {\r\n      versionsHelpOpen.addEventListener('click', () => versionsHelpDialog.showModal());\r\n      versionsHelpClose?.addEventListener('click', () => versionsHelpDialog.close());\r\n      versionsHelpDialog.addEventListener('click', (event) => {\r\n        if (event.target === versionsHelpDialog) versionsHelpDialog.close();\r\n      });\r\n    }\r\n\r\n    const versionsDropdown = this.querySelector('.spark-config__versions-dropdown');\r\n    versionsDropdown?.addEventListener('toggle', () => {\r\n      this.versionsDropdownOpen = versionsDropdown.open;\r\n    });\r\n\r\n    this.querySelectorAll('[data-quantity-disclosure]').forEach((button) => {\r\n      button.addEventListener('click', () => {\r\n        this.showAllFixedQuantities = !this.showAllFixedQuantities;\r\n        this.render();\r\n      });\r\n    });\r\n\r\n    this.querySelectorAll('[data-artwork-mode]').forEach((button) => {\r\n      button.addEventListener('click', () => {\r\n        const willEmailArtwork = button.dataset.artworkMode === 'email_later';\r\n        const modeInput = this.querySelector('[data-input=\"artworkMode\"]');\r\n        if (modeInput) modeInput.checked = willEmailArtwork;\r\n        this.setField('artworkMode', willEmailArtwork, true);\r\n      });\r\n    });\r\n\r\n    const fileInput = this.querySelector('[data-artwork-file]');\r\n    if (fileInput) {\r\n      fileInput.addEventListener('change', () => {\r\n        const selectedFiles = Array.from(fileInput.files || []);\r\n        if (selectedFiles.length) {\r\n          this.mergeArtworkFiles(selectedFiles);\r\n          this.invalidateArtworkManifest();\r\n          fileInput.value = '';\r\n          this.state.artworkMode = 'upload';\r\n          const emailCheckbox = this.querySelector('[data-input=\"artworkMode\"]');\r\n          if (emailCheckbox) emailCheckbox.checked = false;\r\n          this.statusMessage = '';\r\n          this.statusType = '';\r\n        }\r\n        this.updateArtworkFileState();\r\n        this.updateAddButtonState();\r\n      });\r\n    }\r\n\r\n    const dropzone = this.querySelector('[data-artwork-dropzone]');\r\n    if (dropzone && fileInput) {\r\n      ['dragenter', 'dragover'].forEach((eventName) => {\r\n        dropzone.addEventListener(eventName, (event) => {\r\n          event.preventDefault();\r\n          dropzone.classList.add('is-dragging');\r\n        });\r\n      });\r\n\r\n      ['dragleave', 'drop'].forEach((eventName) => {\r\n        dropzone.addEventListener(eventName, () => {\r\n          dropzone.classList.remove('is-dragging');\r\n        });\r\n      });\r\n\r\n      dropzone.addEventListener('drop', (event) => {\r\n        event.preventDefault();\r\n        const files = event.dataTransfer?.files;\r\n        if (!files?.length) return;\r\n        this.mergeArtworkFiles(Array.from(files));\r\n        this.invalidateArtworkManifest();\r\n        fileInput.value = '';\r\n        this.state.artworkMode = 'upload';\r\n        const emailCheckbox = this.querySelector('[data-input=\"artworkMode\"]');\r\n        if (emailCheckbox) emailCheckbox.checked = false;\r\n        this.statusMessage = '';\r\n        this.statusType = '';\r\n        this.updateArtworkFileState();\r\n        this.updateAddButtonState();\r\n      });\r\n    }\r\n\r\n    const artworkFileList = this.querySelector('[data-artwork-file-list]');\r\n    if (artworkFileList) {\r\n      artworkFileList.addEventListener('click', (event) => {\r\n        const removeButton = event.target.closest('[data-remove-artwork-file]');\r\n        if (!removeButton || !artworkFileList.contains(removeButton)) return;\r\n        const index = Number(removeButton.dataset.removeArtworkFile);\r\n        if (!Number.isInteger(index) || index < 0) return;\r\n        const [removedFile] = this.artworkFiles.splice(index, 1);\r\n        this.releaseArtworkPreviewUrl(removedFile);\r\n        this.invalidateArtworkManifest();\r\n        if (fileInput) fileInput.value = '';\r\n        this.artworkFileSelectionKey = '';\r\n        this.updateArtworkFileState();\r\n      });\r\n    }\r\n\r\n    const addButton = this.querySelector('[data-add-to-cart]');\r\n    if (addButton) addButton.addEventListener('click', () => this.addToCart());\r\n\r\n    this.querySelectorAll('[data-next-step]').forEach((nextButton) => nextButton.addEventListener('click', () => {\r\n      if (!this.canContinueOptions()) {\r\n        this.statusMessage = this.continueBlockMessage();\r\n        this.statusType = 'error';\r\n        this.patchStatusUi();\r\n        this.patchCustomSizeMessage();\r\n        this.patchContinueButtons();\r\n        return;\r\n      }\r\n      this.step = 'artwork';\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      this.render();\r\n      this.focusArtworkStep(90, 'page');\r\n    }));\r\n\r\n    this.querySelectorAll('[data-back-to-options]').forEach((backButton) => backButton.addEventListener('click', () => {\r\n      this.step = 'options';\r\n      this.render();\r\n      this.focusArtworkStep(0, 'page');\r\n    }));\r\n  }\r\n\r\n  bindOptionEvents(scope) {\r\n    this.querySelectorAll('[data-choice]').forEach((button) => {\r\n      if (!scope.contains(button)) return;\r\n      button.addEventListener('click', () => {\r\n        const field = button.dataset.field;\r\n        const value = button.dataset.value;\r\n        this.setField(field, value);\r\n      });\r\n    });\r\n\r\n    this.querySelectorAll('[data-input]').forEach((input) => {\r\n      if (!scope.contains(input)) return;\r\n      const eventName = input.type === 'checkbox' ? 'change' : 'input';\r\n      input.addEventListener(eventName, () => {\r\n        const field = input.dataset.input;\r\n        const value = input.type === 'checkbox' ? input.checked : input.value;\r\n        if (input.hasAttribute('data-custom-quantity-input')) {\r\n          this.state.customQuantity = true;\r\n        }\r\n        this.setField(field, value, true);\r\n      });\r\n    });\r\n  }\r\n\r\n  setField(field, value, defer = false) {\r\n    let shouldRender = true;\r\n    let affectsPrice = true;\r\n    let forceInlinePricePatch = false;\r\n\r\n    if (field === 'shape') {\r\n      this.state.shape = value;\r\n      if (this.state.customSize) {\r\n        this.applyCustomSizeLabels();\r\n      } else {\r\n        this.pickCompatibleSize();\r\n      }\r\n    } else if (field === 'size') {\r\n      if (value === 'Custom') {\r\n        this.state.customSize = true;\r\n        this.state.size = 'Custom';\r\n        this.state.sizeLabel = 'Custom';\r\n        this.state.width = 0;\r\n        this.state.height = 0;\r\n        this.price = null;\r\n        this.currentPriceRow = null;\r\n        this.statusMessage = '';\r\n        this.statusType = '';\r\n        affectsPrice = false;\r\n      } else {\r\n        this.state.customSize = false;\r\n        this.applySizeValue(value);\r\n      }\r\n    } else if (field === 'customWidth' || field === 'customHeight') {\r\n      this.state[field === 'customWidth' ? 'width' : 'height'] = toNumber(value);\r\n      this.applyCustomSizeLabels();\r\n      shouldRender = false;\r\n      this.patchCustomSizeMessage();\r\n      if (this.isCustomSizeBlockingPrice()) {\r\n        this.price = null;\r\n        this.currentPriceRow = null;\r\n        this.statusMessage = '';\r\n        this.statusType = '';\r\n        this.patchInlinePricingUi();\r\n        affectsPrice = false;\r\n      }\r\n    } else if (field === 'material') {\r\n      this.state.material = value;\r\n      if (this.profile.engine === 'sheets') {\r\n        this.state.finish = this.normalizedSheetFinish(this.state.finish, value);\r\n      }\r\n      if (this.profile.engine === 'stickers' && !this.laminationTypeForMaterial(value)) {\r\n        this.state.lamination = 'none';\r\n      }\r\n      if (this.profile.engine === 'vista-roll-labels') {\r\n        const availableFinishes = this.rollFinishes();\r\n        if (!availableFinishes.some((finish) => finish.value === this.state.finish)) {\r\n          this.state.finish = availableFinishes[0]?.value || 'Gloss';\r\n        }\r\n      }\r\n    } else if (field === 'quantity' || field === 'labelQuantity') {\r\n      const editingCustomQuantity = defer && this.state.customQuantity;\r\n      this.state[field] = toInteger(value);\r\n      if (!editingCustomQuantity) this.state.customQuantity = false;\r\n      if (editingCustomQuantity) this.clearPresetQuantitySelection();\r\n      shouldRender = !editingCustomQuantity;\r\n      if (editingCustomQuantity && this.state[field] <= 0) {\r\n        this.price = null;\r\n        this.currentPriceRow = null;\r\n        this.statusMessage = '';\r\n        this.statusType = '';\r\n        affectsPrice = false;\r\n      }\r\n    } else if (field === 'customQuantity') {\r\n      this.state.customQuantity = true;\r\n      const quantityField = this.quantityField();\r\n      if (quantityField) this.state[quantityField] = 0;\r\n      this.price = null;\r\n      this.currentPriceRow = null;\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      affectsPrice = false;\r\n    } else if (field === 'artworkVersions') {\r\n      if (value === 'custom') {\r\n        this.state.customArtworkVersions = true;\r\n      } else {\r\n        this.state.customArtworkVersions = false;\r\n        this.state.artworkVersions = toInteger(value);\r\n        this.versionsDropdownOpen = false;\r\n      }\r\n      shouldRender = false;\r\n      forceInlinePricePatch = true;\r\n      this.patchArtworkVersionsControl();\r\n    } else if (field === 'customArtworkVersions') {\r\n      this.state.artworkVersions = Math.max(1, toInteger(value));\r\n      shouldRender = false;\r\n      this.patchArtworkVersionsSummary();\r\n    } else if (field === 'artworkMode') {\r\n      const artworkCheckbox = this.querySelector('[data-input=\"artworkMode\"]');\r\n      const artworkCheckboxTop = artworkCheckbox?.getBoundingClientRect().top;\r\n      const artworkScrollContainer = artworkCheckbox ? this.scrollContainerFor(artworkCheckbox) : null;\r\n      const previousOverflowAnchor = artworkScrollContainer?.style.overflowAnchor || '';\r\n      const maintainArtworkPosition = () => this.restoreViewportTop('[data-input=\"artworkMode\"]', artworkCheckboxTop);\r\n      if (artworkScrollContainer) {\r\n        artworkScrollContainer.style.overflowAnchor = 'none';\r\n        artworkScrollContainer.addEventListener('scroll', maintainArtworkPosition, { passive: true });\r\n      }\r\n      this.state.artworkMode = value ? 'email_later' : 'upload';\r\n      shouldRender = false;\r\n      affectsPrice = false;\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      if (value) {\r\n        this.clearArtworkFiles();\r\n        this.invalidateArtworkManifest();\r\n        const fileInput = this.querySelector('[data-artwork-file]');\r\n        if (fileInput) fileInput.value = '';\r\n        this.artworkFileSelectionKey = '';\r\n      }\r\n      window.setTimeout(() => {\r\n        this.updateArtworkFileState();\r\n        this.updateAddButtonState();\r\n        this.restoreViewportTop('[data-input=\"artworkMode\"]', artworkCheckboxTop);\r\n        window.setTimeout(() => {\r\n          if (artworkScrollContainer) {\r\n            artworkScrollContainer.removeEventListener('scroll', maintainArtworkPosition);\r\n            artworkScrollContainer.style.overflowAnchor = previousOverflowAnchor;\r\n          }\r\n        }, 350);\r\n      }, 0);\r\n    } else if (field === 'artworkNotes' || field === 'artworkReminderEmail') {\r\n      this.state[field] = value;\r\n      shouldRender = false;\r\n      affectsPrice = false;\r\n    } else {\r\n      this.state[field] = value;\r\n    }\r\n\r\n    if (shouldRender) this.render();\r\n    if (affectsPrice) {\r\n      window.clearTimeout(this.priceTimer);\r\n      this.priceTimer = window.setTimeout(() => this.updatePrice({ forceInlinePricePatch }), defer ? 250 : 0);\r\n    }\r\n  }\r\n\r\n  restoreViewportTop(selector, previousTop) {\r\n    if (!Number.isFinite(previousTop)) return;\r\n\r\n    const restore = () => {\r\n      const element = this.querySelector(selector);\r\n      if (!element) return;\r\n      const delta = element.getBoundingClientRect().top - previousTop;\r\n      if (Math.abs(delta) > 0.5) {\r\n        const scrollContainer = this.scrollContainerFor(element);\r\n        if (scrollContainer) {\r\n          scrollContainer.scrollTop += delta;\r\n        } else {\r\n          window.scrollBy({ top: delta, left: 0, behavior: 'auto' });\r\n        }\r\n      }\r\n    };\r\n\r\n    window.requestAnimationFrame(() => {\r\n      restore();\r\n      window.requestAnimationFrame(restore);\r\n    });\r\n  }\r\n\r\n  scrollContainerFor(element) {\r\n    for (let parent = element.parentElement; parent; parent = parent.parentElement) {\r\n      const overflowY = window.getComputedStyle(parent).overflowY;\r\n      const canScroll = /(auto|scroll|overlay)/.test(overflowY) && parent.scrollHeight > parent.clientHeight;\r\n      if (canScroll) return parent;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  applySizeValue(value) {\r\n    const parsed = parseSize(value);\r\n    this.state.size = value;\r\n    this.state.sizeLabel = value.includes(' x ') ? value : value.replace('x', ' x ');\r\n    this.state.width = parsed.width;\r\n    this.state.height = parsed.height;\r\n  }\r\n\r\n  pickCompatibleSize() {\r\n    if (this.profile.engine === 'vista-roll-labels') {\r\n      const sizes = this.rollSizes().map((option) => option.value);\r\n      this.setSizeWithoutRender(this.preferredTwoByTwoValue(sizes));\r\n      return;\r\n    }\r\n    if (this.profile.engine === 'vista-magnets') {\r\n      const sizes = this.magnetSizes().map((option) => option.value);\r\n      this.setSizeWithoutRender(this.preferredTwoByTwoValue(sizes));\r\n      const orientations = this.magnetOrientations().map((option) => option.value);\r\n      this.state.orientation = orientations[0] || this.state.orientation;\r\n      return;\r\n    }\r\n    const sizes = this.stickerSizes().map((option) => option.value);\r\n    this.setSizeWithoutRender(this.preferredTwoByTwoValue(sizes));\r\n  }\r\n\r\n  setSizeWithoutRender(value) {\r\n    if (!value) return;\r\n    this.state.customSize = false;\r\n    this.applySizeValue(value);\r\n  }\r\n\r\n  preferredTwoByTwoValue(values = []) {\r\n    if (!values?.length) return '';\r\n    return values.find((value) => normalizeSizeKey(value) === '2x2') || values[0];\r\n  }\r\n\r\n  applyCustomSizeLabels() {\r\n    const width = Number(this.state.width || 0);\r\n    const height = Number(this.state.height || 0);\r\n    this.state.size = width > 0 && height > 0 ? formatSizeLabel(width, height, false) : 'Custom';\r\n    this.state.sizeLabel = width > 0 && height > 0 ? formatSizeLabel(width, height, true) : 'Custom';\r\n  }\r\n\r\n  customSizeLimit() {\r\n    if (this.profile?.engine === 'stickers') {\r\n      if (this.profile?.priceProfile === 'hang-tags') {\r\n        return {\r\n          type: 'box', minWidth: 0.5, minHeight: 0.5, maxWidth: 12, maxHeight: 12,\r\n          minimumMessage: 'Minimum size is 0.50\" x 0.50\".', maximumMessage: 'Maximum size is 12\" x 12\".',\r\n        };\r\n      }\r\n      return {\r\n        type: 'box', minWidth: 0.5, minHeight: 0.5, maxWidth: 52, maxHeight: 52,\r\n        minimumMessage: 'Minimum size is 0.50\" x 0.50\".', maximumMessage: 'Maximum size is 52\" x 52\".',\r\n      };\r\n    }\r\n    if (this.profile?.engine === 'sheets') {\r\n      return {\r\n        type: 'rectangle', minWidth: 0.5, minHeight: 0.5, maxLongSide: 18, maxShortSide: 12,\r\n        minimumMessage: 'Minimum size is 0.50\" x 0.50\".', maximumMessage: 'Maximum size is 12\" x 18\" or 18\" x 12\".',\r\n      };\r\n    }\r\n    if (this.profile?.engine === 'vista-roll-labels') {\r\n      return { type: 'box', maxWidth: 5.5, maxHeight: 5.5, maximumMessage: 'Maximum size is 5.5\" x 5.5\".' };\r\n    }\r\n    if (this.profile?.engine === 'jukebox-magnets') {\r\n      return {\r\n        type: 'box', minWidth: 1, minHeight: 1, maxWidth: 52, maxHeight: 72,\r\n        minimumMessage: 'Minimum size is 1\" x 1\".', maximumMessage: 'Maximum size is 52\" wide x 72\" high.',\r\n      };\r\n    }\r\n    return null;\r\n  }\r\n\r\n  customRollDimensions() {\r\n    if (this.profile?.engine !== 'vista-roll-labels') return [];\r\n    const dimensions = this.localMatrix?.customRollPriceIndex?.dimensions || [];\r\n    return dimensions\r\n      .map((dimension) => Number(dimension))\r\n      .filter((dimension) => Number.isFinite(dimension) && dimension > 0)\r\n      .sort((first, second) => first - second);\r\n  }\r\n\r\n  customRollDimensionSuggestion(field) {\r\n    if (!this.state.customSize) return '';\r\n    const value = Number(this.state[field] || 0);\r\n    if (!value) return '';\r\n\r\n    const dimensions = this.customRollDimensions();\r\n    if (!dimensions.length || dimensions.some((dimension) => Math.abs(dimension - value) < 0.0001)) return '';\r\n\r\n    const lower = [...dimensions].reverse().find((dimension) => dimension < value);\r\n    const upper = dimensions.find((dimension) => dimension > value);\r\n    const nearby = [lower, upper].filter((dimension) => dimension !== undefined);\r\n    if (!nearby.length) return '';\r\n\r\n    return `Choose a nearby size: ${nearby.map((dimension) => `${formatSizeNumber(dimension)}\u2033`).join(' or ')}.`;\r\n  }\r\n\r\n  customSizeValidationMessage() {\r\n    if (!this.state.customSize) return '';\r\n    const width = Number(this.state.width || 0);\r\n    const height = Number(this.state.height || 0);\r\n    if (!width || !height) return 'Enter a custom width and height';\r\n    const limit = this.customSizeLimit();\r\n    if (this.sizeBelowLimit(width, height, limit)) return limit.minimumMessage;\r\n    if (this.sizeExceedsLimit(width, height, limit)) return limit.maximumMessage;\r\n    return this.customRollDimensionSuggestion('width') || this.customRollDimensionSuggestion('height');\r\n  }\r\n\r\n  canContinueOptions() {\r\n    return Boolean(this.price) && !this.isCustomSizeBlockingPrice();\r\n  }\r\n\r\n  continueBlockMessage() {\r\n    if (this.state.customSize) {\r\n      const message = this.customSizeValidationMessage();\r\n      if (message) return message;\r\n    }\r\n    return 'Choose a valid size and quantity for instant pricing.';\r\n  }\r\n\r\n  isCustomSizeBlockingPrice(payload = this.pricePayload()) {\r\n    if (!this.state.customSize && payload.size !== 'Custom') return false;\r\n    const width = Number(payload.width || 0);\r\n    const height = Number(payload.height || 0);\r\n    if (!width || !height) return true;\r\n    if (this.customRollDimensionSuggestion('width') || this.customRollDimensionSuggestion('height')) return true;\r\n    return this.payloadOutsideProductSizeLimit(payload);\r\n  }\r\n\r\n  payloadOutsideProductSizeLimit(payload = this.pricePayload()) {\r\n    const width = Number(payload.width || 0);\r\n    const height = Number(payload.height || 0);\r\n    const limit = this.customSizeLimit();\r\n    return this.sizeBelowLimit(width, height, limit) || this.sizeExceedsLimit(width, height, limit);\r\n  }\r\n\r\n  sizeBelowLimit(width, height, limit) {\r\n    if (!limit || !width || !height) return false;\r\n    return width < Number(limit.minWidth || 0) || height < Number(limit.minHeight || 0);\r\n  }\r\n\r\n  sizeExceedsLimit(width, height, limit) {\r\n    if (!limit || !width || !height) return false;\r\n    if (limit.type === 'rectangle') {\r\n      return Math.max(width, height) > limit.maxLongSide || Math.min(width, height) > limit.maxShortSide;\r\n    }\r\n    return width > limit.maxWidth || height > limit.maxHeight;\r\n  }\r\n\r\n  async updatePrice({ forceInlinePricePatch = false } = {}) {\r\n    if (!this.profile) return;\r\n    const patchInline = forceInlinePricePatch || this.shouldPatchPriceInline();\r\n    if (this.isCustomSizeBlockingPrice()) {\r\n      this.currentPriceRow = null;\r\n      this.price = null;\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      this.cancelConfiguredVariantPrewarm();\r\n      if (patchInline) {\r\n        this.patchInlinePricingUi();\r\n        return;\r\n      }\r\n      this.render();\r\n      return;\r\n    }\r\n    const localRow = this.findLocalPriceRow();\r\n    if (localRow) {\r\n      this.currentPriceRow = localRow;\r\n      this.price = localRow.price;\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      this.scheduleConfiguredVariantPrewarm();\r\n      if (patchInline) {\r\n        this.patchInlinePricingUi();\r\n        return;\r\n      }\r\n      this.render();\r\n      return;\r\n    }\r\n\r\n    this.currentPriceRow = null;\r\n    if (this.localMatrix && !this.allowApiFallback) {\r\n      this.price = null;\r\n      this.statusMessage = 'Choose one of the available preset options for instant checkout pricing.';\r\n      this.statusType = 'error';\r\n      this.cancelConfiguredVariantPrewarm();\r\n      if (patchInline) {\r\n        this.patchInlinePricingUi();\r\n        return;\r\n      }\r\n      this.render();\r\n      return;\r\n    }\r\n\r\n    try {\r\n      const response = await fetch(`${this.apiBase}/api/configurator/price`, {\r\n        method: 'POST',\r\n        headers: { 'Content-Type': 'application/json', Accept: 'application/json', 'bypass-tunnel-reminder': 'true' },\r\n        body: JSON.stringify(this.pricePayload()),\r\n      });\r\n      const payload = await responseJson(response, 'Custom pricing is temporarily unavailable. Please choose a preset option or try again shortly.');\r\n      if (!response.ok) throw new Error(payload.error || 'Pricing is not available.');\r\n      this.price = payload.price;\r\n      this.statusMessage = '';\r\n      this.statusType = '';\r\n      this.scheduleConfiguredVariantPrewarm();\r\n    } catch (error) {\r\n      this.price = null;\r\n      this.statusMessage = error.message || 'Pricing is not available for this combination.';\r\n      this.statusType = 'error';\r\n      this.cancelConfiguredVariantPrewarm();\r\n    }\r\n    if (patchInline) {\r\n      this.patchInlinePricingUi();\r\n      return;\r\n    }\r\n    this.render();\r\n  }\r\n\r\n  shouldPatchPriceInline() {\r\n    if (this.step !== 'options') return false;\r\n    const active = document.activeElement;\r\n    if (!active || !this.contains(active)) return false;\r\n    const field = active.dataset?.input || '';\r\n    if ((field === 'customWidth' || field === 'customHeight') && this.state.customSize) return true;\r\n    if ((field === 'quantity' || field === 'labelQuantity') && this.state.customQuantity) return true;\r\n    if (field === 'customArtworkVersions' && this.state.customArtworkVersions) return true;\r\n    return false;\r\n  }\r\n\r\n  patchInlinePricingUi() {\r\n    const priceBlockMarkup = this.renderPriceBlock(this.consumePriceAnimationState()).trim();\r\n    this.querySelectorAll('[data-price]').forEach((priceBlock) => {\r\n      const template = document.createElement('template');\r\n      template.innerHTML = priceBlockMarkup;\r\n      const nextBlock = template.content.firstElementChild;\r\n      if (nextBlock) priceBlock.replaceWith(nextBlock);\r\n    });\r\n\r\n    this.patchStatusUi();\r\n\r\n    if (this.state.customQuantity && document.activeElement?.closest('.spark-config__section--quantity')) {\r\n      this.patchCustomQuantityResultRow();\r\n    } else {\r\n      this.patchQuantitySection();\r\n    }\r\n\r\n    if (this.profile.engine === 'sheets') this.patchSheetInfo();\r\n    this.patchCustomSizeMessage();\r\n    this.patchContinueButtons();\r\n    this.updateStickyInputState();\r\n  }\r\n\r\n  patchContinueButtons() {\r\n    const canContinue = this.canContinueOptions();\r\n    this.querySelectorAll('[data-next-step]').forEach((button) => {\r\n      button.disabled = !canContinue;\r\n      button.setAttribute('aria-disabled', canContinue ? 'false' : 'true');\r\n    });\r\n  }\r\n\r\n  patchStatusUi() {\r\n    this.querySelectorAll('[data-status]').forEach((status) => {\r\n      const actions = status.closest('.spark-config__actions');\r\n      const actionRow = actions?.querySelector('.spark-config__action-row');\r\n      if (actionRow && actionRow.nextElementSibling !== status) actionRow.after(status);\r\n      status.className = `spark-config__status${this.statusType ? ` is-${this.statusType}` : ''}`;\r\n      if (this.statusMessage) {\r\n        status.textContent = this.statusMessage;\r\n      } else {\r\n        status.innerHTML = this.defaultStatusMarkup();\r\n      }\r\n    });\r\n  }\r\n\r\n  patchQuantitySection() {\r\n    const current = this.querySelector('.spark-config__section--quantity');\r\n    if (!current) return;\r\n    const template = document.createElement('template');\r\n    template.innerHTML = this.renderQuantitySection(this.profile.engine === 'sheets' ? 'Labels quantity' : 'Quantity').trim();\r\n    const next = template.content.firstElementChild;\r\n    if (!next) return;\r\n    current.replaceWith(next);\r\n    this.bindOptionEvents(next);\r\n  }\r\n\r\n  clearPresetQuantitySelection() {\r\n    this.querySelectorAll('.spark-config__quantity-row:not([data-custom-quantity-result])').forEach((row) => {\r\n      row.classList.remove('is-selected');\r\n      row.setAttribute('aria-pressed', 'false');\r\n    });\r\n  }\r\n\r\n  patchCustomQuantityResultRow() {\r\n    const list = this.querySelector('.spark-config__quantity-list');\r\n    if (!list) return;\r\n    const field = this.quantityField();\r\n    const isSheet = this.profile.engine === 'sheets';\r\n    const basePrice = this.baseQuantityPrice(this.visibleQuantityValues(isSheet), field);\r\n    const current = list.querySelector('[data-custom-quantity-result]');\r\n    const html = this.renderCustomQuantityResultRow(field, isSheet, basePrice).trim();\r\n    if (!html) {\r\n      if (current) current.remove();\r\n      return;\r\n    }\r\n\r\n    const template = document.createElement('template');\r\n    template.innerHTML = html;\r\n    const next = template.content.firstElementChild;\r\n    if (!next) return;\r\n    if (current) {\r\n      current.replaceWith(next);\r\n    } else {\r\n      const customRow = list.querySelector('.spark-config__quantity-custom-row');\r\n      if (customRow) {\r\n        customRow.after(next);\r\n      } else {\r\n        list.append(next);\r\n      }\r\n    }\r\n    this.bindOptionEvents(next);\r\n  }\r\n\r\n  patchSheetInfo() {\r\n    const current = this.querySelector('.spark-config__facts');\r\n    if (!current) return;\r\n    const template = document.createElement('template');\r\n    template.innerHTML = this.renderSheetInfo().trim();\r\n    const next = template.content.firstElementChild;\r\n    if (next) current.replaceWith(next);\r\n  }\r\n\r\n  patchCustomSizeMessage() {\r\n    const widthMessage = this.customRollDimensionSuggestion('width');\r\n    const heightMessage = this.customRollDimensionSuggestion('height');\r\n    const rollMessage = widthMessage || heightMessage;\r\n    const generalMessage = rollMessage ? '' : this.customSizeValidationMessage();\r\n    const messages = { general: generalMessage, roll: rollMessage };\r\n    this.querySelectorAll('[data-custom-size-message]').forEach((element) => {\r\n      const key = element.dataset.customSizeMessage || 'general';\r\n      const message = messages[key] || '';\r\n      element.textContent = message;\r\n      element.hidden = !message;\r\n    });\r\n\r\n    ['width', 'height'].forEach((field) => {\r\n      const input = this.querySelector(`[data-input=\"custom${field[0].toUpperCase()}${field.slice(1)}\"]`);\r\n      if (!input) return;\r\n      const fieldMessage = field === 'width' ? widthMessage : heightMessage;\r\n      input.setAttribute('aria-invalid', fieldMessage ? 'true' : 'false');\r\n      if (fieldMessage) {\r\n        input.setAttribute('aria-describedby', 'spark-custom-roll-size-message');\r\n      } else {\r\n        input.removeAttribute('aria-describedby');\r\n      }\r\n    });\r\n  }\r\n\r\n  findLocalPriceRow() {\r\n    if (!this.localMatrix?.rows?.length) return null;\r\n    return this.findLocalPriceRowForPayload(this.pricePayload());\r\n  }\r\n\r\n  findLocalPriceRowForPayload(payload) {\r\n    if (!this.localMatrix?.rows?.length) return null;\r\n    if (this.payloadOutsideProductSizeLimit(payload)) return null;\r\n    const exactRow = this.localMatrix.rows.find((row) => criteriaMatch(row.criteria || {}, payload)) || null;\r\n    if (this.profile?.engine === 'stickers' && this.profile.priceProfile !== 'hang-tags') {\r\n      // Saved preset rows predate size-boundary protection. Recalculate every\r\n      // sticker quote; reuse a saved variant only when its actual cents match.\r\n      const price = this.calculatedLocalPriceForPayload(payload);\r\n      if (!price) return null;\r\n      const matchingVariant = exactRow && Number(exactRow.price?.total) === price.total\r\n        ? exactRow : this.findPriceVariantForTotal(price.total);\r\n      return {\r\n        key: `calculated:${this.productHandle}:${stablePayloadKey(payload)}`,\r\n        criteria: {...payload},\r\n        price,\r\n        variantTitle: configuredVariantLabel(price.total),\r\n        variantId: matchingVariant?.variantId || '',\r\n        variantGid: matchingVariant?.variantGid || '',\r\n      };\r\n    }\r\n    if (exactRow && payload.lamination !== 'matched') return exactRow;\r\n    if (exactRow && payload.lamination === 'matched' && this.laminationTypeForMaterial(payload.material)) {\r\n      // Apply lamination before the final currency rounding, just like the\r\n      // server and custom-size calculator. Multiplying a rounded preset price\r\n      // can differ by a cent and correctly trigger the checkout price guard.\r\n      const price = this.calculatedLocalPriceForPayload(payload);\r\n      if (!price) return null;\r\n      return {\r\n        ...exactRow,\r\n        key: `${exactRow.key}|lamination:matched`,\r\n        criteria: { ...exactRow.criteria, lamination: 'matched' },\r\n        price,\r\n        variantTitle: configuredVariantLabel(price.total),\r\n        variantId: '',\r\n        variantGid: '',\r\n      };\r\n    }\r\n\r\n    const indexedRollRow = this.rollLabelCustomRowForPayload(payload);\r\n    if (indexedRollRow) return indexedRollRow;\r\n\r\n    const calculatedPrice = this.calculatedLocalPriceForPayload(payload);\r\n    if (!calculatedPrice) return null;\r\n\r\n    const priceVariant = this.findPriceVariantForTotal(calculatedPrice.total);\r\n    return {\r\n      key: `calculated:${this.productHandle}:${stablePayloadKey(payload)}`,\r\n      criteria: { ...payload },\r\n      price: calculatedPrice,\r\n      variantTitle: configuredVariantLabel(calculatedPrice.total),\r\n      variantId: priceVariant?.variantId || '',\r\n      variantGid: priceVariant?.variantGid || '',\r\n    };\r\n  }\r\n\r\n  rollLabelCustomRowForPayload(payload) {\r\n    if (this.profile?.engine !== 'vista-roll-labels') return null;\r\n    const indexRows = this.localMatrix?.customRollPriceIndex?.rows || null;\r\n    if (!indexRows) return null;\r\n\r\n    const width = Number(payload.width || 0);\r\n    const height = Number(payload.height || 0);\r\n    const material = payload.material || this.profile.defaultMaterial || 'White Paper';\r\n    const finish = payload.finish || this.profile.defaultFinish || 'Gloss';\r\n    const quantity = toInteger(payload.quantity);\r\n\r\n    if (!width || !height || !quantity) return null;\r\n\r\n    const widthIndex = indexValueIndex(this.localMatrix.customRollPriceIndex.dimensions, formatSizeNumber(width));\r\n    const heightIndex = indexValueIndex(this.localMatrix.customRollPriceIndex.dimensions, formatSizeNumber(height));\r\n    const materialIndex = indexValueIndex(this.localMatrix.customRollPriceIndex.materials, material);\r\n    const finishIndex = indexValueIndex(this.localMatrix.customRollPriceIndex.finishes, finish);\r\n    const quantityIndex = indexValueIndex(this.localMatrix.customRollPriceIndex.quantities, quantity);\r\n\r\n    if ([widthIndex, heightIndex, materialIndex, finishIndex, quantityIndex].some((index) => index < 0)) return null;\r\n\r\n    const keys = [\r\n      rollLabelCustomIndexKey(widthIndex, heightIndex, materialIndex, finishIndex, quantityIndex),\r\n    ];\r\n\r\n    if (width !== height) {\r\n      keys.push(rollLabelCustomIndexKey(heightIndex, widthIndex, materialIndex, finishIndex, quantityIndex));\r\n    }\r\n\r\n    const matchKey = keys.find((key) => indexRows[key]);\r\n    if (!matchKey) return null;\r\n\r\n    const compact = indexRows[matchKey];\r\n    const total = Array.isArray(compact) ? Number(compact[0] || 0) : Number(compact || 0);\r\n    const variant = this.rollLabelCustomPriceVariant(total);\r\n    const sizeLabel = formatSizeLabel(width, height, true);\r\n    const price = {\r\n      total,\r\n      discount: 0,\r\n      originalTotal: total,\r\n      quantity,\r\n      key: `Custom|Custom|${formatSizeNumber(width)}|${formatSizeNumber(height)}|${material}|${finish}|${quantity}`,\r\n      sizeLabel,\r\n      material,\r\n      finish,\r\n      shape: 'Custom',\r\n    };\r\n\r\n    return {\r\n      key: `roll-custom:${matchKey}`,\r\n      criteria: {\r\n        shape: 'Custom',\r\n        width,\r\n        height,\r\n        material,\r\n        finish,\r\n        quantity,\r\n      },\r\n      price,\r\n      variantTitle: variant?.title || configuredVariantLabel(price.total),\r\n      variantId: variant?.variantId || '',\r\n      variantGid: variant?.variantGid || '',\r\n    };\r\n  }\r\n\r\n  rollLabelCustomPriceVariant(total) {\r\n    const priceKey = Number(total || 0).toFixed(2);\r\n    const variant = this.localMatrix.customRollPriceIndex.priceVariants?.[priceKey] || null;\r\n    if (!variant) return null;\r\n    if (Array.isArray(variant)) {\r\n      const variantId = variant[0] || '';\r\n      return {\r\n        title: configuredVariantLabel(total),\r\n        variantId,\r\n        variantGid: variant[1] || (variantId ? `gid://shopify/ProductVariant/${variantId}` : ''),\r\n      };\r\n    }\r\n    return variant;\r\n  }\r\n\r\n  priceForOverrides(overrides = {}) {\r\n    const row = this.findLocalPriceRowForPayload({ ...this.pricePayload(), ...overrides });\r\n    return row?.price || null;\r\n  }\r\n\r\n  variantIdForOverrides(overrides = {}) {\r\n    if (this.usesBaseCurrency()) return '';\r\n    const row = this.findLocalPriceRowForPayload({ ...this.pricePayload(), ...overrides });\r\n    return row?.variantId ? String(row.variantId) : '';\r\n  }\r\n\r\n  usesBaseCurrency() {\r\n    return String(this.currency || SHOP_BASE_CURRENCY).toUpperCase() === SHOP_BASE_CURRENCY;\r\n  }\r\n\r\n  // Text for one configured amount. Base-currency markets keep the calculated\r\n  // total. Other markets show the cached Shopify price of the exact checkout\r\n  // variant, or a neutral placeholder until it is known.\r\n  moneyText(total, variantId, current = false) {\r\n    if (this.usesBaseCurrency()) return formatMoney(total, this.currency);\r\n    const id = variantId ? String(variantId) : '';\r\n    if (!id) return current && this.displayVariantPending() ? PRESENTMENT_PRICE_PENDING : PRESENTMENT_PRICE_UNAVAILABLE;\r\n    const cents = this.presentmentPrices.get(id);\r\n    if (Number.isSafeInteger(cents)) return formatMoney(cents / 100, this.currency);\r\n    if (cents === null) return PRESENTMENT_PRICE_UNAVAILABLE;\r\n    this.requestPresentmentPrice(id);\r\n    return PRESENTMENT_PRICE_PENDING;\r\n  }\r\n\r\n  moneyMarkup(total, variantId, current = false) {\r\n    const text = this.moneyText(total, variantId, current);\r\n    if (this.usesBaseCurrency()) return text;\r\n    const id = variantId ? String(variantId) : '';\r\n    if (id) return `<span data-presentment-variant=\"${escapeHtml(id)}\">${escapeHtml(text)}</span>`;\r\n    return current ? `<span data-presentment-current>${escapeHtml(text)}</span>` : escapeHtml(text);\r\n  }\r\n\r\n  // The variant checkout will charge for the current selection: the preset\r\n  // row's variant, or the custom variant prepared for this exact payload.\r\n  displayVariantId() {\r\n    const rowVariantId = this.currentPriceRow?.variantId;\r\n    if (rowVariantId) return String(rowVariantId);\r\n    if (this.usesBaseCurrency() || !this.price) return '';\r\n    const entry = this.preparedVariantCache?.get(this.activePreparedVariantKey);\r\n    return entry?.state === 'resolved' && entry.variantId ? String(entry.variantId) : '';\r\n  }\r\n\r\n  displayVariantPending() {\r\n    if (!this.price || this.currentPriceRow?.variantId) return false;\r\n    const entry = this.preparedVariantCache?.get(this.activePreparedVariantKey);\r\n    return Boolean(this.preparedVariantTimer || entry?.state === 'pending');\r\n  }\r\n\r\n  handlePreparedVariantResolved(key) {\r\n    if (this.usesBaseCurrency() || key !== this.activePreparedVariantKey) return;\r\n    const id = this.displayVariantId();\r\n    if (!id) return;\r\n    this.querySelectorAll('[data-presentment-current]').forEach((element) => {\r\n      element.removeAttribute('data-presentment-current');\r\n      element.dataset.presentmentVariant = id;\r\n    });\r\n    if (Number.isSafeInteger(this.presentmentPrices.get(id))) this.applyPresentmentPrice(id);\r\n    else this.requestPresentmentPrice(id);\r\n  }\r\n\r\n  addToCartLabel() {\r\n    if (this.loading) return 'Adding...';\r\n    return `Add to cart \u2014 ${this.price ? this.moneyText(this.price.total, this.displayVariantId(), true) : 'Choose options'}`;\r\n  }\r\n\r\n  requestPresentmentPrice(variantId) {\r\n    const id = String(variantId || '');\r\n    if (!/^\\d+$/.test(id) || this.presentmentPrices.has(id) || this.presentmentPriceRequests.has(id)) return;\r\n    const root = String(window.Shopify?.routes?.root || '/').replace(/\\/?$/, '/');\r\n    const request = fetch(`${root}variants/${id}.js`, {\r\n      credentials: 'same-origin',\r\n      headers: { Accept: 'application/json' },\r\n    })\r\n      .then((response) => (response.ok ? response.json() : null))\r\n      .then((variant) => {\r\n        const cents = Number(variant?.price);\r\n        return String(variant?.id) === id && Number.isSafeInteger(cents) && cents > 0 ? cents : null;\r\n      })\r\n      .catch(() => null)\r\n      .then((cents) => {\r\n        this.presentmentPriceRequests.delete(id);\r\n        this.presentmentPrices.set(id, cents);\r\n        this.applyPresentmentPrice(id);\r\n      });\r\n    this.presentmentPriceRequests.set(id, request);\r\n  }\r\n\r\n  applyPresentmentPrice(variantId) {\r\n    const text = this.moneyText(0, variantId);\r\n    this.querySelectorAll('[data-presentment-variant]').forEach((element) => {\r\n      if (element.dataset.presentmentVariant === variantId) element.textContent = text;\r\n    });\r\n    this.updateAddButtonState();\r\n  }\r\n\r\n  calculatedLocalPriceForPayload(payload) {\r\n    if (!this.profile?.settings || !payload) return null;\r\n    if (this.profile.engine === 'stickers') return calculateStickerPrice(this.profile.settings, payload, this.profile);\r\n    if (this.profile.engine === 'sheets') return calculateSheetPrice(this.profile.settings, payload, this.profile);\r\n    if (this.profile.engine === 'jukebox-magnets') return calculateJukeboxMagnetPrice(this.profile.settings, payload);\r\n    return null;\r\n  }\r\n\r\n  findPriceVariantForTotal(total) {\r\n    const price = roundMoney(total);\r\n    const variantTitle = configuredVariantLabel(price);\r\n    const productVariant = (this.localMatrix?.priceVariants || []).find((variant) => (\r\n      variant.title === variantTitle || Number(variant.price).toFixed(2) === price.toFixed(2)\r\n    )) || null;\r\n    if (productVariant) return productVariant;\r\n\r\n    // Custom prices on API-enabled products must be created on the public\r\n    // product. A shared hidden price-bank variant exposes its backend product\r\n    // title in Shopify checkout, where Basic plans cannot override line titles.\r\n    if (this.allowApiFallback) return null;\r\n\r\n    return this.customPriceBankVariant(price);\r\n  }\r\n\r\n  customPriceBankVariant(total) {\r\n    const priceKey = Number(total || 0).toFixed(2);\r\n    const variant = this.localMatrix?.customPriceBank?.priceVariants?.[priceKey] || null;\r\n    if (!variant) return null;\r\n    if (Array.isArray(variant)) {\r\n      const variantId = variant[0] || '';\r\n      return {\r\n        title: configuredVariantLabel(total),\r\n        variantId,\r\n        variantGid: variant[1] || (variantId ? `gid://shopify/ProductVariant/${variantId}` : ''),\r\n      };\r\n    }\r\n    return variant;\r\n  }\r\n\r\n  pricePayload() {\r\n    const payload = {\r\n      productHandle: this.productHandle,\r\n      shape: this.state.shape,\r\n      material: this.state.material,\r\n      finish: this.state.finish,\r\n      lamination: this.state.lamination,\r\n      width: this.state.width,\r\n      height: this.state.height,\r\n      size: this.state.size,\r\n      sizeLabel: this.state.sizeLabel,\r\n      quantity: this.state.quantity,\r\n      labelQuantity: this.state.labelQuantity,\r\n      orientation: this.state.orientation,\r\n      artworkVersions: this.state.artworkVersions,\r\n    };\r\n\r\n    Object.keys(payload).forEach((key) => {\r\n      if (payload[key] === undefined || payload[key] === '') delete payload[key];\r\n    });\r\n\r\n    return payload;\r\n  }\r\n\r\n  async addToCart() {\r\n    if (this.loading || !this.profile) return;\r\n\r\n    const artworkFiles = this.selectedArtworkFiles();\r\n    const hasRequiredArtworkFiles = artworkFiles.length === this.requiredArtworkFileCount();\r\n    const willEmailArtwork = this.state.artworkMode === 'email_later';\r\n\r\n    if (!hasRequiredArtworkFiles && !willEmailArtwork) {\r\n      this.statusMessage = `Please select exactly ${this.requiredArtworkFileCount()} artwork ${this.requiredArtworkFileCount() === 1 ? 'file' : 'files'} before adding this item.`;\r\n      this.statusType = 'error';\r\n      this.updateAddButtonState();\r\n      return;\r\n    }\r\n\r\n    const oversizedFile = artworkFiles.find((file) => file.size > R2_ARTWORK_FILE_LIMIT_BYTES);\r\n    if (oversizedFile) {\r\n      this.statusMessage = `${oversizedFile.name} is too large. Maximum file size is 50 MB.`;\r\n      this.statusType = 'error';\r\n      this.render();\r\n      this.focusArtworkStep();\r\n      return;\r\n    }\r\n\r\n    const combinedArtworkBytes = artworkFiles.reduce((total, file) => total + Number(file.size || 0), 0);\r\n    if (combinedArtworkBytes > R2_ARTWORK_TOTAL_LIMIT_BYTES) {\r\n      this.statusMessage = 'The combined artwork upload is too large. Maximum combined size is 500 MB.';\r\n      this.statusType = 'error';\r\n      this.render();\r\n      this.focusArtworkStep();\r\n      return;\r\n    }\r\n\r\n    const unsupportedFile = artworkFiles.find((file) => !isAllowedArtworkFile(file.name));\r\n    if (unsupportedFile) {\r\n      this.statusMessage = 'Accepted artwork files are JPG, JPEG, PNG, PDF, AI, EPS, TIF, TIFF, or SVG.';\r\n      this.statusType = 'error';\r\n      this.render();\r\n      this.focusArtworkStep();\r\n      return;\r\n    }\r\n\r\n    this.loading = true;\r\n    this.statusMessage = 'Hang tight! We\u2019re preparing your custom item and adding it to your cart\u2026';\r\n    this.statusType = '';\r\n    this.render();\r\n\r\n    try {\r\n      if (!willEmailArtwork) {\r\n        await this.ensureArtworkUploaded(artworkFiles);\r\n      }\r\n\r\n      let price = this.price;\r\n      let variantId = this.currentPriceRow?.variantId;\r\n\r\n      if (!variantId && (!this.apiBase || !this.allowApiFallback)) {\r\n        throw new Error('This custom price is not ready for checkout yet. Please choose a preset option or contact us for help.');\r\n      }\r\n\r\n      if (!variantId) {\r\n        const prepared = await this.prepareConfiguredVariant(this.pricePayload(), undefined, { forCart: true });\r\n        this.assertPreparedPrice(prepared, price);\r\n        price = prepared.price;\r\n        variantId = prepared.variant.id;\r\n      }\r\n\r\n      const cartPayload = await this.addConfiguredVariantToCart({\r\n        variantId,\r\n        price,\r\n        artworkFiles,\r\n        retryUnavailable: true,\r\n      });\r\n\r\n      const addedVariantId = cartPayload.variant_id || cartPayload.id || variantId;\r\n      this.persistConfigurationSnapshot(addedVariantId);\r\n      await this.openCartDrawer(cartPayload, addedVariantId);\r\n    } catch (error) {\r\n      this.loading = false;\r\n      this.statusMessage = isTransientConfiguredVariantError(error.message)\r\n        ? 'Something went wrong while adding this item. Please try Add to cart again now.'\r\n        : customerSafeError(error.message, 'Could not add configured item to cart.');\r\n      this.statusType = 'error';\r\n      this.render();\r\n      this.focusArtworkStep();\r\n    }\r\n  }\r\n\r\n  cartFormData({ variantId, price, artworkFiles }) {\r\n    const formData = new FormData();\r\n    formData.append('id', variantId);\r\n    formData.append('quantity', '1');\r\n    formData.append('sections', 'cart-drawer-section');\r\n    formData.append('sections_url', window.location.pathname);\r\n    this.cartProperties(price, artworkFiles).forEach(([key, value]) => {\r\n      if (value !== undefined && value !== null && String(value).trim() !== '') {\r\n        formData.append(`properties[${key}]`, value);\r\n      }\r\n    });\r\n\r\n    return formData;\r\n  }\r\n\r\n  async addConfiguredVariantToCart({ variantId, price, artworkFiles, retryUnavailable = false }) {\r\n    const attemptId = crypto.randomUUID();\r\n    const retryDelays = retryUnavailable ? [0, 700, 1300, 2200, 3500, 5000] : [0];\r\n    let activeVariantId = variantId;\r\n    let activePrice = price;\r\n    let lastError = null;\r\n\r\n    for (let attempt = 0; attempt < retryDelays.length; attempt += 1) {\r\n      const delay = retryDelays[attempt];\r\n      if (delay > 0) await sleep(delay);\r\n\r\n      const cartResponse = await fetch('/cart/add.js', {\r\n        method: 'POST',\r\n        headers: { Accept: 'application/json', 'X-Spark-Cart-Attempt': attemptId },\r\n        body: this.cartFormData({ variantId: activeVariantId, price: activePrice, artworkFiles }),\r\n      });\r\n      const cartPayload = await responseJson(cartResponse, 'Could not add item to cart.');\r\n\r\n      if (cartResponse.ok) {\r\n        return cartPayload;\r\n      }\r\n\r\n      lastError = new Error(cartPayload.description || cartPayload.message || 'Could not add item to cart.');\r\n      if (!retryUnavailable || cartResponse.status !== 422 || !isTransientConfiguredVariantError(lastError.message) || attempt === retryDelays.length - 1) {\r\n        throw lastError;\r\n      }\r\n\r\n      // A published pricing asset can briefly contain a Shopify variant ID\r\n      // that was replaced or removed during a price-bank sync. Re-resolve the\r\n      // configured variant from the service before retrying so customers do\r\n      // not get stuck on a 422 \"Cannot find variant\" cart error.\r\n      // Variant recovery is safe for every API-backed product, even when the\r\n      // normal API fallback flag is disabled. That flag controls missing or\r\n      // custom local prices; this path only repairs a stale Shopify ID after\r\n      // Shopify has explicitly rejected it.\r\n      if (this.apiBase && /cannot find variant|variant.*not found/i.test(lastError.message)) {\r\n        try {\r\n          // Do not reuse an entry that Shopify has explicitly rejected.\r\n          this.preparedVariantCache.forEach((entry, key) => {\r\n            if (entry.state === 'resolved' && String(entry.variantId) === String(activeVariantId)) this.preparedVariantCache.delete(key);\r\n          });\r\n          const prepared = await this.prepareConfiguredVariant(this.pricePayload(), undefined, { forCart: true });\r\n          if (prepared?.variant?.id) {\r\n            this.assertPreparedPrice(prepared, price);\r\n            activeVariantId = prepared.variant.id;\r\n            activePrice = prepared.price || activePrice;\r\n          }\r\n        } catch (refreshError) {\r\n          if (refreshError.code === 'SPARK_QUOTE_CHANGED') throw refreshError;\r\n          if (refreshError.name !== 'AbortError') {\r\n            console.warn('SparkStickers configured variant refresh failed.', refreshError);\r\n          }\r\n        }\r\n      }\r\n    }\r\n\r\n    throw lastError || new Error('Could not add item to cart.');\r\n  }\r\n\r\n  assertPreparedPrice(prepared, quotedPrice) {\r\n    const quoted = Math.round(Number(quotedPrice?.total) * 100);\r\n    if (!(quoted > 0) || Math.round(Number(prepared?.price?.total) * 100) !== quoted || Math.round(Number(prepared?.variant?.price) * 100) !== quoted) {\r\n      const error = new Error('The checkout price has changed. Please refresh the page and review your total before adding to cart.');\r\n      error.code = 'SPARK_QUOTE_CHANGED';\r\n      if (this.apiBase && this.productHandle) {\r\n        const selected = this.pricePayload();\r\n        fetch(`${this.apiBase}/api/configurator/cart-failure`, {\r\n          method: 'POST', headers: { 'Content-Type': 'application/json' }, keepalive: true,\r\n          body: JSON.stringify({\r\n            code: 'configured_cart_failed', productHandle: this.productHandle, stage: 'cart-add',\r\n            variantId: String(prepared?.variant?.id || ''), shape: selected.shape, size: selected.sizeLabel || selected.size,\r\n            quantity: selected.labelQuantity || selected.quantity, material: selected.material, finish: selected.finish,\r\n            lamination: selected.lamination, displayedPrice: String(quotedPrice?.total || ''),\r\n            error: `Checkout price mismatch: quoted ${quotedPrice?.total}, prepared ${prepared?.price?.total}, variant ${prepared?.variant?.price}`,\r\n          }),\r\n        }).catch(() => {});\r\n      }\r\n      throw error;\r\n    }\r\n  }\r\n\r\n  configuredVariantNeedsPrewarm(payload = this.pricePayload()) {\r\n    if (!this.profile || !this.allowApiFallback || !this.apiBase) return false;\r\n    if (!this.price || this.isCustomSizeBlockingPrice(payload)) return false;\r\n    if (this.currentPriceRow?.variantId) return false;\r\n    return true;\r\n  }\r\n\r\n  preparedVariantKey(payload = this.pricePayload(), price = this.price) {\r\n    const total = Number(price?.total || 0).toFixed(2);\r\n    return `${stablePayloadKey(payload)}|total:${total}`;\r\n  }\r\n\r\n  clearPreparedVariantTimer() {\r\n    if (this.preparedVariantTimer) {\r\n      window.clearTimeout(this.preparedVariantTimer);\r\n      this.preparedVariantTimer = null;\r\n    }\r\n  }\r\n\r\n  cancelPreparedVariantRequestsExcept(activeKey) {\r\n    if (!this.preparedVariantCache) return;\r\n    this.preparedVariantCache.forEach((entry, key) => {\r\n      if (key === activeKey) return;\r\n      // Once Add to cart uses a prewarm, option/price refreshes must not abort it.\r\n      if (entry?.state === 'pending' && entry.forCart) return;\r\n      if (entry?.state === 'pending') entry.controller?.abort({\r\n        name: 'AbortError',\r\n        message: 'Background preparation was superseded.',\r\n        code: 'SPARK_PREWARM_SUPERSEDED',\r\n      });\r\n      this.preparedVariantCache.delete(key);\r\n    });\r\n  }\r\n\r\n  cancelConfiguredVariantPrewarm() {\r\n    this.clearPreparedVariantTimer();\r\n    this.activePreparedVariantKey = '';\r\n    this.cancelPreparedVariantRequestsExcept('');\r\n  }\r\n\r\n  scheduleConfiguredVariantPrewarm() {\r\n    this.clearPreparedVariantTimer();\r\n    const payload = this.pricePayload();\r\n\r\n    if (!this.configuredVariantNeedsPrewarm(payload)) {\r\n      this.cancelConfiguredVariantPrewarm();\r\n      return;\r\n    }\r\n\r\n    const key = this.preparedVariantKey(payload);\r\n    this.activePreparedVariantKey = key;\r\n    this.cancelPreparedVariantRequestsExcept(key);\r\n\r\n    if (this.preparedVariantCache.has(key)) return;\r\n\r\n    const payloadSnapshot = { ...payload };\r\n    this.preparedVariantTimer = window.setTimeout(() => {\r\n      this.preparedVariantTimer = null;\r\n      this.prepareConfiguredVariant(payloadSnapshot, key).catch((error) => {\r\n        if (error.name !== 'AbortError') {\r\n          console.warn('SparkStickers configured variant prewarm failed.', error);\r\n        }\r\n      });\r\n    }, 750);\r\n  }\r\n\r\n  async prepareConfiguredVariant(payload = this.pricePayload(), key = this.preparedVariantKey(payload), { forCart = false } = {}) {\r\n    const cached = this.preparedVariantCache.get(key);\r\n    if (cached && !cached.controller?.signal.aborted && cached.state !== 'rejected') {\r\n      if (forCart) cached.forCart = true;\r\n      return cached.promise;\r\n    }\r\n\r\n    const controller = new AbortController();\r\n    const entry = {\r\n      state: 'pending',\r\n      forCart,\r\n      controller,\r\n      promise: null,\r\n    };\r\n\r\n    entry.promise = (async () => {\r\n      let waitedMs = 0;\r\n      for (let attempt = 0; ; attempt++) {\r\n        const response = await fetch(`${this.apiBase}/api/configurator/cart-variant`, {\r\n          method: 'POST',\r\n          headers: { 'Content-Type': 'application/json', Accept: 'application/json', 'bypass-tunnel-reminder': 'true' },\r\n          body: JSON.stringify(payload),\r\n          signal: controller.signal,\r\n        });\r\n        const responsePayload = await responseJson(response, 'Custom checkout pricing is temporarily unavailable. Please choose a preset option or try again shortly.');\r\n        if (response.ok) {\r\n          entry.state = 'resolved';\r\n          entry.variantId = responsePayload.variant?.id;\r\n          this.handlePreparedVariantResolved(key);\r\n          return responsePayload;\r\n        }\r\n        const retry = responsePayload.preparationRetry;\r\n        const delayMs = Number(retry?.afterSeconds) * 1000;\r\n        // Only an explicit server guarantee that no write began permits a retry.\r\n        // Network errors, HTML errors and uncertain writes never enter this path.\r\n        if (!entry.forCart || response.status !== 503 || retry?.safe !== true || retry.reason !== 'read-before-write'\r\n          || !Number.isFinite(delayMs) || delayMs <= 0 || attempt >= 2 || waitedMs + delayMs > 150000) {\r\n          throw new Error(responsePayload.error || 'Could not create configured item.');\r\n        }\r\n        waitedMs += delayMs;\r\n        await this.waitForPreparationRetry(entry, delayMs);\r\n      }\r\n    })()\r\n      .catch((error) => {\r\n        if (this.preparedVariantCache.get(key) === entry) this.preparedVariantCache.delete(key);\r\n        entry.state = 'rejected';\r\n        throw error;\r\n      });\r\n\r\n    this.preparedVariantCache.set(key, entry);\r\n    return entry.promise;\r\n  }\r\n\r\n  async waitForPreparationRetry(entry, delayMs) {\r\n    const deadline = Date.now() + delayMs;\r\n    do {\r\n      if (entry.controller.signal.aborted) throw entry.controller.signal.reason || new DOMException('Cancelled', 'AbortError');\r\n      const remaining = Math.max(0, deadline - Date.now());\r\n      if (!remaining) break;\r\n      this.statusMessage = `Checkout is temporarily busy. Your choices stay here. Retrying in ${Math.ceil(remaining / 1000)} seconds...`;\r\n      this.statusType = '';\r\n      const status = this.querySelector('[data-status]');\r\n      if (status) { status.textContent = this.statusMessage; status.classList.remove('is-error'); }\r\n      await new Promise((resolve) => window.setTimeout(resolve, Math.min(1000, remaining)));\r\n    } while (true);\r\n    if (entry.controller.signal.aborted) throw entry.controller.signal.reason || new DOMException('Cancelled', 'AbortError');\r\n    this.statusMessage = 'Reconnecting checkout and preparing your item...';\r\n    const status = this.querySelector('[data-status]');\r\n    if (status) status.textContent = this.statusMessage;\r\n  }\r\n\r\n  cartProperties(price, artworkFiles) {\r\n    const selectedFiles = Array.isArray(artworkFiles) ? artworkFiles : [];\r\n    const finish = String(this.finishLabel(this.state.finish) || '').trim();\r\n    const meaningfulFinish = !['', 'none', 'no foil', 'no finish'].includes(finish.toLowerCase());\r\n    const artworkVersionCount = Math.max(1, Number(price.artworkVersions || this.state.artworkVersions || 1));\r\n    const artworkValue = this.state.artworkMode === 'email_later'\r\n      ? 'I will email artwork later.'\r\n      : (this.artworkManifestToken && selectedFiles[0]?.name ? `Received \u2014 ${selectedFiles[0].name}` : selectedFiles[0]?.name);\r\n    const props = [\r\n      ['_Configured product', this.profile.productLabel || this.productTitle],\r\n      // Configured base-currency amount for purchasing diagnostics; checkout\r\n      // charges the selected variant's market price.\r\n      ['_Configured price', formatMoney(price.total, SHOP_BASE_CURRENCY)],\r\n      ['_Product handle', this.productHandle],\r\n      ['_Configuration', this.configurationToken()],\r\n      ['_Shipping mode', this.profile.shipping?.mode || 'calculated'],\r\n      ['_Shipping group', this.profile.shipping?.shippingGroup || 'general'],\r\n    ];\r\n    if (this.state.artworkMode !== 'email_later' && this.artworkManifestToken) {\r\n      props.push(['_Artwork manifest', this.artworkManifestToken]);\r\n      props.push(['_Artwork access', this.artworkAccessUrl]);\r\n    }\r\n\r\n    if (this.profile.engine === 'vista-roll-labels') {\r\n      props.push(['Roll direction', this.state.unwindDirection || 'Right of Copy']);\r\n    }\r\n    if (!this.profile.lockedShape) props.push(['Shape', this.shapeLabel(this.state.shape)]);\r\n    props.push(['Size', this.state.sizeLabel || this.state.size]);\r\n    if (this.state.material) props.push(['Material', this.materialLabel(this.state.material)]);\r\n    if (meaningfulFinish) props.push(['Finish', finish]);\r\n    if (this.state.lamination === 'matched') {\r\n      props.push(['Lamination', `${this.laminationTypeForMaterial(this.state.material) === 'matte' ? 'Matte' : 'Gloss'} Lamination`]);\r\n    }\r\n    props.push(['Sheet quantity', price.sheetQuantity ? `${price.sheetQuantity} sheets` : '']);\r\n    props.push(['Labels per sheet', price.sheetFit || '']);\r\n    if (this.profile.engine === 'sheets' && artworkVersionCount > 1) {\r\n      props.push(['Artwork versions', artworkVersionCount]);\r\n    }\r\n    if (this.state.orientation && this.profile.engine !== 'vista-magnets') props.push(['Orientation', this.state.orientation]);\r\n    props.push(['Artwork', artworkValue]);\r\n    selectedFiles.slice(1).forEach((file, index) => {\r\n      props.push([`Artwork ${index + 2}`, file.name]);\r\n    });\r\n    props.push(['Artwork notes', this.querySelector('[data-input=\"artworkNotes\"]')?.value || '']);\r\n    const reminderEmail = String(this.querySelector('[data-input=\"artworkReminderEmail\"]')?.value || '').trim();\r\n    if (this.state.artworkMode === 'email_later' && reminderEmail) {\r\n      props.push(['Artwork reminder email', reminderEmail]);\r\n    }\r\n    props.push(['Quantity', this.profile.engine === 'sheets' ? `${price.labelQuantity} labels` : `${price.quantity || this.state.quantity}`]);\r\n    props.push(['Digital proof', 'You\u2019ll receive a digital proof to approve before we print.']);\r\n    return props;\r\n  }\r\n\r\n  renderShapeSection() {\r\n    const order = ['diecut', 'circle', 'square', 'rectangle', 'rounded', 'oval'];\r\n    const shapes = this.profile.settings?.shapes || {};\r\n    const options = order.filter((key) => shapes[key]).map((key) => ({ value: key, label: shapes[key] }));\r\n    return this.renderChoiceSection('Shape', 'shape', options);\r\n  }\r\n\r\n  renderSizeSection() {\r\n    const options = this.stickerSizes();\r\n    return this.renderSizeChoiceSection('Size', [...options, { value: 'Custom', label: 'Custom Size' }]);\r\n  }\r\n\r\n  renderSizeChoiceSection(title, options) {\r\n    if (!options?.length) return '';\r\n    const layoutClass = this.profile?.engine === 'vista-roll-labels'\r\n      ? ' spark-config__section--roll-size'\r\n      : ' spark-config__section--sticker-size';\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--size${layoutClass}\">\r\n        <h3>${escapeHtml(this.selectionTitle(title))}</h3>\r\n        <div class=\"spark-config__choices\">\r\n          ${options.map((option) => {\r\n            const isCustom = option.value === 'Custom';\r\n            if (isCustom && this.state.customSize) {\r\n              const widthMessage = this.customRollDimensionSuggestion('width');\r\n              const heightMessage = this.customRollDimensionSuggestion('height');\r\n              const rollMessage = widthMessage || heightMessage;\r\n              const generalMessage = rollMessage ? '' : this.customSizeValidationMessage();\r\n              return `\r\n                <div class=\"spark-config__custom-size-fields\">\r\n                  <div class=\"spark-config__custom-size-field\">\r\n                    <input data-input=\"customWidth\" type=\"text\" inputmode=\"decimal\" pattern=\"[0-9]*[.]?[0-9]*\" autocomplete=\"off\" value=\"${escapeHtml(this.state.width || '')}\" placeholder=\"Width\" aria-label=\"Custom width\" aria-invalid=\"${widthMessage ? 'true' : 'false'}\"${widthMessage ? ' aria-describedby=\"spark-custom-roll-size-message\"' : ''}>\r\n                  </div>\r\n                  <div class=\"spark-config__custom-size-field\">\r\n                    <input data-input=\"customHeight\" type=\"text\" inputmode=\"decimal\" pattern=\"[0-9]*[.]?[0-9]*\" autocomplete=\"off\" value=\"${escapeHtml(this.state.height || '')}\" placeholder=\"Height\" aria-label=\"Custom height\" aria-invalid=\"${heightMessage ? 'true' : 'false'}\"${heightMessage ? ' aria-describedby=\"spark-custom-roll-size-message\"' : ''}>\r\n                  </div>\r\n                  <p id=\"spark-custom-roll-size-message\" data-custom-size-message=\"roll\" aria-live=\"polite\"${rollMessage ? '' : ' hidden'}>${escapeHtml(rollMessage)}</p>\r\n                  <p data-custom-size-message=\"general\" aria-live=\"polite\"${generalMessage ? '' : ' hidden'}>${escapeHtml(generalMessage)}</p>\r\n                </div>\r\n              `;\r\n            }\r\n\r\n            const selected = isCustom ? this.state.customSize : String(this.state.size) === String(option.value);\r\n            return `\r\n              <button\r\n                type=\"button\"\r\n                class=\"spark-config__choice${selected ? ' is-selected' : ''}\"\r\n                data-choice\r\n                data-field=\"size\"\r\n                data-value=\"${escapeHtml(option.value)}\"\r\n              >\r\n                <span>${escapeHtml(option.label)}</span>\r\n              </button>\r\n            `;\r\n          }).join('')}\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  stickerSizes() {\r\n    const rectangleLike = ['rectangle', 'oval'].includes(this.state.shape);\r\n    const labels = rectangleLike\r\n      ? ['2\" x 1\"', '3\" x 2\"', '4\" x 3\"', '5\" x 3\"']\r\n      : ['2\" x 2\"', '3\" x 3\"', '4\" x 4\"', '5\" x 5\"'];\r\n\r\n    return labels.map((label) => ({ value: label, label }));\r\n  }\r\n\r\n  renderSheetInfo() {\r\n    return `\r\n      <div class=\"spark-config__facts\">\r\n        <div class=\"spark-config__facts-row\">\r\n          <span class=\"spark-config__fact\"><span>Sheet size:</span><strong>8.5\" x 11\"</strong></span>\r\n          <span class=\"spark-config__fact\"><span>Labels per sheet:</span><strong>${this.price?.sheetFit || '-'}</strong></span>\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  renderMaterialSection() {\r\n    const materials = this.materialOptions();\r\n    if (!materials.length) return '';\r\n    return this.renderChoiceSection('Material', 'material', materials);\r\n  }\r\n\r\n  materialOptions() {\r\n    const profile = this.profile;\r\n    if (profile.engine === 'vista-roll-labels') {\r\n      const values = profile.materialOrder || profile.settings?.rollLabels?.materials || [];\r\n      return values.map((value) => ({ value, label: value }));\r\n    }\r\n\r\n    const source = profile.engine === 'sheets' ? profile.settings?.sheetMaterials : profile.settings?.materials;\r\n    return Object.entries(source || {}).map(([value, material]) => {\r\n      if (profile.engine === 'stickers') {\r\n        if (value === 'vinylmatte') return { value, label: 'Matte' };\r\n        if (value === 'vinylglossy') return { value, label: 'Glossy' };\r\n      }\r\n      return { value, label: material.label || value };\r\n    });\r\n  }\r\n\r\n  renderFinishSection() {\r\n    const options = this.sheetFinishOptions();\r\n    return this.renderChoiceSection('Finish', 'finish', options);\r\n  }\r\n\r\n  sheetFinishOptions(material = this.state.material) {\r\n    const source = this.profile.settings?.sheetFinishes || {};\r\n    return Object.entries(source)\r\n      .filter(([value]) => isSheetFinishAvailableForMaterial(material, value))\r\n      .map(([value, finish]) => ({ value, label: finish.label || value }));\r\n  }\r\n\r\n  normalizedSheetFinish(finish, material = this.state.material) {\r\n    const options = this.sheetFinishOptions(material);\r\n    const values = options.map((option) => option.value);\r\n    if (values.includes(finish)) return finish;\r\n    if (values.includes(this.profile.defaultFinish)) return this.profile.defaultFinish;\r\n    return values[0] || 'none';\r\n  }\r\n\r\n  renderArtworkVersionsSection() {\r\n    const selectedLabel = this.artworkVersionsLabel();\r\n    const options = [\r\n      { value: '1', label: '1 Artwork' },\r\n      { value: '2', label: '2 Artworks' },\r\n      { value: '3', label: '3 Artworks' },\r\n      { value: 'custom', label: 'Custom Artwork Quantity' },\r\n    ];\r\n\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--versions\">\r\n        <div class=\"spark-config__section-title-row\">\r\n          <h3>${escapeHtml(this.selectionTitle('Versions'))}</h3>\r\n          <button class=\"spark-config__help-trigger\" type=\"button\" data-versions-help-open aria-label=\"More information about artwork versions\">?</button>\r\n          <dialog class=\"spark-config__help-dialog\" data-versions-help-dialog aria-labelledby=\"spark-versions-help-title\">\r\n            <div class=\"spark-config__help-dialog-inner\">\r\n              <button class=\"spark-config__help-close\" type=\"button\" data-versions-help-close aria-label=\"Close artwork versions information\">\u00D7</button>\r\n              <h4 id=\"spark-versions-help-title\">What are artwork versions?</h4>\r\n              <p>Artwork versions are different designs in the same order, such as different logos, names, or label designs. Choose the number of unique designs you are supplying, not the number of printed pieces. Each design uses the same selected size, material, and finish.</p>\r\n            </div>\r\n          </dialog>\r\n        </div>\r\n        <details class=\"spark-config__versions-dropdown\"${this.versionsDropdownOpen ? ' open' : ''}>\r\n          <summary>\r\n            <span data-versions-summary>${escapeHtml(selectedLabel)}</span>\r\n            <span class=\"spark-config__versions-chevron\" aria-hidden=\"true\"></span>\r\n          </summary>\r\n          <div class=\"spark-config__versions-panel\">\r\n            ${options.map((option) => `\r\n              <button\r\n                type=\"button\"\r\n                class=\"spark-config__versions-option${(option.value === 'custom' ? this.state.customArtworkVersions : (!this.state.customArtworkVersions && String(this.state.artworkVersions) === option.value)) ? ' is-selected' : ''}\"\r\n                data-choice\r\n                data-field=\"artworkVersions\"\r\n                data-value=\"${option.value}\"\r\n              >${escapeHtml(option.label)}</button>\r\n              ${option.value === 'custom' && this.state.customArtworkVersions ? `\r\n                <div class=\"spark-config__versions-custom\">\r\n                  <label for=\"spark-custom-artwork-versions\">Number of artworks</label>\r\n                  <input id=\"spark-custom-artwork-versions\" data-input=\"customArtworkVersions\" type=\"number\" inputmode=\"numeric\" min=\"1\" step=\"1\" value=\"${escapeHtml(this.state.artworkVersions || '')}\" placeholder=\"Enter artwork quantity\">\r\n                </div>\r\n              ` : ''}\r\n            `).join('')}\r\n          </div>\r\n        </details>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  artworkVersionsLabel() {\r\n    return this.state.customArtworkVersions\r\n      ? `Custom: ${formatNumber(this.state.artworkVersions || 1)} Artworks`\r\n      : ({ 1: '1 Artwork', 2: '2 Artworks', 3: '3 Artworks' }[this.state.artworkVersions] || '1 Artwork');\r\n  }\r\n\r\n  patchArtworkVersionsSummary() {\r\n    const summary = this.querySelector('[data-versions-summary]');\r\n    if (summary) summary.textContent = this.artworkVersionsLabel();\r\n  }\r\n\r\n  isRoundedShape(value) {\r\n    return ['rounded', 'roundedsquare'].includes(String(value || '').toLowerCase().replace(/[\\s-]+/g, ''));\r\n  }\r\n\r\n  visibleShapeOptions(options) {\r\n    if (this.profile?.engine === 'vista-roll-labels') return options;\r\n    return (options || []).filter((option) => !this.isRoundedShape(option.value));\r\n  }\r\n\r\n  normalizeVisibleShapeSelection() {\r\n    if (this.profile?.engine === 'vista-roll-labels' || !this.isRoundedShape(this.state?.shape)) return;\r\n\r\n    const options = this.profile?.engine === 'vista-magnets'\r\n      ? this.magnetShapes()\r\n      : ['diecut', 'circle', 'square', 'rectangle', 'rounded', 'oval']\r\n        .filter((key) => this.profile?.settings?.shapes?.[key])\r\n        .map((key) => ({ value: key, label: this.profile.settings.shapes[key] }));\r\n    const fallback = this.visibleShapeOptions(options)[0];\r\n    if (fallback) this.state.shape = fallback.value;\r\n  }\r\n\r\n  patchArtworkVersionsControl() {\r\n    const dropdown = this.querySelector('.spark-config__versions-dropdown');\r\n    const panel = dropdown?.querySelector('.spark-config__versions-panel');\r\n    if (!dropdown || !panel) return;\r\n\r\n    this.versionsDropdownOpen = false;\r\n    dropdown.removeAttribute('open');\r\n    this.patchArtworkVersionsSummary();\r\n\r\n    const selectedValue = this.state.customArtworkVersions ? 'custom' : String(this.state.artworkVersions);\r\n    panel.querySelectorAll('.spark-config__versions-option').forEach((option) => {\r\n      option.classList.toggle('is-selected', option.dataset.value === selectedValue);\r\n    });\r\n\r\n    const currentCustom = panel.querySelector('.spark-config__versions-custom');\r\n    if (!this.state.customArtworkVersions) {\r\n      currentCustom?.remove();\r\n      return;\r\n    }\r\n\r\n    if (currentCustom) {\r\n      const input = currentCustom.querySelector('[data-input=\"customArtworkVersions\"]');\r\n      if (input) input.value = String(this.state.artworkVersions || 1);\r\n      return;\r\n    }\r\n\r\n    const customOption = panel.querySelector('[data-field=\"artworkVersions\"][data-value=\"custom\"]');\r\n    if (!customOption) return;\r\n    const custom = document.createElement('div');\r\n    custom.className = 'spark-config__versions-custom';\r\n    custom.innerHTML = `\r\n      <label for=\"spark-custom-artwork-versions\">Number of artworks</label>\r\n      <input id=\"spark-custom-artwork-versions\" data-input=\"customArtworkVersions\" type=\"number\" inputmode=\"numeric\" min=\"1\" step=\"1\" value=\"${escapeHtml(this.state.artworkVersions || 1)}\" placeholder=\"Enter artwork quantity\">\r\n    `;\r\n    customOption.after(custom);\r\n    this.bindOptionEvents(custom);\r\n  }\r\n\r\n  renderQuantitySection(title) {\r\n    const isSheet = this.profile.engine === 'sheets';\r\n    const isFixedQuantityEngine = this.isFixedQuantityEngine();\r\n    const allFixedValues = isFixedQuantityEngine ? this.quantityOptions() : [];\r\n    const values = isFixedQuantityEngine\r\n      ? (this.showAllFixedQuantities ? allFixedValues : allFixedValues.slice(0, 9))\r\n      : this.visibleQuantityValues(isSheet);\r\n    const field = this.quantityField();\r\n    const basePrice = this.baseQuantityPrice(values, field);\r\n\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--quantity\">\r\n        <div class=\"spark-config__section-heading\">\r\n          <h3>${escapeHtml(this.selectionTitle(title))}</h3>\r\n        </div>\r\n        <div class=\"spark-config__quantity-list\">\r\n          ${values.map((value) => this.renderQuantityRow(value, field, isSheet, basePrice)).join('')}\r\n          ${isFixedQuantityEngine ? this.renderFixedQuantityDisclosure(allFixedValues.length) : `\r\n            ${this.renderCustomQuantityResultRow(field, isSheet, basePrice)}\r\n            ${this.renderCustomQuantityRow(field, isSheet)}\r\n          `}\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  renderLaminationSection() {\r\n    const type = this.laminationTypeForMaterial(this.state.material);\r\n    if (!type) return '';\r\n    const selected = this.state.lamination === 'matched' ? 'matched' : 'none';\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--lamination\">\r\n        <div class=\"spark-config__section-title-row\">\r\n          <span class=\"spark-config__lamination-title\">\r\n            <h3>Protective film</h3>\r\n            <button class=\"spark-config__help-trigger\" type=\"button\" data-lamination-help-open aria-label=\"More information about lamination\">?</button>\r\n          </span>\r\n          <dialog class=\"spark-config__help-dialog\" data-lamination-help-dialog aria-labelledby=\"spark-lamination-help-title\">\r\n            <div class=\"spark-config__help-dialog-inner\">\r\n              <button class=\"spark-config__help-close\" type=\"button\" data-lamination-help-close aria-label=\"Close lamination information\">\u00D7</button>\r\n              <h4 id=\"spark-lamination-help-title\">About lamination</h4>\r\n              <p>Most sticker orders do not need lamination. The selected PVC vinyl finish is already durable for everyday use. Choose matched lamination only for harsher use, heavy handling, abrasion, frequent moisture, or longer outdoor exposure.</p>\r\n            </div>\r\n          </dialog>\r\n        </div>\r\n        <div class=\"spark-config__lamination-choices\" role=\"radiogroup\" aria-label=\"Sticker lamination\">\r\n          <button type=\"button\" class=\"spark-config__lamination-choice${selected === 'none' ? ' is-selected' : ''}\" data-choice data-field=\"lamination\" data-value=\"none\" role=\"radio\" aria-checked=\"${selected === 'none'}\">\r\n            <strong>No lamination</strong>\r\n            <small>Standard finish without added film</small>\r\n          </button>\r\n          <button type=\"button\" class=\"spark-config__lamination-choice${selected === 'matched' ? ' is-selected' : ''}\" data-choice data-field=\"lamination\" data-value=\"matched\" role=\"radio\" aria-checked=\"${selected === 'matched'}\">\r\n            <strong>Protective film</strong>\r\n            <small>Adds resistance to wear and handling</small>\r\n          </button>\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  laminationTypeForMaterial(material) {\r\n    const key = String(material || '').toLowerCase();\r\n    const label = String(this.profile.settings?.materials?.[material]?.label || '').toLowerCase();\r\n    if (key.includes('clear') || label.includes('clear') || key.includes('hangtag') || label.includes('hang tag')) return '';\r\n    if (key.includes('matte') || label.includes('matte')) return 'matte';\r\n    if (key.includes('gloss') || label.includes('gloss') || key === 'vinyl' || label === 'vinyl') return 'gloss';\r\n    return '';\r\n  }\r\n\r\n  isFixedQuantityEngine() {\r\n    return this.profile?.engine === 'vista-roll-labels';\r\n  }\r\n\r\n  renderFixedQuantityDisclosure(totalQuantityChoices) {\r\n    if (totalQuantityChoices <= 9) return '';\r\n    const expanded = this.showAllFixedQuantities;\r\n    return `\r\n      <button\r\n        type=\"button\"\r\n        class=\"spark-config__quantity-disclosure\"\r\n        data-quantity-disclosure\r\n        aria-expanded=\"${expanded}\"\r\n      >\r\n        <span>${expanded ? 'Show fewer quantities' : 'Show more quantities'}</span>\r\n        <span class=\"spark-config__quantity-disclosure-icon\" aria-hidden=\"true\">${expanded ? '\u2212' : '+'}</span>\r\n      </button>\r\n    `;\r\n  }\r\n\r\n  quantityField() {\r\n    return this.profile?.engine === 'sheets' ? 'labelQuantity' : 'quantity';\r\n  }\r\n\r\n  visibleQuantityValues(isSheet = this.profile.engine === 'sheets') {\r\n    return isSheet\r\n      ? [50, 100, 200, 300, 500, 1000, 2000, 3000, 5000]\r\n      : this.profile.engine === 'jukebox-magnets'\r\n        ? this.quantityOptions()\r\n        : this.quantityOptions().slice(0, 9);\r\n  }\r\n\r\n  baseQuantityPrice(values, field) {\r\n    for (const value of values) {\r\n      const price = this.priceForOverrides({ [field]: Number(value) });\r\n      if (this.quantityUnit(price) > 0) return price;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  renderQuantityRow(value, field, isSheet, basePrice = null) {\r\n    const rowPrice = this.priceForOverrides({ [field]: Number(value) });\r\n    const selected = !this.state.customQuantity && Number(this.state[field]) === Number(value);\r\n    return this.renderQuantityButton(value, field, isSheet, rowPrice, basePrice, selected);\r\n  }\r\n\r\n  renderCustomQuantityResultRow(field, isSheet, basePrice = null) {\r\n    if (!this.state.customQuantity || Number(this.state[field] || 0) <= 0) return '';\r\n    const value = Number(this.state[field]);\r\n    const rowPrice = this.priceForOverrides({ [field]: value });\r\n    if (!rowPrice) return '';\r\n    return this.renderQuantityButton(value, field, isSheet, rowPrice, basePrice, true, 'data-custom-quantity-result=\"true\"');\r\n  }\r\n\r\n  renderQuantityButton(value, field, isSheet, rowPrice, basePrice = null, selected = false, extraAttributes = '') {\r\n    const rowVariantId = this.variantIdForOverrides({ [field]: Number(value) });\r\n    const quantityValues = this.visibleQuantityValues(isSheet);\r\n    const firstQuantity = Number(quantityValues[0] || 0);\r\n    const savings = rowPrice ? this.quantityDiscount(rowPrice, basePrice) : 0;\r\n    const descriptor = Number(value) === firstQuantity ? 'Small-batch order' : '';\r\n    const badge = Number(value) === 100\r\n      ? 'Most popular'\r\n      : Number(value) === 500 ? 'Best value' : '';\r\n    return `\r\n      <button\r\n        type=\"button\"\r\n        class=\"spark-config__quantity-row${selected ? ' is-selected' : ''}\"\r\n        data-choice\r\n        data-field=\"${escapeHtml(field)}\"\r\n        data-value=\"${escapeHtml(value)}\"\r\n        aria-pressed=\"${selected ? 'true' : 'false'}\"\r\n        ${extraAttributes}\r\n      >\r\n        <span class=\"spark-config__quantity-radio\" aria-hidden=\"true\"></span>\r\n        <span class=\"spark-config__quantity-choice\">\r\n          <span class=\"spark-config__quantity-title-line\">\r\n            <span class=\"spark-config__quantity-label\">${this.renderQuantityLabel(value, isSheet, rowPrice)}</span>\r\n            ${badge ? `<span class=\"spark-config__quantity-badge\">${escapeHtml(badge)}</span>` : ''}\r\n          </span>\r\n          ${savings > 0\r\n            ? `<small class=\"spark-config__quantity-savings\">Save ${escapeHtml(savings)}%</small>`\r\n            : descriptor ? `<small>${escapeHtml(descriptor)}</small>` : ''}\r\n        </span>\r\n        <span class=\"spark-config__quantity-pricing\">\r\n          <strong class=\"spark-config__quantity-total\">${rowPrice ? this.moneyMarkup(rowPrice.total, rowVariantId) : '-'}</strong>\r\n        </span>\r\n      </button>\r\n    `;\r\n  }\r\n\r\n  renderCustomQuantityRow(field, isSheet) {\r\n    const label = isSheet ? 'Custom Labels Quantity' : 'Custom Quantity';\r\n    return `\r\n      <div class=\"spark-config__quantity-custom-row is-open\">\r\n        <label for=\"spark-config-custom-quantity-${escapeHtml(field)}\">${escapeHtml(label)}</label>\r\n        <input id=\"spark-config-custom-quantity-${escapeHtml(field)}\" data-input=\"${escapeHtml(field)}\" data-custom-quantity-input type=\"text\" inputmode=\"numeric\" pattern=\"[0-9]*\" autocomplete=\"off\" value=\"${escapeHtml(this.state.customQuantity ? (this.state[field] || '') : '')}\" placeholder=\"${isSheet ? 'Enter label count' : 'Enter quantity'}\">\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  quantityOptions() {\r\n    if (this.profile.engine === 'vista-roll-labels') return this.profile.settings?.rollLabels?.quantities || [];\r\n    if (this.profile.engine === 'vista-magnets') return this.profile.settings?.magnets?.quantities || [];\r\n    if (this.profile.engine === 'jukebox-magnets') return this.profile.settings?.magnets?.quantities || [];\r\n    return this.profile.settings?.quantityPresets || [50, 100, 200, 300, 500, 1000, 2000, 3000, 5000];\r\n  }\r\n\r\n  quantityLabel(value, isSheet, price = null) {\r\n    if (!isSheet) return `${formatNumber(value)} ${this.profile.engine === 'vista-roll-labels' ? 'labels' : 'pcs'}`;\r\n    const sheetFit = price?.sheetFit || this.price?.sheetFit || DEFAULT_LABELS_PER_SHEET;\r\n    const sheets = Math.max(1, Math.ceil(Number(value) / Math.max(1, sheetFit)));\r\n    return `${formatNumber(value)} Labels (${formatNumber(sheets)} Sheets)`;\r\n  }\r\n\r\n  renderQuantityLabel(value, isSheet, price = null) {\r\n    if (!isSheet) return escapeHtml(this.quantityLabel(value, false, price));\r\n    const sheetFit = price?.sheetFit || this.price?.sheetFit || DEFAULT_LABELS_PER_SHEET;\r\n    const sheets = Math.max(1, Math.ceil(Number(value) / Math.max(1, sheetFit)));\r\n    return `${formatNumber(value)} Labels <span class=\"spark-config__quantity-sheets\">(${formatNumber(sheets)} Sheets)</span>`;\r\n  }\r\n\r\n  consumePriceAnimationState() {\r\n    const currentTotal = this.price ? Number(this.price.total || 0) : null;\r\n    const previousTotal = this.lastRenderedPriceTotal;\r\n    this.lastRenderedPriceTotal = Number.isFinite(currentTotal) ? currentTotal : null;\r\n    return Number.isFinite(previousTotal)\r\n      && Number.isFinite(currentTotal)\r\n      && Math.abs(currentTotal - previousTotal) >= 0.01;\r\n  }\r\n\r\n  renderPriceBlock(animate = false) {\r\n    const hasPrice = Boolean(this.price);\r\n    const discount = this.currentDiscount();\r\n    const originalTotal = hasPrice ? this.originalTotalForPrice(this.price, discount) : 0;\r\n    const hasOriginal = hasPrice && Number(originalTotal || 0) > Number(this.price.total || 0) + 0.01;\r\n\r\n    const shippingMessage = 'Free Shipping Canada Wide';\r\n    const shippingMarkup = this.country === 'CA'\r\n      ? `<div class=\"spark-config__shipping\" aria-label=\"${shippingMessage}\">\r\n          <span class=\"spark-config__shipping-icon\" aria-hidden=\"true\">\r\n            <svg class=\"spark-config__shipping-truck\" viewBox=\"0 0 38 28\" focusable=\"false\">\r\n              <path class=\"spark-config__shipping-speed\" d=\"M1 7h5M1 12h5M3 17h3\"/>\r\n              <path fill=\"currentColor\" d=\"M8 4.5A2.5 2.5 0 0 1 10.5 2h14A2.5 2.5 0 0 1 27 4.5V17H8V4.5Z\"/>\r\n              <path fill=\"currentColor\" d=\"M27 8h4.5L37 14v5h-2.6a5.4 5.4 0 0 0-10.8 0H27V8Z\"/>\r\n              <path fill=\"currentColor\" d=\"M8 17h2.1a5.4 5.4 0 0 1 10.8 0h2.7v2H20.9a5.4 5.4 0 0 1-10.8 0H8v-2Z\"/>\r\n              <circle cx=\"15.5\" cy=\"20\" r=\"4\" fill=\"currentColor\"/>\r\n              <circle cx=\"29\" cy=\"20\" r=\"4\" fill=\"currentColor\"/>\r\n              <circle cx=\"15.5\" cy=\"20\" r=\"1.7\" fill=\"#ffe2ca\"/>\r\n              <circle cx=\"29\" cy=\"20\" r=\"1.7\" fill=\"#ffe2ca\"/>\r\n            </svg>\r\n          </span>\r\n          <strong>${shippingMessage}</strong>\r\n        </div>`\r\n      : '';\r\n\r\n    return `\r\n      <div class=\"spark-config__price${hasPrice ? ' has-price' : ' is-empty'}${this.country === 'CA' ? ' has-canada-shipping' : ''}\" data-price>\r\n        <span>Your price</span>\r\n        <div class=\"spark-config__price-stack${animate ? ' is-animated' : ''}\">\r\n          <strong>${hasPrice ? this.moneyMarkup(this.price.total, this.displayVariantId(), true) : 'Choose options'}</strong>\r\n          ${hasOriginal && this.usesBaseCurrency() ? `<del>${formatMoney(originalTotal, this.currency)}</del>` : ''}\r\n        </div>\r\n        ${shippingMarkup}\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  currentDiscount() {\r\n    if (!this.price) return 0;\r\n    const explicit = Math.round(Number(this.price.discount || 0));\r\n    if (explicit > 0) return explicit;\r\n    const originalTotal = Number(this.price.originalTotal || 0);\r\n    const total = Number(this.price.total || 0);\r\n    if (originalTotal > total + 0.01) {\r\n      return Math.max(0, Math.round(((originalTotal - total) / originalTotal) * 100));\r\n    }\r\n\r\n    // Per-label quantity comparisons are badges, not former order prices.\r\n    if (this.profile.engine === 'sheets') return 0;\r\n    const isSheet = this.profile.engine === 'sheets';\r\n    const field = isSheet ? 'labelQuantity' : 'quantity';\r\n    const basePrice = this.baseQuantityPrice(this.visibleQuantityValues(isSheet), field);\r\n    return this.quantityDiscount(this.price, basePrice);\r\n  }\r\n\r\n  quantityDiscount(price, basePrice) {\r\n    if (this.profile.engine === 'sheets') {\r\n      const labels = Number(price?.labelQuantity || price?.quantity || 0);\r\n      const baseLabels = Number(basePrice?.labelQuantity || basePrice?.quantity || 0);\r\n      const total = Number(price?.total || 0);\r\n      const baseTotal = Number(basePrice?.total || 0);\r\n      if (![labels, baseLabels, total, baseTotal].every((value) => Number.isFinite(value) && value > 0)) return 0;\r\n      const unit = total / labels;\r\n      const baseUnit = baseTotal / baseLabels;\r\n      if (labels <= baseLabels || unit >= baseUnit) return 0;\r\n      const tier = getDiscountFromRows(labels, settingValue(this.profile.settings, 'quantityDiscounts', 'quantity_discounts', []));\r\n      const actualSavings = Math.max(0, Math.floor((1 - unit / baseUnit) * 100 + 1e-9));\r\n      return Math.max(0, Math.min(99, Math.floor(tier), actualSavings));\r\n    }\r\n    const explicit = Math.round(Number(price?.discount || 0));\r\n    if (explicit > 0) return explicit;\r\n    const originalTotal = Number(price?.originalTotal || 0);\r\n    const total = Number(price?.total || 0);\r\n    if (originalTotal > total + 0.01) {\r\n      return Math.max(0, Math.round(((originalTotal - total) / originalTotal) * 100));\r\n    }\r\n    if (!['vista-roll-labels', 'vista-magnets'].includes(this.profile.engine)) return 0;\r\n    // Custom roll-label totals come from the exact VPS/R2 price index. Comparing\r\n    // their unit cost with the smallest preset quantity invents a misleading\r\n    // savings percentage, so only show savings supplied by the pricing row.\r\n    if (this.profile.engine === 'vista-roll-labels' && this.state.customSize) return 0;\r\n\r\n    const baseUnit = this.quantityUnit(basePrice);\r\n    const unit = this.quantityUnit(price);\r\n    if (!baseUnit || !unit || unit >= baseUnit) return 0;\r\n    return Math.max(0, Math.round(((baseUnit - unit) / baseUnit) * 100));\r\n  }\r\n\r\n  quantityUnit(price) {\r\n    if (!price) return 0;\r\n    const direct = Number(price.each || price.unit || 0);\r\n    if (direct > 0) return direct;\r\n    const quantity = Number(price.quantity || price.labelQuantity || 0);\r\n    return quantity > 0 ? Number(price.total || 0) / quantity : 0;\r\n  }\r\n\r\n  originalTotalForPrice(price, discount) {\r\n    const explicit = Number(price?.originalTotal || 0);\r\n    if (explicit > Number(price?.total || 0) + 0.01) return explicit;\r\n    const percent = Number(discount || 0);\r\n    if (!price?.total || percent <= 0 || percent >= 100) return 0;\r\n    return Number(price.total) / (1 - (percent / 100));\r\n  }\r\n\r\n  selectionSummaryItems() {\r\n    const items = [];\r\n    const finish = String(this.finishLabel(this.state.finish) || '').trim();\r\n    const meaningfulFinish = !['', 'none', 'no foil', 'no finish'].includes(finish.toLowerCase());\r\n    const quantity = this.profile.engine === 'sheets'\r\n      ? Number(this.price?.labelQuantity || this.state.labelQuantity || this.state.quantity || 0)\r\n      : Number(this.price?.quantity || this.state.quantity || 0);\r\n\r\n    if (this.state.shape) items.push({ label: 'Shape', value: this.shapeLabel(this.state.shape) });\r\n    if (this.state.sizeLabel || this.state.size) items.push({ label: 'Size', value: this.state.sizeLabel || this.state.size });\r\n    if (this.state.material) items.push({ label: 'Material', value: this.materialLabel(this.state.material) });\r\n    if (meaningfulFinish) items.push({ label: 'Finish', value: finish });\r\n\r\n    const laminationType = this.profile.engine === 'stickers'\r\n      ? this.laminationTypeForMaterial(this.state.material)\r\n      : '';\r\n    if (laminationType) {\r\n      items.push({\r\n        label: 'Lamination',\r\n        value: this.state.lamination === 'matched'\r\n          ? `${laminationType === 'matte' ? 'Matte' : 'Gloss'} Lamination`\r\n          : 'No Lamination',\r\n      });\r\n    }\r\n\r\n    if (this.profile.engine === 'vista-roll-labels') {\r\n      const directionLabels = {\r\n        'Right of Copy': 'Right Edge First',\r\n        'Left of Copy': 'Left Edge First',\r\n        'Top of Copy': 'Top Edge First',\r\n        'Bottom of Copy': 'Bottom Edge First',\r\n      };\r\n      items.push({\r\n        label: 'Roll direction',\r\n        value: directionLabels[this.state.unwindDirection] || this.state.unwindDirection || 'Right Edge First',\r\n      });\r\n    }\r\n\r\n    if (this.profile.engine === 'sheets') {\r\n      const artworkVersions = Math.max(1, Number(this.price?.artworkVersions || this.state.artworkVersions || 1));\r\n      items.push({\r\n        label: 'Artwork versions',\r\n        value: `${formatNumber(artworkVersions)} ${artworkVersions === 1 ? 'Artwork' : 'Artworks'}`,\r\n      });\r\n    }\r\n\r\n    if (quantity > 0) {\r\n      items.push({\r\n        label: 'Quantity',\r\n        value: this.quantityLabel(quantity, this.profile.engine === 'sheets', this.price),\r\n      });\r\n    }\r\n\r\n    return items.filter((item) => String(item.value || '').trim());\r\n  }\r\n\r\n  renderSelectionSummary() {\r\n    const items = this.selectionSummaryItems();\r\n    if (!items.length) return '';\r\n    const summary = items.map((item) => item.value).join(' \u00B7 ');\r\n\r\n    return `\r\n      <section class=\"spark-config__selection-summary\" aria-label=\"Order summary\">\r\n        <div class=\"spark-config__selection-summary-head\">\r\n          <span>\r\n            <small>Your selected setup</small>\r\n            <strong>${escapeHtml(summary)}</strong>\r\n          </span>\r\n          <button type=\"button\" data-back-to-options>Edit options</button>\r\n        </div>\r\n      </section>\r\n    `;\r\n  }\r\n\r\n  renderArtworkTotal() {\r\n    return `\r\n      <div class=\"spark-config__order-total\" aria-live=\"polite\">\r\n        <span>Order total</span>\r\n        <strong>${this.price ? this.moneyMarkup(this.price.total, this.displayVariantId(), true) : 'Choose options'}</strong>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  renderArtworkSection() {\r\n    const requiredCount = this.requiredArtworkFileCount();\r\n    const isSheetUpload = this.profile?.engine === 'sheets';\r\n    const fileWord = requiredCount === 1 ? 'file' : 'files';\r\n    const initialHelp = isSheetUpload\r\n      ? `Select ${requiredCount} ${fileWord}, one for each artwork version. ${ARTWORK_FILE_HELP}.`\r\n      : `${ARTWORK_FILE_HELP}.`;\r\n    const willEmailArtwork = this.state.artworkMode === 'email_later';\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--artwork\">\r\n        <div class=\"spark-config__artwork-head\">\r\n          <h3>Upload your artwork</h3>\r\n        </div>\r\n\r\n        ${this.renderSelectionSummary()}\r\n\r\n        <div class=\"spark-config__artwork-mode\" role=\"group\" aria-label=\"Artwork delivery method\">\r\n          <button type=\"button\" class=\"${willEmailArtwork ? '' : 'is-active'}\" data-artwork-mode=\"upload\" aria-pressed=\"${!willEmailArtwork}\">Upload artwork now</button>\r\n          <button type=\"button\" class=\"${willEmailArtwork ? 'is-active' : ''}\" data-artwork-mode=\"email_later\" aria-pressed=\"${willEmailArtwork}\">Email artwork later</button>\r\n          <input data-input=\"artworkMode\" type=\"checkbox\" ${willEmailArtwork ? 'checked' : ''} hidden>\r\n        </div>\r\n\r\n        <div class=\"spark-config__upload-panel\" data-artwork-upload-panel${willEmailArtwork ? ' hidden' : ''}>\r\n          <div class=\"spark-config__upload-grid\">\r\n            <div>\r\n              <label class=\"spark-config__dropzone\" data-artwork-dropzone>\r\n                <input data-artwork-file type=\"file\" accept=\".pdf,.ai,.eps,.png,.jpg,.jpeg,.tif,.tiff,.svg\"${requiredCount > 1 ? ' multiple' : ''} data-required-artwork-files=\"${requiredCount}\" aria-describedby=\"spark-artwork-file-help\">\r\n                <span class=\"spark-config__dropzone-icon\" aria-hidden=\"true\">\r\n                  <svg class=\"spark-config__upload-arrow\" viewBox=\"0 0 512 512\" fill-rule=\"evenodd\" clip-rule=\"evenodd\" focusable=\"false\">\r\n                    <path d=\"M145.227 0h221.546c39.961 0 76.278 16.334 102.589 42.638C495.666 68.942 512 105.262 512 145.224v221.549c0 39.965-16.334 76.278-42.638 102.589C443.051 495.666 406.738 512 366.773 512H145.227c-39.961 0-76.278-16.334-102.589-42.638C16.334 443.051 0 406.738 0 366.773V145.224c0-39.962 16.334-76.282 42.638-102.586C68.949 16.334 105.266 0 145.227 0zm57.614 225.515c-4.073-.173-6.969-1.531-8.64-4.07-4.539-6.801 1.656-13.522 5.946-18.251 12.196-13.373 42.058-45.523 48.077-52.604 4.556-5.035 11.05-5.035 15.603 0 6.216 7.261 37.588 40.877 49.175 53.883 4.019 4.527 8.993 10.704 4.805 16.972-1.711 2.539-4.571 3.897-8.648 4.07h-24.744v61.154c0 6.53-5.356 11.893-11.89 11.893h-33.043c-6.533 0-11.889-5.352-11.889-11.893v-61.154h-24.752zm-74.783 62.033c-1.362-5.622.932-10.038 4.596-12.657 3.664-2.619 8.895-3.1 13.221 6.916 3.694 8.55 3.873 30.135 12.942 42.607 4.812 4.073 13.928 5.482 31.397 5.482h122.695c16.121 0 24.539-1.546 28.962-5.544 4.264-3.854 5.935-11.396 8.1-22.968 1.269-6.707 2.566-13.738 4.257-20.577 1.372-5.637 5.435-8.518 9.902-9.16 4.467-.642 9.619 1.989 14.307 9.917-4.979 22.999-5.296 41.581-18.452 54.798-8.615 8.096-22.115 11.525-46.52 11.525H196.214c-25.522 0-39.551-3.072-48.573-11.065-13.413-11.888-14.847-34.607-19.583-53.758z\"/>\r\n                  </svg>\r\n                </span>\r\n                <span aria-live=\"polite\">\r\n                  <strong data-artwork-file-label>${isSheetUpload ? `Drop or choose ${requiredCount} ${requiredCount === 1 ? 'file' : 'files'}` : 'Drop your artwork here'}</strong>\r\n                  <small class=\"spark-config__browse-copy\">or <span>browse your device</span></small>\r\n                  <small id=\"spark-artwork-file-help\" data-artwork-file-help>${initialHelp}</small>\r\n                  <span class=\"spark-config__upload-progress\" aria-hidden=\"true\"><i></i></span>\r\n                </span>\r\n              </label>\r\n              <ul class=\"spark-config__artwork-file-list\" data-artwork-file-list hidden></ul>\r\n            </div>\r\n\r\n            <aside class=\"spark-config__artwork-trust\" aria-label=\"Artwork reassurance\">\r\n              <h4>Your artwork is checked by a person</h4>\r\n              <ul>\r\n                <li><span aria-hidden=\"true\">&check;</span><div><strong>No print-ready file needed</strong><small>Upload the best artwork you have.</small></div></li>\r\n                <li><span aria-hidden=\"true\">&check;</span><div><strong>Human artwork check</strong><small>We prepare the cut line and flag concerns.</small></div></li>\r\n                <li><span aria-hidden=\"true\">&check;</span><div><strong>Proof before printing</strong><small>Nothing prints until you approve the setup.</small></div></li>\r\n              </ul>\r\n            </aside>\r\n\r\n          </div>\r\n        </div>\r\n\r\n        <div class=\"spark-config__later-panel\" data-artwork-later-panel${willEmailArtwork ? '' : ' hidden'}>\r\n          <span class=\"spark-config__later-icon\" aria-hidden=\"true\">\r\n            <svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.9\"><path d=\"M3 6h18v12H3z\"/><path d=\"m3 7 9 6 9-6\"/></svg>\r\n          </span>\r\n          <h4>Order now, send the file when ready</h4>\r\n          <p>After checkout, use the secure artwork-upload link in your order confirmation. Production waits until the artwork and proof are approved.</p>\r\n          <strong class=\"spark-config__later-confirmation\"><span aria-hidden=\"true\">&check;</span>Your order can be placed without a file today.</strong>\r\n        </div>\r\n\r\n        <div class=\"spark-config__artwork-notes\" data-artwork-notes-wrap>\r\n          <label for=\"spark-artwork-notes\">Artwork notes <span>(optional)</span></label>\r\n          <textarea id=\"spark-artwork-notes\" data-input=\"artworkNotes\" rows=\"4\" aria-label=\"Artwork details\" placeholder=\"Example: Please add a white border and keep the small text as large as possible.\">${escapeHtml(this.state.artworkNotes || '')}</textarea>\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  updateArtworkFileState() {\r\n    const fileInput = this.querySelector('[data-artwork-file]');\r\n    const fileLabel = this.querySelector('[data-artwork-file-label]');\r\n    const fileHelp = this.querySelector('[data-artwork-file-help]');\r\n    const fileList = this.querySelector('[data-artwork-file-list]');\r\n    const notesWrap = this.querySelector('[data-artwork-notes-wrap]');\r\n    const dropzone = this.querySelector('[data-artwork-dropzone]');\r\n    const emailLabel = this.querySelector('[data-artwork-email-label]');\r\n    const uploadPanel = this.querySelector('[data-artwork-upload-panel]');\r\n    const laterPanel = this.querySelector('[data-artwork-later-panel]');\r\n    const uploadModeButton = this.querySelector('[data-artwork-mode=\"upload\"]');\r\n    const laterModeButton = this.querySelector('[data-artwork-mode=\"email_later\"]');\r\n    const willEmailArtwork = this.state.artworkMode === 'email_later';\r\n    const inputFiles = Array.from(fileInput?.files || []);\r\n    if (inputFiles.length && !willEmailArtwork) {\r\n      this.mergeArtworkFiles(inputFiles);\r\n      if (fileInput) fileInput.value = '';\r\n    }\r\n    const artworkFiles = willEmailArtwork ? [] : (inputFiles.length ? inputFiles : (this.artworkFiles || []));\r\n    const requiredCount = this.requiredArtworkFileCount();\r\n    const isSheetUpload = this.profile?.engine === 'sheets';\r\n    const selectedCount = artworkFiles.length;\r\n    const hasRequiredArtworkFiles = selectedCount === requiredCount;\r\n    const currentSelectionKey = artworkFiles.map((file) => `${file.name}:${file.size}:${file.lastModified}`).join('|');\r\n\r\n    if (fileLabel) {\r\n      fileLabel.textContent = hasRequiredArtworkFiles\r\n        ? (isSheetUpload\r\n          ? `${selectedCount} ${selectedCount === 1 ? 'artwork file' : 'artwork files'} selected`\r\n          : 'Artwork selected')\r\n        : (isSheetUpload\r\n          ? `Drop or choose ${requiredCount} ${requiredCount === 1 ? 'file' : 'files'}`\r\n          : 'Drop your artwork here');\r\n    }\r\n\r\n    if (fileHelp) {\r\n      fileHelp.textContent = hasRequiredArtworkFiles\r\n        ? (requiredCount === 1\r\n          ? 'Choose another file to replace it.'\r\n          : 'Choose the files again to replace this selection.')\r\n        : (isSheetUpload\r\n          ? `Select ${requiredCount} ${requiredCount === 1 ? 'file' : 'files'}, one for each artwork version. ${ARTWORK_FILE_HELP}.`\r\n          : `${ARTWORK_FILE_HELP}.`);\r\n    }\r\n\r\n    if (fileList) {\r\n      fileList.hidden = selectedCount === 0;\r\n      fileList.innerHTML = artworkFiles.map((file, index) => `\r\n        <li>\r\n          ${this.renderArtworkFilePreview(file)}\r\n          <span class=\"spark-config__artwork-file-copy\">\r\n            <strong title=\"${escapeHtml(file.name)}\">${escapeHtml(file.name)}</strong>\r\n            <small>${escapeHtml(this.artworkFileSizeLabel(file))} \u00B7 Ready to attach to order</small>\r\n          </span>\r\n          <button class=\"spark-config__artwork-file-remove\" type=\"button\" data-remove-artwork-file=\"${index}\" aria-label=\"Delete ${escapeHtml(file.name)}\">\r\n            <svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.8\" aria-hidden=\"true\"><path d=\"M4 7h16M9 7V4h6v3m-8 0 1 13h8l1-13M10 11v5m4-5v5\"/></svg>\r\n          </button>\r\n        </li>\r\n      `).join('');\r\n    }\r\n\r\n    if (dropzone) {\r\n      if (hasRequiredArtworkFiles && currentSelectionKey !== this.artworkFileSelectionKey) {\r\n        dropzone.classList.remove('is-ready');\r\n        void dropzone.offsetWidth;\r\n      }\r\n      dropzone.classList.toggle('is-ready', hasRequiredArtworkFiles);\r\n      dropzone.classList.toggle('is-incomplete', selectedCount > 0 && !hasRequiredArtworkFiles);\r\n      dropzone.classList.toggle('is-email-later', willEmailArtwork);\r\n    }\r\n\r\n    if (emailLabel) emailLabel.classList.toggle('is-active', willEmailArtwork);\r\n    if (uploadPanel) uploadPanel.hidden = willEmailArtwork;\r\n    if (laterPanel) laterPanel.hidden = !willEmailArtwork;\r\n    if (uploadModeButton) {\r\n      uploadModeButton.classList.toggle('is-active', !willEmailArtwork);\r\n      uploadModeButton.setAttribute('aria-pressed', String(!willEmailArtwork));\r\n    }\r\n    if (laterModeButton) {\r\n      laterModeButton.classList.toggle('is-active', willEmailArtwork);\r\n      laterModeButton.setAttribute('aria-pressed', String(willEmailArtwork));\r\n    }\r\n\r\n    this.artworkFileSelectionKey = currentSelectionKey;\r\n\r\n    if (notesWrap) notesWrap.hidden = false;\r\n\r\n    this.updateAddButtonState();\r\n  }\r\n\r\n  requiredArtworkFileCount() {\r\n    return this.profile?.engine === 'sheets'\r\n      ? Math.max(1, toInteger(this.state.artworkVersions || 1))\r\n      : 1;\r\n  }\r\n\r\n  mergeArtworkFiles(files) {\r\n    const requiredCount = this.requiredArtworkFileCount();\r\n    if (requiredCount === 1) {\r\n      const replacement = files.at(-1);\r\n      (this.artworkFiles || []).forEach((file) => {\r\n        if (file !== replacement) this.releaseArtworkPreviewUrl(file);\r\n      });\r\n      this.artworkFiles = replacement ? [replacement] : [];\r\n      return this.artworkFiles;\r\n    }\r\n\r\n    const previousFiles = this.artworkFiles || [];\r\n    const nextFiles = [...previousFiles, ...files].slice(0, requiredCount);\r\n    const retainedFiles = new Set(nextFiles);\r\n    previousFiles.forEach((file) => {\r\n      if (!retainedFiles.has(file)) this.releaseArtworkPreviewUrl(file);\r\n    });\r\n    this.artworkFiles = nextFiles;\r\n    return this.artworkFiles;\r\n  }\r\n\r\n  renderArtworkFilePreview(file) {\r\n    const previewUrl = this.artworkPreviewUrl(file);\r\n    if (previewUrl) {\r\n      return `<span class=\"spark-config__artwork-file-preview\"><img src=\"${escapeHtml(previewUrl)}\" alt=\"\"></span>`;\r\n    }\r\n\r\n    const extension = String(file?.name || '').split('.').pop()?.toUpperCase() || 'FILE';\r\n\r\n    return `\r\n      <span class=\"spark-config__artwork-file-preview is-document\" aria-hidden=\"true\">\r\n        <svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.7\"><path d=\"M6 2.75h8l4 4V21.25H6z\"/><path d=\"M14 2.75v4h4\"/></svg>\r\n        <strong class=\"spark-config__artwork-file-type\">${escapeHtml(extension)}</strong>\r\n      </span>\r\n    `;\r\n  }\r\n\r\n  artworkPreviewUrl(file) {\r\n    if (!file || !/\\.(?:png|jpe?g|svg)$/i.test(file.name || '') || typeof URL?.createObjectURL !== 'function') return '';\r\n    if (!this.artworkPreviewUrls.has(file)) {\r\n      this.artworkPreviewUrls.set(file, URL.createObjectURL(file));\r\n    }\r\n    return this.artworkPreviewUrls.get(file) || '';\r\n  }\r\n\r\n  artworkFileSizeLabel(file) {\r\n    const bytes = Math.max(0, Number(file?.size || 0));\r\n    if (bytes < 1024 * 1024) return `${Math.max(1, Math.round(bytes / 1024))} KB`;\r\n    return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;\r\n  }\r\n\r\n  releaseArtworkPreviewUrl(file) {\r\n    if (!file || !this.artworkPreviewUrls?.has(file)) return;\r\n    const previewUrl = this.artworkPreviewUrls.get(file);\r\n    if (previewUrl && typeof URL?.revokeObjectURL === 'function') URL.revokeObjectURL(previewUrl);\r\n    this.artworkPreviewUrls.delete(file);\r\n  }\r\n\r\n  clearArtworkPreviewUrls() {\r\n    if (!this.artworkPreviewUrls) return;\r\n    this.artworkPreviewUrls.forEach((previewUrl) => {\r\n      if (previewUrl && typeof URL?.revokeObjectURL === 'function') URL.revokeObjectURL(previewUrl);\r\n    });\r\n    this.artworkPreviewUrls.clear();\r\n  }\r\n\r\n  clearArtworkFiles() {\r\n    this.clearArtworkPreviewUrls();\r\n    this.artworkFiles = [];\r\n  }\r\n\r\n  selectedArtworkFiles() {\r\n    const fileInput = this.querySelector('[data-artwork-file]');\r\n    const inputFiles = Array.from(fileInput?.files || []);\r\n    if (inputFiles.length) {\r\n      this.mergeArtworkFiles(inputFiles);\r\n      if (fileInput) fileInput.value = '';\r\n    }\r\n    return this.state.artworkMode === 'email_later' ? [] : (this.artworkFiles || []);\r\n  }\r\n\r\n  artworkSelectionKey(files = this.selectedArtworkFiles()) {\r\n    return files.map((file) => `${file.name}:${file.size}:${file.type}:${file.lastModified}`).join('|');\r\n  }\r\n\r\n  invalidateArtworkManifest() {\r\n    this.artworkManifestToken = '';\r\n    this.artworkAccessUrl = '';\r\n    this.artworkManifestSelectionKey = '';\r\n    this.artworkUploadProgress = 0;\r\n  }\r\n\r\n  storefrontUploadSessionId() {\r\n    const storageKey = 'spark-storefront-upload-session';\r\n    try {\r\n      const existing = window.sessionStorage.getItem(storageKey);\r\n      if (existing) return existing;\r\n      const generated = `session_${window.crypto.randomUUID().replace(/-/g, '')}`;\r\n      window.sessionStorage.setItem(storageKey, generated);\r\n      return generated;\r\n    } catch (_error) {\r\n      return `session_${Date.now()}_${Math.random().toString(36).slice(2)}`;\r\n    }\r\n  }\r\n\r\n  async ensureArtworkUploaded(files) {\r\n    const context = {stage:'authorization'};\r\n    try { return await this.performArtworkUpload(files, context); }\r\n    catch (error) {\r\n      if (!error.cancelled) {\r\n        const details = {code:'configured_cart_failed', productHandle: this.productHandle, stage:'artwork-upload', uploadStage:context.stage, fileCount:files.length, fileBytes:files.reduce((n,f)=>n+f.size,0), fileTypes:[...new Set(files.map(f=>f.type||'unknown'))].slice(0,5).join(','), error:'Artwork upload failed', errorName:error.name||'Error', httpStatus:Number(error.status)||Number(context.httpStatus)||0, requestAborted:String(error.name==='AbortError'), pagePath:location.pathname};\r\n        try { fetch('https://configurator.sparkstickers.com/api/configurator/cart-failure',{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify(details),keepalive:true}).catch(()=>{}); } catch {}\r\n      }\r\n      throw error;\r\n    }\r\n  }\r\n\r\n  async performArtworkUpload(files, context) {\r\n    const selectionKey = this.artworkSelectionKey(files);\r\n    if (this.artworkManifestToken && this.artworkAccessUrl && this.artworkManifestSelectionKey === selectionKey) return this.artworkManifestToken;\r\n\r\n    this.statusMessage = 'Uploading artwork securely... 0%';\r\n    this.statusType = '';\r\n    this.patchStatusUi();\r\n\r\n    const authorizationResponse = await this.fetchUploadRequest(`${this.uploadApiBase}/api/proofs/storefront-upload-authorize`, {\r\n      method: 'POST',\r\n      headers: { Accept: 'application/json', 'Content-Type': 'application/json' },\r\n      body: JSON.stringify({\r\n        productHandle: this.productHandle,\r\n        sessionId: this.storefrontUploadSessionId(),\r\n        files: files.map((file) => ({\r\n          filename: file.name,\r\n          contentType: file.type || 'application/octet-stream',\r\n          size: file.size,\r\n        })),\r\n      }),\r\n    });\r\n    context.httpStatus = authorizationResponse.status;\r\n    const authorization = await responseJson(authorizationResponse, 'Could not prepare the artwork upload.');\r\n    if (!authorizationResponse.ok) throw new Error(authorization.error || 'Could not prepare the artwork upload.');\r\n    if (!Array.isArray(authorization.uploads) || authorization.uploads.length !== files.length) {\r\n      throw new Error('The artwork upload could not be prepared. Please try again.');\r\n    }\r\n\r\n    const completedBytes = new Array(files.length).fill(0);\r\n    const totalBytes = files.reduce((total, file) => total + file.size, 0);\r\n    const updateProgress = (index, loaded) => {\r\n      completedBytes[index] = Math.min(files[index].size, Number(loaded || 0));\r\n      const uploaded = completedBytes.reduce((total, value) => total + value, 0);\r\n      this.artworkUploadProgress = totalBytes > 0 ? Math.min(100, Math.round((uploaded / totalBytes) * 100)) : 0;\r\n      this.statusMessage = `Uploading artwork securely... ${this.artworkUploadProgress}%`;\r\n      this.patchStatusUi();\r\n    };\r\n\r\n    for (let index = 0; index < files.length; index += 1) {\r\n      context.stage = 'direct-transfer';\r\n      context.httpStatus = 0;\r\n      try {\r\n        await this.uploadFileToSignedUrl(files[index], authorization.uploads[index], (loaded) => updateProgress(index, loaded));\r\n      } catch (directError) {\r\n        const upload = authorization.uploads[index];\r\n        if (directError.cancelled || !upload.relayToken) throw directError;\r\n        context.stage = 'relay-transfer';\r\n        context.httpStatus = 0;\r\n        this.statusMessage = 'Reconnecting your secure artwork upload...';\r\n        this.patchStatusUi();\r\n        try {\r\n          const relay = await fetch(`${this.uploadApiBase}/api/proofs/storefront-upload-relay`, {\r\n            method: 'POST', headers: { 'Content-Type': upload.contentType, Authorization: `Bearer ${upload.relayToken}` },\r\n            body: files[index], signal: AbortSignal.timeout(120000),\r\n          });\r\n          context.httpStatus = relay.status;\r\n          if (!relay.ok) throw new Error(`Upload returned HTTP ${relay.status}.`);\r\n        } catch {\r\n          throw new Error('Your artwork could not be transferred. Download the file to your device and select it again, or choose Email artwork later to continue.');\r\n        }\r\n      }\r\n      updateProgress(index, files[index].size);\r\n    }\r\n\r\n    context.stage = 'completion';\r\n      context.httpStatus = 0;\r\n    const completionResponse = await this.fetchUploadRequest(`${this.uploadApiBase}/api/proofs/storefront-upload-complete`, {\r\n      method: 'POST',\r\n      headers: { Accept: 'application/json', 'Content-Type': 'application/json' },\r\n      body: JSON.stringify({ authorizationToken: authorization.authorizationToken }),\r\n    });\r\n    context.httpStatus = completionResponse.status;\r\n    const completion = await responseJson(completionResponse, 'Could not verify the artwork upload.');\r\n    if (!completionResponse.ok || !completion.manifestToken || !completion.artworkAccessUrl) {\r\n      throw new Error(completion.error || 'Could not verify the artwork upload.');\r\n    }\r\n    this.artworkManifestToken = completion.manifestToken;\r\n    this.artworkAccessUrl = completion.artworkAccessUrl;\r\n    this.artworkManifestSelectionKey = selectionKey;\r\n    this.artworkUploadProgress = 100;\r\n    this.statusMessage = 'Artwork uploaded. Adding your custom item to the cart...';\r\n    this.patchStatusUi();\r\n    return this.artworkManifestToken;\r\n  }\r\n\r\n  async fetchUploadRequest(url, options) {\r\n    const attempts = 3;\r\n    let lastError;\r\n    for (let attempt = 1; attempt <= attempts; attempt += 1) {\r\n      try {\r\n        const response = await fetch(url, { ...options, signal: options.signal || AbortSignal.timeout(30000) });\r\n        if (!this.isRetryableUploadStatus(response.status) || attempt === attempts) return response;\r\n        lastError = new Error(`Upload service returned HTTP ${response.status}.`);\r\n      } catch (error) {\r\n        lastError = error;\r\n        if (attempt === attempts) throw error;\r\n      }\r\n      this.statusMessage = `Connection interrupted. Retrying (${attempt + 1} of ${attempts})...`;\r\n      this.patchStatusUi();\r\n      await this.uploadRetryDelay(attempt);\r\n    }\r\n    throw lastError || new Error('The upload service could not be reached.');\r\n  }\r\n\r\n  async uploadFileToSignedUrl(file, upload, onProgress) {\r\n    const attempts = 3;\r\n    let lastError;\r\n    for (let attempt = 1; attempt <= attempts; attempt += 1) {\r\n      try {\r\n        await this.uploadFileAttempt(file, upload, onProgress);\r\n        return;\r\n      } catch (error) {\r\n        lastError = error;\r\n        if (error.cancelled || (!error.transient && !this.isRetryableUploadStatus(error.status)) || attempt === attempts) throw error;\r\n        this.statusMessage = `Connection interrupted. Retrying ${file.name} (${attempt + 1} of ${attempts})...`;\r\n        this.patchStatusUi();\r\n        await this.uploadRetryDelay(attempt);\r\n      }\r\n    }\r\n    throw lastError;\r\n  }\r\n\r\n  uploadFileAttempt(file, upload, onProgress) {\r\n    return new Promise((resolve, reject) => {\r\n      const request = new XMLHttpRequest();\r\n      request.open('PUT', upload.uploadUrl, true);\r\n      request.setRequestHeader('Content-Type', upload.contentType || file.type || 'application/octet-stream');\r\n      request.upload.addEventListener('progress', (event) => {\r\n        if (event.lengthComputable) onProgress(event.loaded);\r\n      });\r\n      request.addEventListener('load', () => {\r\n        if (request.status >= 200 && request.status < 300) {\r\n          resolve();\r\n          return;\r\n        }\r\n        const error = new Error(`Could not upload ${file.name}. Please try again.`);\r\n        error.status = request.status;\r\n        reject(error);\r\n      });\r\n      request.addEventListener('error', () => {\r\n        const error = new Error(`Could not upload ${file.name}. Check your connection and try again.`);\r\n        error.transient = true;\r\n        reject(error);\r\n      });\r\n      request.addEventListener('timeout', () => {\r\n        const error = new Error(`The upload for ${file.name} timed out. Please try again.`);\r\n        error.transient = true;\r\n        reject(error);\r\n      });\r\n      request.addEventListener('abort', () => {\r\n        const error = new Error(`${file.name} upload was cancelled.`);\r\n        error.cancelled = true;\r\n        reject(error);\r\n      });\r\n      request.timeout = 120000;\r\n      request.send(file);\r\n    });\r\n  }\r\n\r\n  isRetryableUploadStatus(status) {\r\n    return [408, 425, 429].includes(Number(status)) || Number(status) >= 500;\r\n  }\r\n\r\n  uploadRetryDelay(attempt) {\r\n    const delay = 400 * (2 ** (attempt - 1)) + Math.floor(Math.random() * 200);\r\n    return new Promise((resolve) => window.setTimeout(resolve, delay));\r\n  }\r\n\r\n  canSubmitArtwork() {\r\n    const artworkFiles = this.selectedArtworkFiles();\r\n    return this.state.artworkMode === 'email_later' || artworkFiles.length === this.requiredArtworkFileCount();\r\n  }\r\n\r\n  updateAddButtonState() {\r\n    const addButton = this.querySelector('[data-add-to-cart]');\r\n    if (!addButton) return;\r\n    const disabled = this.loading || !this.canSubmitArtwork();\r\n    addButton.disabled = disabled;\r\n    addButton.setAttribute('aria-disabled', String(disabled));\r\n    addButton.setAttribute('aria-busy', String(this.loading));\r\n    const label = addButton.querySelector('[data-add-to-cart-label]');\r\n    if (label) label.textContent = this.addToCartLabel();\r\n  }\r\n\r\n  setupStickyActions() {\r\n    if (this.stickyObserver) {\r\n      this.stickyObserver.disconnect();\r\n      this.stickyObserver = null;\r\n    }\r\n    if (this.stickyScrollController) {\r\n      this.stickyScrollController.abort();\r\n      this.stickyScrollController = null;\r\n    }\r\n\r\n    const stickyActions = this.querySelector('[data-sticky-actions]');\r\n    const inlineActions = this.querySelector('.spark-config__actions');\r\n    if (!stickyActions || !inlineActions || !window.matchMedia('(max-width: 749px)').matches) return;\r\n\r\n    const stickyStart = this.querySelector('.spark-config__section--size') || this.querySelector('.spark-config__section');\r\n    const footer = document.querySelector('.spark-footer, footer');\r\n    let inlineVisible = isElementInViewport(inlineActions);\r\n    let footerVisible = isElementInViewport(footer);\r\n\r\n    const updateReachedOptions = () => {\r\n      if (!stickyStart) {\r\n        this.stickyReachedOptions = window.scrollY > 80;\r\n        return;\r\n      }\r\n      const rect = stickyStart.getBoundingClientRect();\r\n      this.stickyReachedOptions = window.scrollY > 8 && rect.top <= window.innerHeight * 0.86;\r\n    };\r\n\r\n    const updateStickyState = (isInlineVisible) => {\r\n      const hideForInput = this.classList.contains('is-input-active') || this.isTextInputFocused();\r\n      footerVisible = isElementInViewport(footer);\r\n      const shouldShow = Boolean(this.price) && this.stickyReachedOptions && !isInlineVisible && !footerVisible && !hideForInput;\r\n      stickyActions.classList.toggle('is-visible', shouldShow);\r\n      stickyActions.setAttribute('aria-hidden', String(!shouldShow));\r\n    };\r\n\r\n    this.stickyObserver = new IntersectionObserver((entries) => {\r\n      entries.forEach((entry) => {\r\n        if (entry.target === inlineActions) inlineVisible = Boolean(entry.isIntersecting);\r\n        if (entry.target === footer) footerVisible = Boolean(entry.isIntersecting);\r\n      });\r\n      updateStickyState(inlineVisible);\r\n    }, {\r\n      root: null,\r\n      threshold: 0.08,\r\n    });\r\n\r\n    this.stickyScrollController = new AbortController();\r\n    window.addEventListener('scroll', () => {\r\n      updateReachedOptions();\r\n      updateStickyState(inlineVisible);\r\n    }, { passive: true, signal: this.stickyScrollController.signal });\r\n\r\n    this.stickyObserver.observe(inlineActions);\r\n    if (footer) this.stickyObserver.observe(footer);\r\n    updateStickyState(inlineVisible);\r\n  }\r\n\r\n  updateStickyInputState() {\r\n    const stickyActions = this.querySelector('[data-sticky-actions]');\r\n    if (!stickyActions) return;\r\n    const inputActive = this.classList.contains('is-input-active') || this.isTextInputFocused();\r\n    this.classList.toggle('is-input-active', inputActive);\r\n    if (inputActive || !this.price) {\r\n      stickyActions.classList.remove('is-visible');\r\n      stickyActions.setAttribute('aria-hidden', 'true');\r\n      return;\r\n    }\r\n    const inlineActions = this.querySelector('.spark-config__actions');\r\n    const footer = document.querySelector('.spark-footer, footer');\r\n    if (inlineActions && this.stickyReachedOptions && !isElementInViewport(inlineActions) && !isElementInViewport(footer) && window.matchMedia('(max-width: 749px)').matches) {\r\n      stickyActions.classList.add('is-visible');\r\n      stickyActions.setAttribute('aria-hidden', 'false');\r\n    }\r\n  }\r\n\r\n  isTextInputFocused() {\r\n    const active = document.activeElement;\r\n    return Boolean(active && this.contains(active) && isTextEntryControl(active));\r\n  }\r\n\r\n  setInputActive(active) {\r\n    this.classList.toggle('is-input-active', Boolean(active));\r\n    this.updateStickyInputState();\r\n  }\r\n\r\n  async openCartDrawer(cartPayload, variantId) {\r\n    const sections = cartPayload?.sections || {};\r\n    const cartResponse = await fetch('/cart.js', { headers: { Accept: 'application/json' } });\r\n    const cart = cartResponse.ok ? await cartResponse.json() : { items: [], item_count: 0 };\r\n    this.updateCartCount(cart.item_count || 0);\r\n\r\n    try {\r\n      const { CartLinesUpdateEvent } = await import('@shopify/events');\r\n      const deferredEventPromise = CartLinesUpdateEvent.createPromise();\r\n      document.dispatchEvent(\r\n        new CartLinesUpdateEvent({\r\n          action: 'add',\r\n          context: 'product',\r\n          lines: [\r\n            {\r\n              merchandiseId: String(variantId),\r\n              quantity: 1,\r\n            },\r\n          ],\r\n          promise: deferredEventPromise.promise,\r\n        })\r\n      );\r\n\r\n      deferredEventPromise.resolve({\r\n        cart: CartLinesUpdateEvent.createCartFromAjaxResponse(cart),\r\n        detail: {\r\n          sections,\r\n          items: cart.items || [],\r\n          itemCount: cart.item_count || 0,\r\n          source: 'spark-product-configurator',\r\n          sourceId: this.productHandle,\r\n          didError: false,\r\n        },\r\n      });\r\n    } catch (error) {\r\n      // Section replacement below is the authoritative drawer refresh for the custom Spark header.\r\n    }\r\n\r\n    await this.refreshCartDrawer(sections);\r\n\r\n    this.loading = false;\r\n    this.statusMessage = '';\r\n    this.statusType = '';\r\n    this.render();\r\n  }\r\n\r\n  updateCartCount(itemCount) {\r\n    document.querySelectorAll('.spark-cart-count').forEach((node) => {\r\n      node.textContent = String(itemCount);\r\n      node.classList.toggle('is-empty', Number(itemCount) <= 0);\r\n    });\r\n  }\r\n\r\n  async refreshCartDrawer(sections = {}) {\r\n    let cartDrawerHtml = sections['cart-drawer-section'];\r\n\r\n    if (!cartDrawerHtml) {\r\n      const sectionResponse = await fetch(`${window.location.pathname}?sections=cart-drawer-section`, {\r\n        headers: { Accept: 'application/json' },\r\n      });\r\n      if (sectionResponse.ok) {\r\n        const sectionPayload = await sectionResponse.json();\r\n        cartDrawerHtml = sectionPayload['cart-drawer-section'];\r\n      }\r\n    }\r\n\r\n    if (cartDrawerHtml) {\r\n      const parsed = new DOMParser().parseFromString(cartDrawerHtml, 'text/html');\r\n      const nextSection = parsed.getElementById('shopify-section-cart-drawer-section')\r\n        || parsed.querySelector('.shopify-section')\r\n        || parsed.body.firstElementChild;\r\n      const currentSection = document.getElementById('shopify-section-cart-drawer-section');\r\n\r\n      if (nextSection && currentSection) {\r\n        currentSection.replaceWith(document.importNode(nextSection, true));\r\n      }\r\n    }\r\n\r\n    await customElements.whenDefined('theme-drawer').catch(() => {});\r\n    await new Promise((resolve) => requestAnimationFrame(resolve));\r\n    const drawer = document.querySelector('theme-drawer#cart-drawer');\r\n\r\n    if (drawer && typeof drawer.open === 'function') {\r\n      drawer.open();\r\n    } else {\r\n      window.location.href = '/cart';\r\n    }\r\n  }\r\n\r\n  focusArtworkStep(delay = 0, targetMode = 'artwork') {\r\n    window.setTimeout(() => {\r\n      const focusTarget = this.querySelector('[data-artwork-dropzone]') || this.querySelector('.spark-config__section--artwork');\r\n      const target = targetMode === 'page'\r\n        ? (this.querySelector('.spark-config__flow') || this.querySelector('.spark-config--artwork') || this.querySelector('.spark-config__section--artwork') || focusTarget)\r\n        : focusTarget;\r\n      if (!target) return;\r\n      const behavior = window.matchMedia?.('(prefers-reduced-motion: reduce)').matches ? 'auto' : 'smooth';\r\n\r\n      const alignTarget = (scrollBehavior) => {\r\n        const headerOffset = document.querySelector('.spark-header-wrap')?.getBoundingClientRect().height || 0;\r\n        const targetRect = target.getBoundingClientRect();\r\n        const topGap = headerOffset + 12;\r\n        const scrollParent = scrollableParent(target);\r\n\r\n        if (scrollParent && scrollParent !== document.scrollingElement && scrollParent !== document.documentElement) {\r\n          const parentRect = scrollParent.getBoundingClientRect();\r\n          const top = Math.max(0, scrollParent.scrollTop + targetRect.top - parentRect.top - topGap);\r\n          scrollParent.scrollTo({ top, behavior: scrollBehavior });\r\n        } else {\r\n          const top = Math.max(0, targetRect.top + window.scrollY - topGap);\r\n          window.scrollTo({ top, behavior: scrollBehavior });\r\n        }\r\n      };\r\n\r\n      window.requestAnimationFrame(() => {\r\n        window.requestAnimationFrame(() => alignTarget(behavior));\r\n      });\r\n      window.setTimeout(() => alignTarget('auto'), 420);\r\n\r\n      if (typeof focusTarget?.focus === 'function') focusTarget.focus({ preventScroll: true });\r\n    }, delay);\r\n  }\r\n\r\n  renderChoiceSection(title, field, options) {\r\n    const visibleOptions = field === 'shape' ? this.visibleShapeOptions(options) : options;\r\n    if (!visibleOptions?.length) return '';\r\n    const layoutClass = field === 'shape'\r\n      ? (this.profile?.engine === 'vista-roll-labels' ? ' spark-config__section--roll-shape' : ' spark-config__section--five-shape')\r\n      : '';\r\n    const helper = this.choiceSectionHelper(field);\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--${escapeHtml(field)}${layoutClass}\">\r\n        <div class=\"spark-config__section-heading\">\r\n          <h3>${escapeHtml(field === 'material' ? 'Material' : this.selectionTitle(title))}</h3>\r\n          ${helper ? `<small>${escapeHtml(helper)}</small>` : ''}\r\n        </div>\r\n        <div class=\"spark-config__choices\">\r\n          ${visibleOptions.map((option) => {\r\n            const selected = String(this.state[field]) === String(option.value);\r\n            const displayLabel = this.choiceDisplayLabel(field, option.value, option.label);\r\n            return `\r\n              <button\r\n                type=\"button\"\r\n                class=\"spark-config__choice${selected ? ' is-selected' : ''}\"\r\n                data-choice\r\n                data-field=\"${escapeHtml(field)}\"\r\n                data-value=\"${escapeHtml(option.value)}\"\r\n              >\r\n                ${field === 'shape'\r\n                  ? shapeIcon(option.value)\r\n                  : field === 'finish'\r\n                    ? this.renderFinishIcon(option.value)\r\n                    : materialSwatch(option.value, option.label)}\r\n                <span class=\"spark-config__choice-copy\">\r\n                  <span>${escapeHtml(displayLabel)}</span>\r\n                </span>\r\n              </button>\r\n            `;\r\n          }).join('')}\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  choiceSectionHelper(field) {\r\n    return '';\r\n  }\r\n\r\n  choiceDisplayLabel(field, value, label) {\r\n    if (field !== 'material' && field !== 'finish') return label;\r\n    const key = `${value || ''} ${label || ''}`.toLowerCase();\r\n    if (key.includes('matte')) return 'Matte';\r\n    if (key.includes('gloss')) return 'Gloss';\r\n    if (key.includes('clear') || key.includes('transparent')) return 'Clear';\r\n    if (key.includes('holographic')) return 'Holographic';\r\n    const rawLabel = String(label || value || '').replace(/\\s{2,}/g, ' ').trim();\r\n    if (/^vinyl$/i.test(rawLabel)) return 'Vinyl';\r\n    return rawLabel.replace(/\\bvinyl\\b/gi, '').replace(/\\s{2,}/g, ' ').trim();\r\n  }\r\n\r\n  selectionTitle(title) {\r\n    const label = String(title || '').trim();\r\n    if (!label || /^select\\s/i.test(label)) return label;\r\n    return `Select ${label}`;\r\n  }\r\n\r\n  orderedRollShapeValues(values = this.profile.settings?.rollLabels?.shapes) {\r\n    const configuredValues = [...new Set(values || [])];\r\n    const dieCutValues = configuredValues.filter((value) => this.rollShapeLabel(value) === 'Die-Cut');\r\n    const remainingValues = configuredValues.filter((value) => this.rollShapeLabel(value) !== 'Die-Cut');\r\n    return [...dieCutValues, ...remainingValues];\r\n  }\r\n\r\n  rollShapes() {\r\n    return this.orderedRollShapeValues().map((value) => ({ value, label: this.rollShapeLabel(value) }));\r\n  }\r\n\r\n  renderRollDirectionSection() {\r\n    const options = [\r\n      { value: 'Right of Copy', label: 'Right Edge First' },\r\n      { value: 'Left of Copy', label: 'Left Edge First' },\r\n      { value: 'Top of Copy', label: 'Top Edge First' },\r\n      { value: 'Bottom of Copy', label: 'Bottom Edge First' },\r\n    ];\r\n    const selectedValue = options.some((option) => option.value === this.state.unwindDirection)\r\n      ? this.state.unwindDirection\r\n      : options[0].value;\r\n    this.state.unwindDirection = selectedValue;\r\n    return `\r\n      <div class=\"spark-config__section spark-config__section--select\">\r\n        <h3>${escapeHtml(this.selectionTitle('Roll direction'))}</h3>\r\n        <div class=\"spark-config__roll-direction-grid\" role=\"radiogroup\" aria-label=\"Roll direction\">\r\n          ${options.map((option) => `\r\n            <button\r\n              type=\"button\"\r\n              class=\"spark-config__roll-direction${selectedValue === option.value ? ' is-selected' : ''}\"\r\n              data-choice\r\n              data-roll-direction-choice\r\n              data-field=\"unwindDirection\"\r\n              data-value=\"${escapeHtml(option.value)}\"\r\n              role=\"radio\"\r\n              aria-checked=\"${selectedValue === option.value ? 'true' : 'false'}\"\r\n            >\r\n              ${this.renderRollDirectionIcon(option.value)}\r\n              <span>${escapeHtml(option.label)}</span>\r\n            </button>\r\n          `).join('')}\r\n        </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  renderRollDirectionIcon(direction) {\r\n    const orientationRotations = {\r\n      'Right of Copy': 0,\r\n      'Left of Copy': 180,\r\n      'Top of Copy': 90,\r\n      'Bottom of Copy': -90,\r\n    };\r\n    const rotation = orientationRotations[direction] ?? orientationRotations['Right of Copy'];\r\n    return `\r\n      <svg class=\"spark-config__roll-direction-icon\" viewBox=\"0 0 96 74\" aria-hidden=\"true\">\r\n        <g class=\"spark-config__roll-web\">\r\n          <path d=\"M18 12h36v40H18z\"/>\r\n          <path d=\"M18 46h36v6H18z\"/>\r\n        </g>\r\n        <g class=\"spark-config__roll-label-face\" transform=\"rotate(${rotation} 36 31)\">\r\n          <rect x=\"23\" y=\"17\" width=\"26\" height=\"28\" rx=\"1.5\"/>\r\n          <path d=\"M26 20h20v22H26z\"/>\r\n          <text x=\"36\" text-anchor=\"middle\" class=\"spark-config__roll-direction-brand\">\r\n            <tspan x=\"36\" y=\"29\">SPARK</tspan>\r\n            <tspan x=\"36\" y=\"35\" class=\"spark-config__roll-direction-brand-subline\">STICKERS</tspan>\r\n          </text>\r\n        </g>\r\n        <g class=\"spark-config__roll-spool\">\r\n          <path d=\"M14 51v7c0 5 10 8 22 8s22-3 22-8v-7\"/>\r\n          <ellipse cx=\"36\" cy=\"51\" rx=\"22\" ry=\"7\"/>\r\n          <ellipse cx=\"36\" cy=\"51\" rx=\"7\" ry=\"2.8\"/>\r\n          <path d=\"M29 54c2 1 4.3 1.5 7 1.5s5-.5 7-1.5\"/>\r\n        </g>\r\n        <g class=\"spark-config__roll-feed-arrow\">\r\n          <path d=\"M59 31h27m-5-5 5 5-5 5\"/>\r\n        </g>\r\n      </svg>\r\n    `;\r\n  }\r\n\r\n  rollSizes() {\r\n    const model = this.profile.settings?.rollLabels || {};\r\n    const values = model.compatible_sizes_by_shape?.[this.state.shape] || model.fixed_sizes || [];\r\n    return values.map((value) => ({ value, label: value === 'Custom' ? 'Custom Size' : value.replace('x', ' x ') }));\r\n  }\r\n\r\n  rollFinishes(material = this.state.material) {\r\n    const model = this.profile.settings?.rollLabels || {};\r\n    const preferredOrder = ['Matte', 'Gloss', 'Soft Touch'];\r\n    const availableFinishes = new Set(\r\n      (this.localMatrix?.rows || [])\r\n        .filter((row) => row.criteria?.material === material && row.criteria?.finish)\r\n        .map((row) => row.criteria.finish),\r\n    );\r\n    const supportedValues = availableFinishes.size\r\n      ? (model.finishes || []).filter((value) => availableFinishes.has(value))\r\n      : (model.finishes || []);\r\n    const values = [\r\n      ...preferredOrder.filter((value) => supportedValues.includes(value)),\r\n      ...supportedValues.filter((value) => !preferredOrder.includes(value)),\r\n    ];\r\n    return values.map((value) => ({ value, label: value }));\r\n  }\r\n\r\n  renderRollFinishSection() {\r\n    return this.renderChoiceSection('Finish', 'finish', this.rollFinishes());\r\n  }\r\n\r\n  renderFinishIcon(finish) {\r\n    const key = String(finish || '').toLowerCase().replace(/\\s+/g, '-');\r\n    if (key === 'soft-touch') {\r\n      return '<span class=\"spark-config__finish-swatch spark-config__finish-swatch--soft-touch\" aria-hidden=\"true\"><svg viewBox=\"0 0 28 28\"><path d=\"M4 9c4-4 8-4 12 0s6 4 8 1M4 14c4-4 8-4 12 0s6 4 8 1M4 19c4-4 8-4 12 0s6 4 8 1\"/></svg></span>';\r\n    }\r\n    if (key === 'matte') return '<span class=\"spark-config__finish-swatch spark-config__finish-swatch--matte\" aria-hidden=\"true\"></span>';\r\n    return '<span class=\"spark-config__finish-swatch spark-config__finish-swatch--gloss\" aria-hidden=\"true\"></span>';\r\n  }\r\n\r\n  magnetShapes() {\r\n    return (this.profile.settings?.magnets?.shapes || []).map((value) => ({ value, label: value }));\r\n  }\r\n\r\n  magnetSizes() {\r\n    const model = this.profile.settings?.magnets || {};\r\n    const values = model.compatible_sizes_by_shape?.[this.state.shape] || model.sizes || [];\r\n    return values.map((value) => ({ value, label: value }));\r\n  }\r\n\r\n  magnetOrientations() {\r\n    const model = this.profile.settings?.magnets || {};\r\n    const values = model.compatible_orientations_by_shape?.[this.state.shape] || model.orientations || [];\r\n    return values.map((value) => ({ value, label: value }));\r\n  }\r\n\r\n  magnetFinishes() {\r\n    const model = this.profile.settings?.magnets || {};\r\n    const compatible = model.compatibility?.[this.state.shape]?.[this.state.size]?.[this.state.orientation];\r\n    const values = compatible || model.finishes || [];\r\n    return values.map((value) => ({ value, label: value }));\r\n  }\r\n\r\n  materialLabel(value) {\r\n    const option = this.materialOptions().find((item) => item.value === value);\r\n    return this.choiceDisplayLabel('material', value, option?.label || value);\r\n  }\r\n\r\n  finishLabel(value) {\r\n    const source = this.profile.settings?.sheetFinishes || {};\r\n    return this.choiceDisplayLabel('finish', value, source[value]?.label || value);\r\n  }\r\n\r\n  shapeLabel(value) {\r\n    if (this.profile.engine === 'vista-roll-labels') {\r\n      return this.rollShapeLabel(value);\r\n    }\r\n\r\n    return labelFor(value, this.profile.settings?.shapes);\r\n  }\r\n\r\n  rollShapeLabel(value) {\r\n    return value === 'Custom' ? 'Die-Cut' : value;\r\n  }\r\n}\r\n\r\nfunction shapeIcon(value) {\r\n  const key = String(value || '').toLowerCase().replace(/[^a-z]/g, '');\r\n  const shapes = {\r\n    circle: 'circle',\r\n    square: 'square',\r\n    rectangle: 'rectangle',\r\n    rounded: 'rounded',\r\n    roundedrectangle: 'rounded-rectangle',\r\n    roundedsquare: 'rounded',\r\n    oval: 'oval',\r\n    diecut: 'diecut',\r\n    custom: 'diecut',\r\n  };\r\n  const icon = shapes[key] || shapes.diecut;\r\n  return `<svg class=\"spark-config__shape-icon\" viewBox=\"0 0 64 64\" aria-hidden=\"true\" focusable=\"false\"><use href=\"#spark-shape-icon-${icon}\"></use></svg>`;\r\n}\r\n\r\nfunction materialSwatch(value, label) {\r\n  const lower = `${value} ${label}`.toLowerCase();\r\n  if (!/(vinyl|clear|holographic|foil|paper|matte|gloss|plastic|silver|gold)/.test(lower)) return '';\r\n  return `<i class=\"spark-config__swatch spark-config__swatch--${swatchClass(lower)}\" aria-hidden=\"true\"></i>`;\r\n}\r\n\r\nfunction swatchClass(value) {\r\n  if (value.includes('holographic')) return 'holographic';\r\n  if (value.includes('gold')) return 'gold';\r\n  if (value.includes('silver')) return 'silver';\r\n  if (value.includes('clear')) return 'clear';\r\n  if (value.includes('gloss')) return 'gloss';\r\n  if (value.includes('plastic') || value.includes('vinyl')) return 'vinyl';\r\n  return 'paper';\r\n}\r\n\r\nfunction labelFor(value, map) {\r\n  return map?.[value] || value;\r\n}\r\n\r\nfunction parseSize(value) {\r\n  const match = String(value || '').match(/([\\d.]+)\\s*\"?\\s*x\\s*([\\d.]+)/i);\r\n  return {\r\n    width: match ? Number(match[1]) : 0,\r\n    height: match ? Number(match[2]) : 0,\r\n  };\r\n}\r\n\r\nfunction normalizeSizeKey(value) {\r\n  const size = parseSize(value);\r\n  if (!size.width || !size.height) return String(value || '').replace(/\\s+/g, '').toLowerCase();\r\n  return `${formatSizeNumber(size.width)}x${formatSizeNumber(size.height)}`;\r\n}\r\n\r\nfunction formatSizeNumber(value) {\r\n  const number = Number(value || 0);\r\n  if (!Number.isFinite(number)) return '0';\r\n  return Number.isInteger(number) ? String(number) : String(Number(number.toFixed(2))).replace(/\\.?0+$/, '');\r\n}\r\n\r\nfunction formatSizeLabel(width, height, spaced = true) {\r\n  const joiner = spaced ? '\" x ' : '\"x';\r\n  return `${formatSizeNumber(width)}${joiner}${formatSizeNumber(height)}\"`;\r\n}\r\n\r\nfunction sizesMatch(expected, actual) {\r\n  if (String(actual ?? '') === String(expected ?? '')) return true;\r\n  const expectedSize = parseSize(expected);\r\n  const actualSize = parseSize(actual);\r\n  if (!expectedSize.width || !expectedSize.height || !actualSize.width || !actualSize.height) return false;\r\n  const exact = Number(expectedSize.width) === Number(actualSize.width) && Number(expectedSize.height) === Number(actualSize.height);\r\n  const swapped = Number(expectedSize.width) === Number(actualSize.height) && Number(expectedSize.height) === Number(actualSize.width);\r\n  return exact || swapped;\r\n}\r\n\r\nfunction toNumber(value) {\r\n  const number = Number.parseFloat(String(value ?? '').replace(',', '.'));\r\n  return Number.isFinite(number) ? number : 0;\r\n}\r\n\r\nfunction toInteger(value) {\r\n  const number = Number.parseInt(String(value ?? '').replace(/[^\\d]/g, ''), 10);\r\n  return Number.isFinite(number) ? number : 0;\r\n}\r\n\r\nfunction numberValue(value, fallback = 0) {\r\n  const number = Number.parseFloat(value);\r\n  return Number.isFinite(number) ? number : fallback;\r\n}\r\n\r\nfunction roundMoney(value) {\r\n  const number = Number.parseFloat(value);\r\n  return Number.isFinite(number) ? Math.round((number + Number.EPSILON) * 100) / 100 : 0;\r\n}\r\n\r\nfunction configuredVariantLabel(price) {\r\n  return `Made to order - $${Number(price).toFixed(2)}`;\r\n}\r\n\r\nfunction stablePayloadKey(payload) {\r\n  return Object.keys(payload || {})\r\n    .sort()\r\n    .map((key) => `${key}:${String(payload[key])}`)\r\n    .join('|');\r\n}\r\n\r\nfunction rollLabelCustomIndexKey(widthIndex, heightIndex, materialIndex, finishIndex, quantityIndex) {\r\n  return [widthIndex, heightIndex, materialIndex, finishIndex, quantityIndex].join('|');\r\n}\r\n\r\nfunction indexValueIndex(values = [], value) {\r\n  return values.indexOf(value);\r\n}\r\n\r\nfunction settingValue(settings, camelKey, snakeKey, fallback = undefined) {\r\n  return settings?.[camelKey] ?? settings?.[snakeKey] ?? fallback;\r\n}\r\n\r\nfunction getDiscountFromRows(quantity, rows) {\r\n  let discount = 0;\r\n  (Array.isArray(rows) ? rows : [])\r\n    .map((row) => ({\r\n      min: toInteger(row.min ?? row.minimum ?? row.min_quantity ?? row.minQuantity),\r\n      discount: numberValue(row.discount, 0),\r\n    }))\r\n    .filter((row) => row.min > 0)\r\n    .sort((a, b) => a.min - b.min)\r\n    .forEach((row) => {\r\n      if (quantity >= row.min) discount = row.discount;\r\n    });\r\n  return discount;\r\n}\r\n\r\nfunction rollLabelDiscount(settings, quantity) {\r\n  return getDiscountFromRows(quantity, settingValue(settings, 'rollLabelDiscountLadder', 'roll_label_discount_ladder', []));\r\n}\r\n\r\nfunction priceProfileMultiplier(settings, priceProfile = '') {\r\n  const markups = settingValue(settings, 'priceProfileMarkups', 'price_profile_markups', {});\r\n  const profileMarkup = numberValue(markups?.[priceProfile], 0);\r\n  return 1 + profileMarkup / 100;\r\n}\r\n\r\nfunction preciseReferenceNumber(value) {\r\n  return Number(Number(value).toFixed(10));\r\n}\r\n\r\nfunction calculateReferencePrice(settings, payload) {\r\n  const reference = settingValue(settings, 'referencePricing', 'reference_pricing');\r\n  const width = Math.max(0, numberValue(payload.width, 0));\r\n  const height = Math.max(0, numberValue(payload.height, 0));\r\n  const quantity = Math.max(0, toInteger(payload.quantity));\r\n  const category = String(payload.category || '');\r\n  const material = String(payload.material || '');\r\n  const curve = reference?.materialCurves?.[material] || reference?.curve;\r\n  const areaBands = Array.isArray(curve?.areaBands) ? curve.areaBands : [];\r\n  if (!reference || reference.category !== category || !width || !height || !quantity || !areaBands.length) return null;\r\n\r\n  const area = preciseReferenceNumber(width * height);\r\n  const areaBand = areaBands.find((band) => area <= numberValue(band.maxArea, 0)) || areaBands.at(-1);\r\n  const quantityBands = Array.isArray(areaBand?.quantityBands) ? areaBand.quantityBands : [];\r\n  const quantityBand = quantityBands.find((band) => quantity <= toInteger(band.maxQuantity)) || quantityBands.at(-1);\r\n  if (!quantityBand) return null;\r\n\r\n  const baseRate = numberValue(curve.baseRate, 0);\r\n  let referenceTotal = preciseReferenceNumber(area * baseRate * quantity * numberValue(quantityBand.factor, 0));\r\n  const areaIndex = areaBands.indexOf(areaBand);\r\n  const lastAreaIndex = payload.sizeMonotonic === true ? areaBands.length - 1 : areaIndex;\r\n  for (let index = areaIndex; index <= lastAreaIndex; index += 1) {\r\n    // Match the server's lower envelope over both size and quantity bands.\r\n    const candidateArea = index === areaIndex ? area : numberValue(areaBands[index - 1].maxArea, 0);\r\n    if (index !== areaIndex && candidateArea >= (payload.maximumArea ?? Infinity)) break;\r\n    const bands = areaBands[index].quantityBands;\r\n    const selected = bands.find((band) => quantity <= toInteger(band.maxQuantity)) || bands.at(-1);\r\n    const selectedIndex = bands.indexOf(selected);\r\n    for (let quantityIndex = selectedIndex; quantityIndex < bands.length; quantityIndex += 1) {\r\n      const candidateQuantity = quantityIndex === selectedIndex\r\n        ? quantity : toInteger(bands[quantityIndex - 1].maxQuantity) + 1;\r\n      referenceTotal = Math.min(referenceTotal, preciseReferenceNumber(\r\n        candidateArea * baseRate * candidateQuantity * numberValue(bands[quantityIndex].factor, 0),\r\n      ));\r\n    }\r\n  }\r\n\r\n  const materialMultiplier = Math.max(0.000001, numberValue(reference.materialMultipliers?.[material], 1));\r\n  const sourceAdjustmentPercent = Math.min(99.999999, Math.max(0, numberValue(reference.sourceAdjustmentPercent, 0)));\r\n  const sourceMaterialMultiplier = Math.max(0.000001, numberValue(\r\n    category === 'sheets'\r\n      ? reference.sourceMaterialMultipliers?.vinyl\r\n      : reference.sourceMaterialMultipliers?.[material],\r\n    1,\r\n  ));\r\n  const adjustmentPercent = Math.min(99.999999, Math.max(0, numberValue(reference.adjustmentPercent, 0)));\r\n  const additionalMultiplier = Math.max(0.000001, numberValue(payload.additionalMultiplier, 1));\r\n  const minimum = Math.max(0, numberValue(payload.minimum, numberValue(settingValue(settings, 'minimumPrice', 'minimum_price'), 30)));\r\n  const sourceTotal = sourceAdjustmentPercent > 0 || sourceMaterialMultiplier !== 1\r\n    ? roundMoney(referenceTotal * (1 - sourceAdjustmentPercent / 100) * sourceMaterialMultiplier)\r\n    : referenceTotal;\r\n  const vinylMaterialMultiplier = Math.max(0.000001, numberValue(reference.materialMultipliers?.vinyl, 1));\r\n  const directCalculatedTotal = roundMoney(\r\n    sourceTotal * (1 - adjustmentPercent / 100) * materialMultiplier * additionalMultiplier,\r\n  );\r\n  const vinylCalculatedTotal = roundMoney(\r\n    sourceTotal * (1 - adjustmentPercent / 100) * vinylMaterialMultiplier * additionalMultiplier,\r\n  );\r\n  const calculatedTotal = category === 'sheets' && (material === 'clear' || material === 'holographic')\r\n    ? roundMoney(vinylCalculatedTotal * (materialMultiplier / vinylMaterialMultiplier))\r\n    : directCalculatedTotal;\r\n  const total = roundMoney(Math.max(\r\n    minimum,\r\n    calculatedTotal,\r\n  ));\r\n\r\n  return {\r\n    total,\r\n    unit: roundMoney(total / quantity),\r\n    each: total / quantity,\r\n    quantity,\r\n    material,\r\n    category,\r\n    pricingModel: 'reference_bands',\r\n    referenceVersion: reference.version,\r\n    referenceCurve: reference?.materialCurves?.[material] ? material : 'default',\r\n    referenceTotal,\r\n    sourceTotal,\r\n    sourceAdjustmentPercent,\r\n    sourceMaterialMultiplier,\r\n    categoryAdjustmentPercent: adjustmentPercent,\r\n    materialMultiplier,\r\n    additionalMultiplier,\r\n  };\r\n}\r\n\r\nfunction stickerLaminationType(settings, material) {\r\n  const materialSettings = settingValue(settings, 'materials', 'materials', {})?.[material] || {};\r\n  const key = String(material || '').toLowerCase();\r\n  const label = String(materialSettings.label || '').toLowerCase();\r\n  if (key.includes('clear') || label.includes('clear') || key.includes('hangtag') || label.includes('hang tag')) return '';\r\n  if (key.includes('matte') || label.includes('matte')) return 'matte';\r\n  if (key.includes('gloss') || label.includes('gloss') || key === 'vinyl' || label === 'vinyl') return 'gloss';\r\n  return '';\r\n}\r\n\r\nfunction calculateJukeboxMagnetPrice(settings, payload) {\r\n  const pricing = settingValue(settings, 'magnetPricing', 'magnet_pricing');\r\n  const options = settingValue(settings, 'magnets', 'magnets', {});\r\n  const customSize = options?.custom_size || options?.customSize || {};\r\n  const width = Math.max(0, numberValue(payload.width, 0));\r\n  const height = Math.max(0, numberValue(payload.height, 0));\r\n  const quantity = Math.max(0, toInteger(payload.quantity));\r\n  const quantities = Array.isArray(options?.quantities) ? options.quantities.map(toInteger) : [];\r\n  const minWidth = numberValue(customSize.min_width ?? customSize.minWidth, 1);\r\n  const minHeight = numberValue(customSize.min_height ?? customSize.minHeight, 1);\r\n  const maxWidth = numberValue(customSize.max_width ?? customSize.maxWidth, 52);\r\n  const maxHeight = numberValue(customSize.max_height ?? customSize.maxHeight, 72);\r\n\r\n  if (!pricing || width < minWidth || height < minHeight || width > maxWidth || height > maxHeight) return null;\r\n  const minimumQuantity = Math.min(...quantities.filter((value) => value > 0), 25);\r\n  if (quantity < minimumQuantity) return null;\r\n\r\n  const sizeLabel = payload.sizeLabel && payload.sizeLabel !== 'Custom'\r\n    ? String(payload.sizeLabel)\r\n    : formatSizeLabel(width, height, true);\r\n  const presetTotal = numberValue(pricing.basePrices?.[sizeLabel]?.[String(quantity)], 0);\r\n  const sourceTotal = presetTotal > 0\r\n    ? presetTotal\r\n    : calculateJukeboxCustomSourceTotal(pricing, width, height, quantity, pricing.basePrices?.[sizeLabel]);\r\n\r\n  if (!sourceTotal || sourceTotal > numberValue(pricing.maximumSourceTotal, 200000)) return null;\r\n\r\n  const markupPercent = numberValue(pricing.markupPercent, 50);\r\n  const minimum = numberValue(settingValue(settings, 'minimumPrice', 'minimum_price'), 30);\r\n  const total = roundMoney(Math.max(minimum, sourceTotal * (1 + markupPercent / 100)));\r\n\r\n  return {\r\n    total,\r\n    unit: roundMoney(total / quantity),\r\n    each: total / quantity,\r\n    discount: 0,\r\n    originalTotal: total,\r\n    quantity,\r\n    shape: String(payload.shape || 'diecut'),\r\n    width,\r\n    height,\r\n    sizeLabel,\r\n    sourceTotal,\r\n    markupPercent,\r\n    pricingModel: presetTotal > 0\r\n      ? 'jukebox_exact_table'\r\n      : (pricing.basePrices?.[sizeLabel] ? 'jukebox_interpolated_quantity' : 'jukebox_calibrated_custom_size'),\r\n    sourceProvider: pricing.sourceProvider || 'Jukebox Print',\r\n    key: [String(payload.shape || 'diecut'), sizeLabel, quantity].join('|'),\r\n  };\r\n}\r\n\r\nfunction calculateJukeboxCustomSourceTotal(pricing, width, height, quantity, presetRow = null) {\r\n  const presetTotal = interpolateMagnetPriceRow(presetRow, quantity);\r\n  if (presetTotal !== null) return presetTotal;\r\n\r\n  const curve = interpolateMagnetCurve(pricing.customPriceCurves, quantity);\r\n  if (!curve) return 0;\r\n\r\n  return Math.round(\r\n    numberValue(curve.setup, 0)\r\n    + numberValue(curve.area, 0) * width * height\r\n    + numberValue(curve.dimension_sum ?? curve.dimensionSum, 0) * (width + height),\r\n  );\r\n}\r\n\r\nfunction interpolateMagnetPriceRow(row, quantity) {\r\n  const points = Object.entries(row || {})\r\n    .map(([key, value]) => ({ quantity: toInteger(key), total: numberValue(value, 0) }))\r\n    .filter((point) => point.quantity > 0 && point.total > 0)\r\n    .sort((a, b) => a.quantity - b.quantity);\r\n\r\n  if (!points.length) return null;\r\n  return interpolateMagnetNumber(points, quantity, 'total');\r\n}\r\n\r\nfunction interpolateMagnetCurve(curves, quantity) {\r\n  const points = Object.entries(curves || {})\r\n    .map(([key, value]) => ({\r\n      quantity: toInteger(key),\r\n      setup: numberValue(value?.setup, 0),\r\n      area: numberValue(value?.area, 0),\r\n      dimension_sum: numberValue(value?.dimension_sum ?? value?.dimensionSum, 0),\r\n    }))\r\n    .filter((point) => point.quantity > 0)\r\n    .sort((a, b) => a.quantity - b.quantity);\r\n\r\n  if (!points.length) return null;\r\n  if (points.length === 1) return points[0];\r\n\r\n  const upperIndex = points.findIndex((point) => point.quantity >= quantity);\r\n  const upper = upperIndex >= 0 ? points[upperIndex] : points[points.length - 1];\r\n  const lower = upperIndex > 0\r\n    ? points[upperIndex - 1]\r\n    : (upperIndex === 0 ? points[0] : points[points.length - 2]);\r\n  if (upper.quantity === lower.quantity) return upper;\r\n\r\n  const ratio = (quantity - lower.quantity) / (upper.quantity - lower.quantity);\r\n  return {\r\n    setup: interpolateMagnetValue(lower.setup, upper.setup, ratio),\r\n    area: interpolateMagnetValue(lower.area, upper.area, ratio),\r\n    dimension_sum: interpolateMagnetValue(lower.dimension_sum, upper.dimension_sum, ratio),\r\n  };\r\n}\r\n\r\nfunction interpolateMagnetNumber(points, quantity, field) {\r\n  if (points.length === 1) return points[0][field];\r\n  const upperIndex = points.findIndex((point) => point.quantity >= quantity);\r\n  const upper = upperIndex >= 0 ? points[upperIndex] : points[points.length - 1];\r\n  const lower = upperIndex > 0\r\n    ? points[upperIndex - 1]\r\n    : (upperIndex === 0 ? points[0] : points[points.length - 2]);\r\n  if (upper.quantity === lower.quantity) return lower[field];\r\n  const ratio = (quantity - lower.quantity) / (upper.quantity - lower.quantity);\r\n  return Math.round(interpolateMagnetValue(lower[field], upper[field], ratio));\r\n}\r\n\r\nfunction interpolateMagnetValue(lower, upper, ratio) {\r\n  return lower + (upper - lower) * ratio;\r\n}\r\n\r\nfunction stickerLaminationMultiplier(settings, lamination, material) {\r\n  if (lamination !== 'matched' || !stickerLaminationType(settings, material)) return 1;\r\n  const markup = numberValue(settingValue(settings, 'laminationMarkup', 'lamination_markup'), 0);\r\n  return 1 + Math.max(0, markup) / 100;\r\n}\r\n\r\nfunction calculateStickerPrice(settings, payload, profile) {\r\n  const width = Math.max(0, numberValue(payload.width, 0));\r\n  const height = Math.max(0, numberValue(payload.height, 0));\r\n  const quantity = Math.max(0, toInteger(payload.quantity));\r\n  const priceProfile = profile?.priceProfile || payload.priceProfile || payload.price_profile || '';\r\n  const maximumSide = priceProfile === 'hang-tags' ? 12 : 52;\r\n  if (width < 0.5 || height < 0.5 || !quantity || width > maximumSide || height > maximumSide) return null;\r\n  const profiles = settingValue(settings, 'priceProfiles', 'price_profiles', {});\r\n  const profileSettings = profiles?.[priceProfile] || {};\r\n  const minimum = numberValue(profileSettings.minimum_price ?? profileSettings.minimumPrice, numberValue(settingValue(settings, 'minimumPrice', 'minimum_price'), 30));\r\n  const material = payload.material || profile?.defaultMaterial || 'vinylmatte';\r\n  const category = priceProfile === 'hang-tags' ? 'hang_tags' : 'stickers';\r\n  const referencePrice = calculateReferencePrice(settings, {\r\n    category,\r\n    width,\r\n    height,\r\n    quantity,\r\n    material,\r\n    minimum,\r\n    additionalMultiplier: priceProfileMultiplier(settings, priceProfile)\r\n      * stickerLaminationMultiplier(settings, payload.lamination || 'none', material),\r\n    sizeMonotonic: category === 'stickers',\r\n    maximumArea: 52 * 52,\r\n  });\r\n  if (!referencePrice) return null;\r\n\r\n  const total = referencePrice.total;\r\n  const discount = getDiscountFromRows(quantity, settingValue(settings, 'quantityDiscounts', 'quantity_discounts', []));\r\n  const originalTotal = discount > 0 && discount < 100 ? roundMoney(total / (1 - discount / 100)) : total;\r\n\r\n  return {\r\n    ...referencePrice,\r\n    total,\r\n    unit: roundMoney(total / quantity),\r\n    each: total / quantity,\r\n    discount,\r\n    originalTotal,\r\n    quantity,\r\n    material,\r\n    sizeLabel: payload.sizeLabel || formatSizeLabel(width, height, true),\r\n    priceProfile,\r\n  };\r\n}\r\n\r\nfunction calculateSheetGridFit(stickerWidth, stickerHeight, sheetWidth, sheetHeight, gap, margin) {\r\n  const safeGap = Math.max(0, numberValue(gap, SHEET_LABEL_GAP_INCHES));\r\n  const safeMargin = Math.max(0, numberValue(margin, SHEET_SAFE_MARGIN_INCHES));\r\n  const usableWidth = Math.max(0, numberValue(sheetWidth, 8.5) - (safeMargin * 2));\r\n  const usableHeight = Math.max(0, numberValue(sheetHeight, 11) - (safeMargin * 2));\r\n  const columns = Math.floor((usableWidth + safeGap) / (Math.max(0.01, numberValue(stickerWidth, 0)) + safeGap));\r\n  const rows = Math.floor((usableHeight + safeGap) / (Math.max(0.01, numberValue(stickerHeight, 0)) + safeGap));\r\n  return Math.max(0, columns * rows);\r\n}\r\n\r\nfunction calculateSheetFit(\r\n  width,\r\n  height,\r\n  sheetWidth = 8.5,\r\n  sheetHeight = 11,\r\n  gap = SHEET_LABEL_GAP_INCHES,\r\n  margin = SHEET_SAFE_MARGIN_INCHES,\r\n) {\r\n  return Math.max(\r\n    calculateSheetGridFit(width, height, sheetWidth, sheetHeight, gap, margin),\r\n    calculateSheetGridFit(height, width, sheetWidth, sheetHeight, gap, margin),\r\n  );\r\n}\r\n\r\nfunction sheetDisplayDiscount(settings, sheetQuantity, configuredDiscount) {\r\n  const rows = settingValue(settings, 'sheetDiscountLadder', 'sheet_discount_ladder', []);\r\n  let discount = 0;\r\n  let matched = false;\r\n\r\n  (Array.isArray(rows) ? rows : []).forEach((row) => {\r\n    const minSheets = toInteger(row.min_sheets ?? row.minSheets ?? row.min);\r\n    if (minSheets > 0 && sheetQuantity >= minSheets) {\r\n      discount = numberValue(row.discount, 0);\r\n      matched = true;\r\n    }\r\n  });\r\n\r\n  return matched ? discount : numberValue(configuredDiscount, 0);\r\n}\r\n\r\nfunction isSheetFinishAvailableForMaterial(material, finish) {\r\n  if (['none', 'goldfoil', 'silverfoil'].includes(finish)) return true;\r\n  if (material === 'paper' || material === 'vinyl') return finish === 'matte' || finish === 'gloss';\r\n  if (material === 'clear' || material === 'holographic') return finish === 'gloss';\r\n  return true;\r\n}\r\n\r\nfunction normalizeSheetFinishValue(material, finish, profile) {\r\n  const available = Array.isArray(profile?.finishes) ? profile.finishes : [];\r\n  const candidates = [finish, profile?.defaultFinish, ...available, material === 'clear' || material === 'holographic' ? 'gloss' : 'matte', 'none'];\r\n  return candidates.find((candidate) => (\r\n    candidate\r\n    && (!available.length || available.includes(candidate))\r\n    && isSheetFinishAvailableForMaterial(material, candidate)\r\n  )) || 'none';\r\n}\r\n\r\nfunction calculateSheetPrice(settings, payload, profile) {\r\n  const width = Math.max(0, numberValue(payload.width, 0));\r\n  const height = Math.max(0, numberValue(payload.height, 0));\r\n  const labelQuantity = Math.max(1, toInteger(payload.labelQuantity ?? payload.quantity));\r\n  if (width < 0.5 || height < 0.5 || !labelQuantity || Math.max(width, height) > 18 || Math.min(width, height) > 12) return null;\r\n\r\n  const sheetFit = Math.max(1, calculateSheetFit(\r\n    width,\r\n    height,\r\n    payload.sheetWidth ?? payload.sheet_width ?? 8.5,\r\n    payload.sheetHeight ?? payload.sheet_height ?? 11,\r\n    payload.sheetGap ?? payload.sheet_gap ?? SHEET_LABEL_GAP_INCHES,\r\n    payload.sheetMargin ?? payload.sheet_margin ?? SHEET_SAFE_MARGIN_INCHES,\r\n  ));\r\n  const sheetQuantity = Math.max(1, Math.ceil(labelQuantity / sheetFit));\r\n  const pricingSheetFit = Math.max(1, calculateSheetFit(\r\n    width,\r\n    height,\r\n    payload.sheetWidth ?? payload.sheet_width ?? 8.5,\r\n    payload.sheetHeight ?? payload.sheet_height ?? 11,\r\n    LEGACY_PRICING_SHEET_GAP_INCHES,\r\n    0,\r\n  ));\r\n  const pricingSheetQuantity = Math.max(1, Math.ceil(labelQuantity / pricingSheetFit));\r\n  const material = payload.material || profile?.defaultMaterial || 'paper';\r\n  const finish = normalizeSheetFinishValue(material, payload.finish || profile?.defaultFinish || '', profile);\r\n  const matrices = settingValue(settings, 'sheetPriceMatrix', 'sheet_price_matrix', {});\r\n  const fallbackBase = settingValue(settings, 'sheetBasePrices', 'sheet_base_prices', {});\r\n  const rows = matrices?.[material] || matrices?.paper || matrices?.default || fallbackBase || {};\r\n  const finishes = settingValue(settings, 'sheetFinishes', 'sheet_finishes', {});\r\n  const finishMultiplier = Math.max(0.001, numberValue(finishes?.[finish]?.multiplier, 1));\r\n  const versionExtra = numberValue(settingValue(settings, 'sheetVersionExtraPercent', 'sheet_version_extra_percent'), 10);\r\n  const artworkVersions = Math.max(1, toInteger(payload.artworkVersions ?? payload.artwork_versions ?? 1));\r\n  const reference = settingValue(settings, 'referencePricing', 'reference_pricing');\r\n  const referenceSheet = reference?.referenceSheet || {};\r\n  const referenceWidth = Math.max(0.01, numberValue(referenceSheet.width, 2));\r\n  const referenceHeight = Math.max(0.01, numberValue(referenceSheet.height, 2));\r\n  const referenceLabelsPerSheet = Math.max(1, toInteger(referenceSheet.labelsPerSheet || 20));\r\n  const referenceQuantity = pricingSheetQuantity * referenceLabelsPerSheet;\r\n  const additionalMultiplier = finishMultiplier * (1 + (artworkVersions - 1) * (versionExtra / 100));\r\n  const referencePrice = calculateReferencePrice(settings, {\r\n    category: 'sheets',\r\n    width: referenceWidth,\r\n    height: referenceHeight,\r\n    quantity: referenceQuantity,\r\n    material,\r\n    additionalMultiplier,\r\n  });\r\n  if (!referencePrice) return null;\r\n\r\n  // Keep the approved matching-size ceiling independent of physical sheet layout.\r\n  const matchingReferencePrice = calculateReferencePrice(settings, {\r\n    category: 'sheets', width, height, quantity: labelQuantity, material, additionalMultiplier,\r\n  });\r\n  if (!matchingReferencePrice) return null;\r\n  const finalTotal = Math.min(referencePrice.total, matchingReferencePrice.total);\r\n  const displayDiscount = sheetDisplayDiscount(settings, pricingSheetQuantity, numberValue(rows?.[pricingSheetQuantity]?.discount, 0));\r\n  const originalTotal = displayDiscount > 0 && displayDiscount < 100 ? roundMoney(finalTotal / (1 - displayDiscount / 100)) : finalTotal;\r\n\r\n  return {\r\n    ...referencePrice,\r\n    total: finalTotal,\r\n    unit: roundMoney(finalTotal / labelQuantity),\r\n    each: finalTotal / labelQuantity,\r\n    discount: displayDiscount,\r\n    originalTotal,\r\n    quantity: labelQuantity,\r\n    labelQuantity,\r\n    sheetQuantity,\r\n    sheetFit,\r\n    pricingSheetQuantity,\r\n    pricingSheetFit,\r\n    material,\r\n    finish,\r\n    artworkVersions,\r\n    pricingModel: 'sheet_count_with_matching_sticker_ceiling',\r\n    physicalSheetTotal: referencePrice.total,\r\n    matchingSheetCeilingTotal: matchingReferencePrice.total,\r\n    ceilingApplied: matchingReferencePrice.total < referencePrice.total,\r\n    referenceQuantity,\r\n    referenceSheetQuantity: pricingSheetQuantity,\r\n    referenceSheetWidth: referenceWidth,\r\n    referenceSheetHeight: referenceHeight,\r\n    referenceLabelsPerSheet,\r\n    sourceStickerTotal: referencePrice.sourceTotal,\r\n  };\r\n}\r\n\r\nfunction formatMoney(value, currency) {\r\n  const normalizedCurrency = String(currency || 'CAD').toUpperCase();\r\n  const formatter = new Intl.NumberFormat('en-CA', {\r\n    style: 'currency',\r\n    currency: normalizedCurrency,\r\n  });\r\n  const parts = formatter.formatToParts(Number(value || 0));\r\n  return parts.map((part) => (\r\n    part.type === 'currency' && normalizedCurrency === 'CAD' ? 'CA$' : part.value\r\n  )).join('');\r\n}\r\n\r\nfunction formatNumber(value) {\r\n  return new Intl.NumberFormat('en-CA').format(Number(value || 0));\r\n}\r\n\r\nfunction isAllowedArtworkFile(filename) {\r\n  return /\\.(jpe?g|png|pdf|ai|eps|tiff?|svg)$/i.test(String(filename || ''));\r\n}\r\n\r\nfunction customerSafeError(message, fallback) {\r\n  const text = String(message || '').trim();\r\n  if (!text) return fallback;\r\n  if (/Command failed|shopify store execute|stored store auth|No stored app authentication|query-file|variable-file|\\.graphql|\\.json|npx shopify/i.test(text)) {\r\n    return 'Custom checkout pricing is temporarily unavailable. Please choose a preset quantity or contact us for help.';\r\n  }\r\n  return text;\r\n}\r\n\r\nfunction isTransientConfiguredVariantError(message) {\r\n  return /sold out|not available|unavailable|cannot find variant|variant.*not found/i.test(String(message || ''));\r\n}\r\n\r\nfunction sleep(milliseconds) {\r\n  return new Promise((resolve) => {\r\n    window.setTimeout(resolve, milliseconds);\r\n  });\r\n}\r\n\r\nfunction isTextEntryControl(element) {\r\n  if (!element || !['INPUT', 'TEXTAREA'].includes(element.tagName)) return false;\r\n  if (element.tagName === 'TEXTAREA') return true;\r\n  return !['checkbox', 'radio', 'file', 'button', 'submit', 'reset', 'hidden'].includes(element.type);\r\n}\r\n\r\nfunction scrollableParent(element) {\r\n  let current = element.parentElement;\r\n  while (current && current !== document.body) {\r\n    const style = window.getComputedStyle(current);\r\n    const canScroll = /(auto|scroll)/.test(style.overflowY) && current.scrollHeight > current.clientHeight;\r\n    if (canScroll) return current;\r\n    current = current.parentElement;\r\n  }\r\n  return document.scrollingElement || document.documentElement;\r\n}\r\n\r\nfunction isElementInViewport(element) {\r\n  if (!element) return false;\r\n  const rect = element.getBoundingClientRect();\r\n  return rect.bottom > 0 && rect.top < window.innerHeight && rect.right > 0 && rect.left < window.innerWidth;\r\n}\r\n\r\nasync function responseJson(response, fallbackMessage) {\r\n  const text = await response.text();\r\n  if (!text) {\r\n    if (!response.ok) throw new Error(fallbackMessage);\r\n    return {};\r\n  }\r\n\r\n  try {\r\n    return JSON.parse(text);\r\n  } catch {\r\n    throw new Error(fallbackMessage);\r\n  }\r\n}\r\n\r\nfunction criteriaMatch(criteria, payload) {\r\n  return Object.entries(criteria).every(([key, expected]) => {\r\n    const actual = payload[key];\r\n    if (typeof expected === 'number') {\r\n      return Number(actual) === expected;\r\n    }\r\n\r\n    if ((key === 'size' || key === 'sizeLabel') && sizesMatch(expected, actual)) {\r\n      return true;\r\n    }\r\n\r\n    return String(actual ?? '') === String(expected ?? '');\r\n  });\r\n}\r\n\r\nfunction normalizePricingMatrix(matrix) {\r\n  if (!matrix || matrix.rowsFormat !== 'compact-v1' || !Array.isArray(matrix.rows)) return matrix;\r\n\r\n  matrix.rows = matrix.rows.map((row) => expandCompactPriceRow(row, matrix));\r\n  matrix.rowsFormat = 'expanded-v1';\r\n  return matrix;\r\n}\r\n\r\nfunction expandCompactPriceRow(row, matrix) {\r\n  if (!Array.isArray(row)) return row;\r\n\r\n  const [\r\n    shape,\r\n    size,\r\n    width,\r\n    height,\r\n    material,\r\n    finish,\r\n    quantity,\r\n    total,\r\n    unit,\r\n    each,\r\n    discount,\r\n    originalTotal,\r\n    variantIndex,\r\n  ] = row;\r\n  const variant = Number(variantIndex) >= 0 ? matrix.priceVariants?.[Number(variantIndex)] : null;\r\n  const criteria = {\r\n    shape,\r\n    material,\r\n    finish,\r\n    quantity: Number(quantity || 0),\r\n  };\r\n\r\n  if (size) criteria.size = size;\r\n  if (width !== '') criteria.width = Number(width);\r\n  if (height !== '') criteria.height = Number(height);\r\n\r\n  const price = {\r\n    total: Number(total || 0),\r\n    unit: Number(unit || 0),\r\n    each: Number(each || 0),\r\n    discount: Number(discount || 0),\r\n    originalTotal: Number(originalTotal || total || 0),\r\n    quantity: Number(quantity || 0),\r\n    key: `${shape}|${size || 'Custom'}|${width || ''}|${height || ''}|${material}|${finish}|${quantity}`,\r\n    sizeLabel: size || formatSizeLabel(Number(width || 0), Number(height || 0), true),\r\n    material,\r\n    finish,\r\n    shape,\r\n  };\r\n\r\n  return {\r\n    key: `compact:${price.key}`,\r\n    criteria,\r\n    price,\r\n    variantTitle: variant?.title || configuredVariantLabel(price.total),\r\n    variantId: variant?.variantId || '',\r\n    variantGid: variant?.variantGid || '',\r\n  };\r\n}\r\n\r\nfunction escapeHtml(value) {\r\n  return String(value ?? '').replace(/[&<>\"']/g, (char) => ({\r\n    '&': '&amp;',\r\n    '<': '&lt;',\r\n    '>': '&gt;',\r\n    '\"': '&quot;',\r\n    \"'\": '&#039;',\r\n  }[char]));\r\n}\r\n\r\nif (!customElements.get('spark-product-configurator')) {\r\n  customElements.define('spark-product-configurator', SparkProductConfigurator);\r\n}\r\n"],
  "mappings": "AAAA,MAAM,4BAA8B,SAC9B,6BAA+B,SAC/B,kBAAoB,6EACpB,yBAA2B,mBAC3B,uBAAyB,EAAI,KAC7B,gCAAkC,GAClC,yBAA2B,GAK3B,mBAAqB,MACrB,0BAA4B,SAC5B,8BAAgC,sBAEtC,MAAM,iCAAiC,WAAY,CACjD,mBAAoB,CACd,KAAK,2BAA6B,SACpC,KAAK,yBAA2B,KAAK,cAAc,yCAAyC,GAAG,UAAU,KAAK,GAAK,GACnH,KAAK,uBAAyB,KAAK,cAAc,uCAAuC,GAAG,UAAU,KAAK,GAAK,IAEjH,KAAK,SAAW,KAAK,QAAQ,SAAW,IAAI,QAAQ,MAAO,EAAE,EAC7D,KAAK,UAAY,KAAK,QAAQ,WAAa,GAC3C,KAAK,iBAAmB,KAAK,QAAQ,mBAAqB,OAC1D,KAAK,cAAgB,KAAK,QAAQ,eAAiB,GACnD,KAAK,aAAe,KAAK,QAAQ,cAAgB,iBACjD,KAAK,SAAW,KAAK,QAAQ,UAAY,MACzC,KAAK,QAAU,OAAO,KAAK,QAAQ,SAAW,EAAE,EAAE,YAAY,EAC9D,KAAK,kBAAoB,IAAI,IAC7B,KAAK,yBAA2B,IAAI,IACpC,KAAK,QAAU,KACf,KAAK,YAAc,KACnB,KAAK,gBAAkB,KACvB,KAAK,MAAQ,CAAC,EACd,KAAK,MAAQ,KACb,KAAK,uBAAyB,KAC9B,KAAK,QAAU,GACf,KAAK,KAAO,UACZ,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,wBAA0B,GAC/B,KAAK,aAAe,CAAC,EACrB,KAAK,mBAAqB,IAAI,IAC9B,KAAK,qBAAuB,GAC5B,KAAK,iBAAmB,GACxB,KAAK,4BAA8B,GACnC,KAAK,sBAAwB,EAC7B,KAAK,cAAgB,KAAK,SAAW,yCACrC,KAAK,uBAAyB,GAC9B,KAAK,qBAAuB,GAC5B,KAAK,qBAAuB,IAAI,IAChC,KAAK,qBAAuB,KAC5B,KAAK,yBAA2B,GAChC,KAAK,eAAiB,KACtB,KAAK,uBAAyB,KAC9B,KAAK,qBAAuB,GAC5B,KAAK,0BAA4B,KAAK,4BAA+B,OAAU,CAC7E,MAAM,SAAW,KAAK,cAAc,wCAAwC,EACxE,UAAY,CAAC,SAAS,SAAS,MAAM,MAAM,IAC7C,KAAK,qBAAuB,GAC5B,SAAS,gBAAgB,MAAM,EAEnC,GACA,SAAS,oBAAoB,cAAe,KAAK,yBAAyB,EAC1E,SAAS,iBAAiB,cAAe,KAAK,yBAAyB,EACvE,KAAK,yBAAyB,EAC9B,KAAK,KAAK,CACZ,CAEA,sBAAuB,CACjB,KAAK,iBACP,KAAK,eAAe,WAAW,EAC/B,KAAK,eAAiB,MAEpB,KAAK,yBACP,KAAK,uBAAuB,MAAM,EAClC,KAAK,uBAAyB,MAEhC,KAAK,0BAA0B,EAC/B,KAAK,oCAAoC,EAAE,EAC3C,KAAK,wBAAwB,EAC7B,SAAS,oBAAoB,cAAe,KAAK,yBAAyB,CAC5E,CAEA,0BAA2B,CACzB,GAAI,CACF,MAAM,SAAW,YAAY,mBAAmB,YAAY,IAAI,CAAC,EAC3D,gBAAkB,OAAO,eAAe,QAAQ,wBAAwB,GAAK,CAAC,EAGpF,GAFuB,UAAU,OAAS,UAAY,iBAAmB,IAAM,CAAC,OAAO,SAAS,KAE5E,CACd,sBAAuB,UAAS,QAAQ,kBAAoB,UAChE,MAAM,SAAW,IAAM,OAAO,SAAS,CAAE,IAAK,EAAG,KAAM,EAAG,SAAU,MAAO,CAAC,EAC5E,CAAC,EAAG,GAAI,IAAK,IAAK,IAAK,KAAM,IAAI,EAAE,QAAS,OAAU,OAAO,WAAW,SAAU,KAAK,CAAC,EACxF,OAAO,iBAAiB,OAAQ,IAAM,CACpC,CAAC,EAAG,IAAK,GAAG,EAAE,QAAS,OAAU,OAAO,WAAW,SAAU,KAAK,CAAC,CACrE,EAAG,CAAE,KAAM,EAAK,CAAC,CACnB,CAEA,OAAO,iBAAiB,WAAY,IAAM,CACxC,eAAe,QAAQ,yBAA0B,OAAO,KAAK,IAAI,EAAG,KAAK,MAAM,OAAO,SAAW,CAAC,CAAC,CAAC,CAAC,CACvG,CAAC,CACH,MAAgB,CAEhB,CACF,CAEA,MAAM,MAAO,CACX,GAAI,CAAC,KAAK,cAAe,CACvB,KAAK,YAAY,iDAAiD,EAClE,MACF,CAEA,KAAK,YAAY,yBAAyB,EAE1C,GAAI,CACF,MAAM,QAAU,MAAM,KAAK,wBAAwB,EACnD,KAAK,YAAc,QAAQ,aAAe,KAC1C,KAAK,QAAU,QAAQ,QACvB,KAAK,MAAQ,KAAK,0BAA0B,KAAK,aAAa,KAAK,OAAO,CAAC,EAC3E,KAAK,+BAA+B,EAChC,KAAK,QAAQ,SAAW,WAC1B,KAAK,MAAM,OAAS,KAAK,sBAAsB,KAAK,MAAM,MAAM,GAElE,KAAK,OAAO,EACZ,MAAM,KAAK,YAAY,CACzB,OAAS,MAAO,CACd,KAAK,YAAY,MAAM,SAAW,gCAAgC,CACpE,CACF,CAEA,MAAM,yBAA0B,CAC9B,GAAI,KAAK,UAAW,CAClB,MAAM,SAAW,MAAM,MAAM,KAAK,UAAW,CAAE,QAAS,CAAE,OAAQ,kBAAmB,CAAE,CAAC,EACxF,GAAI,SAAS,GAAI,CACf,MAAM,OAAS,MAAM,SAAS,KAAK,EACnC,GAAI,QAAQ,QACV,8BAAuB,MAAM,EACtB,CAAE,QAAS,OAAO,QAAS,YAAa,MAAO,CAE1D,CACF,CAEA,GAAI,KAAK,SAAW,KAAK,iBAAkB,CACzC,MAAM,SAAW,MAAM,MAAM,GAAG,KAAK,OAAO,6BAA6B,mBAAmB,KAAK,aAAa,CAAC,GAAI,CACjH,QAAS,CAAE,OAAQ,mBAAoB,yBAA0B,MAAO,CAC1E,CAAC,EACD,GAAI,CAAC,SAAS,GAAI,MAAM,IAAI,MAAM,wCAAwC,EAE1E,MAAO,CAAE,SADO,MAAM,SAAS,KAAK,GACV,QAAS,YAAa,IAAK,CACvD,CAEA,MAAM,IAAI,MAAM,2DAA2D,CAC7E,CAEA,aAAa,QAAS,CACpB,MAAM,OAAS,QAAQ,OACjB,MAAQ,CACZ,MAAO,QAAQ,aAAe,QAAQ,cAAgB,SACtD,SAAU,QAAQ,iBAAmB,GACrC,OAAQ,QAAQ,eAAiB,OACjC,WAAY,OACZ,gBAAiB,gBACjB,YAAa,SACb,aAAc,GACd,qBAAsB,GACtB,WAAY,GACZ,eAAgB,GAChB,sBAAuB,EACzB,EAEA,GAAI,SAAW,YAAc,SAAW,SAAU,CAChD,MAAM,YAAc,SAAW,YAAc,CAAC,YAAa,MAAM,EAAE,SAAS,MAAM,KAAK,EACnF,UACA,UACE,kBAAoB,UAAU,WAAW,EAC/C,OAAO,OAAO,MAAO,CACnB,SAAU,SAAW,SAAY,QAAQ,iBAAmB,QAAY,QAAQ,iBAAmB,aACnG,MAAO,kBAAkB,MACzB,OAAQ,kBAAkB,OAC1B,KAAM,YACN,UAAW,YACX,SAAU,IACV,cAAe,SAAW,SAAW,IAAM,OAC3C,gBAAiB,CACnB,CAAC,CACH,CAEA,GAAI,SAAW,oBAAqB,CAClC,MAAM,MAAQ,QAAQ,UAAU,YAAc,CAAC,EAEzC,MADkB,KAAK,uBAAuB,MAAM,MAAM,EAClC,CAAC,GAAK,QAAQ,cAAgB,SACtD,gBAAkB,MAAM,4BAA4B,KAAK,GAAK,MAAM,aAAe,CAAC,EACpF,SAAW,QAAQ,iBAAmB,QAAQ,gBAAgB,CAAC,GAAK,MAAM,YAAY,CAAC,GAAK,cAC5F,mBAAqB,KAAK,aAAa,QAAQ,EACrD,OAAO,OAAO,MAAO,CACnB,MACA,KAAM,KAAK,uBAAuB,eAAe,EACjD,SACA,OAAQ,mBAAmB,CAAC,GAAG,OAAS,QAAQ,eAAiB,MAAM,WAAW,CAAC,GAAK,QACxF,SAAU,MAAM,YAAY,SAAS,GAAG,EAAI,IAAM,MAAM,aAAa,CAAC,GAAK,EAC7E,CAAC,CACH,CAEA,GAAI,SAAW,gBAAiB,CAC9B,MAAM,MAAQ,QAAQ,UAAU,SAAW,CAAC,EACtC,MAAQ,QAAQ,cAAgB,MAAM,SAAS,CAAC,GAAK,SACrD,gBAAkB,MAAM,4BAA4B,KAAK,GAAK,MAAM,OAAS,CAAC,EAC9E,uBAAyB,MAAM,mCAAmC,KAAK,GAAK,MAAM,cAAgB,CAAC,EACzG,OAAO,OAAO,MAAO,CACnB,MACA,KAAM,KAAK,uBAAuB,eAAe,GAAK,UACtD,YAAa,uBAAuB,CAAC,GAAK,WAC1C,OAAQ,QAAQ,eAAiB,MAAM,WAAW,CAAC,GAAK,OACxD,SAAU,MAAM,YAAY,SAAS,GAAG,EAAI,IAAM,MAAM,aAAa,CAAC,GAAK,EAC7E,CAAC,CACH,CAEA,GAAI,SAAW,kBAAmB,CAChC,MAAM,MAAQ,QAAQ,UAAU,SAAW,CAAC,EACtC,MAAQ,QAAQ,cAAgB,MAAM,SAAS,CAAC,GAAK,SACrD,gBAAkB,MAAM,4BAA4B,KAAK,GAAK,CAAC,EAC/D,KAAO,KAAK,uBAAuB,eAAe,GAAK,gBAAgB,CAAC,GAAK,UAC7E,WAAa,UAAU,IAAI,EACjC,OAAO,OAAO,MAAO,CACnB,MACA,KACA,UAAW,KACX,MAAO,WAAW,MAClB,OAAQ,WAAW,OACnB,SAAU,MAAM,YAAY,SAAS,GAAG,EAAI,IAAM,MAAM,aAAa,CAAC,GAAK,EAC7E,CAAC,CACH,CAEA,OAAO,KACT,CAEA,uBAAwB,CACtB,MAAM,YAAc,CAClB,QAAS,WAAY,SAAU,aAAc,kBAAmB,QAAS,SAAU,OAAQ,YAC3F,WAAY,gBAAiB,cAAe,kBAC5C,aAAc,iBAAkB,wBAAyB,cAAe,eAAgB,sBAC1F,EACM,MAAQ,CAAC,EACf,mBAAY,QAAS,KAAQ,CAC3B,MAAM,MAAQ,KAAK,MAAM,GAAG,EACD,OAAU,MAAQ,QAAU,KAAI,MAAM,GAAG,EAAI,MAC1E,CAAC,EACM,CAAE,QAAS,EAAG,cAAe,KAAK,cAAe,KAAM,CAChE,CAEA,oBAAqB,CACnB,MAAM,MAAQ,IAAI,YAAY,EAAE,OAAO,KAAK,UAAU,KAAK,sBAAsB,CAAC,CAAC,EACnF,IAAI,OAAS,GACb,aAAM,QAAS,MAAS,CAAE,QAAU,OAAO,aAAa,IAAI,CAAG,CAAC,EACzD,OAAO,KAAK,MAAM,EAAE,QAAQ,MAAO,GAAG,EAAE,QAAQ,MAAO,GAAG,EAAE,QAAQ,OAAQ,EAAE,CACvF,CAEA,2BAA2B,MAAO,CAChC,GAAI,CAAC,MAAO,OAAO,KACnB,GAAI,MAAM,WAAW,GAAG,EAAG,OAAO,KAAK,MAAM,KAAK,EAClD,MAAM,OAAS,MAAM,QAAQ,KAAM,GAAG,EAAE,QAAQ,KAAM,GAAG,EACnD,OAAS,OAAO,OAAO,KAAK,KAAK,OAAO,OAAS,CAAC,EAAI,EAAG,GAAG,EAC5D,OAAS,OAAO,KAAK,MAAM,EAC3B,MAAQ,WAAW,KAAK,OAAS,WAAc,UAAU,WAAW,CAAC,CAAC,EAC5E,OAAO,KAAK,MAAM,IAAI,YAAY,EAAE,OAAO,KAAK,CAAC,CACnD,CAEA,0BAA0B,aAAc,CACtC,MAAM,OAAS,IAAI,gBAAgB,OAAO,SAAS,MAAM,EACnD,UAAY,OAAO,IAAI,SAAS,GAAK,GACrC,qBAAuB,OAAO,IAAI,cAAc,EAChD,yBAA2B,EAAQ,qBACzC,IAAI,SAAW,KAEf,GAAI,CACE,uBAAsB,SAAW,KAAK,2BAA2B,oBAAoB,GACrF,CAAC,UAAY,YACf,SAAW,KAAK,MAAM,OAAO,aAAa,QAAQ,KAAK,wBAAwB,SAAS,CAAC,GAAK,MAAM,GAElG,CAAC,UAAY,YACf,SAAW,KAAK,MAAM,OAAO,aAAa,QAAQ,KAAK,wBAAwB,QAAQ,CAAC,GAAK,MAAM,EAEvG,MAAiB,CACf,SAAW,IACb,CAEA,GAAI,CAAC,UAAY,SAAS,gBAAkB,KAAK,eAAiB,CAAC,SAAS,OAAS,OAAO,SAAS,OAAU,SAC7G,OAAO,aAGT,MAAM,YAAc,IAAI,IAAI,CAC1B,QAAS,WAAY,SAAU,aAAc,kBAAmB,QAAS,SAAU,OAAQ,YAC3F,WAAY,gBAAiB,cAAe,kBAC5C,aAAc,iBAAkB,wBAAyB,cAAe,eAAgB,sBAC1F,CAAC,EACK,SAAW,CAAE,GAAG,YAAa,EACnC,cAAO,QAAQ,SAAS,KAAK,EAAE,QAAQ,CAAC,CAAC,IAAK,KAAK,IAAM,CAClD,YAAY,IAAI,GAAG,IAGpB,MAAQ,eAAiB,CAAC,0BACzB,CAAC,SAAU,SAAU,SAAS,EAAE,SAAS,OAAO,KAAK,IAC1D,SAAS,GAAG,EAAI,OAClB,CAAC,EACM,QACT,CAEA,wBAAwB,UAAW,CASjC,MAAO,gBARgB,CACrB,SAAU,MACV,OAAQ,MACR,oBAAqB,MACrB,gBAAiB,MACjB,kBAAmB,KACrB,EACqC,KAAK,SAAS,MAAM,GAAK,EAC1B,GAAG,KAAK,aAAa,IAAI,SAAS,EACxE,CAEA,6BAA6B,UAAW,CACtC,GAAI,CACF,MAAM,WAAa,KAAK,UAAU,KAAK,sBAAsB,CAAC,EAC9D,OAAO,aAAa,QAAQ,KAAK,wBAAwB,OAAO,SAAS,CAAC,EAAG,UAAU,EACvF,OAAO,aAAa,QAAQ,KAAK,wBAAwB,QAAQ,EAAG,UAAU,CAChF,MAAiB,CAEjB,CACF,CAEA,YAAY,QAAS,CACnB,KAAK,UAAY;AAAA;AAAA;AAAA;AAAA,kBAIH,WAAW,OAAO,CAAC;AAAA;AAAA;AAAA,KAInC,CAEA,iBAAiB,cAAe,CAqB9B,MAAO;AAAA;AAAA,UApBa,cAChB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QASA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAYa;AAAA,6CACwB,cAAgB,aAAe,EAAE,mBAAmB,cAAgB,OAAS,OAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAS/H,CAEA,oBAAoB,cAAgB,KAAK,OAAS,UAAW,CAC3D,MAAO,EACT,CAEA,QAAS,CACP,MAAM,iBAAmB,KAAK,cAAc,uBAAuB,GAAG,UAAU,SAAS,YAAY,IAAM,GACrG,QAAU,KAAK,QACf,SAAW,CAAC,GAEd,QAAQ,SAAW,YAAc,QAAQ,SAAW,YACjD,QAAQ,aAAa,SAAS,KAAK,KAAK,mBAAmB,CAAC,EACjE,SAAS,KAAK,KAAK,kBAAkB,CAAC,EAClC,QAAQ,SAAW,UAAU,SAAS,KAAK,KAAK,gBAAgB,CAAC,EAChE,QAAQ,gBAAgB,SAAS,KAAK,KAAK,sBAAsB,CAAC,EACnE,QAAQ,SAAW,UAAY,CAAC,QAAQ,cAAc,SAAS,KAAK,KAAK,oBAAoB,CAAC,EAC9F,QAAQ,SAAW,YAAY,SAAS,KAAK,KAAK,wBAAwB,CAAC,EAC3E,QAAQ,SAAW,UAAU,SAAS,KAAK,KAAK,6BAA6B,CAAC,EAClF,SAAS,KAAK,KAAK,sBAAsB,QAAQ,SAAW,SAAW,kBAAoB,UAAU,CAAC,GAGpG,QAAQ,SAAW,sBACrB,SAAS,KAAK,KAAK,oBAAoB,QAAS,QAAS,KAAK,WAAW,CAAC,CAAC,EAC3E,SAAS,KAAK,KAAK,wBAAwB,OAAQ,KAAK,UAAU,CAAC,CAAC,EAC/D,QAAQ,gBAAgB,SAAS,KAAK,KAAK,sBAAsB,CAAC,EACvE,SAAS,KAAK,KAAK,wBAAwB,CAAC,EAC5C,SAAS,KAAK,KAAK,2BAA2B,CAAC,EAC/C,SAAS,KAAK,KAAK,sBAAsB,UAAU,CAAC,GAGlD,QAAQ,SAAW,kBACrB,SAAS,KAAK,KAAK,oBAAoB,QAAS,QAAS,KAAK,aAAa,CAAC,CAAC,EAC7E,SAAS,KAAK,KAAK,oBAAoB,OAAQ,OAAQ,KAAK,YAAY,CAAC,CAAC,EAC1E,SAAS,KAAK,KAAK,oBAAoB,SAAU,SAAU,KAAK,eAAe,CAAC,CAAC,EACjF,SAAS,KAAK,KAAK,sBAAsB,UAAU,CAAC,GAGlD,QAAQ,SAAW,oBACrB,SAAS,KAAK,KAAK,mBAAmB,CAAC,EACvC,SAAS,KAAK,KAAK,kBAAkB,CAAC,EACtC,SAAS,KAAK,KAAK,sBAAsB,UAAU,CAAC,GAGtD,MAAM,cAAgB,KAAK,OAAS,UAC9B,gBAAkB,cAAgB,CAAC,KAAK,qBAAqB,CAAC,EAAI,SAClE,mBAAqB,eAAiB,KAAK,mBAAmB,EAC9D,qBAAuB,CAAC,eAAiB,KAAK,iBAAiB,EAC/D,iBAAmB,cACrB,GACA,KAAK,iBAAiB,KAAK,2BAA2B,CAAC,EAE3D,KAAK,UAAY;AAAA,+CAC0B,cAAgB,UAAY,SAAS;AAAA,UAC1E,KAAK,iBAAiB,aAAa,CAAC;AAAA;AAAA,YAElC,gBAAgB,KAAK,EAAE,CAAC;AAAA;AAAA;AAAA,YAGxB,cAAgB,KAAK,mBAAmB,EAAI,gBAAgB;AAAA,YAC5D,KAAK,wBAAwB;AAAA,YAC7B,cAAgB;AAAA;AAAA,4FAEgE,KAAK,OAAO,KAAM,CAAC,sBAAwB,KAAK,QAAW,gCAAkC,EAAE;AAAA;AAAA,+CAE5I,WAAW,KAAK,eAAe,CAAC,CAAC;AAAA;AAAA;AAAA;AAAA,YAIlE;AAAA,6EAC+D,mBAAqB,GAAK,+BAA+B;AAAA;AAAA;AAAA;AAAA,WAI3H;AAAA,0CAC+B,KAAK,WAAa,OAAO,KAAK,UAAU,GAAK,EAAE;AAAA,cAC3E,KAAK,cAAgB,WAAW,KAAK,aAAa,EAAI,KAAK,oBAAoB,aAAa,CAAC;AAAA;AAAA,YAE/F,KAAK,sBAAsB;AAAA;AAAA,UAE5B,cAQC,GARe;AAAA,oDACyB,iBAAmB,cAAgB,EAAE,sCAAsC,iBAAmB,QAAU,MAAM;AAAA,cACpJ,gBAAgB;AAAA,6EAC+C,mBAAqB,GAAK,+BAA+B;AAAA;AAAA;AAAA;AAAA;AAAA,SAKxH;AAAA;AAAA,MAIV,KAAK,WAAW,EAChB,KAAK,mBAAmB,EACpB,eAAe,KAAK,uBAAuB,CACjD,CAEA,YAAa,CACX,GAAI,CAAC,KAAK,wBAAyB,CACjC,KAAK,wBAA0B,GAC/B,MAAM,oBAAuB,OAAU,CACjC,KAAK,SAAS,MAAM,MAAM,GAAK,mBAAmB,MAAM,MAAM,GAChE,KAAK,eAAe,EAAI,CAE5B,EACM,qBAAuB,IAAM,CACjC,OAAO,WAAW,IAAM,CACtB,KAAK,eAAe,KAAK,mBAAmB,CAAC,CAC/C,EAAG,EAAE,CACP,EAEA,KAAK,iBAAiB,UAAW,mBAAmB,EACpD,KAAK,iBAAiB,WAAY,oBAAoB,EACtD,SAAS,iBAAiB,UAAW,oBAAqB,EAAI,EAC9D,SAAS,iBAAiB,WAAY,qBAAsB,EAAI,CAClE,CAEA,KAAK,iBAAiB,IAAI,EAE1B,MAAM,SAAW,KAAK,cAAc,6BAA6B,EAC3D,WAAa,KAAK,cAAc,+BAA+B,EAC/D,UAAY,KAAK,cAAc,8BAA8B,EAC/D,UAAY,aACd,SAAS,iBAAiB,QAAS,IAAM,WAAW,UAAU,CAAC,EAC/D,WAAW,iBAAiB,QAAS,IAAM,WAAW,MAAM,CAAC,EAC7D,WAAW,iBAAiB,QAAU,OAAU,CAC1C,MAAM,SAAW,YAAY,WAAW,MAAM,CACpD,CAAC,GAGH,MAAM,iBAAmB,KAAK,cAAc,2BAA2B,EACjE,mBAAqB,KAAK,cAAc,6BAA6B,EACrE,kBAAoB,KAAK,cAAc,4BAA4B,EACrE,kBAAoB,qBACtB,iBAAiB,iBAAiB,QAAS,IAAM,mBAAmB,UAAU,CAAC,EAC/E,mBAAmB,iBAAiB,QAAS,IAAM,mBAAmB,MAAM,CAAC,EAC7E,mBAAmB,iBAAiB,QAAU,OAAU,CAClD,MAAM,SAAW,oBAAoB,mBAAmB,MAAM,CACpE,CAAC,GAGH,MAAM,iBAAmB,KAAK,cAAc,kCAAkC,EAC9E,kBAAkB,iBAAiB,SAAU,IAAM,CACjD,KAAK,qBAAuB,iBAAiB,IAC/C,CAAC,EAED,KAAK,iBAAiB,4BAA4B,EAAE,QAAS,QAAW,CACtE,OAAO,iBAAiB,QAAS,IAAM,CACrC,KAAK,uBAAyB,CAAC,KAAK,uBACpC,KAAK,OAAO,CACd,CAAC,CACH,CAAC,EAED,KAAK,iBAAiB,qBAAqB,EAAE,QAAS,QAAW,CAC/D,OAAO,iBAAiB,QAAS,IAAM,CACrC,MAAM,iBAAmB,OAAO,QAAQ,cAAgB,cAClD,UAAY,KAAK,cAAc,4BAA4B,EAC7D,YAAW,UAAU,QAAU,kBACnC,KAAK,SAAS,cAAe,iBAAkB,EAAI,CACrD,CAAC,CACH,CAAC,EAED,MAAM,UAAY,KAAK,cAAc,qBAAqB,EACtD,WACF,UAAU,iBAAiB,SAAU,IAAM,CACzC,MAAM,cAAgB,MAAM,KAAK,UAAU,OAAS,CAAC,CAAC,EACtD,GAAI,cAAc,OAAQ,CACxB,KAAK,kBAAkB,aAAa,EACpC,KAAK,0BAA0B,EAC/B,UAAU,MAAQ,GAClB,KAAK,MAAM,YAAc,SACzB,MAAM,cAAgB,KAAK,cAAc,4BAA4B,EACjE,gBAAe,cAAc,QAAU,IAC3C,KAAK,cAAgB,GACrB,KAAK,WAAa,EACpB,CACA,KAAK,uBAAuB,EAC5B,KAAK,qBAAqB,CAC5B,CAAC,EAGH,MAAM,SAAW,KAAK,cAAc,yBAAyB,EACzD,UAAY,YACd,CAAC,YAAa,UAAU,EAAE,QAAS,WAAc,CAC/C,SAAS,iBAAiB,UAAY,OAAU,CAC9C,MAAM,eAAe,EACrB,SAAS,UAAU,IAAI,aAAa,CACtC,CAAC,CACH,CAAC,EAED,CAAC,YAAa,MAAM,EAAE,QAAS,WAAc,CAC3C,SAAS,iBAAiB,UAAW,IAAM,CACzC,SAAS,UAAU,OAAO,aAAa,CACzC,CAAC,CACH,CAAC,EAED,SAAS,iBAAiB,OAAS,OAAU,CAC3C,MAAM,eAAe,EACrB,MAAM,MAAQ,MAAM,cAAc,MAClC,GAAI,CAAC,OAAO,OAAQ,OACpB,KAAK,kBAAkB,MAAM,KAAK,KAAK,CAAC,EACxC,KAAK,0BAA0B,EAC/B,UAAU,MAAQ,GAClB,KAAK,MAAM,YAAc,SACzB,MAAM,cAAgB,KAAK,cAAc,4BAA4B,EACjE,gBAAe,cAAc,QAAU,IAC3C,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,uBAAuB,EAC5B,KAAK,qBAAqB,CAC5B,CAAC,GAGH,MAAM,gBAAkB,KAAK,cAAc,0BAA0B,EACjE,iBACF,gBAAgB,iBAAiB,QAAU,OAAU,CACnD,MAAM,aAAe,MAAM,OAAO,QAAQ,4BAA4B,EACtE,GAAI,CAAC,cAAgB,CAAC,gBAAgB,SAAS,YAAY,EAAG,OAC9D,MAAM,MAAQ,OAAO,aAAa,QAAQ,iBAAiB,EAC3D,GAAI,CAAC,OAAO,UAAU,KAAK,GAAK,MAAQ,EAAG,OAC3C,KAAM,CAAC,WAAW,EAAI,KAAK,aAAa,OAAO,MAAO,CAAC,EACvD,KAAK,yBAAyB,WAAW,EACzC,KAAK,0BAA0B,EAC3B,YAAW,UAAU,MAAQ,IACjC,KAAK,wBAA0B,GAC/B,KAAK,uBAAuB,CAC9B,CAAC,EAGH,MAAM,UAAY,KAAK,cAAc,oBAAoB,EACrD,WAAW,UAAU,iBAAiB,QAAS,IAAM,KAAK,UAAU,CAAC,EAEzE,KAAK,iBAAiB,kBAAkB,EAAE,QAAS,YAAe,WAAW,iBAAiB,QAAS,IAAM,CAC3G,GAAI,CAAC,KAAK,mBAAmB,EAAG,CAC9B,KAAK,cAAgB,KAAK,qBAAqB,EAC/C,KAAK,WAAa,QAClB,KAAK,cAAc,EACnB,KAAK,uBAAuB,EAC5B,KAAK,qBAAqB,EAC1B,MACF,CACA,KAAK,KAAO,UACZ,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,OAAO,EACZ,KAAK,iBAAiB,GAAI,MAAM,CAClC,CAAC,CAAC,EAEF,KAAK,iBAAiB,wBAAwB,EAAE,QAAS,YAAe,WAAW,iBAAiB,QAAS,IAAM,CACjH,KAAK,KAAO,UACZ,KAAK,OAAO,EACZ,KAAK,iBAAiB,EAAG,MAAM,CACjC,CAAC,CAAC,CACJ,CAEA,iBAAiB,MAAO,CACtB,KAAK,iBAAiB,eAAe,EAAE,QAAS,QAAW,CACpD,MAAM,SAAS,MAAM,GAC1B,OAAO,iBAAiB,QAAS,IAAM,CACrC,MAAM,MAAQ,OAAO,QAAQ,MACvB,MAAQ,OAAO,QAAQ,MAC7B,KAAK,SAAS,MAAO,KAAK,CAC5B,CAAC,CACH,CAAC,EAED,KAAK,iBAAiB,cAAc,EAAE,QAAS,OAAU,CACvD,GAAI,CAAC,MAAM,SAAS,KAAK,EAAG,OAC5B,MAAM,UAAY,MAAM,OAAS,WAAa,SAAW,QACzD,MAAM,iBAAiB,UAAW,IAAM,CACtC,MAAM,MAAQ,MAAM,QAAQ,MACtB,MAAQ,MAAM,OAAS,WAAa,MAAM,QAAU,MAAM,MAC5D,MAAM,aAAa,4BAA4B,IACjD,KAAK,MAAM,eAAiB,IAE9B,KAAK,SAAS,MAAO,MAAO,EAAI,CAClC,CAAC,CACH,CAAC,CACH,CAEA,SAAS,MAAO,MAAO,MAAQ,GAAO,CACpC,IAAI,aAAe,GACf,aAAe,GACf,sBAAwB,GAE5B,GAAI,QAAU,QACZ,KAAK,MAAM,MAAQ,MACf,KAAK,MAAM,WACb,KAAK,sBAAsB,EAE3B,KAAK,mBAAmB,UAEjB,QAAU,OACf,QAAU,UACZ,KAAK,MAAM,WAAa,GACxB,KAAK,MAAM,KAAO,SAClB,KAAK,MAAM,UAAY,SACvB,KAAK,MAAM,MAAQ,EACnB,KAAK,MAAM,OAAS,EACpB,KAAK,MAAQ,KACb,KAAK,gBAAkB,KACvB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,aAAe,KAEf,KAAK,MAAM,WAAa,GACxB,KAAK,eAAe,KAAK,WAElB,QAAU,eAAiB,QAAU,eAC9C,KAAK,MAAM,QAAU,cAAgB,QAAU,QAAQ,EAAI,SAAS,KAAK,EACzE,KAAK,sBAAsB,EAC3B,aAAe,GACf,KAAK,uBAAuB,EACxB,KAAK,0BAA0B,IACjC,KAAK,MAAQ,KACb,KAAK,gBAAkB,KACvB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,qBAAqB,EAC1B,aAAe,YAER,QAAU,YAQnB,GAPA,KAAK,MAAM,SAAW,MAClB,KAAK,QAAQ,SAAW,WAC1B,KAAK,MAAM,OAAS,KAAK,sBAAsB,KAAK,MAAM,OAAQ,KAAK,GAErE,KAAK,QAAQ,SAAW,YAAc,CAAC,KAAK,0BAA0B,KAAK,IAC7E,KAAK,MAAM,WAAa,QAEtB,KAAK,QAAQ,SAAW,oBAAqB,CAC/C,MAAM,kBAAoB,KAAK,aAAa,EACvC,kBAAkB,KAAM,QAAW,OAAO,QAAU,KAAK,MAAM,MAAM,IACxE,KAAK,MAAM,OAAS,kBAAkB,CAAC,GAAG,OAAS,QAEvD,UACS,QAAU,YAAc,QAAU,gBAAiB,CAC5D,MAAM,sBAAwB,OAAS,KAAK,MAAM,eAClD,KAAK,MAAM,KAAK,EAAI,UAAU,KAAK,EAC9B,wBAAuB,KAAK,MAAM,eAAiB,IACpD,uBAAuB,KAAK,6BAA6B,EAC7D,aAAe,CAAC,sBACZ,uBAAyB,KAAK,MAAM,KAAK,GAAK,IAChD,KAAK,MAAQ,KACb,KAAK,gBAAkB,KACvB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,aAAe,GAEnB,SAAW,QAAU,iBAAkB,CACrC,KAAK,MAAM,eAAiB,GAC5B,MAAM,cAAgB,KAAK,cAAc,EACrC,gBAAe,KAAK,MAAM,aAAa,EAAI,GAC/C,KAAK,MAAQ,KACb,KAAK,gBAAkB,KACvB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,aAAe,EACjB,SAAW,QAAU,kBACf,QAAU,SACZ,KAAK,MAAM,sBAAwB,IAEnC,KAAK,MAAM,sBAAwB,GACnC,KAAK,MAAM,gBAAkB,UAAU,KAAK,EAC5C,KAAK,qBAAuB,IAE9B,aAAe,GACf,sBAAwB,GACxB,KAAK,4BAA4B,UACxB,QAAU,wBACnB,KAAK,MAAM,gBAAkB,KAAK,IAAI,EAAG,UAAU,KAAK,CAAC,EACzD,aAAe,GACf,KAAK,4BAA4B,UACxB,QAAU,cAAe,CAClC,MAAM,gBAAkB,KAAK,cAAc,4BAA4B,EACjE,mBAAqB,iBAAiB,sBAAsB,EAAE,IAC9D,uBAAyB,gBAAkB,KAAK,mBAAmB,eAAe,EAAI,KACtF,uBAAyB,wBAAwB,MAAM,gBAAkB,GACzE,wBAA0B,IAAM,KAAK,mBAAmB,6BAA8B,kBAAkB,EAU9G,GATI,yBACF,uBAAuB,MAAM,eAAiB,OAC9C,uBAAuB,iBAAiB,SAAU,wBAAyB,CAAE,QAAS,EAAK,CAAC,GAE9F,KAAK,MAAM,YAAc,MAAQ,cAAgB,SACjD,aAAe,GACf,aAAe,GACf,KAAK,cAAgB,GACrB,KAAK,WAAa,GACd,MAAO,CACT,KAAK,kBAAkB,EACvB,KAAK,0BAA0B,EAC/B,MAAM,UAAY,KAAK,cAAc,qBAAqB,EACtD,YAAW,UAAU,MAAQ,IACjC,KAAK,wBAA0B,EACjC,CACA,OAAO,WAAW,IAAM,CACtB,KAAK,uBAAuB,EAC5B,KAAK,qBAAqB,EAC1B,KAAK,mBAAmB,6BAA8B,kBAAkB,EACxE,OAAO,WAAW,IAAM,CAClB,yBACF,uBAAuB,oBAAoB,SAAU,uBAAuB,EAC5E,uBAAuB,MAAM,eAAiB,uBAElD,EAAG,GAAG,CACR,EAAG,CAAC,CACN,MAAW,QAAU,gBAAkB,QAAU,wBAC/C,KAAK,MAAM,KAAK,EAAI,MACpB,aAAe,GACf,aAAe,IAEf,KAAK,MAAM,KAAK,EAAI,MAGlB,cAAc,KAAK,OAAO,EAC1B,eACF,OAAO,aAAa,KAAK,UAAU,EACnC,KAAK,WAAa,OAAO,WAAW,IAAM,KAAK,YAAY,CAAE,qBAAsB,CAAC,EAAG,MAAQ,IAAM,CAAC,EAE1G,CAEA,mBAAmB,SAAU,YAAa,CACxC,GAAI,CAAC,OAAO,SAAS,WAAW,EAAG,OAEnC,MAAM,QAAU,IAAM,CACpB,MAAM,QAAU,KAAK,cAAc,QAAQ,EAC3C,GAAI,CAAC,QAAS,OACd,MAAM,MAAQ,QAAQ,sBAAsB,EAAE,IAAM,YACpD,GAAI,KAAK,IAAI,KAAK,EAAI,GAAK,CACzB,MAAM,gBAAkB,KAAK,mBAAmB,OAAO,EACnD,gBACF,gBAAgB,WAAa,MAE7B,OAAO,SAAS,CAAE,IAAK,MAAO,KAAM,EAAG,SAAU,MAAO,CAAC,CAE7D,CACF,EAEA,OAAO,sBAAsB,IAAM,CACjC,QAAQ,EACR,OAAO,sBAAsB,OAAO,CACtC,CAAC,CACH,CAEA,mBAAmB,QAAS,CAC1B,QAAS,OAAS,QAAQ,cAAe,OAAQ,OAAS,OAAO,cAAe,CAC9E,MAAM,UAAY,OAAO,iBAAiB,MAAM,EAAE,UAElD,GADkB,wBAAwB,KAAK,SAAS,GAAK,OAAO,aAAe,OAAO,aAC3E,OAAO,MACxB,CACA,OAAO,IACT,CAEA,eAAe,MAAO,CACpB,MAAM,OAAS,UAAU,KAAK,EAC9B,KAAK,MAAM,KAAO,MAClB,KAAK,MAAM,UAAY,MAAM,SAAS,KAAK,EAAI,MAAQ,MAAM,QAAQ,IAAK,KAAK,EAC/E,KAAK,MAAM,MAAQ,OAAO,MAC1B,KAAK,MAAM,OAAS,OAAO,MAC7B,CAEA,oBAAqB,CACnB,GAAI,KAAK,QAAQ,SAAW,oBAAqB,CAC/C,MAAMA,OAAQ,KAAK,UAAU,EAAE,IAAK,QAAW,OAAO,KAAK,EAC3D,KAAK,qBAAqB,KAAK,uBAAuBA,MAAK,CAAC,EAC5D,MACF,CACA,GAAI,KAAK,QAAQ,SAAW,gBAAiB,CAC3C,MAAMA,OAAQ,KAAK,YAAY,EAAE,IAAK,QAAW,OAAO,KAAK,EAC7D,KAAK,qBAAqB,KAAK,uBAAuBA,MAAK,CAAC,EAC5D,MAAM,aAAe,KAAK,mBAAmB,EAAE,IAAK,QAAW,OAAO,KAAK,EAC3E,KAAK,MAAM,YAAc,aAAa,CAAC,GAAK,KAAK,MAAM,YACvD,MACF,CACA,MAAM,MAAQ,KAAK,aAAa,EAAE,IAAK,QAAW,OAAO,KAAK,EAC9D,KAAK,qBAAqB,KAAK,uBAAuB,KAAK,CAAC,CAC9D,CAEA,qBAAqB,MAAO,CACrB,QACL,KAAK,MAAM,WAAa,GACxB,KAAK,eAAe,KAAK,EAC3B,CAEA,uBAAuB,OAAS,CAAC,EAAG,CAClC,OAAK,QAAQ,OACN,OAAO,KAAM,OAAU,iBAAiB,KAAK,IAAM,KAAK,GAAK,OAAO,CAAC,EADhD,EAE9B,CAEA,uBAAwB,CACtB,MAAM,MAAQ,OAAO,KAAK,MAAM,OAAS,CAAC,EACpC,OAAS,OAAO,KAAK,MAAM,QAAU,CAAC,EAC5C,KAAK,MAAM,KAAO,MAAQ,GAAK,OAAS,EAAI,gBAAgB,MAAO,OAAQ,EAAK,EAAI,SACpF,KAAK,MAAM,UAAY,MAAQ,GAAK,OAAS,EAAI,gBAAgB,MAAO,OAAQ,EAAI,EAAI,QAC1F,CAEA,iBAAkB,CAChB,OAAI,KAAK,SAAS,SAAW,WACvB,KAAK,SAAS,eAAiB,YAC1B,CACL,KAAM,MAAO,SAAU,GAAK,UAAW,GAAK,SAAU,GAAI,UAAW,GACrE,eAAgB,iCAAkC,eAAgB,4BACpE,EAEK,CACL,KAAM,MAAO,SAAU,GAAK,UAAW,GAAK,SAAU,GAAI,UAAW,GACrE,eAAgB,iCAAkC,eAAgB,4BACpE,EAEE,KAAK,SAAS,SAAW,SACpB,CACL,KAAM,YAAa,SAAU,GAAK,UAAW,GAAK,YAAa,GAAI,aAAc,GACjF,eAAgB,iCAAkC,eAAgB,yCACpE,EAEE,KAAK,SAAS,SAAW,oBACpB,CAAE,KAAM,MAAO,SAAU,IAAK,UAAW,IAAK,eAAgB,8BAA+B,EAElG,KAAK,SAAS,SAAW,kBACpB,CACL,KAAM,MAAO,SAAU,EAAG,UAAW,EAAG,SAAU,GAAI,UAAW,GACjE,eAAgB,2BAA4B,eAAgB,sCAC9D,EAEK,IACT,CAEA,sBAAuB,CACrB,OAAI,KAAK,SAAS,SAAW,oBAA4B,CAAC,GACvC,KAAK,aAAa,sBAAsB,YAAc,CAAC,GAEvE,IAAK,WAAc,OAAO,SAAS,CAAC,EACpC,OAAQ,WAAc,OAAO,SAAS,SAAS,GAAK,UAAY,CAAC,EACjE,KAAK,CAAC,MAAO,SAAW,MAAQ,MAAM,CAC3C,CAEA,8BAA8B,MAAO,CACnC,GAAI,CAAC,KAAK,MAAM,WAAY,MAAO,GACnC,MAAM,MAAQ,OAAO,KAAK,MAAM,KAAK,GAAK,CAAC,EAC3C,GAAI,CAAC,MAAO,MAAO,GAEnB,MAAM,WAAa,KAAK,qBAAqB,EAC7C,GAAI,CAAC,WAAW,QAAU,WAAW,KAAM,WAAc,KAAK,IAAI,UAAY,KAAK,EAAI,IAAM,EAAG,MAAO,GAEvG,MAAM,MAAQ,CAAC,GAAG,UAAU,EAAE,QAAQ,EAAE,KAAM,WAAc,UAAY,KAAK,EACvE,MAAQ,WAAW,KAAM,WAAc,UAAY,KAAK,EACxD,OAAS,CAAC,MAAO,KAAK,EAAE,OAAQ,WAAc,YAAc,MAAS,EAC3E,OAAK,OAAO,OAEL,yBAAyB,OAAO,IAAK,WAAc,GAAG,iBAAiB,SAAS,CAAC,QAAG,EAAE,KAAK,MAAM,CAAC,IAF9E,EAG7B,CAEA,6BAA8B,CAC5B,GAAI,CAAC,KAAK,MAAM,WAAY,MAAO,GACnC,MAAM,MAAQ,OAAO,KAAK,MAAM,OAAS,CAAC,EACpC,OAAS,OAAO,KAAK,MAAM,QAAU,CAAC,EAC5C,GAAI,CAAC,OAAS,CAAC,OAAQ,MAAO,kCAC9B,MAAM,MAAQ,KAAK,gBAAgB,EACnC,OAAI,KAAK,eAAe,MAAO,OAAQ,KAAK,EAAU,MAAM,eACxD,KAAK,iBAAiB,MAAO,OAAQ,KAAK,EAAU,MAAM,eACvD,KAAK,8BAA8B,OAAO,GAAK,KAAK,8BAA8B,QAAQ,CACnG,CAEA,oBAAqB,CACnB,MAAO,EAAQ,KAAK,OAAU,CAAC,KAAK,0BAA0B,CAChE,CAEA,sBAAuB,CACrB,GAAI,KAAK,MAAM,WAAY,CACzB,MAAM,QAAU,KAAK,4BAA4B,EACjD,GAAI,QAAS,OAAO,OACtB,CACA,MAAO,uDACT,CAEA,0BAA0B,QAAU,KAAK,aAAa,EAAG,CACvD,GAAI,CAAC,KAAK,MAAM,YAAc,QAAQ,OAAS,SAAU,MAAO,GAChE,MAAM,MAAQ,OAAO,QAAQ,OAAS,CAAC,EACjC,OAAS,OAAO,QAAQ,QAAU,CAAC,EAEzC,MADI,CAAC,OAAS,CAAC,QACX,KAAK,8BAA8B,OAAO,GAAK,KAAK,8BAA8B,QAAQ,EAAU,GACjG,KAAK,+BAA+B,OAAO,CACpD,CAEA,+BAA+B,QAAU,KAAK,aAAa,EAAG,CAC5D,MAAM,MAAQ,OAAO,QAAQ,OAAS,CAAC,EACjC,OAAS,OAAO,QAAQ,QAAU,CAAC,EACnC,MAAQ,KAAK,gBAAgB,EACnC,OAAO,KAAK,eAAe,MAAO,OAAQ,KAAK,GAAK,KAAK,iBAAiB,MAAO,OAAQ,KAAK,CAChG,CAEA,eAAe,MAAO,OAAQ,MAAO,CACnC,MAAI,CAAC,OAAS,CAAC,OAAS,CAAC,OAAe,GACjC,MAAQ,OAAO,MAAM,UAAY,CAAC,GAAK,OAAS,OAAO,MAAM,WAAa,CAAC,CACpF,CAEA,iBAAiB,MAAO,OAAQ,MAAO,CACrC,MAAI,CAAC,OAAS,CAAC,OAAS,CAAC,OAAe,GACpC,MAAM,OAAS,YACV,KAAK,IAAI,MAAO,MAAM,EAAI,MAAM,aAAe,KAAK,IAAI,MAAO,MAAM,EAAI,MAAM,aAEjF,MAAQ,MAAM,UAAY,OAAS,MAAM,SAClD,CAEA,MAAM,YAAY,CAAE,sBAAwB,EAAM,EAAI,CAAC,EAAG,CACxD,GAAI,CAAC,KAAK,QAAS,OACnB,MAAM,YAAc,uBAAyB,KAAK,uBAAuB,EACzE,GAAI,KAAK,0BAA0B,EAAG,CAMpC,GALA,KAAK,gBAAkB,KACvB,KAAK,MAAQ,KACb,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,+BAA+B,EAChC,YAAa,CACf,KAAK,qBAAqB,EAC1B,MACF,CACA,KAAK,OAAO,EACZ,MACF,CACA,MAAM,SAAW,KAAK,kBAAkB,EACxC,GAAI,SAAU,CAMZ,GALA,KAAK,gBAAkB,SACvB,KAAK,MAAQ,SAAS,MACtB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,iCAAiC,EAClC,YAAa,CACf,KAAK,qBAAqB,EAC1B,MACF,CACA,KAAK,OAAO,EACZ,MACF,CAGA,GADA,KAAK,gBAAkB,KACnB,KAAK,aAAe,CAAC,KAAK,iBAAkB,CAK9C,GAJA,KAAK,MAAQ,KACb,KAAK,cAAgB,2EACrB,KAAK,WAAa,QAClB,KAAK,+BAA+B,EAChC,YAAa,CACf,KAAK,qBAAqB,EAC1B,MACF,CACA,KAAK,OAAO,EACZ,MACF,CAEA,GAAI,CACF,MAAM,SAAW,MAAM,MAAM,GAAG,KAAK,OAAO,0BAA2B,CACrE,OAAQ,OACR,QAAS,CAAE,eAAgB,mBAAoB,OAAQ,mBAAoB,yBAA0B,MAAO,EAC5G,KAAM,KAAK,UAAU,KAAK,aAAa,CAAC,CAC1C,CAAC,EACK,QAAU,MAAM,aAAa,SAAU,gGAAgG,EAC7I,GAAI,CAAC,SAAS,GAAI,MAAM,IAAI,MAAM,QAAQ,OAAS,2BAA2B,EAC9E,KAAK,MAAQ,QAAQ,MACrB,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,iCAAiC,CACxC,OAAS,MAAO,CACd,KAAK,MAAQ,KACb,KAAK,cAAgB,MAAM,SAAW,iDACtC,KAAK,WAAa,QAClB,KAAK,+BAA+B,CACtC,CACA,GAAI,YAAa,CACf,KAAK,qBAAqB,EAC1B,MACF,CACA,KAAK,OAAO,CACd,CAEA,wBAAyB,CACvB,GAAI,KAAK,OAAS,UAAW,MAAO,GACpC,MAAM,OAAS,SAAS,cACxB,GAAI,CAAC,QAAU,CAAC,KAAK,SAAS,MAAM,EAAG,MAAO,GAC9C,MAAM,MAAQ,OAAO,SAAS,OAAS,GAGvC,MAFK,YAAU,eAAiB,QAAU,iBAAmB,KAAK,MAAM,aACnE,QAAU,YAAc,QAAU,kBAAoB,KAAK,MAAM,gBAClE,QAAU,yBAA2B,KAAK,MAAM,sBAEtD,CAEA,sBAAuB,CACrB,MAAM,iBAAmB,KAAK,iBAAiB,KAAK,2BAA2B,CAAC,EAAE,KAAK,EACvF,KAAK,iBAAiB,cAAc,EAAE,QAAS,YAAe,CAC5D,MAAM,SAAW,SAAS,cAAc,UAAU,EAClD,SAAS,UAAY,iBACrB,MAAM,UAAY,SAAS,QAAQ,kBAC/B,WAAW,WAAW,YAAY,SAAS,CACjD,CAAC,EAED,KAAK,cAAc,EAEf,KAAK,MAAM,gBAAkB,SAAS,eAAe,QAAQ,kCAAkC,EACjG,KAAK,6BAA6B,EAElC,KAAK,qBAAqB,EAGxB,KAAK,QAAQ,SAAW,UAAU,KAAK,eAAe,EAC1D,KAAK,uBAAuB,EAC5B,KAAK,qBAAqB,EAC1B,KAAK,uBAAuB,CAC9B,CAEA,sBAAuB,CACrB,MAAM,YAAc,KAAK,mBAAmB,EAC5C,KAAK,iBAAiB,kBAAkB,EAAE,QAAS,QAAW,CAC5D,OAAO,SAAW,CAAC,YACnB,OAAO,aAAa,gBAAiB,YAAc,QAAU,MAAM,CACrE,CAAC,CACH,CAEA,eAAgB,CACd,KAAK,iBAAiB,eAAe,EAAE,QAAS,QAAW,CAEzD,MAAM,UADU,OAAO,QAAQ,wBAAwB,GAC5B,cAAc,2BAA2B,EAChE,WAAa,UAAU,qBAAuB,QAAQ,UAAU,MAAM,MAAM,EAChF,OAAO,UAAY,uBAAuB,KAAK,WAAa,OAAO,KAAK,UAAU,GAAK,EAAE,GACrF,KAAK,cACP,OAAO,YAAc,KAAK,cAE1B,OAAO,UAAY,KAAK,oBAAoB,CAEhD,CAAC,CACH,CAEA,sBAAuB,CACrB,MAAM,QAAU,KAAK,cAAc,kCAAkC,EACrE,GAAI,CAAC,QAAS,OACd,MAAM,SAAW,SAAS,cAAc,UAAU,EAClD,SAAS,UAAY,KAAK,sBAAsB,KAAK,QAAQ,SAAW,SAAW,kBAAoB,UAAU,EAAE,KAAK,EACxH,MAAM,KAAO,SAAS,QAAQ,kBACzB,OACL,QAAQ,YAAY,IAAI,EACxB,KAAK,iBAAiB,IAAI,EAC5B,CAEA,8BAA+B,CAC7B,KAAK,iBAAiB,gEAAgE,EAAE,QAAS,KAAQ,CACvG,IAAI,UAAU,OAAO,aAAa,EAClC,IAAI,aAAa,eAAgB,OAAO,CAC1C,CAAC,CACH,CAEA,8BAA+B,CAC7B,MAAM,KAAO,KAAK,cAAc,8BAA8B,EAC9D,GAAI,CAAC,KAAM,OACX,MAAM,MAAQ,KAAK,cAAc,EAC3B,QAAU,KAAK,QAAQ,SAAW,SAClC,UAAY,KAAK,kBAAkB,KAAK,sBAAsB,OAAO,EAAG,KAAK,EAC7E,QAAU,KAAK,cAAc,+BAA+B,EAC5D,KAAO,KAAK,8BAA8B,MAAO,QAAS,SAAS,EAAE,KAAK,EAChF,GAAI,CAAC,KAAM,CACL,SAAS,QAAQ,OAAO,EAC5B,MACF,CAEA,MAAM,SAAW,SAAS,cAAc,UAAU,EAClD,SAAS,UAAY,KACrB,MAAM,KAAO,SAAS,QAAQ,kBAC9B,GAAK,KACL,IAAI,QACF,QAAQ,YAAY,IAAI,MACnB,CACL,MAAM,UAAY,KAAK,cAAc,oCAAoC,EACrE,UACF,UAAU,MAAM,IAAI,EAEpB,KAAK,OAAO,IAAI,CAEpB,CACA,KAAK,iBAAiB,IAAI,EAC5B,CAEA,gBAAiB,CACf,MAAM,QAAU,KAAK,cAAc,sBAAsB,EACzD,GAAI,CAAC,QAAS,OACd,MAAM,SAAW,SAAS,cAAc,UAAU,EAClD,SAAS,UAAY,KAAK,gBAAgB,EAAE,KAAK,EACjD,MAAM,KAAO,SAAS,QAAQ,kBAC1B,MAAM,QAAQ,YAAY,IAAI,CACpC,CAEA,wBAAyB,CACvB,MAAM,aAAe,KAAK,8BAA8B,OAAO,EACzD,cAAgB,KAAK,8BAA8B,QAAQ,EAC3D,YAAc,cAAgB,cAE9B,SAAW,CAAE,QADI,YAAc,GAAK,KAAK,4BAA4B,EAC/B,KAAM,WAAY,EAC9D,KAAK,iBAAiB,4BAA4B,EAAE,QAAS,SAAY,CACvE,MAAM,IAAM,QAAQ,QAAQ,mBAAqB,UAC3C,QAAU,SAAS,GAAG,GAAK,GACjC,QAAQ,YAAc,QACtB,QAAQ,OAAS,CAAC,OACpB,CAAC,EAED,CAAC,QAAS,QAAQ,EAAE,QAAS,OAAU,CACrC,MAAM,MAAQ,KAAK,cAAc,sBAAsB,MAAM,CAAC,EAAE,YAAY,CAAC,GAAG,MAAM,MAAM,CAAC,CAAC,IAAI,EAClG,GAAI,CAAC,MAAO,OACZ,MAAM,aAAe,QAAU,QAAU,aAAe,cACxD,MAAM,aAAa,eAAgB,aAAe,OAAS,OAAO,EAC9D,aACF,MAAM,aAAa,mBAAoB,gCAAgC,EAEvE,MAAM,gBAAgB,kBAAkB,CAE5C,CAAC,CACH,CAEA,mBAAoB,CAClB,OAAK,KAAK,aAAa,MAAM,OACtB,KAAK,4BAA4B,KAAK,aAAa,CAAC,EADf,IAE9C,CAEA,4BAA4B,QAAS,CAEnC,GADI,CAAC,KAAK,aAAa,MAAM,QACzB,KAAK,+BAA+B,OAAO,EAAG,OAAO,KACzD,MAAM,SAAW,KAAK,YAAY,KAAK,KAAM,KAAQ,cAAc,IAAI,UAAY,CAAC,EAAG,OAAO,CAAC,GAAK,KACpG,GAAI,KAAK,SAAS,SAAW,YAAc,KAAK,QAAQ,eAAiB,YAAa,CAGpF,MAAM,MAAQ,KAAK,+BAA+B,OAAO,EACzD,GAAI,CAAC,MAAO,OAAO,KACnB,MAAM,gBAAkB,UAAY,OAAO,SAAS,OAAO,KAAK,IAAM,MAAM,MACxE,SAAW,KAAK,yBAAyB,MAAM,KAAK,EACxD,MAAO,CACL,IAAK,cAAc,KAAK,aAAa,IAAI,iBAAiB,OAAO,CAAC,GAClE,SAAU,CAAC,GAAG,OAAO,EACrB,MACA,aAAc,uBAAuB,MAAM,KAAK,EAChD,UAAW,iBAAiB,WAAa,GACzC,WAAY,iBAAiB,YAAc,EAC7C,CACF,CACA,GAAI,UAAY,QAAQ,aAAe,UAAW,OAAO,SACzD,GAAI,UAAY,QAAQ,aAAe,WAAa,KAAK,0BAA0B,QAAQ,QAAQ,EAAG,CAIpG,MAAM,MAAQ,KAAK,+BAA+B,OAAO,EACzD,OAAK,MACE,CACL,GAAG,SACH,IAAK,GAAG,SAAS,GAAG,sBACpB,SAAU,CAAE,GAAG,SAAS,SAAU,WAAY,SAAU,EACxD,MACA,aAAc,uBAAuB,MAAM,KAAK,EAChD,UAAW,GACX,WAAY,EACd,EATmB,IAUrB,CAEA,MAAM,eAAiB,KAAK,6BAA6B,OAAO,EAChE,GAAI,eAAgB,OAAO,eAE3B,MAAM,gBAAkB,KAAK,+BAA+B,OAAO,EACnE,GAAI,CAAC,gBAAiB,OAAO,KAE7B,MAAM,aAAe,KAAK,yBAAyB,gBAAgB,KAAK,EACxE,MAAO,CACL,IAAK,cAAc,KAAK,aAAa,IAAI,iBAAiB,OAAO,CAAC,GAClE,SAAU,CAAE,GAAG,OAAQ,EACvB,MAAO,gBACP,aAAc,uBAAuB,gBAAgB,KAAK,EAC1D,UAAW,cAAc,WAAa,GACtC,WAAY,cAAc,YAAc,EAC1C,CACF,CAEA,6BAA6B,QAAS,CACpC,GAAI,KAAK,SAAS,SAAW,oBAAqB,OAAO,KACzD,MAAM,UAAY,KAAK,aAAa,sBAAsB,MAAQ,KAClE,GAAI,CAAC,UAAW,OAAO,KAEvB,MAAM,MAAQ,OAAO,QAAQ,OAAS,CAAC,EACjC,OAAS,OAAO,QAAQ,QAAU,CAAC,EACnC,SAAW,QAAQ,UAAY,KAAK,QAAQ,iBAAmB,cAC/D,OAAS,QAAQ,QAAU,KAAK,QAAQ,eAAiB,QACzD,SAAW,UAAU,QAAQ,QAAQ,EAE3C,GAAI,CAAC,OAAS,CAAC,QAAU,CAAC,SAAU,OAAO,KAE3C,MAAM,WAAa,gBAAgB,KAAK,YAAY,qBAAqB,WAAY,iBAAiB,KAAK,CAAC,EACtG,YAAc,gBAAgB,KAAK,YAAY,qBAAqB,WAAY,iBAAiB,MAAM,CAAC,EACxG,cAAgB,gBAAgB,KAAK,YAAY,qBAAqB,UAAW,QAAQ,EACzF,YAAc,gBAAgB,KAAK,YAAY,qBAAqB,SAAU,MAAM,EACpF,cAAgB,gBAAgB,KAAK,YAAY,qBAAqB,WAAY,QAAQ,EAEhG,GAAI,CAAC,WAAY,YAAa,cAAe,YAAa,aAAa,EAAE,KAAM,OAAU,MAAQ,CAAC,EAAG,OAAO,KAE5G,MAAM,KAAO,CACX,wBAAwB,WAAY,YAAa,cAAe,YAAa,aAAa,CAC5F,EAEI,QAAU,QACZ,KAAK,KAAK,wBAAwB,YAAa,WAAY,cAAe,YAAa,aAAa,CAAC,EAGvG,MAAM,SAAW,KAAK,KAAM,KAAQ,UAAU,GAAG,CAAC,EAClD,GAAI,CAAC,SAAU,OAAO,KAEtB,MAAM,QAAU,UAAU,QAAQ,EAC5B,MAAQ,MAAM,QAAQ,OAAO,EAAI,OAAO,QAAQ,CAAC,GAAK,CAAC,EAAI,OAAO,SAAW,CAAC,EAC9E,QAAU,KAAK,4BAA4B,KAAK,EAChD,UAAY,gBAAgB,MAAO,OAAQ,EAAI,EAC/C,MAAQ,CACZ,MACA,SAAU,EACV,cAAe,MACf,SACA,IAAK,iBAAiB,iBAAiB,KAAK,CAAC,IAAI,iBAAiB,MAAM,CAAC,IAAI,QAAQ,IAAI,MAAM,IAAI,QAAQ,GAC3G,UACA,SACA,OACA,MAAO,QACT,EAEA,MAAO,CACL,IAAK,eAAe,QAAQ,GAC5B,SAAU,CACR,MAAO,SACP,MACA,OACA,SACA,OACA,QACF,EACA,MACA,aAAc,SAAS,OAAS,uBAAuB,MAAM,KAAK,EAClE,UAAW,SAAS,WAAa,GACjC,WAAY,SAAS,YAAc,EACrC,CACF,CAEA,4BAA4B,MAAO,CACjC,MAAM,SAAW,OAAO,OAAS,CAAC,EAAE,QAAQ,CAAC,EACvC,QAAU,KAAK,YAAY,qBAAqB,gBAAgB,QAAQ,GAAK,KACnF,GAAI,CAAC,QAAS,OAAO,KACrB,GAAI,MAAM,QAAQ,OAAO,EAAG,CAC1B,MAAM,UAAY,QAAQ,CAAC,GAAK,GAChC,MAAO,CACL,MAAO,uBAAuB,KAAK,EACnC,UACA,WAAY,QAAQ,CAAC,IAAM,UAAY,gCAAgC,SAAS,GAAK,GACvF,CACF,CACA,OAAO,OACT,CAEA,kBAAkB,UAAY,CAAC,EAAG,CAEhC,OADY,KAAK,4BAA4B,CAAE,GAAG,KAAK,aAAa,EAAG,GAAG,SAAU,CAAC,GACzE,OAAS,IACvB,CAEA,sBAAsB,UAAY,CAAC,EAAG,CACpC,GAAI,KAAK,iBAAiB,EAAG,MAAO,GACpC,MAAM,IAAM,KAAK,4BAA4B,CAAE,GAAG,KAAK,aAAa,EAAG,GAAG,SAAU,CAAC,EACrF,OAAO,KAAK,UAAY,OAAO,IAAI,SAAS,EAAI,EAClD,CAEA,kBAAmB,CACjB,OAAO,OAAO,KAAK,UAAY,kBAAkB,EAAE,YAAY,IAAM,kBACvE,CAKA,UAAU,MAAO,UAAW,QAAU,GAAO,CAC3C,GAAI,KAAK,iBAAiB,EAAG,OAAO,YAAY,MAAO,KAAK,QAAQ,EACpE,MAAM,GAAK,UAAY,OAAO,SAAS,EAAI,GAC3C,GAAI,CAAC,GAAI,OAAO,SAAW,KAAK,sBAAsB,EAAI,0BAA4B,8BACtF,MAAM,MAAQ,KAAK,kBAAkB,IAAI,EAAE,EAC3C,OAAI,OAAO,cAAc,KAAK,EAAU,YAAY,MAAQ,IAAK,KAAK,QAAQ,EAC1E,QAAU,KAAa,+BAC3B,KAAK,wBAAwB,EAAE,EACxB,0BACT,CAEA,YAAY,MAAO,UAAW,QAAU,GAAO,CAC7C,MAAM,KAAO,KAAK,UAAU,MAAO,UAAW,OAAO,EACrD,GAAI,KAAK,iBAAiB,EAAG,OAAO,KACpC,MAAM,GAAK,UAAY,OAAO,SAAS,EAAI,GAC3C,OAAI,GAAW,mCAAmC,WAAW,EAAE,CAAC,KAAK,WAAW,IAAI,CAAC,UAC9E,QAAU,kCAAkC,WAAW,IAAI,CAAC,UAAY,WAAW,IAAI,CAChG,CAIA,kBAAmB,CACjB,MAAM,aAAe,KAAK,iBAAiB,UAC3C,GAAI,aAAc,OAAO,OAAO,YAAY,EAC5C,GAAI,KAAK,iBAAiB,GAAK,CAAC,KAAK,MAAO,MAAO,GACnD,MAAM,MAAQ,KAAK,sBAAsB,IAAI,KAAK,wBAAwB,EAC1E,OAAO,OAAO,QAAU,YAAc,MAAM,UAAY,OAAO,MAAM,SAAS,EAAI,EACpF,CAEA,uBAAwB,CACtB,GAAI,CAAC,KAAK,OAAS,KAAK,iBAAiB,UAAW,MAAO,GAC3D,MAAM,MAAQ,KAAK,sBAAsB,IAAI,KAAK,wBAAwB,EAC1E,MAAO,GAAQ,KAAK,sBAAwB,OAAO,QAAU,UAC/D,CAEA,8BAA8B,IAAK,CACjC,GAAI,KAAK,iBAAiB,GAAK,MAAQ,KAAK,yBAA0B,OACtE,MAAM,GAAK,KAAK,iBAAiB,EAC5B,KACL,KAAK,iBAAiB,4BAA4B,EAAE,QAAS,SAAY,CACvE,QAAQ,gBAAgB,0BAA0B,EAClD,QAAQ,QAAQ,mBAAqB,EACvC,CAAC,EACG,OAAO,cAAc,KAAK,kBAAkB,IAAI,EAAE,CAAC,EAAG,KAAK,sBAAsB,EAAE,EAClF,KAAK,wBAAwB,EAAE,EACtC,CAEA,gBAAiB,CACf,OAAI,KAAK,QAAgB,YAClB,sBAAiB,KAAK,MAAQ,KAAK,UAAU,KAAK,MAAM,MAAO,KAAK,iBAAiB,EAAG,EAAI,EAAI,gBAAgB,EACzH,CAEA,wBAAwB,UAAW,CACjC,MAAM,GAAK,OAAO,WAAa,EAAE,EACjC,GAAI,CAAC,QAAQ,KAAK,EAAE,GAAK,KAAK,kBAAkB,IAAI,EAAE,GAAK,KAAK,yBAAyB,IAAI,EAAE,EAAG,OAClG,MAAM,KAAO,OAAO,OAAO,SAAS,QAAQ,MAAQ,GAAG,EAAE,QAAQ,OAAQ,GAAG,EACtE,QAAU,MAAM,GAAG,IAAI,YAAY,EAAE,MAAO,CAChD,YAAa,cACb,QAAS,CAAE,OAAQ,kBAAmB,CACxC,CAAC,EACE,KAAM,UAAc,SAAS,GAAK,SAAS,KAAK,EAAI,IAAK,EACzD,KAAM,SAAY,CACjB,MAAM,MAAQ,OAAO,SAAS,KAAK,EACnC,OAAO,OAAO,SAAS,EAAE,IAAM,IAAM,OAAO,cAAc,KAAK,GAAK,MAAQ,EAAI,MAAQ,IAC1F,CAAC,EACA,MAAM,IAAM,IAAI,EAChB,KAAM,OAAU,CACf,KAAK,yBAAyB,OAAO,EAAE,EACvC,KAAK,kBAAkB,IAAI,GAAI,KAAK,EACpC,KAAK,sBAAsB,EAAE,CAC/B,CAAC,EACH,KAAK,yBAAyB,IAAI,GAAI,OAAO,CAC/C,CAEA,sBAAsB,UAAW,CAC/B,MAAM,KAAO,KAAK,UAAU,EAAG,SAAS,EACxC,KAAK,iBAAiB,4BAA4B,EAAE,QAAS,SAAY,CACnE,QAAQ,QAAQ,qBAAuB,YAAW,QAAQ,YAAc,KAC9E,CAAC,EACD,KAAK,qBAAqB,CAC5B,CAEA,+BAA+B,QAAS,CACtC,MAAI,CAAC,KAAK,SAAS,UAAY,CAAC,QAAgB,KAC5C,KAAK,QAAQ,SAAW,WAAmB,sBAAsB,KAAK,QAAQ,SAAU,QAAS,KAAK,OAAO,EAC7G,KAAK,QAAQ,SAAW,SAAiB,oBAAoB,KAAK,QAAQ,SAAU,QAAS,KAAK,OAAO,EACzG,KAAK,QAAQ,SAAW,kBAA0B,4BAA4B,KAAK,QAAQ,SAAU,OAAO,EACzG,IACT,CAEA,yBAAyB,MAAO,CAC9B,MAAM,MAAQ,WAAW,KAAK,EACxB,aAAe,uBAAuB,KAAK,EAC3C,gBAAkB,KAAK,aAAa,eAAiB,CAAC,GAAG,KAAM,SACnE,QAAQ,QAAU,cAAgB,OAAO,QAAQ,KAAK,EAAE,QAAQ,CAAC,IAAM,MAAM,QAAQ,CAAC,CACvF,GAAK,KACN,OAAI,iBAKA,KAAK,iBAAyB,KAE3B,KAAK,uBAAuB,KAAK,EAC1C,CAEA,uBAAuB,MAAO,CAC5B,MAAM,SAAW,OAAO,OAAS,CAAC,EAAE,QAAQ,CAAC,EACvC,QAAU,KAAK,aAAa,iBAAiB,gBAAgB,QAAQ,GAAK,KAChF,GAAI,CAAC,QAAS,OAAO,KACrB,GAAI,MAAM,QAAQ,OAAO,EAAG,CAC1B,MAAM,UAAY,QAAQ,CAAC,GAAK,GAChC,MAAO,CACL,MAAO,uBAAuB,KAAK,EACnC,UACA,WAAY,QAAQ,CAAC,IAAM,UAAY,gCAAgC,SAAS,GAAK,GACvF,CACF,CACA,OAAO,OACT,CAEA,cAAe,CACb,MAAM,QAAU,CACd,cAAe,KAAK,cACpB,MAAO,KAAK,MAAM,MAClB,SAAU,KAAK,MAAM,SACrB,OAAQ,KAAK,MAAM,OACnB,WAAY,KAAK,MAAM,WACvB,MAAO,KAAK,MAAM,MAClB,OAAQ,KAAK,MAAM,OACnB,KAAM,KAAK,MAAM,KACjB,UAAW,KAAK,MAAM,UACtB,SAAU,KAAK,MAAM,SACrB,cAAe,KAAK,MAAM,cAC1B,YAAa,KAAK,MAAM,YACxB,gBAAiB,KAAK,MAAM,eAC9B,EAEA,cAAO,KAAK,OAAO,EAAE,QAAS,KAAQ,EAChC,QAAQ,GAAG,IAAM,QAAa,QAAQ,GAAG,IAAM,KAAI,OAAO,QAAQ,GAAG,CAC3E,CAAC,EAEM,OACT,CAEA,MAAM,WAAY,CAChB,GAAI,KAAK,SAAW,CAAC,KAAK,QAAS,OAEnC,MAAM,aAAe,KAAK,qBAAqB,EACzC,wBAA0B,aAAa,SAAW,KAAK,yBAAyB,EAChF,iBAAmB,KAAK,MAAM,cAAgB,cAEpD,GAAI,CAAC,yBAA2B,CAAC,iBAAkB,CACjD,KAAK,cAAgB,yBAAyB,KAAK,yBAAyB,CAAC,YAAY,KAAK,yBAAyB,IAAM,EAAI,OAAS,OAAO,4BACjJ,KAAK,WAAa,QAClB,KAAK,qBAAqB,EAC1B,MACF,CAEA,MAAM,cAAgB,aAAa,KAAM,MAAS,KAAK,KAAO,QAA2B,EACzF,GAAI,cAAe,CACjB,KAAK,cAAgB,GAAG,cAAc,IAAI,6CAC1C,KAAK,WAAa,QAClB,KAAK,OAAO,EACZ,KAAK,iBAAiB,EACtB,MACF,CAGA,GAD6B,aAAa,OAAO,CAAC,MAAO,OAAS,MAAQ,OAAO,KAAK,MAAQ,CAAC,EAAG,CAAC,EACxE,SAA8B,CACvD,KAAK,cAAgB,6EACrB,KAAK,WAAa,QAClB,KAAK,OAAO,EACZ,KAAK,iBAAiB,EACtB,MACF,CAGA,GADwB,aAAa,KAAM,MAAS,CAAC,qBAAqB,KAAK,IAAI,CAAC,EAC/D,CACnB,KAAK,cAAgB,8EACrB,KAAK,WAAa,QAClB,KAAK,OAAO,EACZ,KAAK,iBAAiB,EACtB,MACF,CAEA,KAAK,QAAU,GACf,KAAK,cAAgB,qFACrB,KAAK,WAAa,GAClB,KAAK,OAAO,EAEZ,GAAI,CACG,kBACH,MAAM,KAAK,sBAAsB,YAAY,EAG/C,IAAI,MAAQ,KAAK,MACb,UAAY,KAAK,iBAAiB,UAEtC,GAAI,CAAC,YAAc,CAAC,KAAK,SAAW,CAAC,KAAK,kBACxC,MAAM,IAAI,MAAM,wGAAwG,EAG1H,GAAI,CAAC,UAAW,CACd,MAAM,SAAW,MAAM,KAAK,yBAAyB,KAAK,aAAa,EAAG,OAAW,CAAE,QAAS,EAAK,CAAC,EACtG,KAAK,oBAAoB,SAAU,KAAK,EACxC,MAAQ,SAAS,MACjB,UAAY,SAAS,QAAQ,EAC/B,CAEA,MAAM,YAAc,MAAM,KAAK,2BAA2B,CACxD,UACA,MACA,aACA,iBAAkB,EACpB,CAAC,EAEK,eAAiB,YAAY,YAAc,YAAY,IAAM,UACnE,KAAK,6BAA6B,cAAc,EAChD,MAAM,KAAK,eAAe,YAAa,cAAc,CACvD,OAAS,MAAO,CACd,KAAK,QAAU,GACf,KAAK,cAAgB,kCAAkC,MAAM,OAAO,EAChE,iFACA,kBAAkB,MAAM,QAAS,wCAAwC,EAC7E,KAAK,WAAa,QAClB,KAAK,OAAO,EACZ,KAAK,iBAAiB,CACxB,CACF,CAEA,aAAa,CAAE,UAAW,MAAO,YAAa,EAAG,CAC/C,MAAM,SAAW,IAAI,SACrB,gBAAS,OAAO,KAAM,SAAS,EAC/B,SAAS,OAAO,WAAY,GAAG,EAC/B,SAAS,OAAO,WAAY,qBAAqB,EACjD,SAAS,OAAO,eAAgB,OAAO,SAAS,QAAQ,EACxD,KAAK,eAAe,MAAO,YAAY,EAAE,QAAQ,CAAC,CAAC,IAAK,KAAK,IAAM,CACtC,OAAU,MAAQ,OAAO,KAAK,EAAE,KAAK,IAAM,IACpE,SAAS,OAAO,cAAc,GAAG,IAAK,KAAK,CAE/C,CAAC,EAEM,QACT,CAEA,MAAM,2BAA2B,CAAE,UAAW,MAAO,aAAc,iBAAmB,EAAM,EAAG,CAC7F,MAAM,UAAY,OAAO,WAAW,EAC9B,YAAc,iBAAmB,CAAC,EAAG,IAAK,KAAM,KAAM,KAAM,GAAI,EAAI,CAAC,CAAC,EAC5E,IAAI,gBAAkB,UAClB,YAAc,MACd,UAAY,KAEhB,QAAS,QAAU,EAAG,QAAU,YAAY,OAAQ,SAAW,EAAG,CAChE,MAAM,MAAQ,YAAY,OAAO,EAC7B,MAAQ,GAAG,MAAM,MAAM,KAAK,EAEhC,MAAM,aAAe,MAAM,MAAM,eAAgB,CAC/C,OAAQ,OACR,QAAS,CAAE,OAAQ,mBAAoB,uBAAwB,SAAU,EACzE,KAAM,KAAK,aAAa,CAAE,UAAW,gBAAiB,MAAO,YAAa,YAAa,CAAC,CAC1F,CAAC,EACK,YAAc,MAAM,aAAa,aAAc,6BAA6B,EAElF,GAAI,aAAa,GACf,OAAO,YAIT,GADA,UAAY,IAAI,MAAM,YAAY,aAAe,YAAY,SAAW,6BAA6B,EACjG,CAAC,kBAAoB,aAAa,SAAW,KAAO,CAAC,kCAAkC,UAAU,OAAO,GAAK,UAAY,YAAY,OAAS,EAChJ,MAAM,UAWR,GAAI,KAAK,SAAW,0CAA0C,KAAK,UAAU,OAAO,EAClF,GAAI,CAEF,KAAK,qBAAqB,QAAQ,CAAC,MAAO,MAAQ,CAC5C,MAAM,QAAU,YAAc,OAAO,MAAM,SAAS,IAAM,OAAO,eAAe,GAAG,KAAK,qBAAqB,OAAO,GAAG,CAC7H,CAAC,EACD,MAAM,SAAW,MAAM,KAAK,yBAAyB,KAAK,aAAa,EAAG,OAAW,CAAE,QAAS,EAAK,CAAC,EAClG,UAAU,SAAS,KACrB,KAAK,oBAAoB,SAAU,KAAK,EACxC,gBAAkB,SAAS,QAAQ,GACnC,YAAc,SAAS,OAAS,YAEpC,OAAS,aAAc,CACrB,GAAI,aAAa,OAAS,sBAAuB,MAAM,aACnD,aAAa,OAAS,cACxB,QAAQ,KAAK,mDAAoD,YAAY,CAEjF,CAEJ,CAEA,MAAM,WAAa,IAAI,MAAM,6BAA6B,CAC5D,CAEA,oBAAoB,SAAU,YAAa,CACzC,MAAM,OAAS,KAAK,MAAM,OAAO,aAAa,KAAK,EAAI,GAAG,EAC1D,GAAI,EAAE,OAAS,IAAM,KAAK,MAAM,OAAO,UAAU,OAAO,KAAK,EAAI,GAAG,IAAM,QAAU,KAAK,MAAM,OAAO,UAAU,SAAS,KAAK,EAAI,GAAG,IAAM,OAAQ,CACjJ,MAAM,MAAQ,IAAI,MAAM,sGAAsG,EAE9H,GADA,MAAM,KAAO,sBACT,KAAK,SAAW,KAAK,cAAe,CACtC,MAAM,SAAW,KAAK,aAAa,EACnC,MAAM,GAAG,KAAK,OAAO,iCAAkC,CACrD,OAAQ,OAAQ,QAAS,CAAE,eAAgB,kBAAmB,EAAG,UAAW,GAC5E,KAAM,KAAK,UAAU,CACnB,KAAM,yBAA0B,cAAe,KAAK,cAAe,MAAO,WAC1E,UAAW,OAAO,UAAU,SAAS,IAAM,EAAE,EAAG,MAAO,SAAS,MAAO,KAAM,SAAS,WAAa,SAAS,KAC5G,SAAU,SAAS,eAAiB,SAAS,SAAU,SAAU,SAAS,SAAU,OAAQ,SAAS,OACrG,WAAY,SAAS,WAAY,eAAgB,OAAO,aAAa,OAAS,EAAE,EAChF,MAAO,mCAAmC,aAAa,KAAK,cAAc,UAAU,OAAO,KAAK,aAAa,UAAU,SAAS,KAAK,EACvI,CAAC,CACH,CAAC,EAAE,MAAM,IAAM,CAAC,CAAC,CACnB,CACA,MAAM,KACR,CACF,CAEA,8BAA8B,QAAU,KAAK,aAAa,EAAG,CAG3D,MAFI,GAAC,KAAK,SAAW,CAAC,KAAK,kBAAoB,CAAC,KAAK,SACjD,CAAC,KAAK,OAAS,KAAK,0BAA0B,OAAO,GACrD,KAAK,iBAAiB,UAE5B,CAEA,mBAAmB,QAAU,KAAK,aAAa,EAAG,MAAQ,KAAK,MAAO,CACpE,MAAM,MAAQ,OAAO,OAAO,OAAS,CAAC,EAAE,QAAQ,CAAC,EACjD,MAAO,GAAG,iBAAiB,OAAO,CAAC,UAAU,KAAK,EACpD,CAEA,2BAA4B,CACtB,KAAK,uBACP,OAAO,aAAa,KAAK,oBAAoB,EAC7C,KAAK,qBAAuB,KAEhC,CAEA,oCAAoC,UAAW,CACxC,KAAK,sBACV,KAAK,qBAAqB,QAAQ,CAAC,MAAO,MAAQ,CAC5C,MAAQ,YAER,OAAO,QAAU,WAAa,MAAM,UACpC,OAAO,QAAU,WAAW,MAAM,YAAY,MAAM,CACtD,KAAM,aACN,QAAS,yCACT,KAAM,0BACR,CAAC,EACD,KAAK,qBAAqB,OAAO,GAAG,GACtC,CAAC,CACH,CAEA,gCAAiC,CAC/B,KAAK,0BAA0B,EAC/B,KAAK,yBAA2B,GAChC,KAAK,oCAAoC,EAAE,CAC7C,CAEA,kCAAmC,CACjC,KAAK,0BAA0B,EAC/B,MAAM,QAAU,KAAK,aAAa,EAElC,GAAI,CAAC,KAAK,8BAA8B,OAAO,EAAG,CAChD,KAAK,+BAA+B,EACpC,MACF,CAEA,MAAM,IAAM,KAAK,mBAAmB,OAAO,EAI3C,GAHA,KAAK,yBAA2B,IAChC,KAAK,oCAAoC,GAAG,EAExC,KAAK,qBAAqB,IAAI,GAAG,EAAG,OAExC,MAAM,gBAAkB,CAAE,GAAG,OAAQ,EACrC,KAAK,qBAAuB,OAAO,WAAW,IAAM,CAClD,KAAK,qBAAuB,KAC5B,KAAK,yBAAyB,gBAAiB,GAAG,EAAE,MAAO,OAAU,CAC/D,MAAM,OAAS,cACjB,QAAQ,KAAK,mDAAoD,KAAK,CAE1E,CAAC,CACH,EAAG,GAAG,CACR,CAEA,MAAM,yBAAyB,QAAU,KAAK,aAAa,EAAG,IAAM,KAAK,mBAAmB,OAAO,EAAG,CAAE,QAAU,EAAM,EAAI,CAAC,EAAG,CAC9H,MAAM,OAAS,KAAK,qBAAqB,IAAI,GAAG,EAChD,GAAI,QAAU,CAAC,OAAO,YAAY,OAAO,SAAW,OAAO,QAAU,WACnE,OAAI,UAAS,OAAO,QAAU,IACvB,OAAO,QAGhB,MAAM,WAAa,IAAI,gBACjB,MAAQ,CACZ,MAAO,UACP,QACA,WACA,QAAS,IACX,EAEA,aAAM,SAAW,SAAY,CAC3B,IAAI,SAAW,EACf,QAAS,QAAU,GAAK,UAAW,CACjC,MAAM,SAAW,MAAM,MAAM,GAAG,KAAK,OAAO,iCAAkC,CAC5E,OAAQ,OACR,QAAS,CAAE,eAAgB,mBAAoB,OAAQ,mBAAoB,yBAA0B,MAAO,EAC5G,KAAM,KAAK,UAAU,OAAO,EAC5B,OAAQ,WAAW,MACrB,CAAC,EACK,gBAAkB,MAAM,aAAa,SAAU,yGAAyG,EAC9J,GAAI,SAAS,GACX,aAAM,MAAQ,WACd,MAAM,UAAY,gBAAgB,SAAS,GAC3C,KAAK,8BAA8B,GAAG,EAC/B,gBAET,MAAM,MAAQ,gBAAgB,iBACxB,QAAU,OAAO,OAAO,YAAY,EAAI,IAG9C,GAAI,CAAC,MAAM,SAAW,SAAS,SAAW,KAAO,OAAO,OAAS,IAAQ,MAAM,SAAW,qBACrF,CAAC,OAAO,SAAS,OAAO,GAAK,SAAW,GAAK,SAAW,GAAK,SAAW,QAAU,KACrF,MAAM,IAAI,MAAM,gBAAgB,OAAS,mCAAmC,EAE9E,UAAY,QACZ,MAAM,KAAK,wBAAwB,MAAO,OAAO,CACnD,CACF,GAAG,EACA,MAAO,OAAU,CAChB,MAAI,KAAK,qBAAqB,IAAI,GAAG,IAAM,OAAO,KAAK,qBAAqB,OAAO,GAAG,EACtF,MAAM,MAAQ,WACR,KACR,CAAC,EAEH,KAAK,qBAAqB,IAAI,IAAK,KAAK,EACjC,MAAM,OACf,CAEA,MAAM,wBAAwB,MAAO,QAAS,CAC5C,MAAM,SAAW,KAAK,IAAI,EAAI,QAC9B,EAAG,CACD,GAAI,MAAM,WAAW,OAAO,QAAS,MAAM,MAAM,WAAW,OAAO,QAAU,IAAI,aAAa,YAAa,YAAY,EACvH,MAAM,UAAY,KAAK,IAAI,EAAG,SAAW,KAAK,IAAI,CAAC,EACnD,GAAI,CAAC,UAAW,MAChB,KAAK,cAAgB,qEAAqE,KAAK,KAAK,UAAY,GAAI,CAAC,cACrH,KAAK,WAAa,GAClB,MAAMC,QAAS,KAAK,cAAc,eAAe,EAC7CA,UAAUA,QAAO,YAAc,KAAK,cAAeA,QAAO,UAAU,OAAO,UAAU,GACzF,MAAM,IAAI,QAAS,SAAY,OAAO,WAAW,QAAS,KAAK,IAAI,IAAM,SAAS,CAAC,CAAC,CACtF,OAAS,IACT,GAAI,MAAM,WAAW,OAAO,QAAS,MAAM,MAAM,WAAW,OAAO,QAAU,IAAI,aAAa,YAAa,YAAY,EACvH,KAAK,cAAgB,mDACrB,MAAM,OAAS,KAAK,cAAc,eAAe,EAC7C,SAAQ,OAAO,YAAc,KAAK,cACxC,CAEA,eAAe,MAAO,aAAc,CAClC,MAAM,cAAgB,MAAM,QAAQ,YAAY,EAAI,aAAe,CAAC,EAC9D,OAAS,OAAO,KAAK,YAAY,KAAK,MAAM,MAAM,GAAK,EAAE,EAAE,KAAK,EAChE,iBAAmB,CAAC,CAAC,GAAI,OAAQ,UAAW,WAAW,EAAE,SAAS,OAAO,YAAY,CAAC,EACtF,oBAAsB,KAAK,IAAI,EAAG,OAAO,MAAM,iBAAmB,KAAK,MAAM,iBAAmB,CAAC,CAAC,EAClG,aAAe,KAAK,MAAM,cAAgB,cAC5C,8BACC,KAAK,sBAAwB,cAAc,CAAC,GAAG,KAAO,mBAAc,cAAc,CAAC,EAAE,IAAI,GAAK,cAAc,CAAC,GAAG,KAC/G,MAAQ,CACZ,CAAC,sBAAuB,KAAK,QAAQ,cAAgB,KAAK,YAAY,EAGtE,CAAC,oBAAqB,YAAY,MAAM,MAAO,kBAAkB,CAAC,EAClE,CAAC,kBAAmB,KAAK,aAAa,EACtC,CAAC,iBAAkB,KAAK,mBAAmB,CAAC,EAC5C,CAAC,iBAAkB,KAAK,QAAQ,UAAU,MAAQ,YAAY,EAC9D,CAAC,kBAAmB,KAAK,QAAQ,UAAU,eAAiB,SAAS,CACvE,EACI,KAAK,MAAM,cAAgB,eAAiB,KAAK,uBACnD,MAAM,KAAK,CAAC,oBAAqB,KAAK,oBAAoB,CAAC,EAC3D,MAAM,KAAK,CAAC,kBAAmB,KAAK,gBAAgB,CAAC,GAGnD,KAAK,QAAQ,SAAW,qBAC1B,MAAM,KAAK,CAAC,iBAAkB,KAAK,MAAM,iBAAmB,eAAe,CAAC,EAEzE,KAAK,QAAQ,aAAa,MAAM,KAAK,CAAC,QAAS,KAAK,WAAW,KAAK,MAAM,KAAK,CAAC,CAAC,EACtF,MAAM,KAAK,CAAC,OAAQ,KAAK,MAAM,WAAa,KAAK,MAAM,IAAI,CAAC,EACxD,KAAK,MAAM,UAAU,MAAM,KAAK,CAAC,WAAY,KAAK,cAAc,KAAK,MAAM,QAAQ,CAAC,CAAC,EACrF,kBAAkB,MAAM,KAAK,CAAC,SAAU,MAAM,CAAC,EAC/C,KAAK,MAAM,aAAe,WAC5B,MAAM,KAAK,CAAC,aAAc,GAAG,KAAK,0BAA0B,KAAK,MAAM,QAAQ,IAAM,QAAU,QAAU,OAAO,aAAa,CAAC,EAEhI,MAAM,KAAK,CAAC,iBAAkB,MAAM,cAAgB,GAAG,MAAM,aAAa,UAAY,EAAE,CAAC,EACzF,MAAM,KAAK,CAAC,mBAAoB,MAAM,UAAY,EAAE,CAAC,EACjD,KAAK,QAAQ,SAAW,UAAY,oBAAsB,GAC5D,MAAM,KAAK,CAAC,mBAAoB,mBAAmB,CAAC,EAElD,KAAK,MAAM,aAAe,KAAK,QAAQ,SAAW,iBAAiB,MAAM,KAAK,CAAC,cAAe,KAAK,MAAM,WAAW,CAAC,EACzH,MAAM,KAAK,CAAC,UAAW,YAAY,CAAC,EACpC,cAAc,MAAM,CAAC,EAAE,QAAQ,CAAC,KAAM,QAAU,CAC9C,MAAM,KAAK,CAAC,WAAW,MAAQ,CAAC,GAAI,KAAK,IAAI,CAAC,CAChD,CAAC,EACD,MAAM,KAAK,CAAC,gBAAiB,KAAK,cAAc,6BAA6B,GAAG,OAAS,EAAE,CAAC,EAC5F,MAAM,cAAgB,OAAO,KAAK,cAAc,qCAAqC,GAAG,OAAS,EAAE,EAAE,KAAK,EAC1G,OAAI,KAAK,MAAM,cAAgB,eAAiB,eAC9C,MAAM,KAAK,CAAC,yBAA0B,aAAa,CAAC,EAEtD,MAAM,KAAK,CAAC,WAAY,KAAK,QAAQ,SAAW,SAAW,GAAG,MAAM,aAAa,UAAY,GAAG,MAAM,UAAY,KAAK,MAAM,QAAQ,EAAE,CAAC,EACxI,MAAM,KAAK,CAAC,gBAAiB,iEAA4D,CAAC,EACnF,KACT,CAEA,oBAAqB,CACnB,MAAM,MAAQ,CAAC,SAAU,SAAU,SAAU,YAAa,UAAW,MAAM,EACrE,OAAS,KAAK,QAAQ,UAAU,QAAU,CAAC,EAC3C,QAAU,MAAM,OAAQ,KAAQ,OAAO,GAAG,CAAC,EAAE,IAAK,MAAS,CAAE,MAAO,IAAK,MAAO,OAAO,GAAG,CAAE,EAAE,EACpG,OAAO,KAAK,oBAAoB,QAAS,QAAS,OAAO,CAC3D,CAEA,mBAAoB,CAClB,MAAM,QAAU,KAAK,aAAa,EAClC,OAAO,KAAK,wBAAwB,OAAQ,CAAC,GAAG,QAAS,CAAE,MAAO,SAAU,MAAO,aAAc,CAAC,CAAC,CACrG,CAEA,wBAAwB,MAAO,QAAS,CACtC,OAAK,SAAS,OAIP;AAAA,qEAHa,KAAK,SAAS,SAAW,oBACzC,oCACA,sCAEwE;AAAA,cAClE,WAAW,KAAK,eAAe,KAAK,CAAC,CAAC;AAAA;AAAA,YAExC,QAAQ,IAAK,QAAW,CACxB,MAAM,SAAW,OAAO,QAAU,SAClC,GAAI,UAAY,KAAK,MAAM,WAAY,CACrC,MAAM,aAAe,KAAK,8BAA8B,OAAO,EACzD,cAAgB,KAAK,8BAA8B,QAAQ,EAC3D,YAAc,cAAgB,cAC9B,eAAiB,YAAc,GAAK,KAAK,4BAA4B,EAC3E,MAAO;AAAA;AAAA;AAAA,2IAGsH,WAAW,KAAK,MAAM,OAAS,EAAE,CAAC,iEAAiE,aAAe,OAAS,OAAO,IAAI,aAAe,qDAAuD,EAAE;AAAA;AAAA;AAAA,4IAG7M,WAAW,KAAK,MAAM,QAAU,EAAE,CAAC,mEAAmE,cAAgB,OAAS,OAAO,IAAI,cAAgB,qDAAuD,EAAE;AAAA;AAAA,6GAElP,YAAc,GAAK,SAAS,IAAI,WAAW,WAAW,CAAC;AAAA,4EACxF,eAAiB,GAAK,SAAS,IAAI,WAAW,cAAc,CAAC;AAAA;AAAA,eAG7H,CAGA,MAAO;AAAA;AAAA;AAAA,8CADU,SAAW,KAAK,MAAM,WAAa,OAAO,KAAK,MAAM,IAAI,IAAM,OAAO,OAAO,KAAK,GAIvD,eAAiB,EAAE;AAAA;AAAA;AAAA,8BAG7C,WAAW,OAAO,KAAK,CAAC;AAAA;AAAA,wBAE9B,WAAW,OAAO,KAAK,CAAC;AAAA;AAAA,aAGtC,CAAC,EAAE,KAAK,EAAE,CAAC;AAAA;AAAA;AAAA,MAzCY,EA6C/B,CAEA,cAAe,CAMb,OALsB,CAAC,YAAa,MAAM,EAAE,SAAS,KAAK,MAAM,KAAK,EAEjE,CAAC,UAAW,UAAW,UAAW,SAAS,EAC3C,CAAC,UAAW,UAAW,UAAW,SAAS,GAEjC,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CACxD,CAEA,iBAAkB,CAChB,MAAO;AAAA;AAAA;AAAA;AAAA,mFAIwE,KAAK,OAAO,UAAY,GAAG;AAAA;AAAA;AAAA,KAI5G,CAEA,uBAAwB,CACtB,MAAM,UAAY,KAAK,gBAAgB,EACvC,OAAK,UAAU,OACR,KAAK,oBAAoB,WAAY,WAAY,SAAS,EADnC,EAEhC,CAEA,iBAAkB,CAChB,MAAM,QAAU,KAAK,QACrB,GAAI,QAAQ,SAAW,oBAErB,OADe,QAAQ,eAAiB,QAAQ,UAAU,YAAY,WAAa,CAAC,GACtE,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,EAGxD,MAAM,OAAS,QAAQ,SAAW,SAAW,QAAQ,UAAU,eAAiB,QAAQ,UAAU,UAClG,OAAO,OAAO,QAAQ,QAAU,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,MAAO,QAAQ,IAAM,CAC7D,GAAI,QAAQ,SAAW,WAAY,CACjC,GAAI,QAAU,aAAc,MAAO,CAAE,MAAO,MAAO,OAAQ,EAC3D,GAAI,QAAU,cAAe,MAAO,CAAE,MAAO,MAAO,QAAS,CAC/D,CACA,MAAO,CAAE,MAAO,MAAO,SAAS,OAAS,KAAM,CACjD,CAAC,CACH,CAEA,qBAAsB,CACpB,MAAM,QAAU,KAAK,mBAAmB,EACxC,OAAO,KAAK,oBAAoB,SAAU,SAAU,OAAO,CAC7D,CAEA,mBAAmB,SAAW,KAAK,MAAM,SAAU,CACjD,MAAM,OAAS,KAAK,QAAQ,UAAU,eAAiB,CAAC,EACxD,OAAO,OAAO,QAAQ,MAAM,EACzB,OAAO,CAAC,CAAC,KAAK,IAAM,kCAAkC,SAAU,KAAK,CAAC,EACtE,IAAI,CAAC,CAAC,MAAO,MAAM,KAAO,CAAE,MAAO,MAAO,OAAO,OAAS,KAAM,EAAE,CACvE,CAEA,sBAAsB,OAAQ,SAAW,KAAK,MAAM,SAAU,CAE5D,MAAM,OADU,KAAK,mBAAmB,QAAQ,EACzB,IAAK,QAAW,OAAO,KAAK,EACnD,OAAI,OAAO,SAAS,MAAM,EAAU,OAChC,OAAO,SAAS,KAAK,QAAQ,aAAa,EAAU,KAAK,QAAQ,cAC9D,OAAO,CAAC,GAAK,MACtB,CAEA,8BAA+B,CAC7B,MAAM,cAAgB,KAAK,qBAAqB,EAC1C,QAAU,CACd,CAAE,MAAO,IAAK,MAAO,WAAY,EACjC,CAAE,MAAO,IAAK,MAAO,YAAa,EAClC,CAAE,MAAO,IAAK,MAAO,YAAa,EAClC,CAAE,MAAO,SAAU,MAAO,yBAA0B,CACtD,EAEA,MAAO;AAAA;AAAA;AAAA,gBAGK,WAAW,KAAK,eAAe,UAAU,CAAC,CAAC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,0DAUD,KAAK,qBAAuB,QAAU,EAAE;AAAA;AAAA,0CAExD,WAAW,aAAa,CAAC;AAAA;AAAA;AAAA;AAAA,cAIrD,QAAQ,IAAK,QAAW;AAAA;AAAA;AAAA,uDAGiB,OAAO,QAAU,SAAW,KAAK,MAAM,sBAAyB,CAAC,KAAK,MAAM,uBAAyB,OAAO,KAAK,MAAM,eAAe,IAAM,OAAO,OAAU,eAAiB,EAAE;AAAA;AAAA;AAAA,8BAGzM,OAAO,KAAK;AAAA,iBACzB,WAAW,OAAO,KAAK,CAAC;AAAA,gBACzB,OAAO,QAAU,UAAY,KAAK,MAAM,sBAAwB;AAAA;AAAA;AAAA,2JAG2E,WAAW,KAAK,MAAM,iBAAmB,EAAE,CAAC;AAAA;AAAA,gBAErL,EAAE;AAAA,aACP,EAAE,KAAK,EAAE,CAAC;AAAA;AAAA;AAAA;AAAA,KAKrB,CAEA,sBAAuB,CACrB,OAAO,KAAK,MAAM,sBACd,WAAW,aAAa,KAAK,MAAM,iBAAmB,CAAC,CAAC,YACvD,CAAE,EAAG,YAAa,EAAG,aAAc,EAAG,YAAa,EAAE,KAAK,MAAM,eAAe,GAAK,WAC3F,CAEA,6BAA8B,CAC5B,MAAM,QAAU,KAAK,cAAc,yBAAyB,EACxD,UAAS,QAAQ,YAAc,KAAK,qBAAqB,EAC/D,CAEA,eAAe,MAAO,CACpB,MAAO,CAAC,UAAW,eAAe,EAAE,SAAS,OAAO,OAAS,EAAE,EAAE,YAAY,EAAE,QAAQ,UAAW,EAAE,CAAC,CACvG,CAEA,oBAAoB,QAAS,CAC3B,OAAI,KAAK,SAAS,SAAW,oBAA4B,SACjD,SAAW,CAAC,GAAG,OAAQ,QAAW,CAAC,KAAK,eAAe,OAAO,KAAK,CAAC,CAC9E,CAEA,gCAAiC,CAC/B,GAAI,KAAK,SAAS,SAAW,qBAAuB,CAAC,KAAK,eAAe,KAAK,OAAO,KAAK,EAAG,OAE7F,MAAM,QAAU,KAAK,SAAS,SAAW,gBACrC,KAAK,aAAa,EAClB,CAAC,SAAU,SAAU,SAAU,YAAa,UAAW,MAAM,EAC5D,OAAQ,KAAQ,KAAK,SAAS,UAAU,SAAS,GAAG,CAAC,EACrD,IAAK,MAAS,CAAE,MAAO,IAAK,MAAO,KAAK,QAAQ,SAAS,OAAO,GAAG,CAAE,EAAE,EACtE,SAAW,KAAK,oBAAoB,OAAO,EAAE,CAAC,EAChD,WAAU,KAAK,MAAM,MAAQ,SAAS,MAC5C,CAEA,6BAA8B,CAC5B,MAAM,SAAW,KAAK,cAAc,kCAAkC,EAChE,MAAQ,UAAU,cAAc,+BAA+B,EACrE,GAAI,CAAC,UAAY,CAAC,MAAO,OAEzB,KAAK,qBAAuB,GAC5B,SAAS,gBAAgB,MAAM,EAC/B,KAAK,4BAA4B,EAEjC,MAAM,cAAgB,KAAK,MAAM,sBAAwB,SAAW,OAAO,KAAK,MAAM,eAAe,EACrG,MAAM,iBAAiB,gCAAgC,EAAE,QAAS,QAAW,CAC3E,OAAO,UAAU,OAAO,cAAe,OAAO,QAAQ,QAAU,aAAa,CAC/E,CAAC,EAED,MAAM,cAAgB,MAAM,cAAc,gCAAgC,EAC1E,GAAI,CAAC,KAAK,MAAM,sBAAuB,CACrC,eAAe,OAAO,EACtB,MACF,CAEA,GAAI,cAAe,CACjB,MAAM,MAAQ,cAAc,cAAc,sCAAsC,EAC5E,QAAO,MAAM,MAAQ,OAAO,KAAK,MAAM,iBAAmB,CAAC,GAC/D,MACF,CAEA,MAAM,aAAe,MAAM,cAAc,qDAAqD,EAC9F,GAAI,CAAC,aAAc,OACnB,MAAM,OAAS,SAAS,cAAc,KAAK,EAC3C,OAAO,UAAY,gCACnB,OAAO,UAAY;AAAA;AAAA,+IAEwH,WAAW,KAAK,MAAM,iBAAmB,CAAC,CAAC;AAAA,MAEtL,aAAa,MAAM,MAAM,EACzB,KAAK,iBAAiB,MAAM,CAC9B,CAEA,sBAAsB,MAAO,CAC3B,MAAM,QAAU,KAAK,QAAQ,SAAW,SAClC,sBAAwB,KAAK,sBAAsB,EACnD,eAAiB,sBAAwB,KAAK,gBAAgB,EAAI,CAAC,EACnE,OAAS,sBACV,KAAK,uBAAyB,eAAiB,eAAe,MAAM,EAAG,CAAC,EACzE,KAAK,sBAAsB,OAAO,EAChC,MAAQ,KAAK,cAAc,EAC3B,UAAY,KAAK,kBAAkB,OAAQ,KAAK,EAEtD,MAAO;AAAA;AAAA;AAAA,gBAGK,WAAW,KAAK,eAAe,KAAK,CAAC,CAAC;AAAA;AAAA;AAAA,YAG1C,OAAO,IAAK,OAAU,KAAK,kBAAkB,MAAO,MAAO,QAAS,SAAS,CAAC,EAAE,KAAK,EAAE,CAAC;AAAA,YACxF,sBAAwB,KAAK,8BAA8B,eAAe,MAAM,EAAI;AAAA,cAClF,KAAK,8BAA8B,MAAO,QAAS,SAAS,CAAC;AAAA,cAC7D,KAAK,wBAAwB,MAAO,OAAO,CAAC;AAAA,WAC/C;AAAA;AAAA;AAAA,KAIT,CAEA,yBAA0B,CAExB,GAAI,CADS,KAAK,0BAA0B,KAAK,MAAM,QAAQ,EACpD,MAAO,GAClB,MAAM,SAAW,KAAK,MAAM,aAAe,UAAY,UAAY,OACnE,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,wEAgB6D,WAAa,OAAS,eAAiB,EAAE,sFAAsF,WAAa,MAAM;AAAA;AAAA;AAAA;AAAA,wEAIlJ,WAAa,UAAY,eAAiB,EAAE,yFAAyF,WAAa,SAAS;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAOjO,CAEA,0BAA0B,SAAU,CAClC,MAAM,IAAM,OAAO,UAAY,EAAE,EAAE,YAAY,EACzC,MAAQ,OAAO,KAAK,QAAQ,UAAU,YAAY,QAAQ,GAAG,OAAS,EAAE,EAAE,YAAY,EAC5F,OAAI,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,GAAK,IAAI,SAAS,SAAS,GAAK,MAAM,SAAS,UAAU,EAAU,GAClH,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,EAAU,QACzD,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,GAAK,MAAQ,SAAW,QAAU,QAAgB,QAC9F,EACT,CAEA,uBAAwB,CACtB,OAAO,KAAK,SAAS,SAAW,mBAClC,CAEA,8BAA8B,qBAAsB,CAClD,GAAI,sBAAwB,EAAG,MAAO,GACtC,MAAM,SAAW,KAAK,uBACtB,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA,yBAKc,QAAQ;AAAA;AAAA,gBAEjB,SAAW,wBAA0B,sBAAsB;AAAA,kFACO,SAAW,SAAM,GAAG;AAAA;AAAA,KAGpG,CAEA,eAAgB,CACd,OAAO,KAAK,SAAS,SAAW,SAAW,gBAAkB,UAC/D,CAEA,sBAAsB,QAAU,KAAK,QAAQ,SAAW,SAAU,CAChE,OAAO,QACH,CAAC,GAAI,IAAK,IAAK,IAAK,IAAK,IAAM,IAAM,IAAM,GAAI,EAC/C,KAAK,QAAQ,SAAW,kBACtB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EAAE,MAAM,EAAG,CAAC,CACzC,CAEA,kBAAkB,OAAQ,MAAO,CAC/B,UAAW,SAAS,OAAQ,CAC1B,MAAM,MAAQ,KAAK,kBAAkB,CAAE,CAAC,KAAK,EAAG,OAAO,KAAK,CAAE,CAAC,EAC/D,GAAI,KAAK,aAAa,KAAK,EAAI,EAAG,OAAO,KAC3C,CACA,OAAO,IACT,CAEA,kBAAkB,MAAO,MAAO,QAAS,UAAY,KAAM,CACzD,MAAM,SAAW,KAAK,kBAAkB,CAAE,CAAC,KAAK,EAAG,OAAO,KAAK,CAAE,CAAC,EAC5D,SAAW,CAAC,KAAK,MAAM,gBAAkB,OAAO,KAAK,MAAM,KAAK,CAAC,IAAM,OAAO,KAAK,EACzF,OAAO,KAAK,qBAAqB,MAAO,MAAO,QAAS,SAAU,UAAW,QAAQ,CACvF,CAEA,8BAA8B,MAAO,QAAS,UAAY,KAAM,CAC9D,GAAI,CAAC,KAAK,MAAM,gBAAkB,OAAO,KAAK,MAAM,KAAK,GAAK,CAAC,GAAK,EAAG,MAAO,GAC9E,MAAM,MAAQ,OAAO,KAAK,MAAM,KAAK,CAAC,EAChC,SAAW,KAAK,kBAAkB,CAAE,CAAC,KAAK,EAAG,KAAM,CAAC,EAC1D,OAAK,SACE,KAAK,qBAAqB,MAAO,MAAO,QAAS,SAAU,UAAW,GAAM,oCAAoC,EADjG,EAExB,CAEA,qBAAqB,MAAO,MAAO,QAAS,SAAU,UAAY,KAAM,SAAW,GAAO,gBAAkB,GAAI,CAC9G,MAAM,aAAe,KAAK,sBAAsB,CAAE,CAAC,KAAK,EAAG,OAAO,KAAK,CAAE,CAAC,EACpE,eAAiB,KAAK,sBAAsB,OAAO,EACnD,cAAgB,OAAO,eAAe,CAAC,GAAK,CAAC,EAC7C,QAAU,SAAW,KAAK,iBAAiB,SAAU,SAAS,EAAI,EAClE,WAAa,OAAO,KAAK,IAAM,cAAgB,oBAAsB,GACrE,MAAQ,OAAO,KAAK,IAAM,IAC5B,eACA,OAAO,KAAK,IAAM,IAAM,aAAe,GAC3C,MAAO;AAAA;AAAA;AAAA,2CAGgC,SAAW,eAAiB,EAAE;AAAA;AAAA,sBAEnD,WAAW,KAAK,CAAC;AAAA,sBACjB,WAAW,KAAK,CAAC;AAAA,wBACf,SAAW,OAAS,OAAO;AAAA,UACzC,eAAe;AAAA;AAAA;AAAA;AAAA;AAAA,yDAKgC,KAAK,oBAAoB,MAAO,QAAS,QAAQ,CAAC;AAAA,cAC7F,MAAQ,8CAA8C,WAAW,KAAK,CAAC,UAAY,EAAE;AAAA;AAAA,YAEvF,QAAU,EACR,sDAAsD,WAAW,OAAO,CAAC,YACzE,WAAa,UAAU,WAAW,UAAU,CAAC,WAAa,EAAE;AAAA;AAAA;AAAA,yDAGjB,SAAW,KAAK,YAAY,SAAS,MAAO,YAAY,EAAI,GAAG;AAAA;AAAA;AAAA,KAItH,CAEA,wBAAwB,MAAO,QAAS,CACtC,MAAM,MAAQ,QAAU,yBAA2B,kBACnD,MAAO;AAAA;AAAA,mDAEwC,WAAW,KAAK,CAAC,KAAK,WAAW,KAAK,CAAC;AAAA,kDACxC,WAAW,KAAK,CAAC,iBAAiB,WAAW,KAAK,CAAC,2GAA2G,WAAW,KAAK,MAAM,gBAAkB,KAAK,MAAM,KAAK,GAAK,EAAQ,CAAC,kBAAkB,QAAU,oBAAsB,gBAAgB;AAAA;AAAA,KAGtV,CAEA,iBAAkB,CAChB,OAAI,KAAK,QAAQ,SAAW,oBAA4B,KAAK,QAAQ,UAAU,YAAY,YAAc,CAAC,EACtG,KAAK,QAAQ,SAAW,gBAAwB,KAAK,QAAQ,UAAU,SAAS,YAAc,CAAC,EAC/F,KAAK,QAAQ,SAAW,kBAA0B,KAAK,QAAQ,UAAU,SAAS,YAAc,CAAC,EAC9F,KAAK,QAAQ,UAAU,iBAAmB,CAAC,GAAI,IAAK,IAAK,IAAK,IAAK,IAAM,IAAM,IAAM,GAAI,CAClG,CAEA,cAAc,MAAO,QAAS,MAAQ,KAAM,CAC1C,GAAI,CAAC,QAAS,MAAO,GAAG,aAAa,KAAK,CAAC,IAAI,KAAK,QAAQ,SAAW,oBAAsB,SAAW,KAAK,GAC7G,MAAM,SAAW,OAAO,UAAY,KAAK,OAAO,UAAY,yBACtD,OAAS,KAAK,IAAI,EAAG,KAAK,KAAK,OAAO,KAAK,EAAI,KAAK,IAAI,EAAG,QAAQ,CAAC,CAAC,EAC3E,MAAO,GAAG,aAAa,KAAK,CAAC,YAAY,aAAa,MAAM,CAAC,UAC/D,CAEA,oBAAoB,MAAO,QAAS,MAAQ,KAAM,CAChD,GAAI,CAAC,QAAS,OAAO,WAAW,KAAK,cAAc,MAAO,GAAO,KAAK,CAAC,EACvE,MAAM,SAAW,OAAO,UAAY,KAAK,OAAO,UAAY,yBACtD,OAAS,KAAK,IAAI,EAAG,KAAK,KAAK,OAAO,KAAK,EAAI,KAAK,IAAI,EAAG,QAAQ,CAAC,CAAC,EAC3E,MAAO,GAAG,aAAa,KAAK,CAAC,wDAAwD,aAAa,MAAM,CAAC,iBAC3G,CAEA,4BAA6B,CAC3B,MAAM,aAAe,KAAK,MAAQ,OAAO,KAAK,MAAM,OAAS,CAAC,EAAI,KAC5D,cAAgB,KAAK,uBAC3B,YAAK,uBAAyB,OAAO,SAAS,YAAY,EAAI,aAAe,KACtE,OAAO,SAAS,aAAa,GAC/B,OAAO,SAAS,YAAY,GAC5B,KAAK,IAAI,aAAe,aAAa,GAAK,GACjD,CAEA,iBAAiB,QAAU,GAAO,CAChC,MAAM,SAAW,EAAQ,KAAK,MACxB,SAAW,KAAK,gBAAgB,EAChC,cAAgB,SAAW,KAAK,sBAAsB,KAAK,MAAO,QAAQ,EAAI,EAC9E,YAAc,UAAY,OAAO,eAAiB,CAAC,EAAI,OAAO,KAAK,MAAM,OAAS,CAAC,EAAI,IAEvF,gBAAkB,4BAClB,eAAiB,KAAK,UAAY,KACpC,mDAAmD,eAAe;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,oBAatD,eAAe;AAAA,gBAE3B,GAEJ,MAAO;AAAA,uCAC4B,SAAW,aAAe,WAAW,GAAG,KAAK,UAAY,KAAO,uBAAyB,EAAE;AAAA;AAAA,+CAEnF,QAAU,eAAiB,EAAE;AAAA,oBACxD,SAAW,KAAK,YAAY,KAAK,MAAM,MAAO,KAAK,iBAAiB,EAAG,EAAI,EAAI,gBAAgB;AAAA,YACvG,aAAe,KAAK,iBAAiB,EAAI,QAAQ,YAAY,cAAe,KAAK,QAAQ,CAAC,SAAW,EAAE;AAAA;AAAA,UAEzG,cAAc;AAAA;AAAA,KAGtB,CAEA,iBAAkB,CAChB,GAAI,CAAC,KAAK,MAAO,MAAO,GACxB,MAAM,SAAW,KAAK,MAAM,OAAO,KAAK,MAAM,UAAY,CAAC,CAAC,EAC5D,GAAI,SAAW,EAAG,OAAO,SACzB,MAAM,cAAgB,OAAO,KAAK,MAAM,eAAiB,CAAC,EACpD,MAAQ,OAAO,KAAK,MAAM,OAAS,CAAC,EAC1C,GAAI,cAAgB,MAAQ,IAC1B,OAAO,KAAK,IAAI,EAAG,KAAK,OAAQ,cAAgB,OAAS,cAAiB,GAAG,CAAC,EAIhF,GAAI,KAAK,QAAQ,SAAW,SAAU,MAAO,GAC7C,MAAM,QAAU,KAAK,QAAQ,SAAW,SAClC,MAAQ,QAAU,gBAAkB,WACpC,UAAY,KAAK,kBAAkB,KAAK,sBAAsB,OAAO,EAAG,KAAK,EACnF,OAAO,KAAK,iBAAiB,KAAK,MAAO,SAAS,CACpD,CAEA,iBAAiB,MAAO,UAAW,CACjC,GAAI,KAAK,QAAQ,SAAW,SAAU,CACpC,MAAM,OAAS,OAAO,OAAO,eAAiB,OAAO,UAAY,CAAC,EAC5D,WAAa,OAAO,WAAW,eAAiB,WAAW,UAAY,CAAC,EACxEC,OAAQ,OAAO,OAAO,OAAS,CAAC,EAChC,UAAY,OAAO,WAAW,OAAS,CAAC,EAC9C,GAAI,CAAC,CAAC,OAAQ,WAAYA,OAAO,SAAS,EAAE,MAAO,OAAU,OAAO,SAAS,KAAK,GAAK,MAAQ,CAAC,EAAG,MAAO,GAC1G,MAAMC,MAAOD,OAAQ,OACfE,UAAW,UAAY,WAC7B,GAAI,QAAU,YAAcD,OAAQC,UAAU,MAAO,GACrD,MAAM,KAAO,oBAAoB,OAAQ,aAAa,KAAK,QAAQ,SAAU,oBAAqB,qBAAsB,CAAC,CAAC,CAAC,EACrH,cAAgB,KAAK,IAAI,EAAG,KAAK,OAAO,EAAID,MAAOC,WAAY,IAAM,IAAI,CAAC,EAChF,OAAO,KAAK,IAAI,EAAG,KAAK,IAAI,GAAI,KAAK,MAAM,IAAI,EAAG,aAAa,CAAC,CAClE,CACA,MAAM,SAAW,KAAK,MAAM,OAAO,OAAO,UAAY,CAAC,CAAC,EACxD,GAAI,SAAW,EAAG,OAAO,SACzB,MAAM,cAAgB,OAAO,OAAO,eAAiB,CAAC,EAChD,MAAQ,OAAO,OAAO,OAAS,CAAC,EACtC,GAAI,cAAgB,MAAQ,IAC1B,OAAO,KAAK,IAAI,EAAG,KAAK,OAAQ,cAAgB,OAAS,cAAiB,GAAG,CAAC,EAMhF,GAJI,CAAC,CAAC,oBAAqB,eAAe,EAAE,SAAS,KAAK,QAAQ,MAAM,GAIpE,KAAK,QAAQ,SAAW,qBAAuB,KAAK,MAAM,WAAY,MAAO,GAEjF,MAAM,SAAW,KAAK,aAAa,SAAS,EACtC,KAAO,KAAK,aAAa,KAAK,EACpC,MAAI,CAAC,UAAY,CAAC,MAAQ,MAAQ,SAAiB,EAC5C,KAAK,IAAI,EAAG,KAAK,OAAQ,SAAW,MAAQ,SAAY,GAAG,CAAC,CACrE,CAEA,aAAa,MAAO,CAClB,GAAI,CAAC,MAAO,MAAO,GACnB,MAAM,OAAS,OAAO,MAAM,MAAQ,MAAM,MAAQ,CAAC,EACnD,GAAI,OAAS,EAAG,OAAO,OACvB,MAAM,SAAW,OAAO,MAAM,UAAY,MAAM,eAAiB,CAAC,EAClE,OAAO,SAAW,EAAI,OAAO,MAAM,OAAS,CAAC,EAAI,SAAW,CAC9D,CAEA,sBAAsB,MAAO,SAAU,CACrC,MAAM,SAAW,OAAO,OAAO,eAAiB,CAAC,EACjD,GAAI,SAAW,OAAO,OAAO,OAAS,CAAC,EAAI,IAAM,OAAO,SACxD,MAAM,QAAU,OAAO,UAAY,CAAC,EACpC,MAAI,CAAC,OAAO,OAAS,SAAW,GAAK,SAAW,IAAY,EACrD,OAAO,MAAM,KAAK,GAAK,EAAK,QAAU,IAC/C,CAEA,uBAAwB,CACtB,MAAM,MAAQ,CAAC,EACT,OAAS,OAAO,KAAK,YAAY,KAAK,MAAM,MAAM,GAAK,EAAE,EAAE,KAAK,EAChE,iBAAmB,CAAC,CAAC,GAAI,OAAQ,UAAW,WAAW,EAAE,SAAS,OAAO,YAAY,CAAC,EACtF,SAAW,KAAK,QAAQ,SAAW,SACrC,OAAO,KAAK,OAAO,eAAiB,KAAK,MAAM,eAAiB,KAAK,MAAM,UAAY,CAAC,EACxF,OAAO,KAAK,OAAO,UAAY,KAAK,MAAM,UAAY,CAAC,EAEvD,KAAK,MAAM,OAAO,MAAM,KAAK,CAAE,MAAO,QAAS,MAAO,KAAK,WAAW,KAAK,MAAM,KAAK,CAAE,CAAC,GACzF,KAAK,MAAM,WAAa,KAAK,MAAM,OAAM,MAAM,KAAK,CAAE,MAAO,OAAQ,MAAO,KAAK,MAAM,WAAa,KAAK,MAAM,IAAK,CAAC,EACrH,KAAK,MAAM,UAAU,MAAM,KAAK,CAAE,MAAO,WAAY,MAAO,KAAK,cAAc,KAAK,MAAM,QAAQ,CAAE,CAAC,EACrG,kBAAkB,MAAM,KAAK,CAAE,MAAO,SAAU,MAAO,MAAO,CAAC,EAEnE,MAAM,eAAiB,KAAK,QAAQ,SAAW,WAC3C,KAAK,0BAA0B,KAAK,MAAM,QAAQ,EAClD,GAUJ,GATI,gBACF,MAAM,KAAK,CACT,MAAO,aACP,MAAO,KAAK,MAAM,aAAe,UAC7B,GAAG,iBAAmB,QAAU,QAAU,OAAO,cACjD,eACN,CAAC,EAGC,KAAK,QAAQ,SAAW,oBAAqB,CAC/C,MAAM,gBAAkB,CACtB,gBAAiB,mBACjB,eAAgB,kBAChB,cAAe,iBACf,iBAAkB,mBACpB,EACA,MAAM,KAAK,CACT,MAAO,iBACP,MAAO,gBAAgB,KAAK,MAAM,eAAe,GAAK,KAAK,MAAM,iBAAmB,kBACtF,CAAC,CACH,CAEA,GAAI,KAAK,QAAQ,SAAW,SAAU,CACpC,MAAM,gBAAkB,KAAK,IAAI,EAAG,OAAO,KAAK,OAAO,iBAAmB,KAAK,MAAM,iBAAmB,CAAC,CAAC,EAC1G,MAAM,KAAK,CACT,MAAO,mBACP,MAAO,GAAG,aAAa,eAAe,CAAC,IAAI,kBAAoB,EAAI,UAAY,UAAU,EAC3F,CAAC,CACH,CAEA,OAAI,SAAW,GACb,MAAM,KAAK,CACT,MAAO,WACP,MAAO,KAAK,cAAc,SAAU,KAAK,QAAQ,SAAW,SAAU,KAAK,KAAK,CAClF,CAAC,EAGI,MAAM,OAAQ,MAAS,OAAO,KAAK,OAAS,EAAE,EAAE,KAAK,CAAC,CAC/D,CAEA,wBAAyB,CACvB,MAAM,MAAQ,KAAK,sBAAsB,EACzC,GAAI,CAAC,MAAM,OAAQ,MAAO,GAC1B,MAAM,QAAU,MAAM,IAAK,MAAS,KAAK,KAAK,EAAE,KAAK,QAAK,EAE1D,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA,sBAKW,WAAW,OAAO,CAAC;AAAA;AAAA;AAAA;AAAA;AAAA,KAMvC,CAEA,oBAAqB,CACnB,MAAO;AAAA;AAAA;AAAA,kBAGO,KAAK,MAAQ,KAAK,YAAY,KAAK,MAAM,MAAO,KAAK,iBAAiB,EAAG,EAAI,EAAI,gBAAgB;AAAA;AAAA,KAGjH,CAEA,sBAAuB,CACrB,MAAM,cAAgB,KAAK,yBAAyB,EAC9C,cAAgB,KAAK,SAAS,SAAW,SAEzC,YAAc,cAChB,UAAU,aAAa,IAFV,gBAAkB,EAAI,OAAS,OAET,mCAAmC,iBAAiB,IACvF,GAAG,iBAAiB,IAClB,iBAAmB,KAAK,MAAM,cAAgB,cACpD,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,UAMD,KAAK,uBAAuB,CAAC;AAAA;AAAA;AAAA,yCAGE,iBAAmB,GAAK,WAAW,8CAA8C,CAAC,gBAAgB;AAAA,yCAClG,iBAAmB,YAAc,EAAE,mDAAmD,gBAAgB;AAAA,4DACnF,iBAAmB,UAAY,EAAE;AAAA;AAAA;AAAA,2EAGlB,iBAAmB,UAAY,EAAE;AAAA;AAAA;AAAA;AAAA,6GAIC,cAAgB,EAAI,YAAc,EAAE,iCAAiC,aAAa;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,oDAO3I,cAAgB,kBAAkB,aAAa,IAAI,gBAAkB,EAAI,OAAS,OAAO,GAAK,wBAAwB;AAAA;AAAA,+EAE3F,WAAW;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,yEAmBjB,iBAAmB,GAAK,SAAS;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,8MAWoG,WAAW,KAAK,MAAM,cAAgB,EAAE,CAAC;AAAA;AAAA;AAAA,KAIrP,CAEA,wBAAyB,CACvB,MAAM,UAAY,KAAK,cAAc,qBAAqB,EACpD,UAAY,KAAK,cAAc,2BAA2B,EAC1D,SAAW,KAAK,cAAc,0BAA0B,EACxD,SAAW,KAAK,cAAc,0BAA0B,EACxD,UAAY,KAAK,cAAc,2BAA2B,EAC1D,SAAW,KAAK,cAAc,yBAAyB,EACvD,WAAa,KAAK,cAAc,4BAA4B,EAC5D,YAAc,KAAK,cAAc,6BAA6B,EAC9D,WAAa,KAAK,cAAc,4BAA4B,EAC5D,iBAAmB,KAAK,cAAc,8BAA8B,EACpE,gBAAkB,KAAK,cAAc,mCAAmC,EACxE,iBAAmB,KAAK,MAAM,cAAgB,cAC9C,WAAa,MAAM,KAAK,WAAW,OAAS,CAAC,CAAC,EAChD,WAAW,QAAU,CAAC,mBACxB,KAAK,kBAAkB,UAAU,EAC7B,YAAW,UAAU,MAAQ,KAEnC,MAAM,aAAe,iBAAmB,CAAC,EAAK,WAAW,OAAS,WAAc,KAAK,cAAgB,CAAC,EAChG,cAAgB,KAAK,yBAAyB,EAC9C,cAAgB,KAAK,SAAS,SAAW,SACzC,cAAgB,aAAa,OAC7B,wBAA0B,gBAAkB,cAC5C,oBAAsB,aAAa,IAAK,MAAS,GAAG,KAAK,IAAI,IAAI,KAAK,IAAI,IAAI,KAAK,YAAY,EAAE,EAAE,KAAK,GAAG,EAE7G,YACF,UAAU,YAAc,wBACnB,cACC,GAAG,aAAa,IAAI,gBAAkB,EAAI,eAAiB,eAAe,YAC1E,mBACD,cACC,kBAAkB,aAAa,IAAI,gBAAkB,EAAI,OAAS,OAAO,GACzE,0BAGJ,WACF,SAAS,YAAc,wBAClB,gBAAkB,EACjB,qCACA,oDACD,cACC,UAAU,aAAa,IAAI,gBAAkB,EAAI,OAAS,OAAO,mCAAmC,iBAAiB,IACrH,GAAG,iBAAiB,KAGxB,WACF,SAAS,OAAS,gBAAkB,EACpC,SAAS,UAAY,aAAa,IAAI,CAAC,KAAM,QAAU;AAAA;AAAA,YAEjD,KAAK,yBAAyB,IAAI,CAAC;AAAA;AAAA,6BAElB,WAAW,KAAK,IAAI,CAAC,KAAK,WAAW,KAAK,IAAI,CAAC;AAAA,qBACvD,WAAW,KAAK,qBAAqB,IAAI,CAAC,CAAC;AAAA;AAAA,sGAEsC,KAAK,wBAAwB,WAAW,KAAK,IAAI,CAAC;AAAA;AAAA;AAAA;AAAA,OAIjJ,EAAE,KAAK,EAAE,GAGR,WACE,yBAA2B,sBAAwB,KAAK,0BAC1D,SAAS,UAAU,OAAO,UAAU,EAC/B,SAAS,aAEhB,SAAS,UAAU,OAAO,WAAY,uBAAuB,EAC7D,SAAS,UAAU,OAAO,gBAAiB,cAAgB,GAAK,CAAC,uBAAuB,EACxF,SAAS,UAAU,OAAO,iBAAkB,gBAAgB,GAG1D,YAAY,WAAW,UAAU,OAAO,YAAa,gBAAgB,EACrE,cAAa,YAAY,OAAS,kBAClC,aAAY,WAAW,OAAS,CAAC,kBACjC,mBACF,iBAAiB,UAAU,OAAO,YAAa,CAAC,gBAAgB,EAChE,iBAAiB,aAAa,eAAgB,OAAO,CAAC,gBAAgB,CAAC,GAErE,kBACF,gBAAgB,UAAU,OAAO,YAAa,gBAAgB,EAC9D,gBAAgB,aAAa,eAAgB,OAAO,gBAAgB,CAAC,GAGvE,KAAK,wBAA0B,oBAE3B,YAAW,UAAU,OAAS,IAElC,KAAK,qBAAqB,CAC5B,CAEA,0BAA2B,CACzB,OAAO,KAAK,SAAS,SAAW,SAC5B,KAAK,IAAI,EAAG,UAAU,KAAK,MAAM,iBAAmB,CAAC,CAAC,EACtD,CACN,CAEA,kBAAkB,MAAO,CACvB,MAAM,cAAgB,KAAK,yBAAyB,EACpD,GAAI,gBAAkB,EAAG,CACvB,MAAM,YAAc,MAAM,GAAG,EAAE,EAC/B,OAAC,KAAK,cAAgB,CAAC,GAAG,QAAS,MAAS,CACtC,OAAS,aAAa,KAAK,yBAAyB,IAAI,CAC9D,CAAC,EACD,KAAK,aAAe,YAAc,CAAC,WAAW,EAAI,CAAC,EAC5C,KAAK,YACd,CAEA,MAAM,cAAgB,KAAK,cAAgB,CAAC,EACtC,UAAY,CAAC,GAAG,cAAe,GAAG,KAAK,EAAE,MAAM,EAAG,aAAa,EAC/D,cAAgB,IAAI,IAAI,SAAS,EACvC,qBAAc,QAAS,MAAS,CACzB,cAAc,IAAI,IAAI,GAAG,KAAK,yBAAyB,IAAI,CAClE,CAAC,EACD,KAAK,aAAe,UACb,KAAK,YACd,CAEA,yBAAyB,KAAM,CAC7B,MAAM,WAAa,KAAK,kBAAkB,IAAI,EAC9C,GAAI,WACF,MAAO,8DAA8D,WAAW,UAAU,CAAC,mBAG7F,MAAM,UAAY,OAAO,MAAM,MAAQ,EAAE,EAAE,MAAM,GAAG,EAAE,IAAI,GAAG,YAAY,GAAK,OAE9E,MAAO;AAAA;AAAA;AAAA,0DAG+C,WAAW,SAAS,CAAC;AAAA;AAAA,KAG7E,CAEA,kBAAkB,KAAM,CACtB,MAAI,CAAC,MAAQ,CAAC,wBAAwB,KAAK,KAAK,MAAQ,EAAE,GAAK,OAAO,KAAK,iBAAoB,WAAmB,IAC7G,KAAK,mBAAmB,IAAI,IAAI,GACnC,KAAK,mBAAmB,IAAI,KAAM,IAAI,gBAAgB,IAAI,CAAC,EAEtD,KAAK,mBAAmB,IAAI,IAAI,GAAK,GAC9C,CAEA,qBAAqB,KAAM,CACzB,MAAM,MAAQ,KAAK,IAAI,EAAG,OAAO,MAAM,MAAQ,CAAC,CAAC,EACjD,OAAI,MAAQ,KAAO,KAAa,GAAG,KAAK,IAAI,EAAG,KAAK,MAAM,MAAQ,IAAI,CAAC,CAAC,MACjE,IAAI,OAAS,KAAO,OAAO,QAAQ,CAAC,CAAC,KAC9C,CAEA,yBAAyB,KAAM,CAC7B,GAAI,CAAC,MAAQ,CAAC,KAAK,oBAAoB,IAAI,IAAI,EAAG,OAClD,MAAM,WAAa,KAAK,mBAAmB,IAAI,IAAI,EAC/C,YAAc,OAAO,KAAK,iBAAoB,YAAY,IAAI,gBAAgB,UAAU,EAC5F,KAAK,mBAAmB,OAAO,IAAI,CACrC,CAEA,yBAA0B,CACnB,KAAK,qBACV,KAAK,mBAAmB,QAAS,YAAe,CAC1C,YAAc,OAAO,KAAK,iBAAoB,YAAY,IAAI,gBAAgB,UAAU,CAC9F,CAAC,EACD,KAAK,mBAAmB,MAAM,EAChC,CAEA,mBAAoB,CAClB,KAAK,wBAAwB,EAC7B,KAAK,aAAe,CAAC,CACvB,CAEA,sBAAuB,CACrB,MAAM,UAAY,KAAK,cAAc,qBAAqB,EACpD,WAAa,MAAM,KAAK,WAAW,OAAS,CAAC,CAAC,EACpD,OAAI,WAAW,SACb,KAAK,kBAAkB,UAAU,EAC7B,YAAW,UAAU,MAAQ,KAE5B,KAAK,MAAM,cAAgB,cAAgB,CAAC,EAAK,KAAK,cAAgB,CAAC,CAChF,CAEA,oBAAoB,MAAQ,KAAK,qBAAqB,EAAG,CACvD,OAAO,MAAM,IAAK,MAAS,GAAG,KAAK,IAAI,IAAI,KAAK,IAAI,IAAI,KAAK,IAAI,IAAI,KAAK,YAAY,EAAE,EAAE,KAAK,GAAG,CACpG,CAEA,2BAA4B,CAC1B,KAAK,qBAAuB,GAC5B,KAAK,iBAAmB,GACxB,KAAK,4BAA8B,GACnC,KAAK,sBAAwB,CAC/B,CAEA,2BAA4B,CAC1B,MAAM,WAAa,kCACnB,GAAI,CACF,MAAM,SAAW,OAAO,eAAe,QAAQ,UAAU,EACzD,GAAI,SAAU,OAAO,SACrB,MAAM,UAAY,WAAW,OAAO,OAAO,WAAW,EAAE,QAAQ,KAAM,EAAE,CAAC,GACzE,cAAO,eAAe,QAAQ,WAAY,SAAS,EAC5C,SACT,MAAiB,CACf,MAAO,WAAW,KAAK,IAAI,CAAC,IAAI,KAAK,OAAO,EAAE,SAAS,EAAE,EAAE,MAAM,CAAC,CAAC,EACrE,CACF,CAEA,MAAM,sBAAsB,MAAO,CACjC,MAAM,QAAU,CAAC,MAAM,eAAe,EACtC,GAAI,CAAE,OAAO,MAAM,KAAK,qBAAqB,MAAO,OAAO,CAAG,OACvD,MAAO,CACZ,GAAI,CAAC,MAAM,UAAW,CACpB,MAAM,QAAU,CAAC,KAAK,yBAA0B,cAAe,KAAK,cAAe,MAAM,iBAAkB,YAAY,QAAQ,MAAO,UAAU,MAAM,OAAQ,UAAU,MAAM,OAAO,CAAC,EAAE,IAAI,EAAE,EAAE,KAAK,CAAC,EAAG,UAAU,CAAC,GAAG,IAAI,IAAI,MAAM,IAAI,GAAG,EAAE,MAAM,SAAS,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,KAAK,GAAG,EAAG,MAAM,wBAAyB,UAAU,MAAM,MAAM,QAAS,WAAW,OAAO,MAAM,MAAM,GAAG,OAAO,QAAQ,UAAU,GAAG,EAAG,eAAe,OAAO,MAAM,OAAO,YAAY,EAAG,SAAS,SAAS,QAAQ,EACje,GAAI,CAAE,MAAM,uEAAuE,CAAC,OAAO,OAAO,QAAQ,CAAC,eAAe,kBAAkB,EAAE,KAAK,KAAK,UAAU,OAAO,EAAE,UAAU,EAAI,CAAC,EAAE,MAAM,IAAI,CAAC,CAAC,CAAG,MAAQ,CAAC,CACtN,CACA,MAAM,KACR,CACF,CAEA,MAAM,qBAAqB,MAAO,QAAS,CACzC,MAAM,aAAe,KAAK,oBAAoB,KAAK,EACnD,GAAI,KAAK,sBAAwB,KAAK,kBAAoB,KAAK,8BAAgC,aAAc,OAAO,KAAK,qBAEzH,KAAK,cAAgB,mCACrB,KAAK,WAAa,GAClB,KAAK,cAAc,EAEnB,MAAM,sBAAwB,MAAM,KAAK,mBAAmB,GAAG,KAAK,aAAa,0CAA2C,CAC1H,OAAQ,OACR,QAAS,CAAE,OAAQ,mBAAoB,eAAgB,kBAAmB,EAC1E,KAAM,KAAK,UAAU,CACnB,cAAe,KAAK,cACpB,UAAW,KAAK,0BAA0B,EAC1C,MAAO,MAAM,IAAK,OAAU,CAC1B,SAAU,KAAK,KACf,YAAa,KAAK,MAAQ,2BAC1B,KAAM,KAAK,IACb,EAAE,CACJ,CAAC,CACH,CAAC,EACD,QAAQ,WAAa,sBAAsB,OAC3C,MAAM,cAAgB,MAAM,aAAa,sBAAuB,uCAAuC,EACvG,GAAI,CAAC,sBAAsB,GAAI,MAAM,IAAI,MAAM,cAAc,OAAS,uCAAuC,EAC7G,GAAI,CAAC,MAAM,QAAQ,cAAc,OAAO,GAAK,cAAc,QAAQ,SAAW,MAAM,OAClF,MAAM,IAAI,MAAM,6DAA6D,EAG/E,MAAM,eAAiB,IAAI,MAAM,MAAM,MAAM,EAAE,KAAK,CAAC,EAC/C,WAAa,MAAM,OAAO,CAAC,MAAO,OAAS,MAAQ,KAAK,KAAM,CAAC,EAC/D,eAAiB,CAAC,MAAO,SAAW,CACxC,eAAe,KAAK,EAAI,KAAK,IAAI,MAAM,KAAK,EAAE,KAAM,OAAO,QAAU,CAAC,CAAC,EACvE,MAAM,SAAW,eAAe,OAAO,CAAC,MAAO,QAAU,MAAQ,MAAO,CAAC,EACzE,KAAK,sBAAwB,WAAa,EAAI,KAAK,IAAI,IAAK,KAAK,MAAO,SAAW,WAAc,GAAG,CAAC,EAAI,EACzG,KAAK,cAAgB,iCAAiC,KAAK,qBAAqB,IAChF,KAAK,cAAc,CACrB,EAEA,QAAS,MAAQ,EAAG,MAAQ,MAAM,OAAQ,OAAS,EAAG,CACpD,QAAQ,MAAQ,kBAChB,QAAQ,WAAa,EACrB,GAAI,CACF,MAAM,KAAK,sBAAsB,MAAM,KAAK,EAAG,cAAc,QAAQ,KAAK,EAAI,QAAW,eAAe,MAAO,MAAM,CAAC,CACxH,OAAS,YAAa,CACpB,MAAM,OAAS,cAAc,QAAQ,KAAK,EAC1C,GAAI,YAAY,WAAa,CAAC,OAAO,WAAY,MAAM,YACvD,QAAQ,MAAQ,iBAChB,QAAQ,WAAa,EACrB,KAAK,cAAgB,6CACrB,KAAK,cAAc,EACnB,GAAI,CACF,MAAM,MAAQ,MAAM,MAAM,GAAG,KAAK,aAAa,sCAAuC,CACpF,OAAQ,OAAQ,QAAS,CAAE,eAAgB,OAAO,YAAa,cAAe,UAAU,OAAO,UAAU,EAAG,EAC5G,KAAM,MAAM,KAAK,EAAG,OAAQ,YAAY,QAAQ,IAAM,CACxD,CAAC,EAED,GADA,QAAQ,WAAa,MAAM,OACvB,CAAC,MAAM,GAAI,MAAM,IAAI,MAAM,wBAAwB,MAAM,MAAM,GAAG,CACxE,MAAQ,CACN,MAAM,IAAI,MAAM,yIAAyI,CAC3J,CACF,CACA,eAAe,MAAO,MAAM,KAAK,EAAE,IAAI,CACzC,CAEA,QAAQ,MAAQ,aACd,QAAQ,WAAa,EACvB,MAAM,mBAAqB,MAAM,KAAK,mBAAmB,GAAG,KAAK,aAAa,yCAA0C,CACtH,OAAQ,OACR,QAAS,CAAE,OAAQ,mBAAoB,eAAgB,kBAAmB,EAC1E,KAAM,KAAK,UAAU,CAAE,mBAAoB,cAAc,kBAAmB,CAAC,CAC/E,CAAC,EACD,QAAQ,WAAa,mBAAmB,OACxC,MAAM,WAAa,MAAM,aAAa,mBAAoB,sCAAsC,EAChG,GAAI,CAAC,mBAAmB,IAAM,CAAC,WAAW,eAAiB,CAAC,WAAW,iBACrE,MAAM,IAAI,MAAM,WAAW,OAAS,sCAAsC,EAE5E,YAAK,qBAAuB,WAAW,cACvC,KAAK,iBAAmB,WAAW,iBACnC,KAAK,4BAA8B,aACnC,KAAK,sBAAwB,IAC7B,KAAK,cAAgB,2DACrB,KAAK,cAAc,EACZ,KAAK,oBACd,CAEA,MAAM,mBAAmB,IAAK,QAAS,CAErC,IAAI,UACJ,QAAS,QAAU,EAAG,SAAW,EAAU,SAAW,EAAG,CACvD,GAAI,CACF,MAAM,SAAW,MAAM,MAAM,IAAK,CAAE,GAAG,QAAS,OAAQ,QAAQ,QAAU,YAAY,QAAQ,GAAK,CAAE,CAAC,EACtG,GAAI,CAAC,KAAK,wBAAwB,SAAS,MAAM,GAAK,UAAY,EAAU,OAAO,SACnF,UAAY,IAAI,MAAM,gCAAgC,SAAS,MAAM,GAAG,CAC1E,OAAS,MAAO,CAEd,GADA,UAAY,MACR,UAAY,EAAU,MAAM,KAClC,CACA,KAAK,cAAgB,qCAAqC,QAAU,CAAC,YACrE,KAAK,cAAc,EACnB,MAAM,KAAK,iBAAiB,OAAO,CACrC,CACA,MAAM,WAAa,IAAI,MAAM,0CAA0C,CACzE,CAEA,MAAM,sBAAsB,KAAM,OAAQ,WAAY,CAEpD,IAAI,UACJ,QAAS,QAAU,EAAG,SAAW,EAAU,SAAW,EACpD,GAAI,CACF,MAAM,KAAK,kBAAkB,KAAM,OAAQ,UAAU,EACrD,MACF,OAAS,MAAO,CAEd,GADA,UAAY,MACR,MAAM,WAAc,CAAC,MAAM,WAAa,CAAC,KAAK,wBAAwB,MAAM,MAAM,GAAM,UAAY,EAAU,MAAM,MACxH,KAAK,cAAgB,oCAAoC,KAAK,IAAI,KAAK,QAAU,CAAC,YAClF,KAAK,cAAc,EACnB,MAAM,KAAK,iBAAiB,OAAO,CACrC,CAEF,MAAM,SACR,CAEA,kBAAkB,KAAM,OAAQ,WAAY,CAC1C,OAAO,IAAI,QAAQ,CAAC,QAAS,SAAW,CACtC,MAAM,QAAU,IAAI,eACpB,QAAQ,KAAK,MAAO,OAAO,UAAW,EAAI,EAC1C,QAAQ,iBAAiB,eAAgB,OAAO,aAAe,KAAK,MAAQ,0BAA0B,EACtG,QAAQ,OAAO,iBAAiB,WAAa,OAAU,CACjD,MAAM,kBAAkB,WAAW,MAAM,MAAM,CACrD,CAAC,EACD,QAAQ,iBAAiB,OAAQ,IAAM,CACrC,GAAI,QAAQ,QAAU,KAAO,QAAQ,OAAS,IAAK,CACjD,QAAQ,EACR,MACF,CACA,MAAM,MAAQ,IAAI,MAAM,oBAAoB,KAAK,IAAI,qBAAqB,EAC1E,MAAM,OAAS,QAAQ,OACvB,OAAO,KAAK,CACd,CAAC,EACD,QAAQ,iBAAiB,QAAS,IAAM,CACtC,MAAM,MAAQ,IAAI,MAAM,oBAAoB,KAAK,IAAI,wCAAwC,EAC7F,MAAM,UAAY,GAClB,OAAO,KAAK,CACd,CAAC,EACD,QAAQ,iBAAiB,UAAW,IAAM,CACxC,MAAM,MAAQ,IAAI,MAAM,kBAAkB,KAAK,IAAI,+BAA+B,EAClF,MAAM,UAAY,GAClB,OAAO,KAAK,CACd,CAAC,EACD,QAAQ,iBAAiB,QAAS,IAAM,CACtC,MAAM,MAAQ,IAAI,MAAM,GAAG,KAAK,IAAI,wBAAwB,EAC5D,MAAM,UAAY,GAClB,OAAO,KAAK,CACd,CAAC,EACD,QAAQ,QAAU,KAClB,QAAQ,KAAK,IAAI,CACnB,CAAC,CACH,CAEA,wBAAwB,OAAQ,CAC9B,MAAO,CAAC,IAAK,IAAK,GAAG,EAAE,SAAS,OAAO,MAAM,CAAC,GAAK,OAAO,MAAM,GAAK,GACvE,CAEA,iBAAiB,QAAS,CACxB,MAAM,MAAQ,IAAO,IAAM,QAAU,GAAM,KAAK,MAAM,KAAK,OAAO,EAAI,GAAG,EACzE,OAAO,IAAI,QAAS,SAAY,OAAO,WAAW,QAAS,KAAK,CAAC,CACnE,CAEA,kBAAmB,CACjB,MAAM,aAAe,KAAK,qBAAqB,EAC/C,OAAO,KAAK,MAAM,cAAgB,eAAiB,aAAa,SAAW,KAAK,yBAAyB,CAC3G,CAEA,sBAAuB,CACrB,MAAM,UAAY,KAAK,cAAc,oBAAoB,EACzD,GAAI,CAAC,UAAW,OAChB,MAAM,SAAW,KAAK,SAAW,CAAC,KAAK,iBAAiB,EACxD,UAAU,SAAW,SACrB,UAAU,aAAa,gBAAiB,OAAO,QAAQ,CAAC,EACxD,UAAU,aAAa,YAAa,OAAO,KAAK,OAAO,CAAC,EACxD,MAAM,MAAQ,UAAU,cAAc,0BAA0B,EAC5D,QAAO,MAAM,YAAc,KAAK,eAAe,EACrD,CAEA,oBAAqB,CACf,KAAK,iBACP,KAAK,eAAe,WAAW,EAC/B,KAAK,eAAiB,MAEpB,KAAK,yBACP,KAAK,uBAAuB,MAAM,EAClC,KAAK,uBAAyB,MAGhC,MAAM,cAAgB,KAAK,cAAc,uBAAuB,EAC1D,cAAgB,KAAK,cAAc,wBAAwB,EACjE,GAAI,CAAC,eAAiB,CAAC,eAAiB,CAAC,OAAO,WAAW,oBAAoB,EAAE,QAAS,OAE1F,MAAM,YAAc,KAAK,cAAc,8BAA8B,GAAK,KAAK,cAAc,wBAAwB,EAC/G,OAAS,SAAS,cAAc,uBAAuB,EAC7D,IAAI,cAAgB,oBAAoB,aAAa,EACjD,cAAgB,oBAAoB,MAAM,EAE9C,MAAM,qBAAuB,IAAM,CACjC,GAAI,CAAC,YAAa,CAChB,KAAK,qBAAuB,OAAO,QAAU,GAC7C,MACF,CACA,MAAM,KAAO,YAAY,sBAAsB,EAC/C,KAAK,qBAAuB,OAAO,QAAU,GAAK,KAAK,KAAO,OAAO,YAAc,GACrF,EAEM,kBAAqB,iBAAoB,CAC7C,MAAM,aAAe,KAAK,UAAU,SAAS,iBAAiB,GAAK,KAAK,mBAAmB,EAC3F,cAAgB,oBAAoB,MAAM,EAC1C,MAAM,WAAa,EAAQ,KAAK,OAAU,KAAK,sBAAwB,CAAC,iBAAmB,CAAC,eAAiB,CAAC,aAC9G,cAAc,UAAU,OAAO,aAAc,UAAU,EACvD,cAAc,aAAa,cAAe,OAAO,CAAC,UAAU,CAAC,CAC/D,EAEA,KAAK,eAAiB,IAAI,qBAAsB,SAAY,CAC1D,QAAQ,QAAS,OAAU,CACrB,MAAM,SAAW,gBAAe,cAAgB,EAAQ,MAAM,gBAC9D,MAAM,SAAW,SAAQ,cAAgB,EAAQ,MAAM,eAC7D,CAAC,EACD,kBAAkB,aAAa,CACjC,EAAG,CACD,KAAM,KACN,UAAW,GACb,CAAC,EAED,KAAK,uBAAyB,IAAI,gBAClC,OAAO,iBAAiB,SAAU,IAAM,CACtC,qBAAqB,EACrB,kBAAkB,aAAa,CACjC,EAAG,CAAE,QAAS,GAAM,OAAQ,KAAK,uBAAuB,MAAO,CAAC,EAEhE,KAAK,eAAe,QAAQ,aAAa,EACrC,QAAQ,KAAK,eAAe,QAAQ,MAAM,EAC9C,kBAAkB,aAAa,CACjC,CAEA,wBAAyB,CACvB,MAAM,cAAgB,KAAK,cAAc,uBAAuB,EAChE,GAAI,CAAC,cAAe,OACpB,MAAM,YAAc,KAAK,UAAU,SAAS,iBAAiB,GAAK,KAAK,mBAAmB,EAE1F,GADA,KAAK,UAAU,OAAO,kBAAmB,WAAW,EAChD,aAAe,CAAC,KAAK,MAAO,CAC9B,cAAc,UAAU,OAAO,YAAY,EAC3C,cAAc,aAAa,cAAe,MAAM,EAChD,MACF,CACA,MAAM,cAAgB,KAAK,cAAc,wBAAwB,EAC3D,OAAS,SAAS,cAAc,uBAAuB,EACzD,eAAiB,KAAK,sBAAwB,CAAC,oBAAoB,aAAa,GAAK,CAAC,oBAAoB,MAAM,GAAK,OAAO,WAAW,oBAAoB,EAAE,UAC/J,cAAc,UAAU,IAAI,YAAY,EACxC,cAAc,aAAa,cAAe,OAAO,EAErD,CAEA,oBAAqB,CACnB,MAAM,OAAS,SAAS,cACxB,MAAO,GAAQ,QAAU,KAAK,SAAS,MAAM,GAAK,mBAAmB,MAAM,EAC7E,CAEA,eAAe,OAAQ,CACrB,KAAK,UAAU,OAAO,kBAAmB,EAAQ,MAAO,EACxD,KAAK,uBAAuB,CAC9B,CAEA,MAAM,eAAe,YAAa,UAAW,CAC3C,MAAM,SAAW,aAAa,UAAY,CAAC,EACrC,aAAe,MAAM,MAAM,WAAY,CAAE,QAAS,CAAE,OAAQ,kBAAmB,CAAE,CAAC,EAClF,KAAO,aAAa,GAAK,MAAM,aAAa,KAAK,EAAI,CAAE,MAAO,CAAC,EAAG,WAAY,CAAE,EACtF,KAAK,gBAAgB,KAAK,YAAc,CAAC,EAEzC,GAAI,CACF,KAAM,CAAE,oBAAqB,EAAI,KAAM,QAAO,iBAAiB,EACzD,qBAAuB,qBAAqB,cAAc,EAChE,SAAS,cACP,IAAI,qBAAqB,CACvB,OAAQ,MACR,QAAS,UACT,MAAO,CACL,CACE,cAAe,OAAO,SAAS,EAC/B,SAAU,CACZ,CACF,EACA,QAAS,qBAAqB,OAChC,CAAC,CACH,EAEA,qBAAqB,QAAQ,CAC3B,KAAM,qBAAqB,2BAA2B,IAAI,EAC1D,OAAQ,CACN,SACA,MAAO,KAAK,OAAS,CAAC,EACtB,UAAW,KAAK,YAAc,EAC9B,OAAQ,6BACR,SAAU,KAAK,cACf,SAAU,EACZ,CACF,CAAC,CACH,MAAgB,CAEhB,CAEA,MAAM,KAAK,kBAAkB,QAAQ,EAErC,KAAK,QAAU,GACf,KAAK,cAAgB,GACrB,KAAK,WAAa,GAClB,KAAK,OAAO,CACd,CAEA,gBAAgB,UAAW,CACzB,SAAS,iBAAiB,mBAAmB,EAAE,QAAS,MAAS,CAC/D,KAAK,YAAc,OAAO,SAAS,EACnC,KAAK,UAAU,OAAO,WAAY,OAAO,SAAS,GAAK,CAAC,CAC1D,CAAC,CACH,CAEA,MAAM,kBAAkB,SAAW,CAAC,EAAG,CACrC,IAAI,eAAiB,SAAS,qBAAqB,EAEnD,GAAI,CAAC,eAAgB,CACnB,MAAM,gBAAkB,MAAM,MAAM,GAAG,OAAO,SAAS,QAAQ,gCAAiC,CAC9F,QAAS,CAAE,OAAQ,kBAAmB,CACxC,CAAC,EACG,gBAAgB,KAElB,gBADuB,MAAM,gBAAgB,KAAK,GAClB,qBAAqB,EAEzD,CAEA,GAAI,eAAgB,CAClB,MAAM,OAAS,IAAI,UAAU,EAAE,gBAAgB,eAAgB,WAAW,EACpE,YAAc,OAAO,eAAe,qCAAqC,GAC1E,OAAO,cAAc,kBAAkB,GACvC,OAAO,KAAK,kBACX,eAAiB,SAAS,eAAe,qCAAqC,EAEhF,aAAe,gBACjB,eAAe,YAAY,SAAS,WAAW,YAAa,EAAI,CAAC,CAErE,CAEA,MAAM,eAAe,YAAY,cAAc,EAAE,MAAM,IAAM,CAAC,CAAC,EAC/D,MAAM,IAAI,QAAS,SAAY,sBAAsB,OAAO,CAAC,EAC7D,MAAM,OAAS,SAAS,cAAc,0BAA0B,EAE5D,QAAU,OAAO,OAAO,MAAS,WACnC,OAAO,KAAK,EAEZ,OAAO,SAAS,KAAO,OAE3B,CAEA,iBAAiB,MAAQ,EAAG,WAAa,UAAW,CAClD,OAAO,WAAW,IAAM,CACtB,MAAM,YAAc,KAAK,cAAc,yBAAyB,GAAK,KAAK,cAAc,iCAAiC,EACnH,OAAS,aAAe,SACzB,KAAK,cAAc,qBAAqB,GAAK,KAAK,cAAc,wBAAwB,GAAK,KAAK,cAAc,iCAAiC,IAAK,YAE3J,GAAI,CAAC,OAAQ,OACb,MAAM,SAAW,OAAO,aAAa,kCAAkC,EAAE,QAAU,OAAS,SAEtF,YAAe,gBAAmB,CACtC,MAAM,aAAe,SAAS,cAAc,oBAAoB,GAAG,sBAAsB,EAAE,QAAU,EAC/F,WAAa,OAAO,sBAAsB,EAC1C,OAAS,aAAe,GACxB,aAAe,iBAAiB,MAAM,EAE5C,GAAI,cAAgB,eAAiB,SAAS,kBAAoB,eAAiB,SAAS,gBAAiB,CAC3G,MAAM,WAAa,aAAa,sBAAsB,EAChD,IAAM,KAAK,IAAI,EAAG,aAAa,UAAY,WAAW,IAAM,WAAW,IAAM,MAAM,EACzF,aAAa,SAAS,CAAE,IAAK,SAAU,cAAe,CAAC,CACzD,KAAO,CACL,MAAM,IAAM,KAAK,IAAI,EAAG,WAAW,IAAM,OAAO,QAAU,MAAM,EAChE,OAAO,SAAS,CAAE,IAAK,SAAU,cAAe,CAAC,CACnD,CACF,EAEA,OAAO,sBAAsB,IAAM,CACjC,OAAO,sBAAsB,IAAM,YAAY,QAAQ,CAAC,CAC1D,CAAC,EACD,OAAO,WAAW,IAAM,YAAY,MAAM,EAAG,GAAG,EAE5C,OAAO,aAAa,OAAU,YAAY,YAAY,MAAM,CAAE,cAAe,EAAK,CAAC,CACzF,EAAG,KAAK,CACV,CAEA,oBAAoB,MAAO,MAAO,QAAS,CACzC,MAAM,eAAiB,QAAU,QAAU,KAAK,oBAAoB,OAAO,EAAI,QAC/E,GAAI,CAAC,gBAAgB,OAAQ,MAAO,GACpC,MAAM,YAAc,QAAU,QACzB,KAAK,SAAS,SAAW,oBAAsB,qCAAuC,qCACvF,GACE,OAAS,KAAK,oBAAoB,KAAK,EAC7C,MAAO;AAAA,iEACsD,WAAW,KAAK,CAAC,GAAG,WAAW;AAAA;AAAA,gBAEhF,WAAW,QAAU,WAAa,WAAa,KAAK,eAAe,KAAK,CAAC,CAAC;AAAA,YAC9E,OAAS,UAAU,WAAW,MAAM,CAAC,WAAa,EAAE;AAAA;AAAA;AAAA,YAGpD,eAAe,IAAK,QAAW,CAC/B,MAAM,SAAW,OAAO,KAAK,MAAM,KAAK,CAAC,IAAM,OAAO,OAAO,KAAK,EAC5D,aAAe,KAAK,mBAAmB,MAAO,OAAO,MAAO,OAAO,KAAK,EAC9E,MAAO;AAAA;AAAA;AAAA,6CAG0B,SAAW,eAAiB,EAAE;AAAA;AAAA,8BAE7C,WAAW,KAAK,CAAC;AAAA,8BACjB,WAAW,OAAO,KAAK,CAAC;AAAA;AAAA,kBAEpC,QAAU,QACR,UAAU,OAAO,KAAK,EACtB,QAAU,SACR,KAAK,iBAAiB,OAAO,KAAK,EAClC,eAAe,OAAO,MAAO,OAAO,KAAK,CAAC;AAAA;AAAA,0BAEtC,WAAW,YAAY,CAAC;AAAA;AAAA;AAAA,aAIxC,CAAC,EAAE,KAAK,EAAE,CAAC;AAAA;AAAA;AAAA,KAInB,CAEA,oBAAoB,MAAO,CACzB,MAAO,EACT,CAEA,mBAAmB,MAAO,MAAO,MAAO,CACtC,GAAI,QAAU,YAAc,QAAU,SAAU,OAAO,MACvD,MAAM,IAAM,GAAG,OAAS,EAAE,IAAI,OAAS,EAAE,GAAG,YAAY,EACxD,GAAI,IAAI,SAAS,OAAO,EAAG,MAAO,QAClC,GAAI,IAAI,SAAS,OAAO,EAAG,MAAO,QAClC,GAAI,IAAI,SAAS,OAAO,GAAK,IAAI,SAAS,aAAa,EAAG,MAAO,QACjE,GAAI,IAAI,SAAS,aAAa,EAAG,MAAO,cACxC,MAAM,SAAW,OAAO,OAAS,OAAS,EAAE,EAAE,QAAQ,UAAW,GAAG,EAAE,KAAK,EAC3E,MAAI,WAAW,KAAK,QAAQ,EAAU,QAC/B,SAAS,QAAQ,cAAe,EAAE,EAAE,QAAQ,UAAW,GAAG,EAAE,KAAK,CAC1E,CAEA,eAAe,MAAO,CACpB,MAAM,MAAQ,OAAO,OAAS,EAAE,EAAE,KAAK,EACvC,MAAI,CAAC,OAAS,aAAa,KAAK,KAAK,EAAU,MACxC,UAAU,KAAK,EACxB,CAEA,uBAAuB,OAAS,KAAK,QAAQ,UAAU,YAAY,OAAQ,CACzE,MAAM,iBAAmB,CAAC,GAAG,IAAI,IAAI,QAAU,CAAC,CAAC,CAAC,EAC5C,aAAe,iBAAiB,OAAQ,OAAU,KAAK,eAAe,KAAK,IAAM,SAAS,EAC1F,gBAAkB,iBAAiB,OAAQ,OAAU,KAAK,eAAe,KAAK,IAAM,SAAS,EACnG,MAAO,CAAC,GAAG,aAAc,GAAG,eAAe,CAC7C,CAEA,YAAa,CACX,OAAO,KAAK,uBAAuB,EAAE,IAAK,QAAW,CAAE,MAAO,MAAO,KAAK,eAAe,KAAK,CAAE,EAAE,CACpG,CAEA,4BAA6B,CAC3B,MAAM,QAAU,CACd,CAAE,MAAO,gBAAiB,MAAO,kBAAmB,EACpD,CAAE,MAAO,eAAgB,MAAO,iBAAkB,EAClD,CAAE,MAAO,cAAe,MAAO,gBAAiB,EAChD,CAAE,MAAO,iBAAkB,MAAO,mBAAoB,CACxD,EACM,cAAgB,QAAQ,KAAM,QAAW,OAAO,QAAU,KAAK,MAAM,eAAe,EACtF,KAAK,MAAM,gBACX,QAAQ,CAAC,EAAE,MACf,YAAK,MAAM,gBAAkB,cACtB;AAAA;AAAA,cAEG,WAAW,KAAK,eAAe,gBAAgB,CAAC,CAAC;AAAA;AAAA,YAEnD,QAAQ,IAAK,QAAW;AAAA;AAAA;AAAA,mDAGe,gBAAkB,OAAO,MAAQ,eAAiB,EAAE;AAAA;AAAA;AAAA;AAAA,4BAI3E,WAAW,OAAO,KAAK,CAAC;AAAA;AAAA,8BAEtB,gBAAkB,OAAO,MAAQ,OAAS,OAAO;AAAA;AAAA,gBAE/D,KAAK,wBAAwB,OAAO,KAAK,CAAC;AAAA,sBACpC,WAAW,OAAO,KAAK,CAAC;AAAA;AAAA,WAEnC,EAAE,KAAK,EAAE,CAAC;AAAA;AAAA;AAAA,KAInB,CAEA,wBAAwB,UAAW,CACjC,MAAM,qBAAuB,CAC3B,gBAAiB,EACjB,eAAgB,IAChB,cAAe,GACf,iBAAkB,GACpB,EAEA,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,qEADU,qBAAqB,SAAS,GAAK,qBAAqB,eAAe,CAOf;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAmB3E,CAEA,WAAY,CACV,MAAM,MAAQ,KAAK,QAAQ,UAAU,YAAc,CAAC,EAEpD,OADe,MAAM,4BAA4B,KAAK,MAAM,KAAK,GAAK,MAAM,aAAe,CAAC,GAC9E,IAAK,QAAW,CAAE,MAAO,MAAO,QAAU,SAAW,cAAgB,MAAM,QAAQ,IAAK,KAAK,CAAE,EAAE,CACjH,CAEA,aAAa,SAAW,KAAK,MAAM,SAAU,CAC3C,MAAM,MAAQ,KAAK,QAAQ,UAAU,YAAc,CAAC,EAC9C,eAAiB,CAAC,QAAS,QAAS,YAAY,EAChD,kBAAoB,IAAI,KAC3B,KAAK,aAAa,MAAQ,CAAC,GACzB,OAAQ,KAAQ,IAAI,UAAU,WAAa,UAAY,IAAI,UAAU,MAAM,EAC3E,IAAK,KAAQ,IAAI,SAAS,MAAM,CACrC,EACM,gBAAkB,kBAAkB,MACrC,MAAM,UAAY,CAAC,GAAG,OAAQ,OAAU,kBAAkB,IAAI,KAAK,CAAC,EACpE,MAAM,UAAY,CAAC,EAKxB,MAJe,CACb,GAAG,eAAe,OAAQ,OAAU,gBAAgB,SAAS,KAAK,CAAC,EACnE,GAAG,gBAAgB,OAAQ,OAAU,CAAC,eAAe,SAAS,KAAK,CAAC,CACtE,EACc,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CACxD,CAEA,yBAA0B,CACxB,OAAO,KAAK,oBAAoB,SAAU,SAAU,KAAK,aAAa,CAAC,CACzE,CAEA,iBAAiB,OAAQ,CACvB,MAAM,IAAM,OAAO,QAAU,EAAE,EAAE,YAAY,EAAE,QAAQ,OAAQ,GAAG,EAClE,OAAI,MAAQ,aACH,uOAEL,MAAQ,QAAgB,0GACrB,yGACT,CAEA,cAAe,CACb,OAAQ,KAAK,QAAQ,UAAU,SAAS,QAAU,CAAC,GAAG,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CAChG,CAEA,aAAc,CACZ,MAAM,MAAQ,KAAK,QAAQ,UAAU,SAAW,CAAC,EAEjD,OADe,MAAM,4BAA4B,KAAK,MAAM,KAAK,GAAK,MAAM,OAAS,CAAC,GACxE,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CACxD,CAEA,oBAAqB,CACnB,MAAM,MAAQ,KAAK,QAAQ,UAAU,SAAW,CAAC,EAEjD,OADe,MAAM,mCAAmC,KAAK,MAAM,KAAK,GAAK,MAAM,cAAgB,CAAC,GACtF,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CACxD,CAEA,gBAAiB,CACf,MAAM,MAAQ,KAAK,QAAQ,UAAU,SAAW,CAAC,EAGjD,OAFmB,MAAM,gBAAgB,KAAK,MAAM,KAAK,IAAI,KAAK,MAAM,IAAI,IAAI,KAAK,MAAM,WAAW,GACzE,MAAM,UAAY,CAAC,GAClC,IAAK,QAAW,CAAE,MAAO,MAAO,KAAM,EAAE,CACxD,CAEA,cAAc,MAAO,CACnB,MAAM,OAAS,KAAK,gBAAgB,EAAE,KAAM,MAAS,KAAK,QAAU,KAAK,EACzE,OAAO,KAAK,mBAAmB,WAAY,MAAO,QAAQ,OAAS,KAAK,CAC1E,CAEA,YAAY,MAAO,CACjB,MAAM,OAAS,KAAK,QAAQ,UAAU,eAAiB,CAAC,EACxD,OAAO,KAAK,mBAAmB,SAAU,MAAO,OAAO,KAAK,GAAG,OAAS,KAAK,CAC/E,CAEA,WAAW,MAAO,CAChB,OAAI,KAAK,QAAQ,SAAW,oBACnB,KAAK,eAAe,KAAK,EAG3B,SAAS,MAAO,KAAK,QAAQ,UAAU,MAAM,CACtD,CAEA,eAAe,MAAO,CACpB,OAAO,QAAU,SAAW,UAAY,KAC1C,CACF,CAEA,SAAS,UAAU,MAAO,CACxB,MAAM,IAAM,OAAO,OAAS,EAAE,EAAE,YAAY,EAAE,QAAQ,UAAW,EAAE,EAC7D,OAAS,CACb,OAAQ,SACR,OAAQ,SACR,UAAW,YACX,QAAS,UACT,iBAAkB,oBAClB,cAAe,UACf,KAAM,OACN,OAAQ,SACR,OAAQ,QACV,EAEA,MAAO,+HADM,OAAO,GAAG,GAAK,OAAO,MACuG,gBAC5I,CAEA,SAAS,eAAe,MAAO,MAAO,CACpC,MAAM,MAAQ,GAAG,KAAK,IAAI,KAAK,GAAG,YAAY,EAC9C,MAAK,uEAAuE,KAAK,KAAK,EAC/E,wDAAwD,YAAY,KAAK,CAAC,4BADe,EAElG,CAEA,SAAS,YAAY,MAAO,CAC1B,OAAI,MAAM,SAAS,aAAa,EAAU,cACtC,MAAM,SAAS,MAAM,EAAU,OAC/B,MAAM,SAAS,QAAQ,EAAU,SACjC,MAAM,SAAS,OAAO,EAAU,QAChC,MAAM,SAAS,OAAO,EAAU,QAChC,MAAM,SAAS,SAAS,GAAK,MAAM,SAAS,OAAO,EAAU,QAC1D,OACT,CAEA,SAAS,SAAS,MAAO,IAAK,CAC5B,OAAO,MAAM,KAAK,GAAK,KACzB,CAEA,SAAS,UAAU,MAAO,CACxB,MAAM,MAAQ,OAAO,OAAS,EAAE,EAAE,MAAM,+BAA+B,EACvE,MAAO,CACL,MAAO,MAAQ,OAAO,MAAM,CAAC,CAAC,EAAI,EAClC,OAAQ,MAAQ,OAAO,MAAM,CAAC,CAAC,EAAI,CACrC,CACF,CAEA,SAAS,iBAAiB,MAAO,CAC/B,MAAM,KAAO,UAAU,KAAK,EAC5B,MAAI,CAAC,KAAK,OAAS,CAAC,KAAK,OAAe,OAAO,OAAS,EAAE,EAAE,QAAQ,OAAQ,EAAE,EAAE,YAAY,EACrF,GAAG,iBAAiB,KAAK,KAAK,CAAC,IAAI,iBAAiB,KAAK,MAAM,CAAC,EACzE,CAEA,SAAS,iBAAiB,MAAO,CAC/B,MAAM,OAAS,OAAO,OAAS,CAAC,EAChC,OAAK,OAAO,SAAS,MAAM,EACpB,OAAO,UAAU,MAAM,EAAI,OAAO,MAAM,EAAI,OAAO,OAAO,OAAO,QAAQ,CAAC,CAAC,CAAC,EAAE,QAAQ,SAAU,EAAE,EADpE,GAEvC,CAEA,SAAS,gBAAgB,MAAO,OAAQ,OAAS,GAAM,CACrD,MAAM,OAAS,OAAS,OAAS,KACjC,MAAO,GAAG,iBAAiB,KAAK,CAAC,GAAG,MAAM,GAAG,iBAAiB,MAAM,CAAC,GACvE,CAEA,SAAS,WAAW,SAAU,OAAQ,CACpC,GAAI,OAAO,QAAU,EAAE,IAAM,OAAO,UAAY,EAAE,EAAG,MAAO,GAC5D,MAAM,aAAe,UAAU,QAAQ,EACjC,WAAa,UAAU,MAAM,EACnC,GAAI,CAAC,aAAa,OAAS,CAAC,aAAa,QAAU,CAAC,WAAW,OAAS,CAAC,WAAW,OAAQ,MAAO,GACnG,MAAM,MAAQ,OAAO,aAAa,KAAK,IAAM,OAAO,WAAW,KAAK,GAAK,OAAO,aAAa,MAAM,IAAM,OAAO,WAAW,MAAM,EAC3H,QAAU,OAAO,aAAa,KAAK,IAAM,OAAO,WAAW,MAAM,GAAK,OAAO,aAAa,MAAM,IAAM,OAAO,WAAW,KAAK,EACnI,OAAO,OAAS,OAClB,CAEA,SAAS,SAAS,MAAO,CACvB,MAAM,OAAS,OAAO,WAAW,OAAO,OAAS,EAAE,EAAE,QAAQ,IAAK,GAAG,CAAC,EACtE,OAAO,OAAO,SAAS,MAAM,EAAI,OAAS,CAC5C,CAEA,SAAS,UAAU,MAAO,CACxB,MAAM,OAAS,OAAO,SAAS,OAAO,OAAS,EAAE,EAAE,QAAQ,SAAU,EAAE,EAAG,EAAE,EAC5E,OAAO,OAAO,SAAS,MAAM,EAAI,OAAS,CAC5C,CAEA,SAAS,YAAY,MAAO,SAAW,EAAG,CACxC,MAAM,OAAS,OAAO,WAAW,KAAK,EACtC,OAAO,OAAO,SAAS,MAAM,EAAI,OAAS,QAC5C,CAEA,SAAS,WAAW,MAAO,CACzB,MAAM,OAAS,OAAO,WAAW,KAAK,EACtC,OAAO,OAAO,SAAS,MAAM,EAAI,KAAK,OAAO,OAAS,OAAO,SAAW,GAAG,EAAI,IAAM,CACvF,CAEA,SAAS,uBAAuB,MAAO,CACrC,MAAO,oBAAoB,OAAO,KAAK,EAAE,QAAQ,CAAC,CAAC,EACrD,CAEA,SAAS,iBAAiB,QAAS,CACjC,OAAO,OAAO,KAAK,SAAW,CAAC,CAAC,EAC7B,KAAK,EACL,IAAK,KAAQ,GAAG,GAAG,IAAI,OAAO,QAAQ,GAAG,CAAC,CAAC,EAAE,EAC7C,KAAK,GAAG,CACb,CAEA,SAAS,wBAAwB,WAAY,YAAa,cAAe,YAAa,cAAe,CACnG,MAAO,CAAC,WAAY,YAAa,cAAe,YAAa,aAAa,EAAE,KAAK,GAAG,CACtF,CAEA,SAAS,gBAAgB,OAAS,CAAC,EAAG,MAAO,CAC3C,OAAO,OAAO,QAAQ,KAAK,CAC7B,CAEA,SAAS,aAAa,SAAU,SAAU,SAAU,SAAW,OAAW,CACxE,OAAO,WAAW,QAAQ,GAAK,WAAW,QAAQ,GAAK,QACzD,CAEA,SAAS,oBAAoB,SAAU,KAAM,CAC3C,IAAI,SAAW,EACf,OAAC,MAAM,QAAQ,IAAI,EAAI,KAAO,CAAC,GAC5B,IAAK,MAAS,CACb,IAAK,UAAU,IAAI,KAAO,IAAI,SAAW,IAAI,cAAgB,IAAI,WAAW,EAC5E,SAAU,YAAY,IAAI,SAAU,CAAC,CACvC,EAAE,EACD,OAAQ,KAAQ,IAAI,IAAM,CAAC,EAC3B,KAAK,CAAC,EAAG,IAAM,EAAE,IAAM,EAAE,GAAG,EAC5B,QAAS,KAAQ,CACZ,UAAY,IAAI,MAAK,SAAW,IAAI,SAC1C,CAAC,EACI,QACT,CAEA,SAAS,kBAAkB,SAAU,SAAU,CAC7C,OAAO,oBAAoB,SAAU,aAAa,SAAU,0BAA2B,6BAA8B,CAAC,CAAC,CAAC,CAC1H,CAEA,SAAS,uBAAuB,SAAU,aAAe,GAAI,CAC3D,MAAM,QAAU,aAAa,SAAU,sBAAuB,wBAAyB,CAAC,CAAC,EAEzF,MAAO,GADe,YAAY,UAAU,YAAY,EAAG,CAAC,EACjC,GAC7B,CAEA,SAAS,uBAAuB,MAAO,CACrC,OAAO,OAAO,OAAO,KAAK,EAAE,QAAQ,EAAE,CAAC,CACzC,CAEA,SAAS,wBAAwB,SAAU,QAAS,CAClD,MAAM,UAAY,aAAa,SAAU,mBAAoB,mBAAmB,EAC1E,MAAQ,KAAK,IAAI,EAAG,YAAY,QAAQ,MAAO,CAAC,CAAC,EACjD,OAAS,KAAK,IAAI,EAAG,YAAY,QAAQ,OAAQ,CAAC,CAAC,EACnD,SAAW,KAAK,IAAI,EAAG,UAAU,QAAQ,QAAQ,CAAC,EAClD,SAAW,OAAO,QAAQ,UAAY,EAAE,EACxC,SAAW,OAAO,QAAQ,UAAY,EAAE,EACxC,MAAQ,WAAW,iBAAiB,QAAQ,GAAK,WAAW,MAC5D,UAAY,MAAM,QAAQ,OAAO,SAAS,EAAI,MAAM,UAAY,CAAC,EACvE,GAAI,CAAC,WAAa,UAAU,WAAa,UAAY,CAAC,OAAS,CAAC,QAAU,CAAC,UAAY,CAAC,UAAU,OAAQ,OAAO,KAEjH,MAAM,KAAO,uBAAuB,MAAQ,MAAM,EAC5C,SAAW,UAAU,KAAM,MAAS,MAAQ,YAAY,KAAK,QAAS,CAAC,CAAC,GAAK,UAAU,GAAG,EAAE,EAC5F,cAAgB,MAAM,QAAQ,UAAU,aAAa,EAAI,SAAS,cAAgB,CAAC,EACnF,aAAe,cAAc,KAAM,MAAS,UAAY,UAAU,KAAK,WAAW,CAAC,GAAK,cAAc,GAAG,EAAE,EACjH,GAAI,CAAC,aAAc,OAAO,KAE1B,MAAM,SAAW,YAAY,MAAM,SAAU,CAAC,EAC9C,IAAI,eAAiB,uBAAuB,KAAO,SAAW,SAAW,YAAY,aAAa,OAAQ,CAAC,CAAC,EAC5G,MAAM,UAAY,UAAU,QAAQ,QAAQ,EACtC,cAAgB,QAAQ,gBAAkB,GAAO,UAAU,OAAS,EAAI,UAC9E,QAAS,MAAQ,UAAW,OAAS,cAAe,OAAS,EAAG,CAE9D,MAAM,cAAgB,QAAU,UAAY,KAAO,YAAY,UAAU,MAAQ,CAAC,EAAE,QAAS,CAAC,EAC9F,GAAI,QAAU,WAAa,gBAAkB,QAAQ,aAAe,KAAW,MAC/E,MAAM,MAAQ,UAAU,KAAK,EAAE,cACzB,SAAW,MAAM,KAAM,MAAS,UAAY,UAAU,KAAK,WAAW,CAAC,GAAK,MAAM,GAAG,EAAE,EACvF,cAAgB,MAAM,QAAQ,QAAQ,EAC5C,QAAS,cAAgB,cAAe,cAAgB,MAAM,OAAQ,eAAiB,EAAG,CACxF,MAAM,kBAAoB,gBAAkB,cACxC,SAAW,UAAU,MAAM,cAAgB,CAAC,EAAE,WAAW,EAAI,EACjE,eAAiB,KAAK,IAAI,eAAgB,uBACxC,cAAgB,SAAW,kBAAoB,YAAY,MAAM,aAAa,EAAE,OAAQ,CAAC,CAC3F,CAAC,CACH,CACF,CAEA,MAAM,mBAAqB,KAAK,IAAI,KAAU,YAAY,UAAU,sBAAsB,QAAQ,EAAG,CAAC,CAAC,EACjG,wBAA0B,KAAK,IAAI,UAAW,KAAK,IAAI,EAAG,YAAY,UAAU,wBAAyB,CAAC,CAAC,CAAC,EAC5G,yBAA2B,KAAK,IAAI,KAAU,YAClD,WAAa,SACT,UAAU,2BAA2B,MACrC,UAAU,4BAA4B,QAAQ,EAClD,CACF,CAAC,EACK,kBAAoB,KAAK,IAAI,UAAW,KAAK,IAAI,EAAG,YAAY,UAAU,kBAAmB,CAAC,CAAC,CAAC,EAChG,qBAAuB,KAAK,IAAI,KAAU,YAAY,QAAQ,qBAAsB,CAAC,CAAC,EACtF,QAAU,KAAK,IAAI,EAAG,YAAY,QAAQ,QAAS,YAAY,aAAa,SAAU,eAAgB,eAAe,EAAG,EAAE,CAAC,CAAC,EAC5H,YAAc,wBAA0B,GAAK,2BAA6B,EAC5E,WAAW,gBAAkB,EAAI,wBAA0B,KAAO,wBAAwB,EAC1F,eACE,wBAA0B,KAAK,IAAI,KAAU,YAAY,UAAU,qBAAqB,MAAO,CAAC,CAAC,EACjG,sBAAwB,WAC5B,aAAe,EAAI,kBAAoB,KAAO,mBAAqB,oBACrE,EACM,qBAAuB,WAC3B,aAAe,EAAI,kBAAoB,KAAO,wBAA0B,oBAC1E,EACM,gBAAkB,WAAa,WAAa,WAAa,SAAW,WAAa,eACnF,WAAW,sBAAwB,mBAAqB,wBAAwB,EAChF,sBACE,MAAQ,WAAW,KAAK,IAC5B,QACA,eACF,CAAC,EAED,MAAO,CACL,MACA,KAAM,WAAW,MAAQ,QAAQ,EACjC,KAAM,MAAQ,SACd,SACA,SACA,SACA,aAAc,kBACd,iBAAkB,UAAU,QAC5B,eAAgB,WAAW,iBAAiB,QAAQ,EAAI,SAAW,UACnE,eACA,YACA,wBACA,yBACA,0BAA2B,kBAC3B,mBACA,oBACF,CACF,CAEA,SAAS,sBAAsB,SAAU,SAAU,CACjD,MAAM,iBAAmB,aAAa,SAAU,YAAa,YAAa,CAAC,CAAC,IAAI,QAAQ,GAAK,CAAC,EACxF,IAAM,OAAO,UAAY,EAAE,EAAE,YAAY,EACzC,MAAQ,OAAO,iBAAiB,OAAS,EAAE,EAAE,YAAY,EAC/D,OAAI,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,GAAK,IAAI,SAAS,SAAS,GAAK,MAAM,SAAS,UAAU,EAAU,GAClH,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,EAAU,QACzD,IAAI,SAAS,OAAO,GAAK,MAAM,SAAS,OAAO,GAAK,MAAQ,SAAW,QAAU,QAAgB,QAC9F,EACT,CAEA,SAAS,4BAA4B,SAAU,QAAS,CACtD,MAAM,QAAU,aAAa,SAAU,gBAAiB,gBAAgB,EAClE,QAAU,aAAa,SAAU,UAAW,UAAW,CAAC,CAAC,EACzD,WAAa,SAAS,aAAe,SAAS,YAAc,CAAC,EAC7D,MAAQ,KAAK,IAAI,EAAG,YAAY,QAAQ,MAAO,CAAC,CAAC,EACjD,OAAS,KAAK,IAAI,EAAG,YAAY,QAAQ,OAAQ,CAAC,CAAC,EACnD,SAAW,KAAK,IAAI,EAAG,UAAU,QAAQ,QAAQ,CAAC,EAClD,WAAa,MAAM,QAAQ,SAAS,UAAU,EAAI,QAAQ,WAAW,IAAI,SAAS,EAAI,CAAC,EACvF,SAAW,YAAY,WAAW,WAAa,WAAW,SAAU,CAAC,EACrE,UAAY,YAAY,WAAW,YAAc,WAAW,UAAW,CAAC,EACxE,SAAW,YAAY,WAAW,WAAa,WAAW,SAAU,EAAE,EACtE,UAAY,YAAY,WAAW,YAAc,WAAW,UAAW,EAAE,EAE/E,GAAI,CAAC,SAAW,MAAQ,UAAY,OAAS,WAAa,MAAQ,UAAY,OAAS,UAAW,OAAO,KACzG,MAAM,gBAAkB,KAAK,IAAI,GAAG,WAAW,OAAQ,OAAU,MAAQ,CAAC,EAAG,EAAE,EAC/E,GAAI,SAAW,gBAAiB,OAAO,KAEvC,MAAM,UAAY,QAAQ,WAAa,QAAQ,YAAc,SACzD,OAAO,QAAQ,SAAS,EACxB,gBAAgB,MAAO,OAAQ,EAAI,EACjC,YAAc,YAAY,QAAQ,aAAa,SAAS,IAAI,OAAO,QAAQ,CAAC,EAAG,CAAC,EAChF,YAAc,YAAc,EAC9B,YACA,kCAAkC,QAAS,MAAO,OAAQ,SAAU,QAAQ,aAAa,SAAS,CAAC,EAEvG,GAAI,CAAC,aAAe,YAAc,YAAY,QAAQ,mBAAoB,GAAM,EAAG,OAAO,KAE1F,MAAM,cAAgB,YAAY,QAAQ,cAAe,EAAE,EACrD,QAAU,YAAY,aAAa,SAAU,eAAgB,eAAe,EAAG,EAAE,EACjF,MAAQ,WAAW,KAAK,IAAI,QAAS,aAAe,EAAI,cAAgB,IAAI,CAAC,EAEnF,MAAO,CACL,MACA,KAAM,WAAW,MAAQ,QAAQ,EACjC,KAAM,MAAQ,SACd,SAAU,EACV,cAAe,MACf,SACA,MAAO,OAAO,QAAQ,OAAS,QAAQ,EACvC,MACA,OACA,UACA,YACA,cACA,aAAc,YAAc,EACxB,sBACC,QAAQ,aAAa,SAAS,EAAI,gCAAkC,iCACzE,eAAgB,QAAQ,gBAAkB,gBAC1C,IAAK,CAAC,OAAO,QAAQ,OAAS,QAAQ,EAAG,UAAW,QAAQ,EAAE,KAAK,GAAG,CACxE,CACF,CAEA,SAAS,kCAAkC,QAAS,MAAO,OAAQ,SAAU,UAAY,KAAM,CAC7F,MAAM,YAAc,0BAA0B,UAAW,QAAQ,EACjE,GAAI,cAAgB,KAAM,OAAO,YAEjC,MAAM,MAAQ,uBAAuB,QAAQ,kBAAmB,QAAQ,EACxE,OAAK,MAEE,KAAK,MACV,YAAY,MAAM,MAAO,CAAC,EACxB,YAAY,MAAM,KAAM,CAAC,EAAI,MAAQ,OACrC,YAAY,MAAM,eAAiB,MAAM,aAAc,CAAC,GAAK,MAAQ,OACzE,EANmB,CAOrB,CAEA,SAAS,0BAA0B,IAAK,SAAU,CAChD,MAAM,OAAS,OAAO,QAAQ,KAAO,CAAC,CAAC,EACpC,IAAI,CAAC,CAAC,IAAK,KAAK,KAAO,CAAE,SAAU,UAAU,GAAG,EAAG,MAAO,YAAY,MAAO,CAAC,CAAE,EAAE,EAClF,OAAQ,OAAU,MAAM,SAAW,GAAK,MAAM,MAAQ,CAAC,EACvD,KAAK,CAAC,EAAG,IAAM,EAAE,SAAW,EAAE,QAAQ,EAEzC,OAAK,OAAO,OACL,wBAAwB,OAAQ,SAAU,OAAO,EAD7B,IAE7B,CAEA,SAAS,uBAAuB,OAAQ,SAAU,CAChD,MAAM,OAAS,OAAO,QAAQ,QAAU,CAAC,CAAC,EACvC,IAAI,CAAC,CAAC,IAAK,KAAK,KAAO,CACtB,SAAU,UAAU,GAAG,EACvB,MAAO,YAAY,OAAO,MAAO,CAAC,EAClC,KAAM,YAAY,OAAO,KAAM,CAAC,EAChC,cAAe,YAAY,OAAO,eAAiB,OAAO,aAAc,CAAC,CAC3E,EAAE,EACD,OAAQ,OAAU,MAAM,SAAW,CAAC,EACpC,KAAK,CAAC,EAAG,IAAM,EAAE,SAAW,EAAE,QAAQ,EAEzC,GAAI,CAAC,OAAO,OAAQ,OAAO,KAC3B,GAAI,OAAO,SAAW,EAAG,OAAO,OAAO,CAAC,EAExC,MAAM,WAAa,OAAO,UAAW,OAAU,MAAM,UAAY,QAAQ,EACnE,MAAQ,YAAc,EAAI,OAAO,UAAU,EAAI,OAAO,OAAO,OAAS,CAAC,EACvE,MAAQ,WAAa,EACvB,OAAO,WAAa,CAAC,EACpB,aAAe,EAAI,OAAO,CAAC,EAAI,OAAO,OAAO,OAAS,CAAC,EAC5D,GAAI,MAAM,WAAa,MAAM,SAAU,OAAO,MAE9C,MAAM,OAAS,SAAW,MAAM,WAAa,MAAM,SAAW,MAAM,UACpE,MAAO,CACL,MAAO,uBAAuB,MAAM,MAAO,MAAM,MAAO,KAAK,EAC7D,KAAM,uBAAuB,MAAM,KAAM,MAAM,KAAM,KAAK,EAC1D,cAAe,uBAAuB,MAAM,cAAe,MAAM,cAAe,KAAK,CACvF,CACF,CAEA,SAAS,wBAAwB,OAAQ,SAAU,MAAO,CACxD,GAAI,OAAO,SAAW,EAAG,OAAO,OAAO,CAAC,EAAE,KAAK,EAC/C,MAAM,WAAa,OAAO,UAAW,OAAU,MAAM,UAAY,QAAQ,EACnE,MAAQ,YAAc,EAAI,OAAO,UAAU,EAAI,OAAO,OAAO,OAAS,CAAC,EACvE,MAAQ,WAAa,EACvB,OAAO,WAAa,CAAC,EACpB,aAAe,EAAI,OAAO,CAAC,EAAI,OAAO,OAAO,OAAS,CAAC,EAC5D,GAAI,MAAM,WAAa,MAAM,SAAU,OAAO,MAAM,KAAK,EACzD,MAAM,OAAS,SAAW,MAAM,WAAa,MAAM,SAAW,MAAM,UACpE,OAAO,KAAK,MAAM,uBAAuB,MAAM,KAAK,EAAG,MAAM,KAAK,EAAG,KAAK,CAAC,CAC7E,CAEA,SAAS,uBAAuB,MAAO,MAAO,MAAO,CACnD,OAAO,OAAS,MAAQ,OAAS,KACnC,CAEA,SAAS,4BAA4B,SAAU,WAAY,SAAU,CACnE,GAAI,aAAe,WAAa,CAAC,sBAAsB,SAAU,QAAQ,EAAG,MAAO,GACnF,MAAM,OAAS,YAAY,aAAa,SAAU,mBAAoB,mBAAmB,EAAG,CAAC,EAC7F,MAAO,GAAI,KAAK,IAAI,EAAG,MAAM,EAAI,GACnC,CAEA,SAAS,sBAAsB,SAAU,QAAS,QAAS,CACzD,MAAM,MAAQ,KAAK,IAAI,EAAG,YAAY,QAAQ,MAAO,CAAC,CAAC,EACjD,OAAS,KAAK,IAAI,EAAG,YAAY,QAAQ,OAAQ,CAAC,CAAC,EACnD,SAAW,KAAK,IAAI,EAAG,UAAU,QAAQ,QAAQ,CAAC,EAClD,aAAe,SAAS,cAAgB,QAAQ,cAAgB,QAAQ,eAAiB,GACzF,YAAc,eAAiB,YAAc,GAAK,GACxD,GAAI,MAAQ,IAAO,OAAS,IAAO,CAAC,UAAY,MAAQ,aAAe,OAAS,YAAa,OAAO,KAEpG,MAAM,gBADW,aAAa,SAAU,gBAAiB,iBAAkB,CAAC,CAAC,IAC1C,YAAY,GAAK,CAAC,EAC/C,QAAU,YAAY,gBAAgB,eAAiB,gBAAgB,aAAc,YAAY,aAAa,SAAU,eAAgB,eAAe,EAAG,EAAE,CAAC,EAC7J,SAAW,QAAQ,UAAY,SAAS,iBAAmB,aAC3D,SAAW,eAAiB,YAAc,YAAc,WACxD,eAAiB,wBAAwB,SAAU,CACvD,SACA,MACA,OACA,SACA,SACA,QACA,qBAAsB,uBAAuB,SAAU,YAAY,EAC/D,4BAA4B,SAAU,QAAQ,YAAc,OAAQ,QAAQ,EAChF,cAAe,WAAa,WAC5B,YAAa,IACf,CAAC,EACD,GAAI,CAAC,eAAgB,OAAO,KAE5B,MAAM,MAAQ,eAAe,MACvB,SAAW,oBAAoB,SAAU,aAAa,SAAU,oBAAqB,qBAAsB,CAAC,CAAC,CAAC,EAC9G,cAAgB,SAAW,GAAK,SAAW,IAAM,WAAW,OAAS,EAAI,SAAW,IAAI,EAAI,MAElG,MAAO,CACL,GAAG,eACH,MACA,KAAM,WAAW,MAAQ,QAAQ,EACjC,KAAM,MAAQ,SACd,SACA,cACA,SACA,SACA,UAAW,QAAQ,WAAa,gBAAgB,MAAO,OAAQ,EAAI,EACnE,YACF,CACF,CAEA,SAAS,sBAAsB,aAAc,cAAe,WAAY,YAAa,IAAK,OAAQ,CAChG,MAAM,QAAU,KAAK,IAAI,EAAG,YAAY,IAAK,sBAAsB,CAAC,EAC9D,WAAa,KAAK,IAAI,EAAG,YAAY,OAAQ,wBAAwB,CAAC,EACtE,YAAc,KAAK,IAAI,EAAG,YAAY,WAAY,GAAG,EAAK,WAAa,CAAE,EACzE,aAAe,KAAK,IAAI,EAAG,YAAY,YAAa,EAAE,EAAK,WAAa,CAAE,EAC1E,QAAU,KAAK,OAAO,YAAc,UAAY,KAAK,IAAI,IAAM,YAAY,aAAc,CAAC,CAAC,EAAI,QAAQ,EACvG,KAAO,KAAK,OAAO,aAAe,UAAY,KAAK,IAAI,IAAM,YAAY,cAAe,CAAC,CAAC,EAAI,QAAQ,EAC5G,OAAO,KAAK,IAAI,EAAG,QAAU,IAAI,CACnC,CAEA,SAAS,kBACP,MACA,OACA,WAAa,IACb,YAAc,GACd,IAAM,uBACN,OAAS,yBACT,CACA,OAAO,KAAK,IACV,sBAAsB,MAAO,OAAQ,WAAY,YAAa,IAAK,MAAM,EACzE,sBAAsB,OAAQ,MAAO,WAAY,YAAa,IAAK,MAAM,CAC3E,CACF,CAEA,SAAS,qBAAqB,SAAU,cAAe,mBAAoB,CACzE,MAAM,KAAO,aAAa,SAAU,sBAAuB,wBAAyB,CAAC,CAAC,EACtF,IAAI,SAAW,EACX,QAAU,GAEd,OAAC,MAAM,QAAQ,IAAI,EAAI,KAAO,CAAC,GAAG,QAAS,KAAQ,CACjD,MAAM,UAAY,UAAU,IAAI,YAAc,IAAI,WAAa,IAAI,GAAG,EAClE,UAAY,GAAK,eAAiB,YACpC,SAAW,YAAY,IAAI,SAAU,CAAC,EACtC,QAAU,GAEd,CAAC,EAEM,QAAU,SAAW,YAAY,mBAAoB,CAAC,CAC/D,CAEA,SAAS,kCAAkC,SAAU,OAAQ,CAC3D,MAAI,CAAC,OAAQ,WAAY,YAAY,EAAE,SAAS,MAAM,EAAU,GAC5D,WAAa,SAAW,WAAa,QAAgB,SAAW,SAAW,SAAW,QACtF,WAAa,SAAW,WAAa,cAAsB,SAAW,QACnE,EACT,CAEA,SAAS,0BAA0B,SAAU,OAAQ,QAAS,CAC5D,MAAM,UAAY,MAAM,QAAQ,SAAS,QAAQ,EAAI,QAAQ,SAAW,CAAC,EAEzE,MADmB,CAAC,OAAQ,SAAS,cAAe,GAAG,UAAW,WAAa,SAAW,WAAa,cAAgB,QAAU,QAAS,MAAM,EAC9H,KAAM,WACtB,YACI,CAAC,UAAU,QAAU,UAAU,SAAS,SAAS,IAClD,kCAAkC,SAAU,SAAS,CACzD,GAAK,MACR,CAEA,SAAS,oBAAoB,SAAU,QAAS,QAAS,CACvD,MAAM,MAAQ,KAAK,IAAI,EAAG,YAAY,QAAQ,MAAO,CAAC,CAAC,EACjD,OAAS,KAAK,IAAI,EAAG,YAAY,QAAQ,OAAQ,CAAC,CAAC,EACnD,cAAgB,KAAK,IAAI,EAAG,UAAU,QAAQ,eAAiB,QAAQ,QAAQ,CAAC,EACtF,GAAI,MAAQ,IAAO,OAAS,IAAO,CAAC,eAAiB,KAAK,IAAI,MAAO,MAAM,EAAI,IAAM,KAAK,IAAI,MAAO,MAAM,EAAI,GAAI,OAAO,KAE1H,MAAM,SAAW,KAAK,IAAI,EAAG,kBAC3B,MACA,OACA,QAAQ,YAAc,QAAQ,aAAe,IAC7C,QAAQ,aAAe,QAAQ,cAAgB,GAC/C,QAAQ,UAAY,QAAQ,WAAa,uBACzC,QAAQ,aAAe,QAAQ,cAAgB,wBACjD,CAAC,EACK,cAAgB,KAAK,IAAI,EAAG,KAAK,KAAK,cAAgB,QAAQ,CAAC,EAC/D,gBAAkB,KAAK,IAAI,EAAG,kBAClC,MACA,OACA,QAAQ,YAAc,QAAQ,aAAe,IAC7C,QAAQ,aAAe,QAAQ,cAAgB,GAC/C,gCACA,CACF,CAAC,EACK,qBAAuB,KAAK,IAAI,EAAG,KAAK,KAAK,cAAgB,eAAe,CAAC,EAC7E,SAAW,QAAQ,UAAY,SAAS,iBAAmB,QAC3D,OAAS,0BAA0B,SAAU,QAAQ,QAAU,SAAS,eAAiB,GAAI,OAAO,EACpG,SAAW,aAAa,SAAU,mBAAoB,qBAAsB,CAAC,CAAC,EAC9E,aAAe,aAAa,SAAU,kBAAmB,oBAAqB,CAAC,CAAC,EAChF,KAAO,WAAW,QAAQ,GAAK,UAAU,OAAS,UAAU,SAAW,cAAgB,CAAC,EACxF,SAAW,aAAa,SAAU,gBAAiB,iBAAkB,CAAC,CAAC,EACvE,iBAAmB,KAAK,IAAI,KAAO,YAAY,WAAW,MAAM,GAAG,WAAY,CAAC,CAAC,EACjF,aAAe,YAAY,aAAa,SAAU,2BAA4B,6BAA6B,EAAG,EAAE,EAChH,gBAAkB,KAAK,IAAI,EAAG,UAAU,QAAQ,iBAAmB,QAAQ,kBAAoB,CAAC,CAAC,EAEjG,eADY,aAAa,SAAU,mBAAoB,mBAAmB,GAC9C,gBAAkB,CAAC,EAC/C,eAAiB,KAAK,IAAI,IAAM,YAAY,eAAe,MAAO,CAAC,CAAC,EACpE,gBAAkB,KAAK,IAAI,IAAM,YAAY,eAAe,OAAQ,CAAC,CAAC,EACtE,wBAA0B,KAAK,IAAI,EAAG,UAAU,eAAe,gBAAkB,EAAE,CAAC,EACpF,kBAAoB,qBAAuB,wBAC3C,qBAAuB,kBAAoB,GAAK,gBAAkB,IAAM,aAAe,MACvF,eAAiB,wBAAwB,SAAU,CACvD,SAAU,SACV,MAAO,eACP,OAAQ,gBACR,SAAU,kBACV,SACA,oBACF,CAAC,EACD,GAAI,CAAC,eAAgB,OAAO,KAG5B,MAAM,uBAAyB,wBAAwB,SAAU,CAC/D,SAAU,SAAU,MAAO,OAAQ,SAAU,cAAe,SAAU,oBACxE,CAAC,EACD,GAAI,CAAC,uBAAwB,OAAO,KACpC,MAAM,WAAa,KAAK,IAAI,eAAe,MAAO,uBAAuB,KAAK,EACxE,gBAAkB,qBAAqB,SAAU,qBAAsB,YAAY,OAAO,oBAAoB,GAAG,SAAU,CAAC,CAAC,EAC7H,cAAgB,gBAAkB,GAAK,gBAAkB,IAAM,WAAW,YAAc,EAAI,gBAAkB,IAAI,EAAI,WAE5H,MAAO,CACL,GAAG,eACH,MAAO,WACP,KAAM,WAAW,WAAa,aAAa,EAC3C,KAAM,WAAa,cACnB,SAAU,gBACV,cACA,SAAU,cACV,cACA,cACA,SACA,qBACA,gBACA,SACA,OACA,gBACA,aAAc,4CACd,mBAAoB,eAAe,MACnC,0BAA2B,uBAAuB,MAClD,eAAgB,uBAAuB,MAAQ,eAAe,MAC9D,kBACA,uBAAwB,qBACxB,oBAAqB,eACrB,qBAAsB,gBACtB,wBACA,mBAAoB,eAAe,WACrC,CACF,CAEA,SAAS,YAAY,MAAO,SAAU,CACpC,MAAM,mBAAqB,OAAO,UAAY,KAAK,EAAE,YAAY,EAMjE,OALkB,IAAI,KAAK,aAAa,QAAS,CAC/C,MAAO,WACP,SAAU,kBACZ,CAAC,EACuB,cAAc,OAAO,OAAS,CAAC,CAAC,EAC3C,IAAK,MAChB,KAAK,OAAS,YAAc,qBAAuB,MAAQ,MAAQ,KAAK,KACzE,EAAE,KAAK,EAAE,CACZ,CAEA,SAAS,aAAa,MAAO,CAC3B,OAAO,IAAI,KAAK,aAAa,OAAO,EAAE,OAAO,OAAO,OAAS,CAAC,CAAC,CACjE,CAEA,SAAS,qBAAqB,SAAU,CACtC,MAAO,uCAAuC,KAAK,OAAO,UAAY,EAAE,CAAC,CAC3E,CAEA,SAAS,kBAAkB,QAAS,SAAU,CAC5C,MAAM,KAAO,OAAO,SAAW,EAAE,EAAE,KAAK,EACxC,OAAK,KACD,6IAA6I,KAAK,IAAI,EACjJ,8GAEF,KAJW,QAKpB,CAEA,SAAS,kCAAkC,QAAS,CAClD,MAAO,6EAA6E,KAAK,OAAO,SAAW,EAAE,CAAC,CAChH,CAEA,SAAS,MAAM,aAAc,CAC3B,OAAO,IAAI,QAAS,SAAY,CAC9B,OAAO,WAAW,QAAS,YAAY,CACzC,CAAC,CACH,CAEA,SAAS,mBAAmB,QAAS,CACnC,MAAI,CAAC,SAAW,CAAC,CAAC,QAAS,UAAU,EAAE,SAAS,QAAQ,OAAO,EAAU,GACrE,QAAQ,UAAY,WAAmB,GACpC,CAAC,CAAC,WAAY,QAAS,OAAQ,SAAU,SAAU,QAAS,QAAQ,EAAE,SAAS,QAAQ,IAAI,CACpG,CAEA,SAAS,iBAAiB,QAAS,CACjC,IAAI,QAAU,QAAQ,cACtB,KAAO,SAAW,UAAY,SAAS,MAAM,CAC3C,MAAM,MAAQ,OAAO,iBAAiB,OAAO,EAE7C,GADkB,gBAAgB,KAAK,MAAM,SAAS,GAAK,QAAQ,aAAe,QAAQ,aAC3E,OAAO,QACtB,QAAU,QAAQ,aACpB,CACA,OAAO,SAAS,kBAAoB,SAAS,eAC/C,CAEA,SAAS,oBAAoB,QAAS,CACpC,GAAI,CAAC,QAAS,MAAO,GACrB,MAAM,KAAO,QAAQ,sBAAsB,EAC3C,OAAO,KAAK,OAAS,GAAK,KAAK,IAAM,OAAO,aAAe,KAAK,MAAQ,GAAK,KAAK,KAAO,OAAO,UAClG,CAEA,eAAe,aAAa,SAAU,gBAAiB,CACrD,MAAM,KAAO,MAAM,SAAS,KAAK,EACjC,GAAI,CAAC,KAAM,CACT,GAAI,CAAC,SAAS,GAAI,MAAM,IAAI,MAAM,eAAe,EACjD,MAAO,CAAC,CACV,CAEA,GAAI,CACF,OAAO,KAAK,MAAM,IAAI,CACxB,MAAQ,CACN,MAAM,IAAI,MAAM,eAAe,CACjC,CACF,CAEA,SAAS,cAAc,SAAU,QAAS,CACxC,OAAO,OAAO,QAAQ,QAAQ,EAAE,MAAM,CAAC,CAAC,IAAK,QAAQ,IAAM,CACzD,MAAM,OAAS,QAAQ,GAAG,EAC1B,OAAI,OAAO,UAAa,SACf,OAAO,MAAM,IAAM,UAGvB,MAAQ,QAAU,MAAQ,cAAgB,WAAW,SAAU,MAAM,EACjE,GAGF,OAAO,QAAU,EAAE,IAAM,OAAO,UAAY,EAAE,CACvD,CAAC,CACH,CAEA,SAAS,uBAAuB,OAAQ,CACtC,MAAI,CAAC,QAAU,OAAO,aAAe,cAAgB,CAAC,MAAM,QAAQ,OAAO,IAAI,IAE/E,OAAO,KAAO,OAAO,KAAK,IAAK,KAAQ,sBAAsB,IAAK,MAAM,CAAC,EACzE,OAAO,WAAa,eACb,MACT,CAEA,SAAS,sBAAsB,IAAK,OAAQ,CAC1C,GAAI,CAAC,MAAM,QAAQ,GAAG,EAAG,OAAO,IAEhC,KAAM,CACJ,MACA,KACA,MACA,OACA,SACA,OACA,SACA,MACA,KACA,KACA,SACA,cACA,YACF,EAAI,IACE,QAAU,OAAO,YAAY,GAAK,EAAI,OAAO,gBAAgB,OAAO,YAAY,CAAC,EAAI,KACrF,SAAW,CACf,MACA,SACA,OACA,SAAU,OAAO,UAAY,CAAC,CAChC,EAEI,OAAM,SAAS,KAAO,MACtB,QAAU,KAAI,SAAS,MAAQ,OAAO,KAAK,GAC3C,SAAW,KAAI,SAAS,OAAS,OAAO,MAAM,GAElD,MAAM,MAAQ,CACZ,MAAO,OAAO,OAAS,CAAC,EACxB,KAAM,OAAO,MAAQ,CAAC,EACtB,KAAM,OAAO,MAAQ,CAAC,EACtB,SAAU,OAAO,UAAY,CAAC,EAC9B,cAAe,OAAO,eAAiB,OAAS,CAAC,EACjD,SAAU,OAAO,UAAY,CAAC,EAC9B,IAAK,GAAG,KAAK,IAAI,MAAQ,QAAQ,IAAI,OAAS,EAAE,IAAI,QAAU,EAAE,IAAI,QAAQ,IAAI,MAAM,IAAI,QAAQ,GAClG,UAAW,MAAQ,gBAAgB,OAAO,OAAS,CAAC,EAAG,OAAO,QAAU,CAAC,EAAG,EAAI,EAChF,SACA,OACA,KACF,EAEA,MAAO,CACL,IAAK,WAAW,MAAM,GAAG,GACzB,SACA,MACA,aAAc,SAAS,OAAS,uBAAuB,MAAM,KAAK,EAClE,UAAW,SAAS,WAAa,GACjC,WAAY,SAAS,YAAc,EACrC,CACF,CAEA,SAAS,WAAW,MAAO,CACzB,OAAO,OAAO,OAAS,EAAE,EAAE,QAAQ,WAAa,OAAU,CACxD,IAAK,QACL,IAAK,OACL,IAAK,OACL,IAAK,SACL,IAAK,QACP,GAAE,IAAI,CAAE,CACV,CAEK,eAAe,IAAI,4BAA4B,GAClD,eAAe,OAAO,6BAA8B,wBAAwB",
  "names": ["sizes", "status", "total", "unit", "baseUnit"]
}
