1/** 2 * Site Scripts 3 * 4 * Contains native site functionality such as: 5 * - Anchor linking with smooth scroll and highlight effects 6 * - Other site-specific JavaScript utilities 7 * 8 * For external integrations (chatbot, OptinMonster), see external-integrations.js 9 */ 10 11// Generic function to handle anchor linking to specific sections 12function setupAnchorLinking(config) { 13 jQuery(document).ready(function ($) { 14 // Default configuration 15 var settings = $.extend( 16 { 17 targetPage: '', // Path pattern to match (e.g., '/terms-of-use/') 18 headingTexts: [], // Array of text patterns to search for in headings 19 anchorId: '', // ID to assign/look for 20 highlightDuration: 2000, // How long to show highlight effect (ms) 21 scrollOffset: 20, // Additional offset below header 22 scrollDuration: 800, // Scroll animation duration (ms) 23 }, 24 config 25 ); 26 27 // Validate required parameters 28 if (!settings.targetPage || !settings.headingTexts.length || !settings.anchorId) { 29 return; 30 } 31 32 // Check if we're on the target page 33 if (window.location.pathname.includes(settings.targetPage)) { 34 // Look for headings containing any of the specified texts 35 $('h1, h2, h3, h4, h5, h6').each(function () { 36 var headingText = $(this).text().toUpperCase(); 37 var matchFound = false; 38 39 // Check if heading matches any of our search patterns 40 for (var i = 0; i < settings.headingTexts.length; i++) { 41 if (headingText.includes(settings.headingTexts[i].toUpperCase())) { 42 matchFound = true; 43 break; 44 } 45 } 46 47 if (matchFound) { 48 // Add the ID if it doesn't already have one 49 if (!$(this).attr('id')) { 50 $(this).attr('id', settings.anchorId); 51 } 52 53 // If we came here with the hash, scroll to it after a short delay 54 if (window.location.hash === '#' + settings.anchorId) { 55 setTimeout(function () { 56 var $target = $('#' + settings.anchorId); 57 var offset = $target.offset(); 58 if (offset) { 59 // Account for sticky header height 60 var headerHeight = $('#desktop-header').outerHeight() || 0; 61 $('html, body').animate( 62 { 63 scrollTop: offset.top - headerHeight - settings.scrollOffset, 64 }, 65 settings.scrollDuration, 66 function () { 67 // Add a highlight effect 68 $target.addClass('highlight-section'); 69 setTimeout(function () { 70 $target.removeClass('highlight-section'); 71 }, settings.highlightDuration); 72 } 73 ); 74 } 75 }, 100); 76 } 77 78 return false; // Stop searching once found 79 } 80 }); 81 } 82 }); 83} 84 85// Setup eClub terms anchor linking 86setupAnchorLinking({ 87 targetPage: '/terms-of-use/', 88 headingTexts: ['ECLUB TERMS', 'ECLUB TERMS AND CONDITIONS'], 89 anchorId: 'eclub-terms', 90}); 91 92// TDB-E722: Patch UserWay nav tooltips with proper role, id, and aria-describedby. 93// UserWay injects .userway__nav-menu-tooltip into each <nav> but marks it 94// aria-hidden="true", so screen readers never learn the tooltip exists. 95// We add role="tooltip" + a stable id, remove aria-hidden, and add 96// aria-describedby on every link in the same nav pointing to that id. 97(function () { 98 function patchTooltips() { 99 document.querySelectorAll('.userway__nav-menu-tooltip:not([role])').forEach(function (tooltip, i) { 100 var id = 'uw-nav-tooltip-' + i; 101 tooltip.id = id; 102 tooltip.setAttribute('role', 'tooltip'); 103 tooltip.removeAttribute('aria-hidden'); 104 105 var nav = tooltip.closest('nav'); 106 if (!nav) return; 107 nav.querySelectorAll('a').forEach(function (link) { 108 link.setAttribute('aria-describedby', id); 109 }); 110 }); 111 } 112 113 // UserWay loads asynchronously â watch for injection then stop observing. 114 var observer = new MutationObserver(function () { 115 if (document.querySelector('.userway__nav-menu-tooltip:not([role])')) { 116 patchTooltips(); 117 observer.disconnect(); 118 } 119 }); 120 observer.observe(document.body, { childList: true, subtree: true }); 121 122 // Also run immediately in case UserWay already ran before this script. 123 patchTooltips(); 124}());
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.