https://www.jayjeffers.com/dyad/wp-content/mu-plugins/dyad-compliance/assets/compliance.js?ver=0.1.0
1(function () { 2 "use strict"; 3 4 var config = window.DyadComplianceConfig || {}; 5 var loadedGa = false; 6 var NOTICE_CLOSE_MS = 350; 7 var consentLevel = String(config.consentLevel || "us_opt_out"); 8 var footerMode = false; 9 var footerSelector = "footer, #colophon, [role='contentinfo'], .site-footer, .footer"; 10 var footerPositionWasOverridden = false; 11 var footerPositionElement = null; 12 var footerPositionOriginalValue = ""; 13 14 function getFooterElement() { 15 return document.querySelector(footerSelector); 16 } 17 18 function getActivePageContainer(preferredContainer) { 19 if (preferredContainer && preferredContainer.nodeType === 1) { 20 return preferredContainer; 21 } 22 23 var visibleBarbaContainer = document.querySelector("[data-barba='container']:not(.hidden)"); 24 if (visibleBarbaContainer) { 25 return visibleBarbaContainer; 26 } 27 28 return document.getElementById("primary-container"); 29 } 30 31 function normalizePageTitle(title) { 32 var rawTitle = String(title || ""); 33 var firstSegment = rawTitle.split("|")[0].split("-")[0].split("â")[0].trim(); 34 35 return firstSegment.toLowerCase(); 36 } 37 38 function getCurrentPageTitle(preferredContainer) { 39 var container = getActivePageContainer(preferredContainer); 40 if (container) { 41 var containerTitle = String(container.getAttribute("data-title") || "").trim(); 42 if (containerTitle) { 43 return containerTitle; 44 } 45 } 46 47 return String(document.title || "").trim(); 48 } 49 50 function shouldStayFixedForCurrentPage(preferredContainer) { 51 var container = getActivePageContainer(preferredContainer); 52 var hasBarba = !!window.barba; 53 54 if (hasBarba && container) { 55 var namespace = String(container.getAttribute("data-barba-namespace") || "").toLowerCase(); 56 if (namespace === "home-page") { 57 return true; 58 } 59 60 var title = normalizePageTitle(getCurrentPageTitle(container)); 61 if (title === "contact" || title === "inquire") { 62 return true; 63 } 64 65 return false; 66 } 67 68 if (document.body.classList.contains("home") || document.body.classList.contains("front-page")) { 69 return true; 70 } 71 72 if (document.body.classList.contains("contact") || document.body.classList.contains("inquire")) { 73 return true; 74 } 75 76 return false; 77 } 78 79 function setFooterPositioning(footer, enabled) { 80 if (enabled) { 81 if (!footer) { 82 return; 83 } 84 85 if (footerPositionWasOverridden && footerPositionElement && footerPositionElement !== footer) { 86 footerPositionElement.style.position = footerPositionOriginalValue; 87 footerPositionOriginalValue = ""; 88 footerPositionWasOverridden = false; 89 footerPositionElement = null; 90 } 91 92 var computedPosition = window.getComputedStyle(footer).position; 93 if (computedPosition === "static" && !footerPositionWasOverridden) { 94 footerPositionOriginalValue = footer.style.position || ""; 95 footer.style.position = "relative"; 96 footerPositionWasOverridden = true; 97 footerPositionElement = footer; 98 } 99 return; 100 } 101 102 if (footerPositionWasOverridden) { 103 if (footerPositionElement) { 104 footerPositionElement.style.position = footerPositionOriginalValue; 105 } 106 footerPositionOriginalValue = ""; 107 footerPositionWasOverridden = false; 108 footerPositionElement = null; 109 } 110 } 111 112 function moveRootToFooter(root, footer) { 113 if (!root || !footer) { 114 return; 115 } 116 117 if (root.parentNode !== footer) { 118 footer.appendChild(root); 119 } 120 root.classList.add("dyad-compliance-root--footer"); 121 } 122 123 function moveRootToBody(root) { 124 if (!root) { 125 return; 126 } 127 128 if (root.parentNode !== document.body) { 129 document.body.appendChild(root); 130 } 131 root.style.removeProperty("--dyad-footer-toggle-color"); 132 root.classList.remove("dyad-compliance-root--footer"); 133 } 134 135 function syncFooterToggleColor(preferredContainer) { 136 var root = document.getElementById("dyad-compliance-root"); 137 if (!root || !root.classList.contains("dyad-compliance-root--footer")) { 138 return; 139 } 140 141 var footer = getFooterElement(); 142 if (!footer) { 143 root.style.removeProperty("--dyad-footer-toggle-color"); 144 return; 145 } 146 147 var footerColor = window.getComputedStyle(footer).color || ""; 148 if (footerColor) { 149 root.style.setProperty("--dyad-footer-toggle-color", footerColor); 150 } else { 151 root.style.removeProperty("--dyad-footer-toggle-color"); 152 } 153 } 154 155 function updateFooterPlacement(preferredContainer) { 156 var root = document.getElementById("dyad-compliance-root"); 157 if (!root) { 158 return; 159 } 160 161 var footer = getFooterElement(); 162 var useFixedMode = shouldStayFixedForCurrentPage(preferredContainer) || !footer; 163 164 if (useFixedMode) { 165 setFooterPositioning(null, false); 166 moveRootToBody(root); 167 footerMode = false;
168 return; 169 } 170 171 setFooterPositioning(footer, true); 172 moveRootToFooter(root, footer); 173 footerMode = true; 174 } 175 176 function registerPageChangeListener() { 177 if (window.DyadCompliancePageChangeListenerRegistered) { 178 return; 179 } 180 181 window.DyadCompliancePageChangeListenerRegistered = true; 182 183 window.addEventListener("dyad:page-change", function (event) { 184 var pageContainer = event && event.detail ? event.detail.newContainer : null; 185 if (window.barba) { 186 closePopupOnPageChange(); 187 } 188 updateFooterPlacement(pageContainer); 189 }); 190 } 191 192 function shouldKeepPopupOpenOnPageChange() { 193 return consentLevel === "gdpr_opt_in" && String(window.DyadComplianceState || "unknown") === "unknown"; 194 } 195 196 function closePopupOnPageChange() { 197 if (shouldKeepPopupOpenOnPageChange()) { 198 return; 199 } 200 201 var popup = document.getElementById("dyad-compliance-popup"); 202 if (popup) { 203 popup.hidden = true; 204 } 205 } 206 207 function registerBarbaPageChangeHook() { 208 if (window.DyadComplianceBarbaHookRegistered) { 209 return; 210 } 211 212 if (!window.barba || !window.barba.hooks) { 213 return; 214 } 215 216 var hook = null;
217 if (typeof window.barba.hooks.afterEnter === "function") { 218 hook = window.barba.hooks.afterEnter; 219 } else if (typeof window.barba.hooks.after === "function") { 220 hook = window.barba.hooks.after; 221 } 222 223 if (!hook) { 224 return; 225 } 226 227 window.DyadComplianceBarbaHookRegistered = true; 228 hook(function (data) { 229 var pageContainer = data && data.next ? data.next.container : null; 230 closePopupOnPageChange(); 231 updateFooterPlacement(pageContainer); 232 window.requestAnimationFrame(function () { 233 syncFooterToggleColor(pageContainer); 234 }); 235 }); 236 } 237 238 function setNoticeExpanded(expanded, isClosing) { 239 var notice = document.getElementById("dyad-compliance-notice"); 240 if (!notice) { 241 return; 242 } 243 244 var toggle = notice.querySelector(".dyad-consent-toggle"); 245 if (toggle) { 246 toggle.setAttribute("aria-expanded", expanded ? "true" : "false"); 247 } 248 249 if (expanded) { 250 notice.classList.remove("is-collapsing"); 251 notice.classList.add("is-expanded"); 252 updateNoticeDetailHeight(); 253 return; 254 } 255 256 if (isClosing) { 257 notice.classList.add("is-collapsing"); 258 } 259 notice.classList.remove("is-expanded"); 260 261 if (isClosing) { 262 window.setTimeout(function () { 263 notice.classList.remove("is-collapsing"); 264 }, NOTICE_CLOSE_MS); 265 } 266 } 267 268 function updateNoticeDetailHeight() { 269 var notice = document.getElementById("dyad-compliance-notice"); 270 if (!notice) { 271 return; 272 } 273 274 var details = notice.querySelector(".dyad-consent-details"); 275 if (!details) { 276 return; 277 } 278 279 // Measure actual scrollHeight and apply via CSS custom property for dynamic animation 280 var height = Math.ceil(details.scrollHeight); 281 notice.style.setProperty("--dyad-detail-max-height", height + "px"); 282 } 283 284 function registerNoticeResizeObserver() { 285 var notice = document.getElementById("dyad-compliance-notice"); 286 if (!notice) { 287 return; 288 } 289 290 if (!window.ResizeObserver) { 291 return; 292 } 293 294 var details = notice.querySelector(".dyad-consent-details"); 295 if (!details) { 296 return; 297 } 298 299 var observer = new window.ResizeObserver(function () { 300 if (notice.classList.contains("is-expanded")) { 301 updateNoticeDetailHeight(); 302 } 303 }); 304 observer.observe(details); 305 } 306 307 function getUsNoticeCopyForState(state, defaultCopy) { 308 if (state === "denied" || state === "gpc_denied") { 309 if (defaultCopy) { 310 return "You are no longer being tracked. " + defaultCopy; 311 } 312 return "You are no longer being tracked."; 313 } 314 return defaultCopy; 315 } 316 317 function getGdprNoticeCopyForState(state, defaultCopy) { 318 if (state === "denied" || state === "gpc_denied") { 319 if (defaultCopy) { 320 return "You have declined analytics cookies. " + defaultCopy; 321 } 322 return "You have declined analytics cookies."; 323 } 324 325 if (state === "granted") { 326 if (defaultCopy) { 327 return "You have accepted analytics cookies. " + defaultCopy; 328 } 329 return "You have accepted analytics cookies."; 330 } 331 332 return defaultCopy; 333 } 334 335 function log() { 336 if (!config.diagnosticsMode) { 337 return; 338 } 339 if (window.console && typeof window.console.log === "function") { 340 window.console.log.apply(window.console, arguments); 341 } 342 } 343 344 function getCookie(name) { 345 var escaped = name.replace(/[-.+*]/g, "\\$&"); 346 var match = document.cookie.match(new RegExp("(?:^|; )" + escaped + "=([^;]*)")); 347 return match ? decodeURIComponent(match[1]) : ""; 348 } 349 350 function setCookie(name, value, days) { 351 var maxAge = Math.max(1, Number(days || 365)) * 24 * 60 * 60; 352 var secure = window.location.protocol === "https:" ? "; Secure" : ""; 353 document.cookie = name + "=" + encodeURIComponent(value) + "; path=/; max-age=" + maxAge + "; SameSite=Lax" + secure; 354 } 355 356 function getLocal(name) { 357 try { 358 return window.localStorage.getItem(name) || ""; 359 } catch (error) { 360 return ""; 361 } 362 } 363 364 function setLocal(name, value) { 365 try { 366 window.localStorage.setItem(name, value); 367 } catch (error) { 368 // no-op 369 } 370 } 371 372 function shouldUseCookie() { 373 return config.consentStateStorageMode === "cookie_only" || config.consentStateStorageMode === "cookie_and_local_storage"; 374 } 375 376 function shouldUseLocalStorage() { 377 return config.consentStateStorageMode === "local_storage_only" || config.consentStateStorageMode === "cookie_and_local_storage"; 378 } 379 380 function readStoredState() { 381 var cookieName = config.consentCookieName || "site_consent_pref"; 382 var state = ""; 383
384 if (shouldUseCookie()) { 385 state = getCookie(cookieName); 386 } 387 if (!state && shouldUseLocalStorage()) { 388 state = getLocal(cookieName); 389 } 390 if (state === "granted" || state === "denied" || state === "gpc_denied") { 391 return state; 392 } 393 return "unknown"; 394 } 395 396 function persistState(state) { 397 var cookieName = config.consentCookieName || "site_consent_pref"; 398 if (shouldUseCookie()) { 399 setCookie(cookieName, state, Number(config.cookieTtlDays || 365)); 400 } 401 if (shouldUseLocalStorage()) { 402 setLocal(cookieName, state); 403 } 404 } 405 406 function gpcEnabled() { 407 if (config.gpcServerDetected) { 408 return true; 409 } 410 return navigator.globalPrivacyControl === true || navigator.globalPrivacyControl === 1 || navigator.globalPrivacyControl === "1"; 411 } 412 413 function ensureGtagBase() { 414 window.dataLayer = window.dataLayer || []; 415 if (typeof window.gtag !== "function") { 416 window.gtag = function () { 417 window.dataLayer.push(arguments); 418 }; 419 } 420 } 421 422 function setGaDisable(denied) { 423 var id = String(config.ga4MeasurementId || "").trim(); 424 if (!id) { 425 return; 426 } 427 window["ga-disable-" + id] = !!denied; 428 } 429 430 function applyConsentMode(state) { 431 ensureGtagBase(); 432 var analyticsStorage = state === "granted" ? "granted" : "denied"; 433 window.gtag("consent", "default", { 434 analytics_storage: analyticsStorage, 435 ad_storage: "denied", 436 ad_user_data: "denied", 437 ad_personalization: "denied", 438 security_storage: "granted", 439 }); 440 window.gtag("consent", "update", { 441 analytics_storage: analyticsStorage, 442 ad_storage: "denied", 443 ad_user_data: "denied", 444 ad_personalization: "denied", 445 }); 446 } 447 448 function maybeLoadGa4(state) { 449 if (config.useSiteKit) { 450 return; 451 } 452 var gaId = String(config.ga4MeasurementId || "").trim(); 453 if (!gaId || loadedGa || state !== "granted") { 454 return; 455 } 456 457 var script = document.createElement("script"); 458 script.async = true; 459 script.src = "https://www.googletagmanager.com/gtag/js?id=" + encodeURIComponent(gaId); 460 document.head.appendChild(script); 461 462 ensureGtagBase(); 463 window.gtag("js", new Date()); 464 var gaConfig = { 465 send_page_view: true, 466 allow_google_signals: false, 467 allow_ad_personalization_signals: false, 468 }; 469 if (config.enableGa4IpRandomization) { 470 // Best-effort browser-side privacy flag; strict proxy randomization is server-side work. 471 gaConfig.anonymize_ip = true; 472 } 473 window.gtag("config", gaId, gaConfig); 474 loadedGa = true; 475 log("[Dyad Compliance] GA4 loaded in manual mode"); 476 } 477 478 function computeInitialState() { 479 if (consentLevel === "disabled") { 480 return "granted"; 481 } 482 483 if (gpcEnabled()) { 484 return "gpc_denied"; 485 } 486 487 var stored = readStoredState(); 488 if (stored !== "unknown") { 489 return stored; 490 } 491 492 if (consentLevel === "gdpr_opt_in") { 493 return "unknown"; 494 } 495 496 return "granted"; 497 } 498 499 function updateUsNoticeState(state) { 500 var notice = document.getElementById("dyad-compliance-notice"); 501 if (!notice) { 502 return; 503 } 504 505 var copy = notice.querySelector(".dyad-consent-copy"); 506 var optOutButton = document.getElementById("dyad-consent-opt-out"); 507 var reEnableButton = document.getElementById("dyad-consent-re-enable"); 508 var gdprAcceptInlineButton = document.getElementById("dyad-consent-accept-inline"); 509 var gdprDenyInlineButton = document.getElementById("dyad-consent-deny-inline"); 510 var defaultCopy = copy ? String(copy.getAttribute("data-us-copy") || copy.getAttribute("data-default-copy") || "") : ""; 511 512 if (copy) { 513 copy.textContent = getUsNoticeCopyForState(state, defaultCopy); 514 } 515 516 if (gdprAcceptInlineButton) { 517 gdprAcceptInlineButton.hidden = true; 518 } 519 if (gdprDenyInlineButton) { 520 gdprDenyInlineButton.hidden = true; 521 } 522 523 if (state === "denied") { 524 if (optOutButton) { 525 optOutButton.hidden = true; 526 } 527 if (reEnableButton) { 528 reEnableButton.hidden = false; 529 } 530 setNoticeExpanded(true, false); 531 return; 532 } 533 534 if (state === "gpc_denied") { 535 if (optOutButton) { 536 optOutButton.hidden = true; 537 } 538 if (reEnableButton) { 539 reEnableButton.hidden = true; 540 } 541 setNoticeExpanded(true, false); 542 return; 543 } 544 545 if (optOutButton) { 546 optOutButton.hidden = false;
547 } 548 if (reEnableButton) { 549 reEnableButton.hidden = true; 550 } 551 setNoticeExpanded(false, false); 552 } 553 554 function updateGdprNoticeState(state) { 555 var notice = document.getElementById("dyad-compliance-notice"); 556 if (!notice) { 557 return; 558 } 559 560 var copy = notice.querySelector(".dyad-consent-copy"); 561 var optOutButton = document.getElementById("dyad-consent-opt-out"); 562 var reEnableButton = document.getElementById("dyad-consent-re-enable"); 563 var acceptInlineButton = document.getElementById("dyad-consent-accept-inline"); 564 var denyInlineButton = document.getElementById("dyad-consent-deny-inline"); 565 var defaultCopy = copy ? String(copy.getAttribute("data-gdpr-copy") || copy.getAttribute("data-default-copy") || "") : ""; 566 567 if (copy) { 568 copy.textContent = getGdprNoticeCopyForState(state, defaultCopy); 569 } 570 571 if (optOutButton) { 572 optOutButton.hidden = true; 573 } 574 if (reEnableButton) { 575 reEnableButton.hidden = true; 576 } 577 578 if (state === "gpc_denied") { 579 if (acceptInlineButton) { 580 acceptInlineButton.hidden = true; 581 } 582 if (denyInlineButton) { 583 denyInlineButton.hidden = true; 584 } 585 } else { 586 if (acceptInlineButton) { 587 acceptInlineButton.hidden = false; 588 } 589 if (denyInlineButton) { 590 denyInlineButton.hidden = false; 591 } 592 } 593 594 setNoticeExpanded(false, false); 595 } 596 597 function openManager() { 598 var notice = document.getElementById("dyad-compliance-notice"); 599 var popup = document.getElementById("dyad-compliance-popup"); 600 if (consentLevel === "disabled") { 601 return; 602 } 603 604 if (consentLevel === "gdpr_opt_in") { 605 var currentState = String(window.DyadComplianceState || "unknown"); 606 if (currentState === "unknown") { 607 if (popup) { 608 popup.hidden = false; 609 } 610 if (notice) { 611 notice.hidden = true; 612 } 613 } else if (notice) { 614 notice.hidden = false; 615 setNoticeExpanded(true, false); 616 if (popup) { 617 popup.hidden = true; 618 } 619 } 620 } else if (notice) { 621 notice.hidden = false; 622 setNoticeExpanded(true, false); 623 } 624 } 625 626 function closeManager() { 627 var notice = document.getElementById("dyad-compliance-notice"); 628 var popup = document.getElementById("dyad-compliance-popup"); 629 if (notice) { 630 notice.hidden = true; 631 } 632 if (popup) { 633 popup.hidden = true; 634 } 635 } 636 637 function updateUiForState(state) { 638 var notice = document.getElementById("dyad-compliance-notice"); 639 var popup = document.getElementById("dyad-compliance-popup"); 640 var root = document.getElementById("dyad-compliance-root"); 641 642 if (consentLevel === "disabled") { 643 if (notice) { 644 notice.hidden = true; 645 } 646 if (popup) { 647 popup.hidden = true; 648 } 649 if (root) { 650 root.hidden = true; 651 } 652 return; 653 } 654 655 if (root) { 656 root.hidden = false; 657 } 658 659 if (consentLevel === "gdpr_opt_in") { 660 if (popup) { 661 popup.hidden = state !== "unknown"; 662 } 663 if (notice) { 664 notice.hidden = state === "unknown"; 665 if (state !== "unknown") { 666 updateGdprNoticeState(state); 667 } 668 } 669 } else { 670 if (notice) { 671 notice.hidden = false; 672 updateUsNoticeState(state); 673 } 674 if (popup) { 675 popup.hidden = true; 676 } 677 } 678 } 679 680 function applyState(state, persist) { 681 var finalState = state; 682 if (consentLevel !== "disabled" && gpcEnabled()) { 683 finalState = "gpc_denied"; 684 } 685 686 if (persist) { 687 persistState(finalState); 688 } 689 690 setGaDisable(finalState !== "granted"); 691 applyConsentMode(finalState); 692 maybeLoadGa4(finalState); 693 updateUiForState(finalState); 694 log("[Dyad Compliance] state:", finalState); 695 window.DyadComplianceState = finalState; 696 } 697 698 function bindUi() { 699 var denyButton = document.getElementById("dyad-consent-deny"); 700 var acceptButton = document.getElementById("dyad-consent-accept"); 701 var inlineDenyButton = document.getElementById("dyad-consent-deny-inline"); 702 var inlineAcceptButton = document.getElementById("dyad-consent-accept-inline"); 703 var ccpaOptOutButton = document.getElementById("dyad-consent-opt-out"); 704 var reEnableButton = document.getElementById("dyad-consent-re-enable"); 705 var ccpaCloseButton = document.querySelector("#dyad-compliance-notice .ccpa-close"); 706 var ccpaTitleToggle = document.querySelector("#dyad-compliance-notice .dyad-consent-toggle"); 707 708 if (denyButton) { 709 denyButton.addEventListener("click", function () { 710 applyState("denied", true); 711 }); 712 } 713 if (acceptButton) { 714 acceptButton.addEventListener("click", function () { 715 applyState("granted", true); 716 }); 717 } 718 if (inlineDenyButton) { 719 inlineDenyButton.addEventListener("click", function () { 720 applyState("denied", true); 721 }); 722 } 723 if (inlineAcceptButton) { 724 inlineAcceptButton.addEventListener("click", function () { 725 applyState("granted", true); 726 }); 727 } 728 if (ccpaOptOutButton) { 729 ccpaOptOutButton.addEventListener("click", function () { 730 applyState("denied", true); 731 }); 732 } 733 if (reEnableButton) { 734 reEnableButton.addEventListener("click", function () { 735 applyState("granted", true); 736 }); 737 } 738 if (ccpaTitleToggle) { 739 ccpaTitleToggle.addEventListener("click", function () { 740 var notice = document.getElementById("dyad-compliance-notice"); 741 var isExpanded = !!(notice && notice.classList.contains("is-expanded")); 742 setNoticeExpanded(!isExpanded, false); 743 }); 744 } 745 if (ccpaCloseButton) { 746 ccpaCloseButton.addEventListener("click", function () { 747 setNoticeExpanded(false, true); 748 }); 749 } 750 } 751
752 function init() { 753 bindUi(); 754 var initial = computeInitialState(); 755 applyState(initial, consentLevel !== "disabled" && initial !== "unknown"); 756 window.DyadComplianceLevel = consentLevel; 757 registerPageChangeListener(); 758 registerBarbaPageChangeHook(); 759 registerNoticeResizeObserver(); 760 updateFooterPlacement(); 761 syncFooterToggleColor(); 762 window.addEventListener("load", function () { 763 registerBarbaPageChangeHook(); 764 updateFooterPlacement(); 765 syncFooterToggleColor(); 766 }); 767 768 window.addEventListener("dyad:open-privacy-settings", function () { 769 openManager(); 770 }); 771 } 772 773 if (document.readyState === "loading") { 774 document.addEventListener("DOMContentLoaded", init); 775 } else { 776 init(); 777 } 778})();
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.