1import { 2 init_modal_sidebar_v1 3} from "./chunk-MO2D3CXO.js"; 4import { 5 init_text_area_v1 6} from "./chunk-TWAA7YIK.js"; 7import { 8 init_survey_image_option_v1 9} from "./chunk-RVGXNBF6.js"; 10import { 11 init_select_box_v2 12} from "./chunk-R4YB6JIA.js"; 13import { 14 Fetcher, 15 MANUALLY_ABORTED, 16 checkoutNonceParams, 17 fetchCheckoutNonce, 18 fetcher_exports, 19 init_fetcher, 20 init_nonce 21} from "./chunk-YSVSPNWW.js"; 22import { 23 init_addToCart, 24 mountComponent 25} from "./chunk-372FPXG6.js"; 26import { 27 debounce, 28 init_general, 29 init_nanostores, 30 nanostores_exports 31} from "./chunk-BY72GGKB.js"; 32import { 33 init_checkbox_v1, 34 init_radio_v1 35} from "./chunk-Y32E43UA.js"; 36import { 37 init_input_v1 38} from "./chunk-7HBS56XK.js"; 39import { 40 init_cf_utils, 41 isWithinCustomerCenterView, 42 uuidv4 43} from "./chunk-KIZY5IRN.js"; 44import { 45 init_modal_v1 46} from "./chunk-5NUE6T5P.js"; 47import { 48 CF2Component, 49 init_runtime, 50 registerComponent, 51 runtime_exports 52} from "./chunk-NQUHJ6NR.js"; 53import { 54 __commonJS, 55 __esm, 56 __export, 57 __toCommonJS, 58 init_define_process 59} from "./chunk-RFSPGZ3L.js"; 60
61// projects/user_pages/app/javascript/lander/utils/replace_tag.js 62var require_replace_tag = __commonJS({ 63 "projects/user_pages/app/javascript/lander/utils/replace_tag.js"() { 64 init_define_process(); 65 (function($4) { 66 $4.fn.changeElementType = function(newType) { 67 var attrs = {}; 68 $4.each(this[0].attributes, function(idx, attr) { 69 attrs[attr.nodeName] = attr.nodeValue; 70 }); 71 this.replaceWith(function() { 72 return $4("<" + newType + "/>", attrs).append($4(this).contents()); 73 }); 74 }; 75 })(jQuery); 76 } 77}); 78
79// projects/shared/javascript/parseurl.js 80var require_parseurl = __commonJS({ 81 "projects/shared/javascript/parseurl.js"() { 82 init_define_process(); 83 (function($4) { 84 var re = /([^&=]+)=?([^&]*)/g; 85 var decode = function(str) { 86 return decodeURIComponent(str.replace(/\+/g, " ")); 87 }; 88 $4.parseParams = function(query) { 89 function createElement(params2, key2, value2) { 90 key2 = key2 + ""; 91 if (key2.indexOf(".") !== -1) { 92 var list = key2.split("."); 93 var new_key = key2.split(/\.(.+)?/)[1]; 94 if (!params2[list[0]]) params2[list[0]] = {}; 95 if (new_key !== "") { 96 createElement(params2[list[0]], new_key, value2); 97 } else console.warn('parseParams :: empty property in key "' + key2 + '"'); 98 } else if (key2.indexOf("[") !== -1) { 99 var list = key2.split("["); 100 key2 = list[0]; 101 var list = list[1].split("]"); 102 var index = list[0]; 103 if (index == "") { 104 if (!params2) params2 = {}; 105 if (!params2[key2] || !$4.isArray(params2[key2])) params2[key2] = []; 106 params2[key2].push(value2); 107 } else { 108 if (!params2) params2 = {}; 109 if (!params2[key2] || !$4.isArray(params2[key2])) params2[key2] = []; 110 params2[key2][parseInt(index)] = value2; 111 } 112 } else { 113 if (!params2) params2 = {}; 114 params2[key2] = value2; 115 } 116 } 117 query = query + ""; 118 if (query === "") query = window.location + ""; 119 var params = {}, e; 120 if (query) { 121 if (query.indexOf("#") !== -1) { 122 query = query.substr(0, query.indexOf("#")); 123 } 124 if (query.indexOf("?") !== -1) { 125 query = query.substr(query.indexOf("?") + 1, query.length); 126 } else return {}; 127 if (query == "") return {}; 128 while (e = re.exec(query)) { 129 var key = decode(e[1]); 130 var value = decode(e[2]); 131 createElement(params, key, value); 132 } 133 } 134 return params; 135 }; 136 })(jQuery); 137 } 138}); 139
140// projects/user_pages/app/javascript/lander/audio_player.ts 141var require_audio_player = __commonJS({ 142 "projects/user_pages/app/javascript/lander/audio_player.ts"() { 143 init_define_process(); 144 var CFbuildAudioPlayer = function(el) { 145 try { 146 el.each(function() { 147 const $this = $(this); 148 const audioURL = $this.attr("data-audio-url") || "https://images.clickfunnels.com/images/SevenNationArmy.mp3"; 149 const loop = $this.attr("data-audio-loop") || "no"; 150 const playerOptions = { 151 class: "elAudioElement", 152 audioWidth: "100%", 153 audioHeight: "100%", 154 enableAutosize: true, 155 enableProgressTooltip: false, 156 loop: loop === "yes", 157 features: ["playpause", "current", "progress", "duration", "volume"] 158 }; 159 const audio = $(this).find("audio"); 160 audio.attr("src", audioURL); 161 audio.mediaelementplayer(playerOptions); 162 }); 163 } catch (err) { 164 console.log(err); 165 } 166 }; 167 window.addEventListener("load", function() { 168 CFbuildAudioPlayer($(".pageRoot .elAudioWrapper")); 169 }); 170 } 171}); 172
173// projects/user_pages/app/javascript/lander/vendor/garlic.cf.js 174var require_garlic_cf = __commonJS({ 175 "projects/user_pages/app/javascript/lander/vendor/garlic.cf.js"() { 176 init_define_process(); 177 globalThis.CFGarlicValues = {}; 178 !function($4) { 179 "use strict"; 180 class Storage { 181 constructor() { 182 this.defined = "undefined" !== typeof localStorage; 183 } 184 get(key, placeholder) { 185 return localStorage.getItem(key) ? localStorage.getItem(key) : "undefined" !== typeof placeholder ? placeholder : null; 186 } 187 has(key) { 188 return localStorage.getItem(key) ? true : false; 189 } 190 set(key, value, fn) { 191 if ("string" === typeof value) { 192 if ("" === value) { 193 this.destroy(key); 194 } else { 195 localStorage.setItem(key, value); 196 } 197 } 198 return "function" === typeof fn ? fn() : true; 199 } 200 destroy(key, fn) { 201 localStorage.removeItem(key); 202 return "function" === typeof fn ? fn() : true; 203 } 204 } 205 window.cfGarlicUtils = { 206 buildKey: (name) => { 207 return `garlic::${document.domain}*:${name}`; 208 }, 209 retrieve: (name) => { 210 if (window.CF2_DISABLE_GARLIC) return; 211 const storage = new Storage(); 212 const key = window.cfGarlicUtils.buildKey(name); 213 return storage.get(key); 214 }, 215 store: (name, value) => { 216 if (window.CF2_DISABLE_GARLIC) return; 217 const storage = new Storage(); 218 const key = window.cfGarlicUtils.buildKey(name); 219 return storage.set(key, value); 220 } 221 }; 222 var Garlic = function(element, storage, options) { 223 this.init("garlic", element, storage, options); 224 }; 225 Garlic.prototype = { 226 constructor: Garlic, 227 /* init data, bind jQuery on() actions */ 228 init: function(type, element, storage, options) { 229 this.type = type; 230 this.$element = $4(element); 231 this.options = this.getOptions(options); 232 this.storage = storage; 233 this.path = this.getPath(); 234 this.$element.addClass("garlic-auto-save"); 235 this.$element.on(this.options.events.join("." + this.type + " "), false, $4.proxy(this.persist, this)); 236 this.retrieve(); 237 }, 238 getOptions: function(options) { 239 return $4.extend({}, $4.fn[this.type].defaults, options, this.$element.data()); 240 }, 241 /* temporary store data / state in localStorage */ 242 persist: function() { 243 if (window.CF2_DISABLE_GARLIC) return; 244 if (this.val === this.getVal()) { 245 return; 246 } 247 this.val = this.getVal(); 248 this.storage.set(this.path, this.getVal()); 249 this.options.onPersist(this.$element, this.getVal()); 250 }, 251 getVal: function() { 252 return !this.$element.is("input[type=checkbox]") ? this.$element.val() : this.$element.prop("checked") ? "checked" : "unchecked"; 253 }, 254 /* retrieve localStorage data / state and update elem accordingly */ 255 retrieve: function() { 256 if (window.CF2_DISABLE_GARLIC) return; 257 if (this.storage.has(this.path)) { 258 var storedValue = this.storage.get(this.path); 259 if (this.$element.is("input[type=radio], input[type=checkbox]")) { 260 if ("checked" === storedValue || this.$element.val() === storedValue) { 261 return this.$element.attr("checked", true); 262 } else if ("unchecked" === storedValue) { 263 this.$element.attr("checked", false); 264 } 265 return; 266 } 267 this.$element.val(storedValue); 268 this.$element.trigger("input"); 269 this.options.onRetrieve(this.$element, storedValue); 270 return; 271 } 272 }, 273 /* delete localStorage persistance only */ 274 destroy: function() { 275 if (window.CF2_DISABLE_GARLIC) return; 276 this.storage.destroy(this.path); 277 }, 278 getPath: function(elem) { 279 if ("undefined" === typeof elem) { 280 elem = this.$element; 281 } 282 if (elem.length != 1) { 283 return false;
284 } 285 const node = elem.length ? elem[0] : elem; 286 const name = node.getAttribute("name"); 287 return window.cfGarlicUtils.buildKey(name); 288 }, 289 getStorage: function() { 290 return this.storage; 291 } 292 }; 293 $4.fn.garlic = function(option, fn) { 294 const options = $4.extend(true, {}, $4.fn.garlic.defaults, option, this.data()); 295 const storage = new Storage(); 296 if (!storage.defined) { 297 return false; 298 } 299 function bind(self) { 300 var $this = $4(self), data = $this.data("garlic"), fieldOptions = $4.extend({}, options, $this.data()); 301 if ("undefined" !== typeof fieldOptions.storage && !fieldOptions.storage) { 302 return; 303 } 304 if ("password" === $4(self).attr("type")) { 305 return; 306 } 307 if (!data) { 308 $this.data("garlic", data = new Garlic(self, storage, fieldOptions)); 309 } 310 if ("string" === typeof option && "function" === typeof data[option]) { 311 return data[option](); 312 } 313 } 314 const returnValue = bind($4(this)); 315 return "function" === typeof fn ? fn() : returnValue; 316 }; 317 $4.fn.garlic.Constructor = Garlic; 318 $4.fn.garlic.defaults = { 319 events: ["DOMAttrModified", "textInput", "input", "change", "click", "keypress", "paste", "focus"], 320 // Events list that trigger a localStorage 321 onRetrieve: function() { 322 }, 323 // This function will be triggered each time Garlic find an retrieve a local stored data for a field 324 onPersist: function() { 325 } 326 // This function will be triggered each time Garlic stores a field to local storage 327 }; 328 }(window.jQuery || window.Zepto); 329 } 330}); 331
332// projects/user_pages/app/javascript/lander/populate_select.ts 333var populate_select_exports = {}; 334__export(populate_select_exports, { 335 populateSelect: () => populateSelect 336}); 337var populateSelect; 338var init_populate_select = __esm({ 339 "projects/user_pages/app/javascript/lander/populate_select.ts"() { 340 init_define_process(); 341 globalThis.ClickFunnels = globalThis.ClickFunnels ?? {}; 342 populateSelect = (selectElement, type = void 0) => { 343 type = type ?? $(selectElement).parents(".elSelectWrapper").attr("data-type"); 344 let items; 345 const allCountries = globalThis.ClickFunnels.all_countries; 346 if (type == "all_united_states") { 347 selectElement.innerHTML = "<option> Select State </option>"; 348 items = allCountries.find((c) => c.iso2 == "US")?.regions; 349 items.forEach((item) => selectElement.innerHTML += `<option value="${item.state_code}" > ${item.name} </option>`); 350 } else if (type == "all_canadian_provinces") { 351 selectElement.innerHTML = "<option> Select State </option>"; 352 items = allCountries.find((c) => c.iso2 == "CA")?.regions; 353 items.forEach((item) => selectElement.innerHTML += `<option value="${item.state_code}" > ${item.name} </option>`); 354 } else if (type == "all_countries") { 355 const topMapping = ["US", "CA", "GB", "IE", "AU", "NZ"]; 356 const topHash = topMapping.reduce((acc, val) => { 357 acc[val] = true; 358 return acc; 359 }, {}); 360 const topOptions = topMapping.map((iso2) => ({ iso2 })); 361 const remainingOptions = []; 362 allCountries.forEach((item) => { 363 if (topHash[item.iso2]) { 364 const option = topOptions.find((option2) => option2.iso2 == item.iso2); 365 option.name = item.name; 366 } else { 367 remainingOptions.push(item); 368 } 369 }); 370 let html = ""; 371 topOptions.forEach((item) => html += `<option value="${item.iso2}" > ${item.name} </option>`); 372 remainingOptions.forEach((item) => html += `<option value="${item.iso2}" > ${item.name} </option>`); 373 selectElement.innerHTML = html; 374 } 375 }; 376 globalThis.ClickFunnels.populateSelect = populateSelect; 377 window.addEventListener("load", function() { 378 if (!$(".elCheckout, .elSelect, .elSuperSelect").length) return; 379 if ($('[data-page-element="Checkout/V2"]').length) return; 380 $.ajax({ 381 type: "GET", 382 contentType: "application/json", 383 url: "/cf_countries_states" 384 }).then((data) => { 385 globalThis.ClickFunnels.all_countries = data.result; 386 window.dispatchEvent(new CustomEvent("CF2_COUNTRIES_FETCHED")); 387 $(".elSelect, .elSuperSelect").each((index, element) => { 388 populateSelect(element); 389 }); 390 }); 391 }); 392 } 393}); 394
395// projects/user_pages/app/javascript/lander/runtime_events.ts 396var require_runtime_events = __commonJS({ 397 "projects/user_pages/app/javascript/lander/runtime_events.ts"() { 398 init_define_process(); 399 var CFEvents2 = /* @__PURE__ */ ((CFEvents3) => { 400 CFEvents3["FORM_SUBMITTED"] = "cf:form_submitted"; 401 CFEvents3["FORM_SUBMITTED_OK"] = "cf:form_submitted:ok"; 402 CFEvents3["FORM_SUBMITTED_FINALIZED"] = "cf:form_submitted:finalized"; 403 return CFEvents3; 404 })(CFEvents2 || {}); 405 globalThis.CFEvents = CFEvents2; 406 globalThis.CFDispatchEvent = function(eventName, detail) { 407 const event = new CustomEvent(eventName, { detail }); 408 document.dispatchEvent(event); 409 }; 410 } 411}); 412
413// projects/user_pages/app/javascript/lander/fhl_handle_select_transformation.ts 414var fhl_handle_select_transformation_exports = {}; 415var init_fhl_handle_select_transformation = __esm({ 416 "projects/user_pages/app/javascript/lander/fhl_handle_select_transformation.ts"() { 417 init_define_process(); 418 init_populate_select(); 419 window.addEventListener("CF2_COUNTRIES_FETCHED", function() { 420 const $allCountrySelects = $(".elSelectWrapper[data-type='all_countries'] .elSelect[name='country']"); 421 const $allStateInputs = $(".elInput[name='state']"); 422 let $allStates = $(".elSelect[name='state']"); 423 if ($allCountrySelects.length && $allStates.length && !$allStateInputs.length) { 424 $allCountrySelects.on("change", function() { 425 const $select = $(this); 426 const val = $select.val(); 427 $allStates = $(".elSelect[name='state']"); 428 if (val != "US") { 429 $allStates.html(""); 430 $allStates.val(""); 431 $allStates.changeElementType("input"); 432 $allStates = $(".elSelect[name='state']"); 433 $allStates.attr("placeholder", "Shipping State"); 434 } else { 435 $allStates.val(""); 436 $allStates.changeElementType("select"); 437 $allStates = $(".elSelect[name='state']"); 438 $allStates.each((index, element) => populateSelect(element)); 439 } 440 }); 441 $allCountrySelects.trigger("change"); 442 } 443 }); 444 } 445}); 446
vendor: 868 bytes, lines 447-461
447// node_modules/uuid/dist/esm-browser/stringify.js 448function unsafeStringify(arr, offset = 0) { 449 return (byteToHex[arr[offset + 0]] + byteToHex[arr[offset + 1]] + byteToHex[arr[offset + 2]] + byteToHex[arr[offset + 3]] + "-" + byteToHex[arr[offset + 4]] + byteToHex[arr[offset + 5]] + "-" + byteToHex[arr[offset + 6]] + byteToHex[arr[offset + 7]] + "-" + byteToHex[arr[offset + 8]] + byteToHex[arr[offset + 9]] + "-" + byteToHex[arr[offset + 10]] + byteToHex[arr[offset + 11]] + byteToHex[arr[offset + 12]] + byteToHex[arr[offset + 13]] + byteToHex[arr[offset + 14]] + byteToHex[arr[offset + 15]]).toLowerCase(); 450} 451var byteToHex; 452var init_stringify = __esm({ 453 "node_modules/uuid/dist/esm-browser/stringify.js"() { 454 init_define_process(); 455 byteToHex = []; 456 for (let i = 0; i < 256; ++i) { 457 byteToHex.push((i + 256).toString(16).slice(1)); 458 } 459 } 460}); 461
vendor: 560 bytes, lines 462-479
462// node_modules/uuid/dist/esm-browser/rng.js 463function rng() { 464 if (!getRandomValues) { 465 if (typeof crypto === "undefined" || !crypto.getRandomValues) { 466 throw new Error("crypto.getRandomValues() not supported. See https://github.com/uuidjs/uuid#getrandomvalues-not-supported"); 467 } 468 getRandomValues = crypto.getRandomValues.bind(crypto); 469 } 470 return getRandomValues(rnds8); 471} 472var getRandomValues, rnds8; 473var init_rng = __esm({ 474 "node_modules/uuid/dist/esm-browser/rng.js"() { 475 init_define_process(); 476 rnds8 = new Uint8Array(16); 477 } 478}); 479
vendor: 335 bytes, lines 480-489
480// node_modules/uuid/dist/esm-browser/native.js 481var randomUUID, native_default; 482var init_native = __esm({ 483 "node_modules/uuid/dist/esm-browser/native.js"() { 484 init_define_process(); 485 randomUUID = typeof crypto !== "undefined" && crypto.randomUUID && crypto.randomUUID.bind(crypto); 486 native_default = { randomUUID }; 487 } 488}); 489
vendor: 936 bytes, lines 490-524
490// node_modules/uuid/dist/esm-browser/v4.js 491function v4(options, buf, offset) { 492 if (native_default.randomUUID && !buf && !options) { 493 return native_default.randomUUID(); 494 } 495 options = options || {}; 496 const rnds = options.random ?? options.rng?.() ?? rng(); 497 if (rnds.length < 16) { 498 throw new Error("Random bytes length must be >= 16"); 499 } 500 rnds[6] = rnds[6] & 15 | 64; 501 rnds[8] = rnds[8] & 63 | 128; 502 if (buf) { 503 offset = offset || 0; 504 if (offset < 0 || offset + 16 > buf.length) { 505 throw new RangeError(`UUID byte range ${offset}:${offset + 15} is out of buffer bounds`); 506 } 507 for (let i = 0; i < 16; ++i) { 508 buf[offset + i] = rnds[i]; 509 } 510 return buf; 511 } 512 return unsafeStringify(rnds); 513} 514var v4_default; 515var init_v4 = __esm({ 516 "node_modules/uuid/dist/esm-browser/v4.js"() { 517 init_define_process(); 518 init_native(); 519 init_rng(); 520 init_stringify(); 521 v4_default = v4; 522 } 523}); 524
vendor: 181 bytes, lines 525-532
525// node_modules/uuid/dist/esm-browser/index.js 526var init_esm_browser = __esm({ 527 "node_modules/uuid/dist/esm-browser/index.js"() { 528 init_define_process(); 529 init_v4(); 530 } 531}); 532
vendor: 16,955 bytes, lines 533-1103
533// node_modules/@clickfunnels2/cfhoy.js/dist/cfhoy.esm.js 534function visitsUrl() { 535 return config.urlPrefix + config.visitsUrl; 536} 537function eventsUrl() { 538 return config.urlPrefix + config.eventsUrl; 539} 540function isEmpty(obj) { 541 return Object.keys(obj).length === 0; 542} 543function canTrackNow() { 544 return (config.useBeacon || config.trackNow) && isEmpty(config.headers) && canStringify && typeof window.navigator.sendBeacon !== "undefined" && !config.withCredentials; 545} 546function serialize(object) { 547 var data = new FormData(); 548 for (var key in object) { 549 if (object.hasOwnProperty(key)) { 550 data.append(key, object[key]); 551 } 552 } 553 return data; 554} 555function setCookie(name, value, ttl) { 556 Cookies.set(name, value, ttl, config.cookieDomain || config.domain); 557} 558function getCookie(name) { 559 return Cookies.get(name); 560} 561function destroyCookie(name) { 562 Cookies.set(name, "", -1); 563} 564function getFbclid() { 565 var fbclidQueryString = QueryString.get("fbclid"); 566 if (fbclidQueryString) { 567 return fbclidQueryString; 568 } else { 569 var fbcCookie = getCookie("_fbc"); 570 if (fbcCookie) { 571 var fbclid = fbcCookie.slice(19); 572 return fbclid; 573 } else { 574 return null; 575 } 576 } 577} 578function getG4ClientId() { 579 var g4Cookie = getCookie("_ga"); 580 if (g4Cookie) { 581 var g4ClientId = g4Cookie.slice(6); 582 return g4ClientId; 583 } else { 584 return null; 585 } 586} 587function log(message) { 588 if (getCookie("cfhoy_debug")) { 589 window.console.log(message); 590 } 591} 592function setReady() { 593 var callback; 594 while (callback = queue.shift()) { 595 callback(); 596 } 597 isReady = true; 598} 599function matchesSelector(element, selector) { 600 var matches = element.matches || element.matchesSelector || element.mozMatchesSelector || element.msMatchesSelector || element.oMatchesSelector || element.webkitMatchesSelector; 601 if (matches) { 602 if (matches.apply(element, [selector])) { 603 return element; 604 } else if (element.parentElement) { 605 return matchesSelector(element.parentElement, selector); 606 } 607 return null; 608 } else { 609 log("Unable to match"); 610 return null; 611 } 612} 613function onEvent(eventName, selector, callback) { 614 document.addEventListener(eventName, function(e) { 615 var matchedElement = matchesSelector(e.target, selector); 616 if (matchedElement) { 617 callback.call(matchedElement, e); 618 } 619 }); 620} 621function documentReady(callback) { 622 if (document.readyState === "interactive" || document.readyState === "complete") { 623 setTimeout(callback, 0); 624 } else { 625 document.addEventListener("DOMContentLoaded", callback); 626 } 627} 628function generateId(key) { 629 if (key === void 0) key = null; 630 if (key) { 631 if (idCache[key]) { 632 return idCache[key]; 633 } else { 634 var newId = v4_default(); 635 idCache[key] = newId; 636 return newId; 637 } 638 } 639 return v4_default(); 640} 641function saveEventQueue() { 642 if (config.cookies && canStringify) { 643 setCookie("cfhoy_events", JSON.stringify(eventQueue), 1); 644 } 645} 646function csrfToken() { 647 var meta = document.querySelector("meta[name=csrf-token]"); 648 return meta && meta.content; 649} 650function csrfParam() { 651 var meta = document.querySelector("meta[name=csrf-param]"); 652 return meta && meta.content; 653} 654function CSRFProtection(xhr) { 655 var token = csrfToken(); 656 if (token) { 657 xhr.setRequestHeader("X-CSRF-Token", token); 658 } 659} 660function sendRequest(url, data, success, error) { 661 if (canStringify) { 662 if ($2 && $2.ajax) { 663 $2.ajax({ 664 type: "POST", 665 url, 666 data: JSON.stringify(data), 667 contentType: "application/json; charset=utf-8", 668 dataType: "json", 669 beforeSend: CSRFProtection, 670 success, 671 error, 672 headers: config.headers, 673 xhrFields: { 674 withCredentials: config.withCredentials 675 } 676 }); 677 } else { 678 var xhr = new XMLHttpRequest(); 679 xhr.open("POST", url, true); 680 xhr.withCredentials = config.withCredentials; 681 xhr.setRequestHeader("Content-Type", "application/json"); 682 for (var header in config.headers) { 683 if (config.headers.hasOwnProperty(header)) { 684 xhr.setRequestHeader(header, config.headers[header]); 685 } 686 } 687 xhr.onload = function() { 688 if (xhr.status >= 200 && xhr.status < 400) { 689 success(null, null, xhr); 690 } else if (error) { 691 error(null, null, xhr); 692 } 693 }; 694 xhr.onerror = function() { 695 if (error) { 696 error(null, null, xhr); 697 } 698 }; 699 CSRFProtection(xhr); 700 xhr.send(JSON.stringify(data)); 701 } 702 } 703} 704function eventData(event) { 705 var data = { 706 events: [event] 707 }; 708 if (config.cookies) { 709 data.visit_token = event.visit_token; 710 data.visitor_token = event.visitor_token; 711 } 712 delete event.visit_token; 713 delete event.visitor_token; 714 return data; 715} 716function trackEvent(event) { 717 ahoy.ready(function() { 718 sendRequest(eventsUrl(), eventData(event), function() { 719 for (var i = 0; i < eventQueue.length; i++) { 720 if (eventQueue[i].id == event.id) { 721 eventQueue.splice(i, 1); 722 break; 723 } 724 } 725 saveEventQueue(); 726 }); 727 }); 728} 729function trackEventNow(event) { 730 ahoy.ready(function() { 731 var data = eventData(event); 732 var param = csrfParam(); 733 var token = csrfToken(); 734 if (param && token) { 735 data[param] = token; 736 } 737 data.events_json = JSON.stringify(data.events); 738 delete data.events; 739 window.navigator.sendBeacon(eventsUrl(), serialize(data)); 740 }); 741} 742function page() { 743 return config.page || window.location.pathname; 744} 745function presence(str) { 746 return str && str.length > 0 ? str : null; 747} 748function cleanObject(obj) { 749 for (var key in obj) { 750 if (obj.hasOwnProperty(key)) { 751 if (obj[key] === null) { 752 delete obj[key]; 753 } 754 } 755 } 756 return obj; 757} 758function eventProperties() { 759 return cleanObject({ 760 tag: this.tagName.toLowerCase(), 761 id: presence(this.id), 762 "class": presence(this.className), 763 page: page(), 764 section: getClosestSection(this) 765 }); 766} 767function getClosestSection(element) { 768 for (; element && element !== document; element = element.parentNode) { 769 if (element.hasAttribute("data-section")) { 770 return element.getAttribute("data-section"); 771 } 772 } 773 return null; 774} 775function createVisit() { 776 if (visitTrackedThisRequest) { 777 return; 778 } 779 isReady = false; 780 if (config.adoptVisit && config.adoptVisit.visitId && config.adoptVisit.visitorId) { 781 if (getCookie("cfhoy_visit") !== config.adoptVisit.visitId) { 782 setCookie("cfhoy_visit", config.adoptVisit.visitId, config.visitDuration); 783 } 784 if (getCookie("cfhoy_visitor") !== config.adoptVisit.visitorId) { 785 setCookie("cfhoy_visitor", config.adoptVisit.visitorId, config.visitorDuration); 786 } 787 if (getCookie("cfhoy_successful_visit_track") !== config.adoptVisit.visitId) { 788 setCookie("cfhoy_successful_visit_track", config.adoptVisit.visitId, config.visitDuration); 789 } 790 } 791 visitId = ahoy.getVisitId(); 792 visitorId = ahoy.getVisitorId(); 793 track = getCookie("cfhoy_track"); 794 var successful_visit_track = getCookie("cfhoy_successful_visit_track") === visitId; 795 if (config.cookies === false || config.trackVisits === false) { 796 log("Visit tracking disabled"); 797 setReady(); 798 } else if (visitId && visitorId && successful_visit_track && !track) { 799 log("Active visit"); 800 setReady(); 801 } else { 802 if (!visitId) { 803 visitId = generateId(); 804 setCookie("cfhoy_visit", visitId, config.visitDuration); 805 } 806 if (getCookie("cfhoy_visit")) { 807 log("Visit started"); 808 if (!visitorId) { 809 visitorId = generateId(); 810 setCookie("cfhoy_visitor", visitorId, config.visitorDuration); 811 } 812 var fbclid = getFbclid(); 813 var fbc = getCookie("_fbc"); 814 var fbp = getCookie("_fbp"); 815 var g4_client_id = getG4ClientId(); 816 var data = { 817 visit_token: visitId, 818 visitor_token: visitorId, 819 time: (/* @__PURE__ */ new Date()).getTime() / 1e3, 820 platform: config.platform, 821 landing_page: window.location.href, 822 screen_width: window.screen.width, 823 screen_height: window.screen.height, 824 fbclid, 825 fbc, 826 fbp, 827 js: true, 828 g4_client_id, 829 track_events: config.trackPageViewWithVisit ? [visitPageViewEvent()] : [] 830 }; 831 if (document.referrer.length > 0) { 832 data.referrer = document.referrer; 833 } 834 for (var key in config.visitParams) { 835 if (config.visitParams.hasOwnProperty(key)) { 836 data[key] = config.visitParams[key]; 837 } 838 } 839 log(data); 840 visitTrackedThisRequest = true; 841 sendRequest( 842 visitsUrl(), 843 data, 844 function(_data, _textStatus, jqXHR) { 845 if (config.extendedInstrumentation) { 846 var visitResponseCode = jqXHR.status; 847 var headers = config.extendedIntrumentationResponseHeaders.map(function(header) { 848 return header + "_" + jqXHR.getResponseHeader(header); 849 }).join("__"); 850 setCookie("cfhoy_extended_instrumentation", visitResponseCode + "__" + headers, config.visitDuration); 851 } 852 setCookie("cfhoy_successful_visit_track", visitId, config.visitDuration); 853 destroyCookie("cfhoy_track"); 854 setReady(); 855 }, 856 function() { 857 visitTrackedThisRequest = false; 858 setReady(); 859 } 860 ); 861 } else { 862 log("Cookies disabled"); 863 setReady(); 864 } 865 } 866} 867function visitPageViewEvent() { 868 var additionalProperties = config.trackPageViewWithVisitAdditionalProps() || {}; 869 return trackEventData("$view", trackPageViewData(additionalProperties)); 870} 871function trackEventData(name, properties) { 872 var event = { 873 name, 874 properties: properties || {}, 875 time: (/* @__PURE__ */ new Date()).getTime() / 1e3, 876 id: generateId(name === "$view" ? "pageview" : null), 877 source: window.location.href, 878 js: true 879 }; 880 return event; 881} 882function trackPageViewData(additionalProperties) { 883 var properties = { 884 url: window.location.href, 885 title: document.title, 886 page: page(), 887 platform: config.platform 888 }; 889 if (additionalProperties) { 890 for (var propName in additionalProperties) { 891 if (additionalProperties.hasOwnProperty(propName)) { 892 properties[propName] = additionalProperties[propName]; 893 } 894 } 895 } 896 return properties; 897} 898var Cookies, QueryString, config, ahoy, $2, visitId, visitorId, track, isReady, queue, canStringify, eventQueue, visitTrackedThisRequest, idCache, i, originalStart; 899var init_cfhoy_esm = __esm({ 900 "node_modules/@clickfunnels2/cfhoy.js/dist/cfhoy.esm.js"() { 901 init_define_process(); 902 init_esm_browser(); 903 Cookies = { 904 set: function(name, value, ttl, domain) { 905 var expires = ""; 906 var cookieDomain = ""; 907 if (ttl) { 908 var date = /* @__PURE__ */ new Date(); 909 date.setTime(date.getTime() + ttl * 60 * 1e3); 910 expires = "; expires=" + date.toGMTString(); 911 } 912 if (domain) { 913 cookieDomain = "; domain=" + domain; 914 } 915 document.cookie = name + "=" + escape(value) + expires + cookieDomain + "; path=/; samesite=lax"; 916 }, 917 get: function(name) { 918 var i, c; 919 var nameEQ = name + "="; 920 var ca = document.cookie.split(";"); 921 for (i = 0; i < ca.length; i++) { 922 c = ca[i]; 923 while (c.charAt(0) === " ") { 924 c = c.substring(1, c.length); 925 } 926 if (c.indexOf(nameEQ) === 0) { 927 return unescape(c.substring(nameEQ.length, c.length)); 928 } 929 } 930 return null; 931 } 932 }; 933 QueryString = { 934 get: function(name) { 935 var query = window.location.search.substring(1); 936 var vars = query.split("&"); 937 for (var i = 0; i < vars.length; i++) { 938 var pair = vars[i].split("="); 939 if (decodeURIComponent(pair[0]) == name) { 940 return decodeURIComponent(pair[1]); 941 } 942 } 943 return null; 944 } 945 }; 946 config = { 947 urlPrefix: "", 948 visitsUrl: "/ahoy/visits", 949 eventsUrl: "/ahoy/events", 950 page: null, 951 platform: "Web", 952 useBeacon: true, 953 startOnReady: true, 954 trackVisits: true, 955 cookies: true, 956 cookieDomain: null, 957 trackPageViewWithVisit: false, 958 headers: {}, 959 visitParams: {}, 960 withCredentials: false, 961 visitDuration: 4 * 60, 962 // default 4 hours 963 visitorDuration: 2 * 365 * 24 * 60, 964 // default 2 years, 965 trackPageViewWithVisitAdditionalProps: function() { 966 }, 967 extendedInstrumentation: false, 968 extendedIntrumentationResponseHeaders: ["X-Clickfunnels-Version"] 969 }; 970 ahoy = window.ahoy || window.Ahoy || {}; 971 ahoy.configure = function(options) { 972 for (var key in options) { 973 if (options.hasOwnProperty(key)) { 974 config[key] = options[key]; 975 } 976 } 977 }; 978 ahoy.configure(ahoy); 979 $2 = window.jQuery || window.Zepto || window.$; 980 isReady = false; 981 queue = []; 982 canStringify = typeof JSON !== "undefined" && typeof JSON.stringify !== "undefined"; 983 eventQueue = []; 984 visitTrackedThisRequest = false; 985 idCache = {}; 986 ahoy.ready = function(callback) { 987 if (isReady) { 988 callback(); 989 } else { 990 queue.push(callback); 991 } 992 }; 993 ahoy.getVisitId = ahoy.getVisitToken = function() { 994 return getCookie("cfhoy_visit"); 995 }; 996 ahoy.getVisitorId = ahoy.getVisitorToken = function() { 997 return getCookie("cfhoy_visitor"); 998 }; 999 ahoy.reset = function() { 1000 destroyCookie("cfhoy_visit"); 1001 destroyCookie("cfhoy_visitor"); 1002 destroyCookie("cfhoy_events"); 1003 destroyCookie("cfhoy_track"); 1004 destroyCookie("cfhoy_successful_visit_track"); 1005 visitTrackedThisRequest = false; 1006 ahoy.start = originalStart; 1007 return true; 1008 }; 1009 ahoy.debug = function(enabled) { 1010 if (enabled === false) { 1011 destroyCookie("cfhoy_debug"); 1012 } else { 1013 setCookie("cfhoy_debug", "t", 365 * 24 * 60); 1014 } 1015 return true; 1016 }; 1017 ahoy.track = function(name, properties, options) { 1018 var event = trackEventData(name, properties); 1019 var force = options && options.force; 1020 ahoy.ready(function() { 1021 if (name === "$view" && config.cookies && !getCookie("cfhoy_successful_visit_track")) { 1022 createVisit(); 1023 return; 1024 } 1025 if (config.cookies && !ahoy.getVisitId()) { 1026 createVisit(); 1027 } 1028 ahoy.ready(function() { 1029 log(event); 1030 event.visit_token = ahoy.getVisitId(); 1031 event.visitor_token = ahoy.getVisitorId(); 1032 var documentEvent = new CustomEvent("cfhoy:tracked", { detail: event }); 1033 document.dispatchEvent(documentEvent); 1034 if (name === "$view" && config.trackPageViewWithVisit && visitTrackedThisRequest && !force) { 1035 return; 1036 } 1037 if (canTrackNow()) { 1038 trackEventNow(event); 1039 } else { 1040 eventQueue.push(event); 1041 saveEventQueue(); 1042 setTimeout(function() { 1043 trackEvent(event); 1044 }, 1e3); 1045 } 1046 }); 1047 }); 1048 return true; 1049 }; 1050 ahoy.trackView = function(additionalProperties, options) { 1051 ahoy.track("$view", trackPageViewData(additionalProperties), options); 1052 }; 1053 ahoy.trackClicks = function(selector) { 1054 if (selector === void 0) { 1055 throw new Error("Missing selector"); 1056 } 1057 onEvent("click", selector, function(e) { 1058 var properties = eventProperties.call(this, e); 1059 properties.text = properties.tag == "input" ? this.value : (this.textContent || this.innerText || this.innerHTML).replace(/[\s\r\n]+/g, " ").trim(); 1060 properties.href = this.href; 1061 ahoy.track("$click", properties); 1062 }); 1063 }; 1064 ahoy.trackSubmits = function(selector) { 1065 if (selector === void 0) { 1066 throw new Error("Missing selector"); 1067 } 1068 onEvent("submit", selector, function(e) { 1069 var properties = eventProperties.call(this, e); 1070 ahoy.track("$submit", properties); 1071 }); 1072 }; 1073 ahoy.trackChanges = function(selector) { 1074 log("trackChanges is deprecated and will be removed in 0.5.0"); 1075 if (selector === void 0) { 1076 throw new Error("Missing selector"); 1077 } 1078 onEvent("change", selector, function(e) { 1079 var properties = eventProperties.call(this, e); 1080 ahoy.track("$change", properties); 1081 }); 1082 }; 1083 try { 1084 eventQueue = JSON.parse(getCookie("cfhoy_events") || "[]"); 1085 } catch (e) { 1086 } 1087 for (i = 0; i < eventQueue.length; i++) { 1088 trackEvent(eventQueue[i]); 1089 } 1090 ahoy.start = function() { 1091 createVisit(); 1092 ahoy.start = function() { 1093 }; 1094 }; 1095 originalStart = ahoy.start; 1096 documentReady(function() { 1097 if (config.startOnReady) { 1098 ahoy.start(); 1099 } 1100 }); 1101 } 1102}); 1103
1104// projects/user_pages/app/javascript/lander/track_events.js 1105var track_events_exports = {}; 1106function cfhoyVisitorData() { 1107 return { 1108 firstName: Cookies.get("contact_first_name"), 1109 lastName: Cookies.get("contact_last_name"), 1110 emailAddress: Cookies.get("contact_email_address"), 1111 phoneNumber: Cookies.get("contact_phone_number"), 1112 postalCode: Cookies.get("contact_postal_code"), 1113 country: Cookies.get("contact_country"), 1114 uuid: Cookies.get("cfhoy_visitor") 1115 }; 1116} 1117function getLeadEventID() { 1118 return Cookies.get("cfhoy_lead_event_id"); 1119} 1120function removeLeadEventID() { 1121 Cookies.set("cfhoy_lead_event_id", "", -1); 1122 return true; 1123} 1124function getPurchaseEventID() { 1125 return Cookies.get("cfhoy_purchase_event_id"); 1126} 1127function removePurchaseEventID() { 1128 Cookies.set("cfhoy_purchase_event_id", "", -1); 1129 return true; 1130} 1131function getRenderedPage() { 1132 return document.querySelector('meta[name="rendered-page-url"]')?.getAttribute("content"); 1133} 1134function getCfTokenFromUrl() { 1135 return new URLSearchParams(window.location.search).get(CF_TOKEN_PARAM); 1136} 1137function stripCfTokenFromUrl() { 1138 const url = new URL(window.location.href); 1139 if (!url.searchParams.has(CF_TOKEN_PARAM)) return; 1140 url.searchParams.delete(CF_TOKEN_PARAM); 1141 window.history.replaceState({}, "", url.toString()); 1142} 1143function pageUrlWithoutQuery() { 1144 const url = new URL(window.location.href); 1145 url.search = ""; 1146 url.hash = ""; 1147 return url.toString(); 1148} 1149function workspaceResolveTokenUrl() { 1150 return "/_cf/resolve_token"; 1151} 1152async function resolveCfTokenIfPresent() { 1153 const token = getCfTokenFromUrl(); 1154 if (!token) return; 1155 try { 1156 const response = await fetch(workspaceResolveTokenUrl(), { 1157 method: "POST", 1158 headers: { "Content-Type": "application/json", Accept: "application/json" }, 1159 body: JSON.stringify({ cf_token: token, url: pageUrlWithoutQuery() }) 1160 }); 1161 stripCfTokenFromUrl(); 1162 if (!response.ok) return; 1163 const payload = await response.json(); 1164 if (!payload.contact_uuid || !payload.visit_uuid) return; 1165 ahoy.configure({ 1166 adoptVisit: { visitId: payload.visit_uuid, visitorId: payload.contact_uuid } 1167 }); 1168 } catch { 1169 stripCfTokenFromUrl(); 1170 } 1171} 1172function isLivePage(queryString) { 1173 const urlParams = new URLSearchParams(queryString); 1174 return urlParams.get("preview") !== "true"; 1175} 1176var livePage, trackingDisabled, renderedPage, CF_TOKEN_PARAM; 1177var init_track_events = __esm({ 1178 "projects/user_pages/app/javascript/lander/track_events.js"() { 1179 init_define_process(); 1180 init_cfhoy_esm(); 1181 init_cfhoy_esm(); 1182 livePage = isLivePage(window.location.search); 1183 trackingDisabled = window.disableTracking; 1184 renderedPage = getRenderedPage(); 1185 ahoy.configure({ 1186 urlPrefix: "/_cf", 1187 visitsUrl: "/s", 1188 eventsUrl: "/a", 1189 platform: "Web", 1190 useBeacon: true, 1191 startOnReady: false, 1192 trackVisits: true, 1193 cookies: true, 1194 withCredentials: false, 1195 visitDuration: 4 * 60, 1196 // 4 hours 1197 visitorDuration: 2 * 365 * 24 * 60, 1198 // 2 years 1199 page: renderedPage, 1200 trackPageViewWithVisit: true, 1201 trackPageViewWithVisitAdditionalProps: () => ({ 1202 cfhoy_visitor: Cookies.get("cfhoy_visitor") || "", 1203 request_type: "visit" 1204 }), 1205 extendedInstrumentation: true 1206 }); 1207 CF_TOKEN_PARAM = "__cf_token"; 1208 if (!trackingDisabled && livePage) { 1209 const startCfHoy = () => { 1210 if (window._cfHoyStarted) return; 1211 window._cfHoyStarted = true; 1212 ahoy.start(); 1213 }; 1214 const resolveAndStart = () => resolveCfTokenIfPresent().finally(startCfHoy); 1215 if (document.readyState === "complete") { 1216 resolveAndStart(); 1217 } else { 1218 window.addEventListener("load", resolveAndStart); 1219 } 1220 document.addEventListener("cfhoy:tracked", function(event) { 1221 window.dataLayer = window.dataLayer || []; 1222 if (event.detail.name == "$view") { 1223 const visitorData = cfhoyVisitorData(); 1224 dataLayer.push({ 1225 event: "cfPageView", 1226 contactFirstName: visitorData.firstName, 1227 contactLastName: visitorData.lastName, 1228 contactEmailAddress: visitorData.emailAddress, 1229 contactPhoneNumber: visitorData.phoneNumber, 1230 contactPostalCode: visitorData.postalCode, 1231 contactCountry: visitorData.country, 1232 contactExternalID: visitorData.uuid, 1233 visitEventID: event.detail.id 1234 }); 1235 } 1236 }); 1237 document.addEventListener("DOMContentLoaded", function(event) { 1238 const additionalProps = { 1239 cfhoy_visitor: Cookies.get("cfhoy_visitor") || "", 1240 request_type: "trackView" 1241 }; 1242 ahoy.trackView(additionalProps); 1243 $(document).on("click", '[event-tracking="enable"]', function() { 1244 const data = { 1245 url: window.location.href, 1246 page: renderedPage || window.location.pathname, 1247 title: document.title 1248 }; 1249 ahoy.track("$button_click", data); 1250 }); 1251 }); 1252 } 1253 document.addEventListener("DOMContentLoaded", function(event) { 1254 window.dataLayer = window.dataLayer || []; 1255 const visitorData = cfhoyVisitorData(); 1256 const leadEventID = getLeadEventID(); 1257 const purchaseEventID = getPurchaseEventID(); 1258 if (leadEventID) { 1259 dataLayer.push({ 1260 event: "cfLead", 1261 contactFirstName: visitorData.firstName, 1262 contactLastName: visitorData.lastName, 1263 contactEmailAddress: visitorData.emailAddress, 1264 contactPhoneNumber: visitorData.phoneNumber, 1265 contactPostalCode: visitorData.postalCode, 1266 contactCountry: visitorData.country, 1267 contactExternalID: visitorData.uuid, 1268 leadEventID 1269 }); 1270 removeLeadEventID(); 1271 } 1272 if (purchaseEventID) { 1273 dataLayer.push({ 1274 event: "cfPurchase", 1275 contactFirstName: visitorData.firstName, 1276 contactLastName: visitorData.lastName, 1277 contactEmailAddress: visitorData.emailAddress, 1278 contactPhoneNumber: visitorData.phoneNumber, 1279 contactPostalCode: visitorData.postalCode, 1280 contactCountry: visitorData.country, 1281 contactExternalID: visitorData.uuid, 1282 purchaseEventID 1283 }); 1284 removePurchaseEventID(); 1285 } 1286 }); 1287 } 1288}); 1289
1290// projects/user_pages/app/javascript/lander/resource_sharing_concern.js 1291var resource_sharing_concern_exports = {}; 1292var init_resource_sharing_concern = __esm({ 1293 "projects/user_pages/app/javascript/lander/resource_sharing_concern.js"() { 1294 init_define_process(); 1295 init_cfhoy_esm(); 1296 document.addEventListener("DOMContentLoaded", function() { 1297 const queryString = window.location.search; 1298 const urlParams = new URLSearchParams(queryString); 1299 const ttl = 30 * 24 * 60; 1300 const workspace_sharing_id = urlParams.get("workspace_sharing_id"); 1301 if (workspace_sharing_id) { 1302 Cookies.set("workspace_sharing_id", workspace_sharing_id, ttl); 1303 } 1304 const resource_install_intent_ttl = 24 * 60 * 60; 1305 const resource_install_intent = urlParams.get("resource_install_intent"); 1306 if (resource_install_intent) { 1307 Cookies.set("resource_install_intent", resource_install_intent, resource_install_intent_ttl); 1308 } 1309 const awid_ttl = 60 * 60; 1310 const awid = urlParams.get("awid"); 1311 if (awid) { 1312 Cookies.set("awid", awid, awid_ttl); 1313 } 1314 }); 1315 } 1316}); 1317
1318// projects/user_pages/app/javascript/lander/contact_fields.ts 1319function contactCarrierInputId(name) { 1320 return `cf_contact_${CONTACT_CARRIER_ID_SUFFIXES.get(name) ?? name}`; 1321} 1322var CONTACT_CARRIER_ID_SUFFIXES; 1323var init_contact_fields = __esm({ 1324 "projects/user_pages/app/javascript/lander/contact_fields.ts"() { 1325 init_define_process(); 1326 CONTACT_CARRIER_ID_SUFFIXES = /* @__PURE__ */ new Map([["phone_number", "phone"]]); 1327 } 1328}); 1329
1330// projects/user_pages/app/javascript/lander/vendor/mailCheck/domains.ts 1331var defaultDomains, defaultSecondLevelDomains, defaultTopLevelDomains; 1332var init_domains = __esm({ 1333 "projects/user_pages/app/javascript/lander/vendor/mailCheck/domains.ts"() { 1334 init_define_process(); 1335 defaultDomains = [ 1336 "msn.com", 1337 "bellsouth.net", 1338 "telus.net", 1339 "comcast.net", 1340 "optusnet.com.au", 1341 "earthlink.net", 1342 "qq.com", 1343 "sky.com", 1344 "icloud.com", 1345 "mac.com", 1346 "sympatico.ca", 1347 "googlemail.com", 1348 "att.net", 1349 "xtra.co.nz", 1350 "web.de", 1351 "cox.net", 1352 "gmail.com", 1353 "ymail.com", 1354 "aim.com", 1355 "rogers.com", 1356 "verizon.net", 1357 "rocketmail.com", 1358 "google.com", 1359 "optonline.net", 1360 "sbcglobal.net", 1361 "aol.com", 1362 "me.com", 1363 "btinternet.com", 1364 "charter.net", 1365 "shaw.ca" 1366 ]; 1367 defaultSecondLevelDomains = ["yahoo", "hotmail", "mail", "live", "outlook", "gmx"]; 1368 defaultTopLevelDomains = [ 1369 "com", 1370 "com.au", 1371 "com.tw", 1372 "ca", 1373 "co.nz", 1374 "co.uk", 1375 "de", 1376 "fr", 1377 "it", 1378 "ru", 1379 "net", 1380 "org", 1381 "edu", 1382 "gov", 1383 "jp", 1384 "nl", 1385 "kr", 1386 "se", 1387 "eu", 1388 "ie", 1389 "co.il", 1390 "us", 1391 "at", 1392 "be", 1393 "dk", 1394 "hk", 1395 "es", 1396 "gr", 1397 "ch", 1398 "no", 1399 "cz", 1400 "in", 1401 "net", 1402 "net.au", 1403 "info", 1404 "biz", 1405 "mil", 1406 "co.jp", 1407 "sg", 1408 "hu", 1409 "uk", 1410 "io" 1411 ]; 1412 } 1413}); 1414
1415// projects/user_pages/app/javascript/lander/vendor/mailCheck/main.ts 1416var define, Mailcheck; 1417var init_main = __esm({ 1418 "projects/user_pages/app/javascript/lander/vendor/mailCheck/main.ts"() { 1419 init_define_process(); 1420 init_domains(); 1421 Mailcheck = { 1422 domainThreshold: 2, 1423 secondLevelThreshold: 2, 1424 topLevelThreshold: 2, 1425 run: function(opts) { 1426 opts.domains = opts.domains || defaultDomains; 1427 opts.secondLevelDomains = opts.secondLevelDomains || defaultSecondLevelDomains; 1428 opts.topLevelDomains = opts.topLevelDomains || defaultTopLevelDomains; 1429 opts.distanceFunction = opts.distanceFunction || Mailcheck.sift4Distance; 1430 const defaultCallback = function(result2) { 1431 return result2; 1432 }; 1433 const suggestedCallback = opts.suggested || defaultCallback; 1434 const emptyCallback = opts.empty || defaultCallback; 1435 const result = Mailcheck.suggest( 1436 Mailcheck.encodeEmail(opts.email), 1437 opts.domains, 1438 opts.secondLevelDomains, 1439 opts.topLevelDomains, 1440 opts.distanceFunction 1441 ); 1442 return result ? suggestedCallback(result) : emptyCallback(); 1443 }, 1444 suggest: function(email, domains, secondLevelDomains, topLevelDomains, distanceFunction) { 1445 email = email.toLowerCase(); 1446 const emailParts = this.splitEmail(email); 1447 if (secondLevelDomains && topLevelDomains) { 1448 if (secondLevelDomains.indexOf(emailParts.secondLevelDomain) !== -1 && topLevelDomains.indexOf(emailParts.topLevelDomain) !== -1) { 1449 return false; 1450 } 1451 } 1452 let closestDomain = this.findClosestDomain(emailParts.domain, domains, distanceFunction, this.domainThreshold); 1453 if (closestDomain) { 1454 if (closestDomain == emailParts.domain) { 1455 return false; 1456 } else { 1457 return { address: emailParts.address, domain: closestDomain, full: emailParts.address + "@" + closestDomain }; 1458 } 1459 } 1460 const closestSecondLevelDomain = this.findClosestDomain( 1461 emailParts.secondLevelDomain, 1462 secondLevelDomains, 1463 distanceFunction, 1464 this.secondLevelThreshold 1465 ); 1466 const closestTopLevelDomain = this.findClosestDomain( 1467 emailParts.topLevelDomain, 1468 topLevelDomains, 1469 distanceFunction, 1470 this.topLevelThreshold 1471 ); 1472 if (emailParts.domain) { 1473 closestDomain = emailParts.domain; 1474 let rtrn = false; 1475 if (closestSecondLevelDomain && closestSecondLevelDomain != emailParts.secondLevelDomain) { 1476 closestDomain = closestDomain.replace(emailParts.secondLevelDomain, closestSecondLevelDomain); 1477 rtrn = true; 1478 } 1479 if (closestTopLevelDomain && closestTopLevelDomain != emailParts.topLevelDomain && emailParts.secondLevelDomain !== "") { 1480 closestDomain = closestDomain.replace(new RegExp(emailParts.topLevelDomain + "$"), closestTopLevelDomain); 1481 rtrn = true; 1482 } 1483 if (rtrn) { 1484 return { address: emailParts.address, domain: closestDomain, full: emailParts.address + "@" + closestDomain }; 1485 } 1486 } 1487 return false; 1488 }, 1489 findClosestDomain: function(domain, domains, distanceFunction, threshold) { 1490 threshold = threshold || this.topLevelThreshold; 1491 let dist; 1492 let minDist = Infinity; 1493 let closestDomain = null; 1494 if (!domain || !domains) { 1495 return false; 1496 } 1497 if (!distanceFunction) { 1498 distanceFunction = this.sift4Distance; 1499 } 1500 for (let i = 0; i < domains.length; i++) { 1501 if (domain === domains[i]) { 1502 return domain; 1503 } 1504 dist = distanceFunction(domain, domains[i]); 1505 if (dist < minDist) { 1506 minDist = dist; 1507 closestDomain = domains[i]; 1508 } 1509 } 1510 if (minDist <= threshold && closestDomain !== null) { 1511 return closestDomain; 1512 } else { 1513 return false; 1514 } 1515 }, 1516 sift4Distance: function(s1, s2, maxOffset) { 1517 if (maxOffset === void 0) { 1518 maxOffset = 5; 1519 } 1520 if (!s1 || !s1.length) { 1521 if (!s2) { 1522 return 0; 1523 } 1524 return s2.length; 1525 } 1526 if (!s2 || !s2.length) { 1527 return s1.length; 1528 } 1529 const l1 = s1.length; 1530 const l2 = s2.length; 1531 let c1 = 0; 1532 let c2 = 0; 1533 let lcss = 0; 1534 let local_cs = 0; 1535 let trans = 0; 1536 const offset_arr = []; 1537 while (c1 < l1 && c2 < l2) { 1538 if (s1.charAt(c1) == s2.charAt(c2)) { 1539 local_cs++; 1540 let isTrans = false;
1541 let i = 0; 1542 while (i < offset_arr.length) { 1543 const ofs = offset_arr[i]; 1544 if (c1 <= ofs.c1 || c2 <= ofs.c2) { 1545 isTrans = Math.abs(c2 - c1) >= Math.abs(ofs.c2 - ofs.c1); 1546 if (isTrans) { 1547 trans++; 1548 } else { 1549 if (!ofs.trans) { 1550 ofs.trans = true; 1551 trans++; 1552 } 1553 } 1554 break; 1555 } else { 1556 if (c1 > ofs.c2 && c2 > ofs.c1) { 1557 offset_arr.splice(i, 1); 1558 } else { 1559 i++; 1560 } 1561 } 1562 } 1563 offset_arr.push({ 1564 c1, 1565 c2, 1566 trans: isTrans 1567 }); 1568 } else { 1569 lcss += local_cs; 1570 local_cs = 0; 1571 if (c1 != c2) { 1572 c1 = c2 = Math.min(c1, c2); 1573 } 1574 for (let j = 0; j < maxOffset && (c1 + j < l1 || c2 + j < l2); j++) { 1575 if (c1 + j < l1 && s1.charAt(c1 + j) == s2.charAt(c2)) { 1576 c1 += j - 1; 1577 c2--; 1578 break; 1579 } 1580 if (c2 + j < l2 && s1.charAt(c1) == s2.charAt(c2 + j)) { 1581 c1--; 1582 c2 += j - 1; 1583 break; 1584 } 1585 } 1586 } 1587 c1++; 1588 c2++; 1589 if (c1 >= l1 || c2 >= l2) { 1590 lcss += local_cs; 1591 local_cs = 0; 1592 c1 = c2 = Math.min(c1, c2); 1593 } 1594 } 1595 lcss += local_cs; 1596 return Math.round(Math.max(l1, l2) - lcss + trans); 1597 }, 1598 splitEmail: function(email) { 1599 email = email !== null ? email.replace(/^\s*/, "").replace(/\s*$/, "") : null; 1600 const parts = email.split("@"); 1601 if (parts.length < 2) { 1602 return false; 1603 } 1604 for (let i = 0; i < parts.length; i++) { 1605 if (parts[i] === "") { 1606 return false; 1607 } 1608 } 1609 const domain = parts.pop(); 1610 const domainParts = domain.split("."); 1611 let sld = ""; 1612 let tld = ""; 1613 if (domainParts.length === 0) { 1614 return false; 1615 } else if (domainParts.length == 1) { 1616 tld = domainParts[0]; 1617 } else { 1618 sld = domainParts[0]; 1619 for (let j = 1; j < domainParts.length; j++) { 1620 tld += domainParts[j] + "."; 1621 } 1622 tld = tld.substring(0, tld.length - 1); 1623 } 1624 return { 1625 topLevelDomain: tld, 1626 secondLevelDomain: sld, 1627 domain, 1628 address: parts.join("@") 1629 }; 1630 }, 1631 // Encode the email address to prevent XSS but leave in valid 1632 // characters, following this official spec: 1633 // http://en.wikipedia.org/wiki/Email_address#Syntax 1634 encodeEmail: function(email) { 1635 let result = encodeURI(email); 1636 result = result.replace("%20", " ").replace("%25", "%").replace("%5E", "^").replace("%60", "`").replace("%7B", "{").replace("%7C", "|").replace("%7D", "}"); 1637 return result; 1638 } 1639 }; 1640 if (typeof define === "function" && define.amd) { 1641 define("mailcheck", [], function() { 1642 return Mailcheck; 1643 }); 1644 } 1645 if (typeof window !== "undefined" && window.jQuery) { 1646 ; 1647 (function($4) { 1648 $4.fn.mailcheck = function(opts) { 1649 const self = this; 1650 if (opts.suggested) { 1651 const oldSuggested = opts.suggested; 1652 opts.suggested = function(result) { 1653 oldSuggested(self, result); 1654 }; 1655 } 1656 if (opts.empty) { 1657 const oldEmpty = opts.empty; 1658 opts.empty = function() { 1659 oldEmpty.call(null, self); 1660 }; 1661 } 1662 opts.email = this.val(); 1663 Mailcheck.run(opts); 1664 }; 1665 })(jQuery); 1666 } 1667 } 1668}); 1669
1670// projects/user_pages/app/javascript/lander/submit.ts 1671var submit_exports = {}; 1672__export(submit_exports, { 1673 checkValidInputs: () => checkValidInputs, 1674 restoreButtonState: () => restoreButtonState, 1675 submitPage: () => submitPage 1676}); 1677function restoreButtonState() { 1678 $3('.elBTN a[href="#submit-form"]').each(function() { 1679 const $this = $3(this); 1680 const $text = $this.find(".elButtonMainText"); 1681 const $subText = $this.find(".elButtonSub"); 1682 const previousText = $this.attr("data-before-submit-text"); 1683 const previousSub = $this.attr("data-before-submit-sub"); 1684 const loadingSpinner = $text.parent().find(".elButtonSpinner"); 1685 loadingSpinner.css("display", "none"); 1686 if (previousText) { 1687 $this.removeClass("cf-submitting-page"); 1688 $text.text(previousText); 1689 $subText.text(previousSub); 1690 $this.removeAttr("data-before-submit-text"); 1691 $this.removeAttr("data-before-submit-sub"); 1692 } 1693 }); 1694} 1695function setButtonSubmitText(text, subtext) { 1696 $3('.elBTN a[href="#submit-form"]').each(function() { 1697 const $this = $3(this); 1698 const $text = $this.find(".elButtonMainText"); 1699 const $subText = $this.find(".elButtonSub"); 1700 const submitText = text ?? ($this.attr("data-param-submittingtext")?.length ? $this.attr("data-param-submittingtext") : "Submitting..."); 1701 const dataBeforeSubmit = $this.attr("data-before-submit-text"); 1702 if (!dataBeforeSubmit) { 1703 $this.attr("data-before-submit-text", $text.text()); 1704 $this.attr("data-before-submit-sub", $subText.text()); 1705 $this.addClass("cf-submitting-page"); 1706 } 1707 const loadingSpinner = $this.find(".elButtonSpinner"); 1708 $text.text(`${submitText}`); 1709 $subText.text(subtext ?? ""); 1710 loadingSpinner.css("display", "inline-block"); 1711 }); 1712} 1713async function sleepMs(timeMs) { 1714 return new Promise((resolve) => { 1715 setTimeout(resolve, timeMs); 1716 }); 1717} 1718function getRenderedHref() { 1719 const renderedPage2 = document.querySelector('meta[name="rendered-page-url"]')?.getAttribute("content"); 1720 const renderedPath = renderedPage2 ?? window.location.pathname; 1721 const url = new URL(window.location.href); 1722 url.pathname = renderedPath; 1723 return url.toString(); 1724} 1725function submitRedirectTarget(response) { 1726 const location = response.headers.get("Location"); 1727 if (location && location !== "null" && location !== "undefined") return location; 1728 if (response.redirected && response.url) return response.url; 1729 return null; 1730} 1731async function submitOrderAsync(body, maxRetries = 3, onBeforeSubmit, onRetryAfter) { 1732 let response; 1733 for (let i = 0; i < maxRetries; i++) { 1734 try { 1735 onBeforeSubmit(); 1736 const nonce = await fetchCheckoutNonce(); 1737 const nonceQuery = new URLSearchParams(checkoutNonceParams(nonce)).toString(); 1738 response = await fetch(getRenderedHref(), { 1739 credentials: "same-origin", 1740 method: "post", 1741 body: [body, nonceQuery].filter(Boolean).join("&"), 1742 headers: { 1743 "Content-Type": "application/x-www-form-urlencoded", 1744 "X-CF2-POST-TYPE": "submit" 1745 } 1746 }); 1747 if (response.status === 429) { 1748 const sleepTime = parseInt(response.headers.get("Retry-After")); 1749 onRetryAfter(sleepTime); 1750 console.log(`Waiting on queue, retrying after ${sleepTime}`); 1751 await sleepMs(sleepTime); 1752 } else { 1753 break; 1754 } 1755 } catch (err) { 1756 console.log(err); 1757 await sleepMs(5e3); 1758 } 1759 } 1760 return response; 1761} 1762function submitPage() { 1763 const data = globalThis.processForm(); 1764 $3("#cfAR .purchaseInput").remove(); 1765 data.purchase?.product_variants?.forEach((pv) => { 1766 $3("#cfAR").append( 1767 `<input type="text" class="purchaseInput" name="purchase[product_variants][][id]" value="${pv.id}" />` 1768 ); 1769 $3("#cfAR").append( 1770 `<input type="number" class="purchaseInput" name="purchase[product_variants][][quantity]" value="${pv.quantity}"/>` 1771 ); 1772 $3("#cfAR").append( 1773 `<input type="number" class="purchaseInput" name="purchase[product_variants][][price_id]" value="${pv.price_id}" />` 1774 ); 1775 }); 1776 data.purchase?.coupon_codes?.forEach((couponCode) => { 1777 $3("#cfAR").append( 1778 `<input type="text" class="purchaseInput" name="purchase[coupon_codes][]" value="${couponCode}" />` 1779 ); 1780 }); 1781 $3("#cfAR").append('<input type="text" class="purchaseInput" name="purchase[process_new_order]" value="true" />'); 1782 clearBlankInputFields(); 1783 const formData = [$3("#cfAR").serialize(), `request_idempotency=${uuidv4()}`].join("&"); 1784 let timer = null;
1785 globalThis.CFDispatchEvent(CFEvents.FORM_SUBMITTED, data); 1786 submitOrderAsync( 1787 formData, 1788 3, 1789 () => { 1790 clearInterval(timer); 1791 setButtonSubmitText(); 1792 }, 1793 (sleepTime) => { 1794 let remainingSeconds = sleepTime / 1e3; 1795 clearInterval(timer); 1796 timer = setInterval(() => { 1797 remainingSeconds -= 1; 1798 setButtonSubmitText("Waiting on queue", `(Retrying in ${remainingSeconds}s)`); 1799 }, 1e3); 1800 } 1801 ).then((response) => { 1802 if (response.status == 422) { 1803 response.json().then((responseJson) => { 1804 clearInterval(timer); 1805 window.dispatchEvent( 1806 new CustomEvent("checkout:order-submit-errors", { 1807 detail: { 1808 error: `Failed to submit: ${responseJson.error}` 1809 } 1810 }) 1811 ); 1812 restoreButtonState(); 1813 }); 1814 } else if (response.ok) { 1815 globalThis.CFDispatchEvent(CFEvents.FORM_SUBMITTED_OK, data); 1816 restoreButtonState(); 1817 if (response.headers.get("X-CF2-APPROVAL-URL")) { 1818 const approvalUrl = response.headers.get("X-CF2-APPROVAL-URL"); 1819 const auxWrapper = document.querySelector(".multiple-payment-aux-frame"); 1820 const $auxWrapper = $3(auxWrapper); 1821 const iframe = document.createElement("iframe"); 1822 const orderStautsIframe = "/cf_order_status?disable-dispatch=true"; 1823 iframe.onload = () => { 1824 if (iframe.src.includes(orderStautsIframe)) { 1825 $auxWrapper.css("display", "flex"); 1826 iframe.src = approvalUrl; 1827 } 1828 }; 1829 auxWrapper.innerHTML = ""; 1830 auxWrapper.appendChild(iframe); 1831 iframe.src = orderStautsIframe; 1832 } else { 1833 const isOrder = !!data.purchase; 1834 globalThis.CFDispatchEvent(CFEvents.FORM_SUBMITTED_FINALIZED, data); 1835 window.location.href = isOrder ? response.headers.get("Location") : submitRedirectTarget(response) ?? getRenderedHref(); 1836 } 1837 } else if (response.status === 429) { 1838 clearInterval(timer); 1839 setButtonSubmitText("Failed to submit", "Retry again in a few seconds"); 1840 sleepMs(5e3).then(() => { 1841 window.dispatchEvent(new CustomEvent("payments:submit-failed")); 1842 restoreButtonState(); 1843 }); 1844 } else if (response.status >= 300 && response.status < 400) { 1845 window.location.href = submitRedirectTarget(response) ?? window.location.href; 1846 } else { 1847 window.dispatchEvent(new CustomEvent("checkout:order-submit-errors")); 1848 } 1849 }).catch((err) => { 1850 console.log(err); 1851 clearInterval(timer); 1852 window.dispatchEvent(new CustomEvent("payments:submit-failed")); 1853 restoreButtonState(); 1854 }); 1855} 1856function clearBlankInputFields() { 1857 $3("#cfAR").find("input,select,textarea").each((index, input) => { 1858 if (input.value == "" && !input.classList.contains("keep")) { 1859 input.remove(); 1860 } 1861 }); 1862} 1863function getPurchaseForm() { 1864 const orderCart = window["OrderCart/V1"]?.default; 1865 if (!orderCart) return {}; 1866 const products = orderCart?.productVariants; 1867 const formPurchaseProductVariants = products?.map((product) => { 1868 return { 1869 id: product.id, 1870 price_id: product.priceId, 1871 quantity: product.quantity 1872 }; 1873 }); 1874 const rebillyToken = $3('#cfAR input[data-rebilly="token"]').val(); 1875 return { 1876 purchase: { 1877 product_variants: formPurchaseProductVariants, 1878 rebilly_token: rebillyToken, 1879 coupon_codes: [orderCart?.couponCode].filter(Boolean) 1880 } 1881 }; 1882} 1883function getAppointmentScheduleRequestForm() { 1884 const request = { appointments_schedule_request: {} }; 1885 document.querySelectorAll(".appointment_schedule_request_field").forEach((field) => { 1886 const fieldName = field.getAttribute("name")?.replace("appointment_schedule_request_", ""); 1887 cfARAppendInput(`appointments_schedule_request[${fieldName}]`, field.value, { 1888 param: `appointments_schedule_request[${fieldName}]` 1889 }); 1890 request.appointments_schedule_request[fieldName] = field.value; 1891 }); 1892 const emailField = document.querySelector("[name='email']"); 1893 if (emailField) { 1894 const cfEmailInput = document.querySelector("#cf_contact_email"); 1895 cfEmailInput.value = emailField.value; 1896 } 1897 const guestEmailInputs = document.querySelectorAll("input.guest-input"); 1898 const guestEmailStrings = [];
1899 guestEmailInputs.forEach((i) => guestEmailStrings.push(i.value)); 1900 cfARAppendInput("appointments_schedule_request[guest_emails]", guestEmailStrings.join(",")); 1901 return request; 1902} 1903function getContactForm() { 1904 const data = { contact: {} }; 1905 const writtenCarriers = /* @__PURE__ */ new Set(); 1906 $3('.elFormItem:not([data-prevent-submit="true"])').each(function() { 1907 const $this = $3(this); 1908 if ($this.parents('[data-page-element="Checkout/V2"]').length > 0) return; 1909 let name = $this.attr("name"); 1910 if (name == "" || name == "not-set") return; 1911 if (["country", "state"].includes(name)) { 1912 name = "shipping_" + name; 1913 } 1914 let value = $this.val(); 1915 if (name == "phone_number" && this.iti) { 1916 value = this.iti.getNumber(); 1917 } 1918 if (this.getAttribute("type") == "checkbox") { 1919 if (name.endsWith("[]")) { 1920 const checkboxName = name.slice(0, -2); 1921 if (!data.contact[checkboxName]) { 1922 data.contact[checkboxName] = []; 1923 } 1924 if ($this.is(":checked")) { 1925 data.contact[checkboxName].push(value); 1926 } else { 1927 const index = data.contact[checkboxName].indexOf(value); 1928 if (index > -1) { 1929 data.contact[checkboxName].splice(index, 1); 1930 } 1931 } 1932 return; 1933 } else { 1934 value = $this.is(":checked"); 1935 data.contact[name] = value; 1936 } 1937 } else if (value) { 1938 data.contact[name] = value; 1939 } 1940 const carrierId = contactCarrierInputId(name); 1941 const $contactInput = $3("#" + carrierId); 1942 if ($contactInput.length == 0 && name) { 1943 let customType = name.toLowerCase(); 1944 customType = customType.replace(/\s+/g, "_"); 1945 $3("#cf_contact_" + customType).remove(); 1946 cfARAppendInput(customType, value, { prefix: "cf_contact_" }); 1947 } else { 1948 if ($this.attr("data-prevent-submit") == "true") { 1949 $contactInput.val(""); 1950 } else if (value !== "" || !writtenCarriers.has(carrierId)) { 1951 $contactInput.val(value); 1952 writtenCarriers.add(carrierId); 1953 } 1954 } 1955 }); 1956 return data; 1957} 1958function handleMultiCheckboxForm() { 1959 $3('.elGroupedCheckbox .elFormItem:not([data-prevent-submit="true"])').each(function() { 1960 const $this = $3(this); 1961 const name = $this.attr("name"); 1962 const value = $this.val(); 1963 const checked = $this.is(":checked"); 1964 if (checked && value && !document.querySelector(`#cfAR input[name="${name}"][value="${value}"]`)) { 1965 cfARAppendInput(name, value); 1966 } else if (!document.querySelector(`#cfAR input[name="${name}"]`)) { 1967 cfARAppendInput(name, "", { keep: true }); 1968 } 1969 }); 1970 return {}; 1971} 1972function cfARAppendInput(name, value, options = {}) { 1973 const input = document.createElement("INPUT"); 1974 const prefix = options["prefix"] || "cf_"; 1975 const param = options["param"] || name; 1976 const keep = options["keep"] || false; 1977 input.id = prefix + name; 1978 input.name = name; 1979 input.setAttribute("value", value); 1980 if (keep) { 1981 input.classList.add("keep"); 1982 } 1983 input.setAttribute("data-cf-form-field", name); 1984 input.setAttribute("data-param", param); 1985 input.setAttribute("data-storage", "false"); 1986 $3("#cfAR").append(input); 1987} 1988function validateEmail(email) { 1989 email = $3.trim(email); 1990 const re = /^(([^<>()[\]\\.,;:#`%\s@"]+(\.[^<>()[\]\\.,;:#`%\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/; 1991 return re.test(email); 1992} 1993function updateInputStyle(selectedInput, type) { 1994 if (type === "error") { 1995 selectedInput.css("border-color", "#B91517"); 1996 selectedInput.css("border-width", "3px"); 1997 selectedInput.css("border-style", "solid"); 1998 } else { 1999 selectedInput.css("border-color", "#4a8920"); 2000 selectedInput.css("border-width", "3px"); 2001 selectedInput.css("border-style", "solid"); 2002 } 2003} 2004function checkValidInputs() { 2005 const popupVisibleCheck = $3(".modal-wrapper").is(":visible"); 2006 let fail = false; 2007 let elementPathSelector; 2008 if (popupVisibleCheck == true) { 2009 elementPathSelector = '#modalPopup .elFormItem.required1, #modalPopup .elFormItem[name="phone_number"]'; 2010 } else { 2011 elementPathSelector = '.pageRoot .elFormItem.required1, .pageRoot .elFormItem[name="phone_number"]'; 2012 } 2013 $3(elementPathSelector).each(function() { 2014 const $this = $3(this); 2015 const visible = $this.is(":visible"); 2016 const isRequired = $this.hasClass("required1"); 2017 if (visible) { 2018 let value = $this.val(); 2019 const isSelect = $this.is("select"); 2020 if (isSelect) value = $this.find(":selected").attr("value"); 2021 const parent = $this.parents(".elFormItemWrapper"); 2022 const selector = ".inputHolder, .borderHolder, .elCheckbox"; 2023 const selectedInput = parent.length && parent.find(selector).length ? parent.find(selector) : $this; 2024 if (selectedInput.is(":checkbox") ? !selectedInput.is(":checked") : isRequired && (value === null || typeof value === "undefined" || value === "")) { 2025 fail = true; 2026 updateInputStyle(selectedInput, "error"); 2027 } else { 2028 if (selectedInput.attr("name") == "email") { 2029 if (validateEmail(value)) { 2030 updateInputStyle(selectedInput, "valid"); 2031 } else { 2032 fail = true; 2033 updateInputStyle(selectedInput, "error"); 2034 } 2035 } else if (selectedInput.attr("name") == "phone_number" && selectedInput.get(0).iti) { 2036 if (selectedInput.get(0).iti.isValidNumber() || !isRequired && !value) { 2037 updateInputStyle(selectedInput, "valid"); 2038 } else { 2039 fail = true; 2040 updateInputStyle(selectedInput, "error"); 2041 } 2042 } else { 2043 updateInputStyle(selectedInput, "valid"); 2044 } 2045 } 2046 } 2047 }); 2048 if (popupVisibleCheck == true) { 2049 elementPathSelector = "#modalPopup .elGroupedCheckboxWrapper.required1"; 2050 } else { 2051 elementPathSelector = ".pageRoot .elGroupedCheckboxWrapper.required1"; 2052 } 2053 $3(elementPathSelector).each(function() { 2054 const $this = $3(this); 2055 const $checkboxes = $this.find(".elCheckboxInput"); 2056 const checked = $checkboxes.toArray().some((checkbox) => $3(checkbox).is(":checked")); 2057 fail = !checked; 2058 updateInputStyle($this, fail ? "error" : "valid"); 2059 }); 2060 return fail == false; 2061} 2062function mailCheck() { 2063 const inputsSelector = Array.from(document.getElementsByName("email")); 2064 inputsSelector.forEach((input, index) => { 2065 const mailCheckNode = document.createElement("div"); 2066 mailCheckNode.classList.add("mailcheck"); 2067 mailCheckNode.classList.add(`index${index}`); 2068 input.parentElement.appendChild(mailCheckNode); 2069 input.addEventListener("blur", function() { 2070 Mailcheck.run({ 2071 email: this.value, 2072 domains: defaultDomains, 2073 secondLevelDomains: defaultSecondLevelDomains, 2074 // optional 2075 topLevelDomains: defaultTopLevelDomains, 2076 // optional 2077 suggested: function(suggestion) { 2078 mailCheckNode.innerHTML = `<span>Did you mean <b>${suggestion.full}?</b></span>`;
2079 }, 2080 empty: function() { 2081 mailCheckNode.innerHTML = ""; 2082 } 2083 }); 2084 }); 2085 }); 2086} 2087function handleEnterSubmit() { 2088 const popupVisibleCheck = $3(".modal-wrapper").is(":visible"); 2089 let buttonsPathSelector; 2090 if (popupVisibleCheck == true) { 2091 buttonsPathSelector = '#modalPopup .elBTN a[href="#submit-form"]:visible'; 2092 } else { 2093 buttonsPathSelector = '.pageRoot .elBTN a[href="#submit-form"]:visible'; 2094 } 2095 const submitButton = $3(buttonsPathSelector).first(); 2096 const now = Date.now(); 2097 if (now - lastSubmitTime < SUBMIT_COOLDOWN) { 2098 return; 2099 } 2100 lastSubmitTime = now; 2101 handleFormSubmit(submitButton); 2102} 2103function setupEnterKeySubmit() { 2104 const inputsPathSelector = ".elFormItem"; 2105 $3(inputsPathSelector).each(function() { 2106 const thisInput = $3(this); 2107 if (thisInput.closest('[data-page-element="Checkout/V1"]').length > 0) { 2108 return true; 2109 } 2110 if (thisInput.closest('[data-page-element="Checkout/V2"]').length > 0) { 2111 return true; 2112 } 2113 thisInput.on("keypress", function(evt) { 2114 if (evt.originalEvent?.isComposing || evt.keyCode === 229) return; 2115 if (evt.key === "Enter") { 2116 handleEnterSubmit(); 2117 } 2118 }); 2119 }); 2120} 2121function setRedirectOverride($button) { 2122 let redirectOverride; 2123 if ($button.parents(".elBTN").length) { 2124 redirectOverride = $button.attr("data-on-submit-go-to"); 2125 } 2126 if (redirectOverride && redirectOverride !== "null" && redirectOverride !== "undefined") { 2127 $3("#cfAR").append(`<input type="text" class="redirectParams" name="redirect_to" value="${redirectOverride}" />`); 2128 } else { 2129 $3("#cfAR .redirectParams").remove(); 2130 } 2131} 2132function handleFormSubmit($button) { 2133 setRedirectOverride($button); 2134 setButtonSubmitText(); 2135 if ($3(".pai-payment-methods-inner:visible").length > 0) { 2136 const $rebillySubmit = $3(".pai-submit"); 2137 const $rebillyForm = $3(".elPAI"); 2138 if ($rebillySubmit.length) { 2139 $rebillySubmit.trigger("click"); 2140 return; 2141 } else if ($rebillyForm.length) { 2142 rebillyProcessOrder(); 2143 return; 2144 } else if (!checkValidInputs()) { 2145 restoreButtonState(); 2146 return; 2147 } 2148 } 2149 if (checkValidInputs()) { 2150 submitPage(); 2151 } else { 2152 restoreButtonState(); 2153 } 2154 return true; 2155} 2156var $3, lastSubmitTime, SUBMIT_COOLDOWN; 2157var init_submit = __esm({ 2158 "projects/user_pages/app/javascript/lander/submit.ts"() { 2159 init_define_process(); 2160 init_rebilly_element(); 2161 init_contact_fields(); 2162 init_nonce(); 2163 init_cf_utils(); 2164 init_domains(); 2165 init_main(); 2166 $3 = window.$; 2167 globalThis.processForm = function() { 2168 return { 2169 ...getPurchaseForm(), 2170 ...getContactForm(), 2171 ...handleMultiCheckboxForm(), 2172 ...getAppointmentScheduleRequestForm() 2173 }; 2174 }; 2175 globalThis.submitPage = submitPage; 2176 lastSubmitTime = 0; 2177 SUBMIT_COOLDOWN = 1e3; 2178 globalThis.handleFormSubmit = handleFormSubmit; 2179 globalThis.setButtonSubmitText = setButtonSubmitText; 2180 globalThis.restoreButtonState = restoreButtonState; 2181 globalThis.setRedirectOverride = setRedirectOverride; 2182 globalThis.clearBlankInputFields = clearBlankInputFields; 2183 window.addEventListener("DOMContentLoaded", function() { 2184 mailCheck(); 2185 setupEnterKeySubmit(); 2186 $3(document).on("click", '[href="#submit-form"],[data-element-link="#submit-form"]', function() { 2187 const $button = $3(this); 2188 if ($button.closest('[data-page-element="Checkout/V1"]').length == 0) { 2189 handleFormSubmit($button); 2190 } 2191 }); 2192 }); 2193 } 2194}); 2195
2196// projects/user_pages/app/javascript/lander/rebilly_element.ts 2197var rebilly_element_exports = {}; 2198__export(rebilly_element_exports, { 2199 rebillyProcessOrder: () => rebillyProcessOrder 2200}); 2201function leadSourceGenerator() { 2202 const DEFAULT_MAX_CHARS_LENGTH = 512; 2203 const leadQueryParamMapping = { 2204 utm_source: { 2205 name: "source" 2206 }, 2207 utm_medium: { 2208 name: "medium" 2209 }, 2210 utm_campaign: { 2211 name: "campaign" 2212 }, 2213 utm_term: { 2214 name: "term" 2215 }, 2216 utm_content: { 2217 name: "content" 2218 }, 2219 affiliate: {}, 2220 subAffiliate: {}, 2221 clickId: {}, 2222 salesAgent: {} 2223 }; 2224 const params = new URLSearchParams(window.location.search); 2225 return Array.from(params.keys()).reduce((acc, key) => { 2226 const mappedValue = leadQueryParamMapping[key]; 2227 if (mappedValue) { 2228 const paramValue = params.get(key); 2229 const leadSourceName = mappedValue.name ?? key; 2230 acc[leadSourceName] = paramValue.substring(0, DEFAULT_MAX_CHARS_LENGTH); 2231 } 2232 return acc; 2233 }, {}); 2234} 2235var scrollToForm, rebillyProcessOrder; 2236var init_rebilly_element = __esm({ 2237 "projects/user_pages/app/javascript/lander/rebilly_element.ts"() { 2238 init_define_process(); 2239 init_submit(); 2240 scrollToForm = () => { 2241 if (!$(".elPAI").length) return; 2242 $([document.documentElement, document.body]).animate({ scrollTop: $(".elPAI").offset().top - 50 }, 200); 2243 }; 2244 globalThis.addEventListener("DOMContentLoad", function() { 2245 $(document).on("change", ".elInput", function() { 2246 globalThis.processForm(); 2247 }); 2248 window.addEventListener("payments:token-ready", () => { 2249 globalThis.processForm(); 2250 if (!checkValidInputs()) { 2251 restoreButtonState(); 2252 scrollToForm(); 2253 this.window.dispatchEvent(new CustomEvent("payments:submit-failed")); 2254 return; 2255 } 2256 submitPage(); 2257 }); 2258 }); 2259 rebillyProcessOrder = () => { 2260 const Rebilly = globalThis.Rebilly; 2261 let extraData = { 2262 method: globalThis.paymentsSelectedPaymentMethod 2263 }; 2264 const leadSource = leadSourceGenerator(); 2265 if (Object.keys(leadSource).length) { 2266 extraData = { ...extraData, leadSource }; 2267 } 2268 const form = document.querySelector("#cfAR"); 2269 window.dispatchEvent(new CustomEvent("payments:clear-errors")); 2270 globalThis.processForm(); 2271 if (!checkValidInputs()) { 2272 restoreButtonState(); 2273 scrollToForm(); 2274 window.dispatchEvent(new CustomEvent("payments:submit-failed")); 2275 return; 2276 } 2277 Rebilly.createToken(form, extraData).then(function(result) { 2278 console.log("Framepay success", result); 2279 globalThis.parent.postMessage("success", "*"); 2280 submitPage(); 2281 }).catch(function(error) { 2282 console.log("Framepay error", error); 2283 globalThis.parent.postMessage("error", "*"); 2284 form.querySelector('input[data-rebilly="token"]').value = ""; 2285 window.dispatchEvent( 2286 new CustomEvent("payments:set-token-error", { 2287 detail: { 2288 error 2289 } 2290 }) 2291 ); 2292 restoreButtonState(); 2293 scrollToForm(); 2294 window.dispatchEvent(new CustomEvent("payments:submit-failed")); 2295 }); 2296 }; 2297 globalThis.rebillyProcessOrder = rebillyProcessOrder; 2298 globalThis.scrollToForm = scrollToForm; 2299 } 2300}); 2301
2302// projects/user_pages/app/javascript/lander/upsell_element.js 2303var upsell_element_exports = {}; 2304__export(upsell_element_exports, { 2305 submitUpsellOrder: () => submitUpsellOrder 2306}); 2307var submitUpsellOrder; 2308var init_upsell_element = __esm({ 2309 "projects/user_pages/app/javascript/lander/upsell_element.js"() { 2310 init_define_process(); 2311 init_submit(); 2312 (function() { 2313 window.addEventListener("load", function() { 2314 $(document).on("click", "#upsell-submit-button", function(event) { 2315 event.preventDefault(); 2316 submitUpsellOrder(); 2317 }); 2318 }); 2319 })(); 2320 submitUpsellOrder = () => { 2321 $("#cfAR input[data-order-form]").val(true); 2322 submitPage(); 2323 }; 2324 } 2325}); 2326
2327// projects/user_pages/app/javascript/lander/order/main.ts 2328var main_exports = {}; 2329var init_main2 = __esm({ 2330 "projects/user_pages/app/javascript/lander/order/main.ts"() { 2331 init_define_process(); 2332 (function() { 2333 window.addEventListener("load", function() { 2334 const orderCart = window["OrderCart/V1"]?.default; 2335 let previousRadioProductVariant; 2336 document.querySelectorAll(".elOrderSelect").forEach(function(orderSelect) { 2337 const type = orderSelect.getAttribute("data-order-select-type"); 2338 if (type == "single") { 2339 const firstInput = orderSelect.querySelector('input[type="radio"]'); 2340 if (firstInput) { 2341 firstInput.checked = true; 2342 } 2343 const newProductVariant = orderCart.getProductVariant(firstInput, "single"); 2344 previousRadioProductVariant = newProductVariant; 2345 orderCart.updateProductVariant(newProductVariant); 2346 } 2347 }); 2348 $(document).on("change", '.elOrderSelect input[type="radio"]', function(event) { 2349 const input = event.target; 2350 $(`.elOrderSelect input[type="radio"][value=${input.value}]`).prop("checked", true); 2351 const newProductVariant = orderCart.getProductVariant(input, "single"); 2352 if (previousRadioProductVariant) { 2353 orderCart.incrementProductVariantQuantity(previousRadioProductVariant, -1); 2354 } 2355 orderCart.updateProductVariant(newProductVariant); 2356 previousRadioProductVariant = newProductVariant; 2357 }); 2358 $(document).on("change", '.elOrderSelect input[type="number"]', function(event) { 2359 const input = event.target; 2360 const productVariantId = input.getAttribute("data-product-variant-id"); 2361 const quantity = input.value; 2362 $(`.elOrderSelect input[type="number"][data-product-variant-id="${productVariantId}"]`).val(quantity); 2363 const productVariant = orderCart.getProductVariant(input, "multiple"); 2364 orderCart.updateProductVariant(productVariant); 2365 }); 2366 $(document).on("change", ".elOrderProductOptionsPrice select", function(event) { 2367 const priceSelect = event.target; 2368 const productVariantId = priceSelect.getAttribute("data-product-variant-id"); 2369 const priceId = priceSelect.value; 2370 const priceCents = priceSelect.querySelector(`option[value="${priceId}"`).getAttribute("data-product-variant-price-cents"); 2371 const orderSelectType = document.querySelector(".elOrderSelect").getAttribute("data-order-select-type"); 2372 const orderSelectInputType = orderSelectType == "single" ? "radio" : "number"; 2373 const productVariantInput = document.querySelector( 2374 `.elOrderSelect input[type="${orderSelectInputType}"][data-product-variant-id="${productVariantId}"]` 2375 ); 2376 productVariantInput.setAttribute("data-product-variant-price-id", priceId); 2377 productVariantInput.setAttribute("data-product-variant-price-cents", priceCents); 2378 if (orderSelectType == "single" && !productVariantInput.checked) return; 2379 const productVariant = orderCart.getProductVariant(productVariantInput, orderSelectType); 2380 orderCart.updateProductVariant(productVariant); 2381 }); 2382 $(document).on("change", ".elOrderBump input", function(event) { 2383 const input = event.target; 2384 const productVariant = orderCart.getProductVariant(input); 2385 orderCart.updateProductVariant(productVariant); 2386 }); 2387 $(document).on("change", ".elOrderBump select", function(event) { 2388 const select = event.target; 2389 const productId = select.getAttribute("data-product-id"); 2390 const selectedOption = select.querySelector(`option[value="${select.value}"]`); 2391 const productInput = document.querySelector( 2392 `.elOrderBump input[data-product-id="${productId}"]` 2393 ); 2394 const variantAttrs = ["id", "name", "price-id", "price-cents", "price-currency"]; 2395 variantAttrs.forEach(function(variantAttr) { 2396 productInput.setAttribute( 2397 `data-product-variant-${variantAttr}`, 2398 selectedOption.getAttribute(`data-product-variant-${variantAttr}`) 2399 ); 2400 }); 2401 if (!productInput.checked) return; 2402 const productVariant = orderCart.getProductVariant(productInput); 2403 orderCart.updateProductVariant(productVariant); 2404 }); 2405 $(document).on("click", ".elOrderCoupon button", function() { 2406 const input = document.querySelector(".elOrderCoupon input"); 2407 orderCart.updateCouponCode(input.value); 2408 }); 2409 document.querySelectorAll(".elOrderCoupon input[readonly]").forEach(function(element) { 2410 element.removeAttribute("readonly"); 2411 }); 2412 }); 2413 })(); 2414 } 2415}); 2416
2417// projects/user_pages/app/javascript/lander/utils/action_matching.ts 2418function matchesAction(element, action) { 2419 const link = element.getAttribute("data-element-link"); 2420 if (link !== null) return link === action; 2421 const { hash, origin, pathname } = element; 2422 return hash === action && origin === window.location.origin && pathname === window.location.pathname; 2423} 2424var init_action_matching = __esm({ 2425 "projects/user_pages/app/javascript/lander/utils/action_matching.ts"() { 2426 init_define_process(); 2427 } 2428}); 2429
2430// projects/user_pages/app/javascript/lander/action_link.ts 2431var action_link_exports = {}; 2432function setupActionLinkListeners() { 2433 $(document).on("click", "[data-element-link='#print'], a[href$='#print']", function(evt) { 2434 if (!matchesAction(evt.currentTarget, "#print")) return; 2435 window.print(); 2436 return false; 2437 }); 2438 $(document).on("click", "[data-element-link='#open-popup'], a[href$='#open-popup']", function(evt) { 2439 if (!matchesAction(evt.currentTarget, "#open-popup")) return; 2440 evt.preventDefault(); 2441 const checkIfShowHide = evt.target.parentElement?.getAttribute("data-elbuttontype"); 2442 if (typeof checkIfShowHide == "undefined" || !["2", "showHide"].includes(checkIfShowHide)) { 2443 globalThis.CFOpenPopup(); 2444 } 2445 }); 2446 $(document).on("click", "[data-element-link='#close-popup'], a[href$='#close-popup']", function(evt) { 2447 if (!matchesAction(evt.currentTarget, "#close-popup")) return; 2448 evt.preventDefault(); 2449 globalThis.CFClosePopup(); 2450 }); 2451 $(document).on("click", "a[href*='#scroll-'], [data-element-link*='#scroll-']", function(evt) { 2452 const href = evt.currentTarget.getAttribute("href") ?? ""; 2453 const [, id] = href.split("#scroll-"); 2454 if (id) { 2455 if (isWithinCustomerCenterView()) { 2456 const el = document.querySelector(`.${id}`); 2457 const mainElement = window.parent.document.body.querySelector("main"); 2458 if (el && mainElement) { 2459 mainElement.scrollTo({ top: $(el).offset().top, behavior: "smooth" }); 2460 } 2461 } else { 2462 const el = document.querySelector(`.${id}`); 2463 const popupParent = el?.closest(".modal-wrapper"); 2464 const scrollContainer = popupParent || document.documentElement; 2465 if (el && scrollContainer) { 2466 scrollContainer.scrollTo({ top: $(el).offset().top, behavior: "smooth" }); 2467 } 2468 } 2469 } 2470 return false; 2471 }); 2472 const getElementsIds = (evt, type) => (evt.currentTarget.getAttribute(`data-${type}-button-ids`) || "").split(",").filter((s) => s); 2473 const performActionOnId = (id, action) => { 2474 const $el = $(`.${id}`); 2475 if ($el.attr("data-show-only") && action === "fadeIn") { 2476 $el.removeAttr("data-show-only"); 2477 $el.css("display", "none"); 2478 } 2479 $el[action]({ duration: 500 }); 2480 }; 2481 $(document).on("click", "a[href*='#show-hide'], [data-element-link*='#show-hide']", function(evt) { 2482 evt.preventDefault(); 2483 const hideIds = getElementsIds(evt, "hide"); 2484 const showIds = getElementsIds(evt, "show"); 2485 hideIds.forEach((id) => performActionOnId(id, "fadeOut")); 2486 showIds.forEach((id) => performActionOnId(id, "fadeIn")); 2487 return false; 2488 }); 2489 $(document).on("click", "a[href=''], [data-element-link='']", function(evt) { 2490 evt.preventDefault(); 2491 return false; 2492 }); 2493 $(document).on("click", "[data-element-link]", function(evt) { 2494 evt.preventDefault(); 2495 const linkableElement = evt.currentTarget; 2496 const link = linkableElement.getAttribute("data-element-link"); 2497 if (link && !internalLinks.includes(link)) { 2498 const target = linkableElement.getAttribute("target") ?? "_self"; 2499 if (target === "_self") { 2500 window.location.href = link; 2501 } else { 2502 window.open(link, "_blank"); 2503 } 2504 } 2505 }); 2506 $(document).on("click", "a[href^='#download-asset:']", function(evt) { 2507 evt.preventDefault(); 2508 const id = evt.currentTarget.getAttribute("href").replace("#download-asset:", ""); 2509 window.location.href = `/account/downloads/${id}/file`; 2510 return false; 2511 }); 2512 $(document).on("click", "a[href^='#download-inline:']", function(evt) { 2513 evt.preventDefault(); 2514 const id = evt.currentTarget.getAttribute("href").replace("#download-inline:", ""); 2515 window.open(`/account/downloads/${id}/preview`, "_blank"); 2516 return false; 2517 }); 2518 $(document).on("click", "a[href*='#no-link'], [data-element-link*='#no-link']", function(evt) { 2519 evt.preventDefault(); 2520 const urlParams = new URLSearchParams(window.location.search); 2521 urlParams.set("next_funnel_step", "true"); 2522 window.location.href = `${window.location.pathname}?${urlParams}`; 2523 }); 2524 document.querySelectorAll("[data-element-link]").forEach((linkableElement) => { 2525 if (linkableElement.getAttribute("data-element-link")) linkableElement.setAttribute("tabindex", "0"); 2526 }); 2527} 2528var internalLinks; 2529var init_action_link = __esm({ 2530 "projects/user_pages/app/javascript/lander/action_link.ts"() { 2531 init_define_process(); 2532 init_cf_utils(); 2533 init_action_matching(); 2534 internalLinks = [ 2535 "#open-popup", 2536 "#close-popup", 2537 "#submit-form", 2538 "#scroll", 2539 "#print", 2540 "#show-hide", 2541 "#download-asset", 2542 "#download-inline" 2543 ]; 2544 window.addEventListener("DOMContentLoaded", setupActionLinkListeners); 2545 } 2546}); 2547
2548// projects/user_pages/app/javascript/lander/animation.ts 2549var require_animation = __commonJS({ 2550 "projects/user_pages/app/javascript/lander/animation.ts"() { 2551 init_define_process(); 2552 var unobserve = (element, observer) => { 2553 observer.unobserve(element); 2554 if (element.getAttribute("data-animation-once") !== "true") { 2555 const time = element.getAttribute("data-animation-time"); 2556 const delay = element.getAttribute("data-animation-delay"); 2557 const timeout = Number(time) + Number(delay); 2558 setTimeout(() => { 2559 observer.observe(element); 2560 }, timeout); 2561 } 2562 }; 2563 var startAnimation = (element) => { 2564 element.setAttribute("data-animation-state", "running"); 2565 }; 2566 var params = new URLSearchParams(window.location.search); 2567 var disabledAnimations = params.get("animations") == "skip"; 2568 window.addEventListener("DOMContentLoaded", function() { 2569 if (disabledAnimations) { 2570 const allAnimatedElements = document.querySelectorAll("[data-animation-type]"); 2571 allAnimatedElements.forEach((el) => { 2572 el.setAttribute("data-animation-type", "none"); 2573 }); 2574 } 2575 }); 2576 var setupStyleGuideAnimatedNodes = () => { 2577 if (disabledAnimations) return; 2578 const styleGuideAnimationNode = JSON.parse( 2579 document.getElementById("cf-lander-serialized-style-guide-animation-node")?.textContent ?? "{}" 2580 ); 2581 document.querySelectorAll("[data-style-guide-animation]").forEach((element) => { 2582 const style = element.getAttribute("data-style-guide-animation"); 2583 const selectedAnimation = styleGuideAnimationNode.selectors[`.elPageContent [data-style-guide-animation="${style}"]`]; 2584 element.setAttribute("data-animation-type", selectedAnimation.attrs["data-animation-type"]); 2585 element.setAttribute("data-animation-trigger", selectedAnimation.attrs["data-animation-trigger"]); 2586 }); 2587 }; 2588 $(document).ready(function() { 2589 const runAllAnimations = function() { 2590 setupStyleGuideAnimatedNodes(); 2591 const scrollElements = document.querySelectorAll('[data-animation-trigger="scroll"]'); 2592 const loadElements = document.querySelectorAll('[data-animation-trigger="load"]'); 2593 const config2 = { 2594 rootMargin: "50px 20px 75px 30px", 2595 threshold: [0, 0.25, 0.75, 1] 2596 }; 2597 const observer = new IntersectionObserver((entries) => { 2598 entries.forEach((entry) => { 2599 if (entry.isIntersecting) { 2600 if (entry.target.getAttribute("data-animation-state") !== "running") { 2601 unobserve(entry.target, observer); 2602 startAnimation(entry.target); 2603 } 2604 } else { 2605 entry.target.setAttribute("data-animation-state", "off"); 2606 } 2607 }); 2608 }, config2); 2609 scrollElements.forEach((element) => { 2610 observer.observe(element); 2611 }); 2612 loadElements.forEach((element) => { 2613 startAnimation(element); 2614 }); 2615 }; 2616 if (!disabledAnimations) runAllAnimations(); 2617 }); 2618 } 2619}); 2620
2621// projects/user_pages/app/javascript/lander/sticky.ts 2622var require_sticky = __commonJS({ 2623 "projects/user_pages/app/javascript/lander/sticky.ts"() { 2624 init_define_process(); 2625 var STUCK_CLASS = "stickyClone"; 2626 function createPlaceholder() { 2627 return $("<div>").addClass("stickyPlaceholder").attr("aria-hidden", "true"); 2628 } 2629 function sizePlaceholder(sticky, placeholder) { 2630 const height = sticky.outerHeight() ?? 0; 2631 placeholder.css({ 2632 boxSizing: "border-box", 2633 height, 2634 marginTop: sticky.css("marginTop"), 2635 marginBottom: sticky.css("marginBottom") 2636 }); 2637 return height; 2638 } 2639 $(document).ready(function() { 2640 const $stickyElements = $(".stickyTop"); 2641 $stickyElements.each((_index, element) => { 2642 const sticky = $(element); 2643 const placeholder = createPlaceholder(); 2644 let stuck = false; 2645 let flowHeight = 0; 2646 const hasBox = () => element.getClientRects().length > 0; 2647 const resizeObserver = typeof ResizeObserver === "undefined" ? null : new ResizeObserver(() => { 2648 if (stuck) placeholder.css("height", Math.max(flowHeight, sticky.outerHeight() ?? 0)); 2649 }); 2650 const pin = () => { 2651 flowHeight = sizePlaceholder(sticky, placeholder); 2652 placeholder.insertBefore(sticky); 2653 sticky.addClass(STUCK_CLASS); 2654 stuck = true; 2655 resizeObserver?.observe(element); 2656 }; 2657 const unpin = () => { 2658 resizeObserver?.unobserve(element); 2659 sticky.removeClass(STUCK_CLASS); 2660 placeholder.detach(); 2661 stuck = false; 2662 }; 2663 const stickyTop = () => stuck ? placeholder.offset().top : sticky.offset().top; 2664 if (hasBox() && $(window).scrollTop() > stickyTop()) { 2665 pin(); 2666 } 2667 document.addEventListener("scroll", () => { 2668 const scrollTop = $(window).scrollTop(); 2669 if (!stuck && hasBox() && scrollTop >= stickyTop()) { 2670 pin(); 2671 } else if (stuck && scrollTop < stickyTop()) { 2672 unpin(); 2673 } 2674 }); 2675 }); 2676 }); 2677 } 2678}); 2679
2680// projects/user_pages/app/javascript/lander.js 2681var require_lander = __commonJS({ 2682 "projects/user_pages/app/javascript/lander.js"() { 2683 init_define_process(); 2684 require_replace_tag(); 2685 init_fetcher(); 2686 require_parseurl(); 2687 require_audio_player(); 2688 require_garlic_cf(); 2689 init_populate_select(); 2690 require_runtime_events(); 2691 init_fhl_handle_select_transformation(); 2692 init_track_events(); 2693 init_resource_sharing_concern(); 2694 init_rebilly_element(); 2695 init_upsell_element(); 2696 init_main2(); 2697 init_runtime(); 2698 init_action_link(); 2699 require_animation(); 2700 init_submit(); 2701 require_sticky(); 2702 window.nanostores = (init_nanostores(), __toCommonJS(nanostores_exports)); 2703 var originalFetch = window.fetch; 2704 window.inflightRequests = 0; 2705 window.fetch = async (request, init) => { 2706 window.inflightRequests++; 2707 try { 2708 const rendered_page_url = document.querySelector('meta[name="rendered-page-url"]')?.getAttribute("content"); 2709 if (rendered_page_url) { 2710 const url = new URL(new Request(request).url); 2711 if (url.hostname == window.location.hostname) { 2712 init = init || {}; 2713 if (!init.headers) init.headers = {}; 2714 init.headers["X-Rendered-Page-Url"] = rendered_page_url; 2715 } 2716 } 2717 } catch (e) { 2718 console.error("Failed to set X-Rendered-Page-Url header", e); 2719 } 2720 return originalFetch(request, init).finally(() => { 2721 window.inflightRequests--; 2722 }); 2723 }; 2724 $(window).on("DOMContentLoaded", function() { 2725 $('.elFormItem:not([data-prevent-garlic="true"])').each(function() { 2726 let onPersist = () => { 2727 }; 2728 if (this.getAttribute("name") == "name") { 2729 onPersist = () => { 2730 const value = this.value.trim(); 2731 const firstName = value.split(" ")[0]; 2732 const lastName = value.split(" ").slice(1).join(" "); 2733 window.cfGarlicUtils.store("first_name", firstName); 2734 window.cfGarlicUtils.store("last_name", lastName); 2735 }; 2736 } else if (this.getAttribute("name") == "phone_number") { 2737 onPersist = () => { 2738 if (!this.iti?.isValidNumber()) return; 2739 const value = this.iti?.getNumber() ?? this.value.trim(); 2740 window.cfGarlicUtils.store("phone_number", value); 2741 }; 2742 } 2743 $(this).garlic({ 2744 onPersist, 2745 onRetrieve: function($el, retrievedValue) { 2746 const elemName = $el.attr("name"); 2747 globalThis.CFGarlicValues[elemName] = retrievedValue; 2748 $el.each((_, element) => { 2749 const closestBlueprintInstance = element.closest("[data-page-element]")?.cf2_instance; 2750 if (closestBlueprintInstance && closestBlueprintInstance.update) { 2751 closestBlueprintInstance.update(retrievedValue); 2752 } 2753 }); 2754 } 2755 }); 2756 }); 2757 }); 2758 } 2759}); 2760
2761// projects/shared/stylesheets/page-content/main.scss 2762var init_main3 = __esm({ 2763 "projects/shared/stylesheets/page-content/main.scss"() { 2764 } 2765}); 2766
2767// projects/shared/stylesheets/bootstrap-modal.min.css 2768var init_bootstrap_modal_min = __esm({ 2769 "projects/shared/stylesheets/bootstrap-modal.min.css"() { 2770 } 2771}); 2772
2773// projects/user_pages/app/stylesheets/core.css 2774var init_core = __esm({ 2775 "projects/user_pages/app/stylesheets/core.css"() { 2776 } 2777}); 2778
2779// projects/user_pages/app/stylesheets/mediaelementplayer-custom.css 2780var init_mediaelementplayer_custom = __esm({ 2781 "projects/user_pages/app/stylesheets/mediaelementplayer-custom.css"() { 2782 } 2783}); 2784
2785// projects/user_pages/app/stylesheets/alert_messages.scss 2786var init_alert_messages = __esm({ 2787 "projects/user_pages/app/stylesheets/alert_messages.scss"() { 2788 } 2789}); 2790
2791// projects/lib/packages/yggdrasil-blueprints/__generated__/dist/systemBluprints.min.css 2792var init_systemBluprints_min = __esm({ 2793 "projects/lib/packages/yggdrasil-blueprints/__generated__/dist/systemBluprints.min.css"() { 2794 } 2795}); 2796
2797// projects/user_pages/app/javascript/lander_styles.js 2798var lander_styles_exports = {}; 2799var init_lander_styles = __esm({ 2800 "projects/user_pages/app/javascript/lander_styles.js"() { 2801 init_define_process(); 2802 init_main3(); 2803 init_bootstrap_modal_min(); 2804 init_core(); 2805 init_mediaelementplayer_custom(); 2806 init_alert_messages(); 2807 init_systemBluprints_min(); 2808 } 2809}); 2810
2811// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/content-node.ts 2812var ContentNode; 2813var init_content_node = __esm({ 2814 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/content-node.ts"() { 2815 init_define_process(); 2816 init_runtime(); 2817 ContentNode = class extends CF2Component { 2818 constructor(el, runtimeSel) { 2819 super(el, runtimeSel); 2820 } 2821 mount(el) { 2822 this.syncSameNameInputs(); 2823 } 2824 syncSameNameInputs() { 2825 const formInputs = document.querySelectorAll(".elFormItem[name]"); 2826 formInputs.forEach((input) => { 2827 const inputName = input.name; 2828 input.addEventListener("change", () => { 2829 if (input.type === "checkbox" || input.type === "radio") { 2830 const inputValue = input.value; 2831 const otherInputs = document.querySelectorAll( 2832 `.elFormItem.elInput[name="${inputName}"][value="${inputValue}"]` 2833 ); 2834 otherInputs.forEach((otherInput) => { 2835 otherInput.checked = input.checked; 2836 }); 2837 } else { 2838 const otherInputs = document.querySelectorAll( 2839 `.elFormItem.elInput[name="${inputName}"]` 2840 ); 2841 otherInputs.forEach((otherInput) => { 2842 otherInput.value = input.value; 2843 }); 2844 } 2845 }); 2846 }); 2847 } 2848 }; 2849 registerComponent("ContentNode", ContentNode); 2850 window["ContentNode"] = ContentNode; 2851 } 2852}); 2853
2854// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/modal-container-v1.ts 2855var ModalContainerV1; 2856var init_modal_container_v1 = __esm({ 2857 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/modal-container-v1.ts"() { 2858 init_define_process(); 2859 init_modal_v1(); 2860 init_runtime(); 2861 ModalContainerV1 = class extends CF2Component { 2862 constructor(el, runtimeSel) { 2863 super(el, runtimeSel); 2864 } 2865 mount() { 2866 this.isAudioInitialized = false; 2867 this.modal = this.getComponent("Modal/V1"); 2868 this.videoElements = this.getComponents("Video/V1"); 2869 this.modalElement = this.modal.element; 2870 this.containerModal = document.getElementById("modalPopup"); 2871 this.showOnExit = this.containerModal.getAttribute("data-show-popup-on-exit") === "true"; 2872 this.showOnLoad = this.containerModal.getAttribute("data-show-popup-on-page-load") === "true"; 2873 this.showWhenElementIsVisible = this.element.getAttribute("data-selected-element"); 2874 this.closeButton = this.element.querySelector(".closeLPModal"); 2875 if (this.showWhenElementIsVisible) { 2876 const visibleElementSelector = this.showWhenElementIsVisible.startsWith("id-") ? `.${this.showWhenElementIsVisible}` : `.id-${this.showWhenElementIsVisible}`; 2877 this.visibleElement = document.querySelector(visibleElementSelector); 2878 } 2879 const self = this; 2880 this.modal.close = function() { 2881 handleModalClose(); 2882 }; 2883 if (this.visibleElement) { 2884 handleShowWhenElementIsVisible(this.visibleElement); 2885 } 2886 if (this.showOnExit) { 2887 handleShowOnExit(); 2888 } 2889 if (this.showOnLoad) { 2890 if (this.showOnLoadDelay) { 2891 setTimeout(() => { 2892 handleModalOpen(); 2893 }, this.showOnLoadDelay); 2894 } else { 2895 handleModalOpen(); 2896 } 2897 } 2898 function handleModalOpen() { 2899 const containerModal = self.containerModal; 2900 const modalElement = self.modalElement; 2901 const closeButton = self.closeButton; 2902 const scrollY = window.scrollY; 2903 $(containerModal).show(); 2904 $(containerModal).css("top", -800); 2905 $(closeButton).css("top", -800); 2906 $(containerModal).addClass("popup-relative-position"); 2907 $("html").addClass("hide-page-scroll"); 2908 $("body").css("position", "fixed"); 2909 $("body").css("top", `-${scrollY}px`); 2910 $("body").css("width", "100%"); 2911 $(modalElement).show(); 2912 if (!self.isAudioInitialized) { 2913 self.isAudioInitialized = true; 2914 setupAudioElements(); 2915 } 2916 $(modalElement).css({ 2917 opacity: 1, 2918 top: 0 2919 }); 2920 $(containerModal).animate( 2921 { 2922 opacity: 1, 2923 top: 0 2924 }, 2925 { 2926 duration: 200 2927 } 2928 ); 2929 $(closeButton).animate({ top: -20 }, { duration: 200 }); 2930 } 2931 function handleModalClose() { 2932 const containerModal = self.containerModal; 2933 const modalElement = self.modalElement; 2934 const closeButton = self.closeButton; 2935 const scrollY = $("body").css("top"); 2936 $(closeButton).animate({ top: -800 }, { duration: 200 }); 2937 $(containerModal).animate( 2938 { 2939 opacity: 0, 2940 top: -800 2941 }, 2942 { 2943 duration: 200, 2944 complete: function() { 2945 $(modalElement).css({ 2946 opacity: 0, 2947 top: -800 2948 }); 2949 $(modalElement).hide(); 2950 $(containerModal).hide(); 2951 $(containerModal).removeClass("popup-relative-position"); 2952 } 2953 } 2954 ); 2955 $("html").removeClass("hide-page-scroll"); 2956 $("body").css("position", ""); 2957 $("body").css("top", ""); 2958 $("body").css("width", ""); 2959 if (scrollY) { 2960 window.scrollTo(0, parseInt(scrollY || "0", 10) * -1); 2961 } 2962 } 2963 function handleShowWhenElementIsVisible() { 2964 const config2 = { 2965 rootMargin: "50px 20px 75px 30px", 2966 threshold: [0, 0.25, 0.75, 1] 2967 }; 2968 const observer = new IntersectionObserver((entries) => {
2969 entries.forEach((entry) => { 2970 if (entry.isIntersecting) { 2971 observer.unobserve(entry.target, observer); 2972 handleModalOpen(); 2973 } 2974 }); 2975 }, config2); 2976 observer.observe(self.visibleElement); 2977 } 2978 function handleShowOnExit() { 2979 let cfMouseP = 0; 2980 const modalElement = self.modalElement; 2981 const handleMouseMove = (evt) => { 2982 cfMouseP = evt.clientY; 2983 }; 2984 const handleMouseLeave = () => { 2985 if (cfMouseP <= 40) { 2986 if (!$(modalElement).is(":visible")) { 2987 handleModalOpen(); 2988 document.querySelector("body").removeEventListener("mouseleave", handleMouseLeave); 2989 document.querySelector("body").removeEventListener("mousemove", handleMouseMove); 2990 } 2991 } 2992 }; 2993 document.querySelector("body").addEventListener("mousemove", handleMouseMove); 2994 document.querySelector("body").addEventListener("mouseleave", handleMouseLeave); 2995 } 2996 function setupAudioElements() { 2997 const audioElements = $(".containerModal .elAudioWrapper"); 2998 try { 2999 audioElements.each(function() { 3000 const $this = $(this); 3001 const audioURL = $this.attr("data-audio-url") || "https://images.clickfunnels.com/images/SevenNationArmy.mp3"; 3002 const loop = $this.attr("data-audio-loop") || "no"; 3003 const playerOptions = { 3004 class: "elAudioElement", 3005 audioWidth: "100%", 3006 audioHeight: "100%", 3007 enableAutosize: true, 3008 enableProgressTooltip: false, 3009 loop: loop === "yes", 3010 features: [ 3011 "playpause", 3012 "current", 3013 "progress", 3014 "duration", 3015 "volume" 3016 ] 3017 }; 3018 const audio = $(this).find("audio"); 3019 audio.attr("src", audioURL); 3020 audio.mediaelementplayer(playerOptions); 3021 }); 3022 } catch (err) { 3023 console.log(err); 3024 } 3025 } 3026 globalThis.CFOpenPopup = handleModalOpen; 3027 globalThis.CFClosePopup = handleModalClose; 3028 } 3029 }; 3030 registerComponent("ModalContainer/V1", ModalContainerV1); 3031 window["ModalContainerV1"] = ModalContainerV1; 3032 } 3033}); 3034
3035// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/add-to-cart.ts 3036var AddToCart; 3037var init_add_to_cart = __esm({ 3038 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/add-to-cart.ts"() { 3039 init_define_process(); 3040 init_addToCart(); 3041 init_runtime(); 3042 AddToCart = class extends CF2Component { 3043 constructor(el, runtimeSel) { 3044 super(el, runtimeSel); 3045 } 3046 mount() { 3047 mountComponent(this); 3048 } 3049 remove() { 3050 this.element.innerHTML = ""; 3051 } 3052 render(initializeChildrenInstances = false) { 3053 const is_server = true; 3054 const product = this.product ?? null; 3055 const currentVariant = this.currentVariant ?? null; 3056 const selected_price = this.selected_price ?? null; 3057 const button_layout_size = this.button_layout_size ?? null; 3058 const input_layout_size = this.input_layout_size ?? null; 3059 const show_name = this.show_name ?? null; 3060 const show_description = this.show_description ?? null; 3061 const show_compare_at = this.show_compare_at ?? null; 3062 const editor_product = this.element.getAttribute("data-param-editor_product"); 3063 const primary_text = this.element.getAttribute("data-param-primary_text"); 3064 const secondary_text = this.element.getAttribute("data-param-secondary_text"); 3065 let html = ""; 3066 { 3067 const is_editor = false; 3068 const customVariants = product?.variants.filter((value) => value["default_variant"] == false); 3069 const variant = currentVariant ?? product; 3070 const selected_price2 = variant?.prices?.[0]; 3071 const desc = (product?.description_override ?? variant.description ?? product.description ?? product.default_variant.description ?? "").replaceAll(` 3072`, "<br>"); 3073 html += `<div class="elAddToCartWrapper">`; 3074 if (show_name) { 3075 html += `<a class="elAddToCartNameLink" href="${product?.url}"><span class="elAddToCartName">${variant?.name ?? product.default_variant.name}</span></a>`; 3076 } 3077 if (variant?.prices?.length == 1) { 3078 html += `<div class="elAddToCartSinglePriceWrapper"><span class="elAddToCartPrice">${selected_price2?.name}</span>`; 3079 const compare_at_amount = selected_price2?.compare_at_amount; 3080 if (compare_at_amount && show_compare_at) { 3081 html += `<span class="elAddToCartCompareAt">${compare_at_amount}</span>`; 3082 } 3083 html += `</div>`; 3084 } else { 3085 html += `<div class="elSelectWrapper`; 3086 if (input_layout_size == "xs") { 3087 html += ` elAddToCartInputExtraSmall`; 3088 } 3089 if (input_layout_size == "s") { 3090 html += ` elAddToCartInputSmall`; 3091 } 3092 if (input_layout_size == "m") { 3093 html += ` elAddToCartInputMedium`; 3094 } 3095 if (input_layout_size == "l") { 3096 html += ` elAddToCartInputLarge`; 3097 } 3098 if (input_layout_size == "xl") { 3099 html += ` elAddToCartInputExtraLarge`; 3100 } 3101 html += `"><select name="variant_price">`; 3102 const c0 = variant.prices; 3103 const fl1 = new CF2ForloopDrop(c0.length); 3104 for (const price of c0) { 3105 const forloop = fl1; 3106 html += `<option `; 3107 if (selected_price2?.id == price?.id) { 3108 html += `selected`; 3109 } 3110 html += ` value="${price?.id}">${price?.name}</option>`; 3111 forloop.next(); 3112 } 3113 html += `</select><div class="elSelectArrow"><i class="fas fa-chevron-down"></i></div></div>`; 3114 } 3115 if (desc != "" && show_description) { 3116 html += `<span class="elAddToCartDescription">${desc}</span>`; 3117 } 3118 if (customVariants?.length > 1) { 3119 html += `<div class="elAddToCartVariantSelectorWrapper">`; 3120 const c2 = product.sorted_property_values; 3121 const fl3 = new CF2ForloopDrop(c2.length); 3122 for (const property_values of c2) { 3123 const forloop = fl3; 3124 const property_id = property_values?.property_id; 3125 const select_index = forloop?.index0; 3126 html += `<div class="elSelectWrapper`; 3127 if (input_layout_size == "xs") { 3128 html += ` elAddToCartInputExtraSmall`; 3129 } 3130 if (input_layout_size == "s") { 3131 html += ` elAddToCartInputSmall`; 3132 } 3133 if (input_layout_size == "m") { 3134 html += ` elAddToCartInputMedium`; 3135 } 3136 if (input_layout_size == "l") { 3137 html += ` elAddToCartInputLarge`; 3138 } 3139 if (input_layout_size == "xl") { 3140 html += ` elAddToCartInputExtraLarge`; 3141 } 3142 html += `"><span class="elAddToCartVariantSelectorTitle">${product?.all_properties?.[property_id]}</span><div style="position:relative;"><select class="elVariantSelector" name="property_${property_id}">`; 3143 const c4 = property_values.value_ids; 3144 const fl5 = new CF2ForloopDrop(c4.length); 3145 for (const value_id of c4) { 3146 const forloop2 = fl5; 3147 html += `<option `; 3148 if (variant?.property_value_ids?.[select_index] == value_id) { 3149 html += `selected`; 3150 } 3151 html += ` value="${value_id}">${product?.all_properties_values?.[value_id]}</option>`; 3152 forloop2.next(); 3153 } 3154 html += `</select><div class="elSelectArrow"><i class="fas fa-chevron-down"></i></div></div></div>`; 3155 forloop.next(); 3156 } 3157 html += `</div>`; 3158 } 3159 html += `<div class="elAddToCartButtonsWrapper"><div data-page-element="Button/V1" class="elBTN elAddToCartAddToCartButton i
3159d-Button/V1`; 3160 if (button_layout_size == "xs") { 3161 html += ` elAddToCartButtonExtraSmall`; 3162 } 3163 if (button_layout_size == "s") { 3164 html += ` elAddToCartButtonSmall`; 3165 } 3166 if (button_layout_size == "m") { 3167 html += ` elAddToCartButtonMedium`; 3168 } 3169 if (button_layout_size == "l") { 3170 html += ` elAddToCartButtonLarge`; 3171 } 3172 if (button_layout_size == "xl") { 3173 html += ` elAddToCartButtonExtraLarge`; 3174 } 3175 html += `" data-liquid-replace="item">`; 3176 const label_key = "addtocart"; 3177 const label_key_slice = "addtoc"; 3178 let data_content_key = ""; 3179 data_content_key = "addtocart"; 3180 html += `<a target="_self" href="#add-to-cart" class="elButton" aria-label="" data-disabled="false" data-show-button-ids="" data-hide-button-ids="" data-on-submit-go-to="" data-param-submittingText="Submitting..." data-content="" data-style-guide-button="" rel="noopener"><span class="elButtonMain"><i class="fas fa-spinner fa-spin elButtonSpinner elButtonText"></i><span class="elButtonMainText elButtonText">${primary_text}</span></span><span class="elButtonSub"></span></a></div></div></div>`; 3181 } 3182 this.replaceContent(html); 3183 if (initializeChildrenInstances) { 3184 const scopeToYggRender = this.element.querySelectorAll("[ygg-render]").length > 0; 3185 const options = { scopeToYggRender }; 3186 CF2Component.hydrateTree(this.element, options); 3187 } 3188 } 3189 }; 3190 registerComponent("AddToCart", AddToCart); 3191 window["AddToCart"] = AddToCart; 3192 } 3193}); 3194
3195// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/store-search-products.ts 3196var StoreSearchProducts; 3197var init_store_search_products = __esm({ 3198 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/store-search-products.ts"() { 3199 init_define_process(); 3200 init_runtime(); 3201 StoreSearchProducts = class extends CF2Component { 3202 constructor(el, runtimeSel) { 3203 super(el, runtimeSel); 3204 } 3205 mount() { 3206 } 3207 remove() { 3208 this.element.innerHTML = ""; 3209 } 3210 render(initializeChildrenInstances = false) { 3211 const is_server = true; 3212 const selected_products = this.selected_products ?? null; 3213 let html = ""; 3214 { 3215 const c0 = selected_products; 3216 const fl1 = new CF2ForloopDrop(c0.length); 3217 for (const product of c0) { 3218 const forloop = fl1; 3219 const default_variant = product?.default_variant ?? "{}"; 3220 const image = product?.image ?? default_variant.image ?? "/editor/editor-demo-image-placeholder.svg"; 3221 const name = product?.name ?? default_variant.name; 3222 const price = product?.price ?? default_variant.price; 3223 html += `<div class="elStoreSearchProductCard">`; 3224 if (image) { 3225 html += `<a class="elStoreSearchImageWrapper" href="${product?.url}"><div data-page-element="Image/V2" class="elImageWrapper de-image-block id-Image/V2`; 3226 if (CF2Blank(image) && CF2Blank(null) && true) { 3227 html += ` forceHide`; 3228 } 3229 html += `" data-liquid-replace="item">`; 3230 if (image || !CF2Blank(null)) { 3231 html += `<img class="elImage" src="${image ?? null}" data-lazy-loading="true" data-lazy-loading="true"/>`; 3232 } else if (false) { 3233 html += `<div class="image-placeholder" title=""><span class="image-placeholder-header"></span></div>`; 3234 } 3235 html += `</div></a>`; 3236 } 3237 html += `<div class="elStoreSearchProductCardInfo"><a href="${product?.url}" class="elStoreSearchProductCardName">${name}</a><span class="elStoreSearchProductCardPrice">${price}</span></div></div>`; 3238 forloop.next(); 3239 } 3240 } 3241 this.replaceContent(html); 3242 if (initializeChildrenInstances) { 3243 const scopeToYggRender = this.element.querySelectorAll("[ygg-render]").length > 0; 3244 const options = { scopeToYggRender }; 3245 CF2Component.hydrateTree(this.element, options); 3246 } 3247 } 3248 }; 3249 registerComponent("StoreSearchProducts", StoreSearchProducts); 3250 window["StoreSearchProducts"] = StoreSearchProducts; 3251 } 3252}); 3253
3254// projects/lib/packages/yggdrasil-blueprints/src/Elements/Store/Search/storeSearch.ts 3255var allProductsById, productSearchFetcher, fetchProducts, handleSearchResults, searchProducts, debounceHandler, mountComponent2, getProductsElementComponent, updateProducts, showModal, productsReady, hideModal, showSearchProducts, hideProducts, hideTitle, showTitle, showResultsNotFound, hideResultsNotFound, showLoading, hideLoading; 3256var init_storeSearch = __esm({ 3257 "projects/lib/packages/yggdrasil-blueprints/src/Elements/Store/Search/storeSearch.ts"() { 3258 init_define_process(); 3259 init_general(); 3260 init_fetcher(); 3261 allProductsById = {}; 3262 fetchProducts = (component, searchQuery) => { 3263 if (productSearchFetcher) { 3264 productSearchFetcher.abort(); 3265 } 3266 const url = new URL("/products/search", window.location.origin); 3267 url.searchParams.set("q", searchQuery); 3268 productSearchFetcher = new Fetcher(); 3269 return productSearchFetcher.fetch( 3270 url.toString(), 3271 { 3272 headers: { "Content-Type": "application/json" } 3273 }, 3274 { retries: 3, shouldCaptureServerError: true } 3275 ).then((res) => { 3276 if (res instanceof Response && res.ok) { 3277 return res.json(); 3278 } 3279 throw new Error("Search request failed"); 3280 }).then((json) => { 3281 const products = json.products; 3282 if (!products) return; 3283 handleSearchResults(component, products, searchQuery); 3284 }).catch((error) => { 3285 if (error === MANUALLY_ABORTED) { 3286 return; 3287 } 3288 console.error("Product search error:", error); 3289 }).finally(() => { 3290 productSearchFetcher = null; 3291 hideLoading(component); 3292 }); 3293 }; 3294 handleSearchResults = (component, products, searchQuery) => { 3295 hideLoading(component); 3296 if (products.length > 0) { 3297 updateProducts(component, products); 3298 hideTitle(component); 3299 showSearchProducts(component); 3300 hideResultsNotFound(component); 3301 } else { 3302 hideProducts(component); 3303 hideTitle(component); 3304 showResultsNotFound(component, searchQuery); 3305 } 3306 }; 3307 searchProducts = (search, component) => { 3308 showLoading(component); 3309 fetchProducts(component, search); 3310 }; 3311 debounceHandler = debounce( 3312 ([evt, component]) => searchProducts(evt.target.value, component), 3313 500 3314 ); 3315 mountComponent2 = (component) => { 3316 showTitle(component); 3317 productsReady(component); 3318 const searchIcon = component.element.querySelector('[href="#open-store-search"]'); 3319 searchIcon.addEventListener("click", () => showModal(component)); 3320 const searchElement = component.element.querySelector('[name="store-search"]'); 3321 searchElement.addEventListener("input", (evt) => debounceHandler(evt, component)); 3322 searchElement.addEventListener("focus", (evt) => debounceHandler(evt, component)); 3323 const modal = component.getComponent("Modal/V1"); 3324 modal.element.addEventListener("click", () => { 3325 hideModal(component); 3326 }); 3327 component.element.querySelector(".elStoreSearch").addEventListener("click", (evt) => { 3328 evt.stopPropagation(); 3329 }); 3330 component.element.querySelectorAll(".elModalClose").forEach( 3331 (elem) => elem.addEventListener("click", () => { 3332 hideModal(component); 3333 }) 3334 ); 3335 document.addEventListener("keydown", (evt) => { 3336 if (evt.key === "Escape") hideModal(component); 3337 }); 3338 }; 3339 getProductsElementComponent = (component) => { 3340 return component.getComponent("StoreSearchProducts"); 3341 }; 3342 updateProducts = (component, products) => { 3343 ; 3344 getProductsElementComponent(component).selected_products = products; 3345 getProductsElementComponent(component).render(); 3346 }; 3347 showModal = (component) => { 3348 document.documentElement.classList.add("hide-page-scroll"); 3349 component.getComponent("Modal/V1").element.style.display = "flex"; 3350 component.element.querySelector(".elStoreSearch").setAttribute("data-animation-state", "running"); 3351 component.element.querySelector('[name="store-search"]').focus(); 3352 }; 3353 productsReady = (component) => { 3354 updateProducts(component, Object.values(allProductsById).slice(0, 6)); 3355 getProductsElementComponent(component).element.classList.remove("forceHide"); 3356 component.element.querySelector(".elStoreSearchTitle").classList.remove("forceHide"); 3357 component.element.querySelector('[name="store-search"]').disabled = false;
3358 component.element.querySelector(".elStoreSearchLoading").classList.add("forceHide"); 3359 }; 3360 hideModal = (component) => { 3361 document.documentElement.classList.remove("hide-page-scroll"); 3362 component.getComponent("Modal/V1").element.style.display = "none"; 3363 }; 3364 showSearchProducts = (component) => { 3365 getProductsElementComponent(component).element.classList.remove("forceHide"); 3366 }; 3367 hideProducts = (component) => { 3368 getProductsElementComponent(component).element.classList.add("forceHide"); 3369 }; 3370 hideTitle = (component) => { 3371 component.element.querySelector(".elStoreSearchTitle").classList.add("forceHide"); 3372 }; 3373 showTitle = (component) => { 3374 component.element.querySelector(".elStoreSearchTitle").classList.remove("forceHide"); 3375 }; 3376 showResultsNotFound = (component, text) => { 3377 const [split1, split2] = component.not_found_text.split("{search}"); 3378 component.element.querySelector(".elStoreSearchResultsNotFound").innerHTML = split1 + text + split2; 3379 component.element.querySelector(".elStoreSearchResultsNotFound").classList.remove("forceHide"); 3380 }; 3381 hideResultsNotFound = (component) => { 3382 component.element.querySelector(".elStoreSearchResultsNotFound").classList.add("forceHide"); 3383 }; 3384 showLoading = (component) => { 3385 component.element.querySelector(".elStoreSearchLoading").classList.remove("forceHide"); 3386 }; 3387 hideLoading = (component) => { 3388 component.element.querySelector(".elStoreSearchLoading").classList.add("forceHide"); 3389 }; 3390 } 3391}); 3392
3393// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/store-search.ts 3394var StoreSearch; 3395var init_store_search = __esm({ 3396 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/store-search.ts"() { 3397 init_define_process(); 3398 init_modal_v1(); 3399 init_store_search_products(); 3400 init_storeSearch(); 3401 init_runtime(); 3402 StoreSearch = class extends CF2Component { 3403 constructor(el, runtimeSel) { 3404 super(el, runtimeSel); 3405 } 3406 mount() { 3407 mountComponent2(this); 3408 } 3409 }; 3410 registerComponent("StoreSearch", StoreSearch); 3411 window["StoreSearch"] = StoreSearch; 3412 } 3413}); 3414
3415// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/accordion-v1.ts 3416var AccordionV1; 3417var init_accordion_v1 = __esm({ 3418 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/accordion-v1.ts"() { 3419 init_define_process(); 3420 init_runtime(); 3421 AccordionV1 = class extends CF2Component { 3422 constructor(el, runtimeSel) { 3423 super(el, runtimeSel); 3424 } 3425 mount() { 3426 const allAccordionElements = this.element.querySelector(".elAccordionWrapper").childNodes; 3427 const bodySelector = ".elAccordionItemBody"; 3428 const openClass = "elAccordionItemOpen"; 3429 const closeClass = "elAccordionItemClosing"; 3430 allAccordionElements.forEach((accordion) => { 3431 const header = accordion.querySelector(".elAccordionItemHeader"); 3432 const body = accordion.querySelector(bodySelector); 3433 header.addEventListener("click", () => { 3434 const isOpen = accordion.classList.contains(openClass); 3435 if (isOpen) { 3436 accordion.classList.add(closeClass); 3437 $(body).slideUp(300, () => { 3438 accordion.classList.remove(openClass); 3439 accordion.classList.remove(closeClass); 3440 }); 3441 } else { 3442 accordion.classList.add(openClass); 3443 $(body).slideDown(300); 3444 } 3445 allAccordionElements.forEach((otherAccordion) => { 3446 if (otherAccordion === accordion) return; 3447 const body2 = otherAccordion.querySelector(bodySelector); 3448 otherAccordion.classList.add(closeClass);
3449 $(body2).slideUp(300, () => { 3450 otherAccordion.classList.remove(openClass); 3451 otherAccordion.classList.remove(closeClass); 3452 }); 3453 }); 3454 }); 3455 }); 3456 } 3457 }; 3458 registerComponent("Accordion/V1", AccordionV1); 3459 window["AccordionV1"] = AccordionV1; 3460 } 3461}); 3462
3463// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/checkout-product-image-carousel-v1.ts 3464var CheckoutProductImageCarouselV1; 3465var init_checkout_product_image_carousel_v1 = __esm({ 3466 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/checkout-product-image-carousel-v1.ts"() { 3467 init_define_process(); 3468 init_runtime(); 3469 CheckoutProductImageCarouselV1 = class extends CF2Component { 3470 constructor(el, runtimeSel) { 3471 super(el, runtimeSel); 3472 } 3473 selectProduct(productId, variantId) { 3474 const changedProduct = productId != this.currentProduct?.id; 3475 if (changedProduct) { 3476 this.currentVariantId = variantId; 3477 this.currentProduct = globalResourceData.productsById[productId]; 3478 this.render(); 3479 this.calculateTotalThumbnails(); 3480 this.mountSlider(); 3481 this.scrollToVariant(true); 3482 } 3483 const changedVariant = variantId != this.currentVariantId; 3484 if (changedVariant) { 3485 this.currentVariantId = variantId; 3486 this.scrollToVariant(changedProduct); 3487 } 3488 } 3489 initialize() { 3490 document.addEventListener("ProductCarousel:Update", (evt) => { 3491 const { productId, variantId } = evt.detail; 3492 this.selectProduct(productId, variantId); 3493 }); 3494 } 3495 // The sliders have to be mounted on load, not only when a ProductCarousel:Update 3496 // arrives. That event is dispatched exclusively by CheckoutProductSelect/V2 and 3497 // AddToCart, so a page carrying the carousel without one of those elements (a 3498 // plain sales page, for example) never mounted Swiper at all: the thumbnail strip 3499 // fell back to Swiper's own 100%-wide .swiper-slide rule, so only the first 3500 // thumbnail was visible and it was stretched across the whole strip. The editor 3501 // hides this because it does not hydrate CF2 components, and lays the strip out 3502 // with the editor-only editor-styles macro instead - hence thumbnails that show 3503 // in the builder but not on preview or live (ENG-7465). 3504 mount() { 3505 this.calculateTotalThumbnails(); 3506 this.mountSlider(); 3507 } 3508 calculateTotalThumbnails() { 3509 this.totalImages = this.element.querySelectorAll(".slider-nav .swiper-slide").length; 3510 } 3511 scrollToVariant(disableAnimation = false) { 3512 const variantImages = this.element.querySelectorAll(`.slider-nav [data-variant-id="${this.currentVariantId}"]`); 3513 const productImages = this.element.querySelectorAll(".slider-nav .swiper-slide:not([data-variant-id])"); 3514 const itemImages = variantImages.length ? variantImages : productImages; 3515 if (itemImages.length) { 3516 const itemPositions = [...itemImages].map((item) => item.getAttribute("data-image-position")); 3517 const firstPosition = itemPositions[0]; 3518 const lastPosition = itemPositions[itemPositions.length - 1]; 3519 const speed = disableAnimation ? 0 : void 0; 3520 if (this.swiperNav) { 3521 this.swiperNav.setProgress(firstPosition / (this.totalImages - this.numberOfThumbnails), speed); 3522 } 3523 this.swiper.slideTo(firstPosition, speed); 3524 } 3525 } 3526 // Destroys with cleanStyles = false on purpose: selectProduct() re-renders the 3527 // element before re-mounting, so by the time this runs the instances point at 3528 // detached nodes and there is nothing worth restoring styles on. 3529 destroySliders() { 3530 this.swiper?.destroy(true, false); 3531 this.swiper = null; 3532 this.swiperNav?.destroy(true, false); 3533 this.swiperNav = null; 3534 } 3535 mountSlider() { 3536 const mainSliderEl = this.element.querySelector(".slider-main"); 3537 const navSliderEl = this.element.querySelector(".slider-nav"); 3538 const hasThumbnails = !!navSliderEl; 3539 const hasNextPrevButtons = !!this.element.querySelector(".swiper-button-next, .swiper-button-prev"); 3540 this.destroySliders(); 3541 if (!mainSliderEl) return; 3542 if (hasThumbnails) { 3543 this.swiperNav = new Swiper(navSliderEl, { 3544 spaceBetween: this.spaceBetweenThumbnails, 3545 slidesPerView: this.numberOfThumbnails, 3546 freeMode: true, 3547 watchSlidesProgress: true, 3548 mousewheel: true, 3549 scrollbar: { 3550 // The scrollbar is a sibling of .slider-nav rather than a descendant, so 3551 // Swiper resolves a selector string here against the document, not this 3552 // carousel. Harmless while only one carousel was ever mounted at a time; 3553 // now that every carousel mounts on load, two on the same page would both 3554 // bind to the first match. Pass this element's own node instead. 3555 el: this.element.querySelector(".swiper-scrollbar"), 3556 draggable: true 3557 } 3558 }); 3559 } 3560 this.swiper = new Swiper(mainSliderEl, { 3561 spaceBetween: 1, 3562 loop: true, 3563 ...hasNextPrevButtons ? { 3564 navigation: { 3565 nextEl: ".swiper-button-next", 3566 prevEl: ".swiper-button-prev" 3567 } 3568 } : {}, 3569 ...hasThumbnails ? { 3570 thumbs: { 3571 swiper: this.swiperNav 3572 } 3573 } : {} 3574 }); 3575 } 3576 remove() { 3577 this.element.innerHTML = ""; 3578 } 3579 render(initializeChildrenInstances = false) { 3580 const is_server = true; 3581 const currentProduct = this.currentProduct ?? null; 3582 const numberOfThumbnails = this.numberOfThumbnails ?? null; 3583 const spaceBetweenThumbnails = this.spaceBetweenThumbnails ?? null; 3584 const showThumbnails = this.element.getAttribute("data-param-showThumbnails"); 3585 const linkedCheckoutId = this.element.getAttribute("data-param-linkedCheckoutId"); 3586 let html = ""; 3587 { 3588 let assignedProduct = currentProduct; 3589 html += `<div class="elProductImageCarouselOuterFrame"></div>`; 3590 const is_editor = false;
3591 let warning = ""; 3592 if (CF2Blank(assignedProduct)) { 3593 assignedProduct = globalResourceData?.productsWithNoBump?.[0]; 3594 } 3595 let imagePosition = 0; 3596 const variantImages = assignedProduct?.variants.map((i) => i.images).flat(); 3597 const allImages = assignedProduct?.images.concat(variantImages).filter((v) => v != null && v != void 0); 3598 const totalImages = allImages?.length ?? 0; 3599 html += `<div style="--widget-tooltip-message-bottom:0px;--number-of-thumbnails:${numberOfThumbnails};--space-between-thumbnails:${spaceBetweenThumbnails};--total-images:${totalImages};" class="elCheckoutProductImageCarouselContainer" data-widget-tooltip-message="">`; 3600 if (totalImages > 0) { 3601 html += `<div class="slider-main-wrapper"><div class="elProductCarouselMainImageOuterFrame"></div><div class="swiper slider-main"><div class="swiper-wrapper">`; 3602 imagePosition = 0; 3603 if (assignedProduct?.images?.length > 0) { 3604 const c0 = assignedProduct.images; 3605 const fl1 = new CF2ForloopDrop(c0.length); 3606 for (const imageUrl of c0) { 3607 const forloop = fl1; 3608 html += `<div class="swiper-slide`; 3609 if (imagePosition == 0 && false) { 3610 html += ` swiper-slide-thumb-active`; 3611 } 3612 html += `" data-image-position="${imagePosition}"><img src="${imageUrl}"/></div>`; 3613 imagePosition = imagePosition + 1; 3614 forloop.next(); 3615 } 3616 } 3617 const c2 = assignedProduct.variants; 3618 const fl3 = new CF2ForloopDrop(c2.length); 3619 for (const variant of c2) { 3620 const forloop = fl3; 3621 if (variant?.images?.length > 0) { 3622 const c4 = variant.images; 3623 const fl5 = new CF2ForloopDrop(c4.length); 3624 for (const imageUrl of c4) { 3625 const forloop2 = fl5; 3626 html += `<div class="swiper-slide`; 3627 if (imagePosition == 0 && false) { 3628 html += ` swiper-slide-thumb-active`; 3629 } 3630 html += `" data-image-position="${imagePosition}" data-variant-id="${variant?.id}"><img src="${imageUrl}"/></div>`; 3631 imagePosition = imagePosition + 1; 3632 forloop2.next(); 3633 } 3634 } 3635 forloop.next(); 3636 } 3637 html += `</div>`; 3638 if (totalImages > 1) { 3639 html += `<div class="swiper-button-next"></div>`; 3640 html += `<div class="swiper-button-prev"></div>`; 3641 } 3642 html += `</div></div>`; 3643 if (showThumbnails && totalImages > 1) { 3644 html += `<div class="slider-nav-wrapper"><div class="swiper slider-nav"><div class="swiper-wrapper">`; 3645 imagePosition = 0; 3646 if (assignedProduct?.images?.length > 0) { 3647 const c6 = assignedProduct.images; 3648 const fl7 = new CF2ForloopDrop(c6.length); 3649 for (const imageUrl of c6) { 3650 const forloop = fl7; 3651 html += `<div class="swiper-slide`; 3652 if (imagePosition == 0 && true) { 3653 html += ` swiper-slide-thumb-active`; 3654 } 3655 html += `" data-image-position="${imagePosition}"><img src="${imageUrl}"/></div>`; 3656 imagePosition = imagePosition + 1; 3657 forloop.next(); 3658 } 3659 } 3660 const c8 = assignedProduct.variants; 3661 const fl9 = new CF2ForloopDrop(c8.length); 3662 for (const variant of c8) { 3663 const forloop = fl9; 3664 if (variant?.images?.length > 0) { 3665 const c10 = variant.images; 3666 const fl11 = new CF2ForloopDrop(c10.length); 3667 for (const imageUrl of c10) { 3668 const forloop2 = fl11; 3669 html += `<div class="swiper-slide`; 3670 if (imagePosition == 0 && true) { 3671 html += ` swiper-slide-thumb-active`; 3672 } 3673 html += `" data-image-position="${imagePosition}" data-variant-id="${variant?.id}"><img src="${imageUrl}"/></div>`; 3674 imagePosition = imagePosition + 1; 3675 forloop2.next(); 3676 } 3677 } 3678 forloop.next(); 3679 } 3680 html += `</div></div><div class="swiper-scrollbar swiper-scrollbar-horizontal"></div></div>`; 3681 } 3682 } 3683 html += `</div>`; 3684 } 3685 this.replaceContent(html); 3686 if (initializeChildrenInstances) { 3687 const scopeToYggRender = this.element.querySelectorAll("[ygg-render]").length > 0; 3688 const options = { scopeToYggRender }; 3689 CF2Component.hydrateTree(this.element, options); 3690 } 3691 } 3692 }; 3693 registerComponent("CheckoutProductImageCarousel/V1", CheckoutProductImageCarouselV1); 3694 window["CheckoutProductImageCarouselV1"] = CheckoutProductImageCarouselV1; 3695 } 3696}); 3697
3698// projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/sharedModules.ts 3699var sharedModules_exports = {}; 3700var init_sharedModules = __esm({ 3701 "projects/lib/packages/yggdrasil-blueprints/__generated__/blueprints/sharedModules.ts"() { 3702 init_define_process(); 3703 init_content_node(); 3704 init_modal_v1(); 3705 init_modal_sidebar_v1(); 3706 init_modal_container_v1(); 3707 init_select_box_v2(); 3708 init_checkbox_v1(); 3709 init_input_v1(); 3710 init_radio_v1(); 3711 init_text_area_v1(); 3712 init_add_to_cart(); 3713 init_store_search_products(); 3714 init_store_search(); 3715 init_accordion_v1(); 3716 init_checkout_product_image_carousel_v1(); 3717 init_survey_image_option_v1(); 3718 } 3719}); 3720
3721// projects/user_pages/app/packs/user_pages.js 3722init_define_process(); 3723require_lander(); 3724init_lander_styles(); 3725init_sharedModules(); 3726//# sourceMappingURL=user_pages-T4PSV4XN.js.map
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.