/** * Includes.js - Handles the inclusion of header and footer files * and applies the correct active states to navigation items */ document.addEventListener('DOMContentLoaded', function() { // Function to include HTML content async function includeHTML(elementId, filePath, callback) { try { const response = await fetch(filePath); if (!response.ok) { throw new Error(`Failed to load ${filePath}: ${response.status} ${response.statusText}`); } const content = await response.text(); document.getElementById(elementId).innerHTML = content; if (callback) callback(); } catch (error) { console.error('Error including HTML:', error); } } // Function to set active navigation item function setActiveNavItem() { const currentPath = window.location.pathname; // Wait for the navigation to be loaded setTimeout(() => { // Remove all active classes first document.querySelectorAll('.main-nav a').forEach(link => { link.classList.remove('active'); }); // Set active class based on current path if (currentPath === '/' || currentPath === '/index.html') { const portfolioLink = document.getElementById('nav-portfolio'); if (portfolioLink) portfolioLink.classList.add('active'); } else if (currentPath.includes('/stories/')) { const storiesLink = document.getElementById('nav-stories'); if (storiesLink) storiesLink.classList.add('active'); // Check for specific story pages if (currentPath.includes('viperwire.html')) { const link = document.getElementById('nav-viperwire'); if (link) link.classList.add('active'); } else if (currentPath.includes('fawe-plotsquared.html')) { const link = document.getElementById('nav-fawe'); if (link) link.classList.add('active'); } else if (currentPath.includes('healthcare-platform.html')) { const link = document.getElementById('nav-healthcare'); if (link) link.classList.add('active'); } else if (currentPath.includes('wordpress-security.html')) { const link = document.getElementById('nav-wordpress'); if (link) link.classList.add('active'); } else if (currentPath.includes('airport-dns.html')) { const link = document.getElementById('nav-airport'); if (link) link.classList.add('active'); } else if (currentPath.includes('nitric-leadership.html')) { const link = document.getElementById('nav-nitric'); if (link) link.classList.add('active'); } else if (currentPath.includes('open-source-success.html')) { const link = document.getElementById('nav-opensource'); if (link) link.classList.add('active'); } } else if (currentPath.includes('/one-pager-tools/')) { const toolsLink = document.getElementById('nav-tools'); if (toolsLink) toolsLink.classList.add('active'); // Check for specific tool pages if (currentPath.includes('csv-tool.html')) { const link = document.getElementById('nav-csv'); if (link) link.classList.add('active'); } } }, 100); // Small delay to ensure the DOM is updated } // Process header and footer placeholders const headerElement = document.getElementById('header-include'); const footerElement = document.getElementById('footer-include'); if (headerElement) { includeHTML('header-include', '/includes/header.html', () => { setActiveNavItem(); setupNavDropdowns(); }); } if (footerElement) { includeHTML('footer-include', '/includes/footer.html'); } // Setup dropdown behavior with delay function setupNavDropdowns() { const dropdowns = document.querySelectorAll('.main-nav .dropdown'); let timeoutId; dropdowns.forEach(dropdown => { // Mouse interactions dropdown.addEventListener('mouseenter', () => { clearTimeout(timeoutId); dropdowns.forEach(d => { if (d !== dropdown) { d.querySelector('.dropdown-content').style.display = 'none'; d.querySelector('.dropdown-content').style.opacity = '0'; d.querySelector('.dropdown-content').style.visibility = 'hidden'; } }); const dropdownContent = dropdown.querySelector('.dropdown-content'); dropdownContent.style.display = 'block'; // Small delay to allow CSS transition to work properly setTimeout(() => { dropdownContent.style.opacity = '1'; dropdownContent.style.visibility = 'visible'; }, 10); }); dropdown.addEventListener('mouseleave', () => { const dropdownContent = dropdown.querySelector('.dropdown-content'); // Add delay before hiding the dropdown timeoutId = setTimeout(() => { dropdownContent.style.opacity = '0'; dropdownContent.style.visibility = 'hidden'; // Wait for transition to complete before changing display setTimeout(() => { if (dropdownContent.style.opacity === '0') { dropdownContent.style.display = 'none'; } }, 200); }, 300); // 300ms delay before starting to close }); // Keyboard interactions const dropdownLink = dropdown.querySelector('a'); dropdownLink.addEventListener('keydown', (e) => { if (e.key === 'Enter' || e.key === ' ' || e.key === 'ArrowDown') { e.preventDefault(); const dropdownContent = dropdown.querySelector('.dropdown-content'); dropdownContent.style.display = 'block'; setTimeout(() => { dropdownContent.style.opacity = '1'; dropdownContent.style.visibility = 'visible'; // Focus the first link in the dropdown const firstLink = dropdownContent.querySelector('a'); if (firstLink) firstLink.focus(); }, 10); } }); // Add keyboard navigation for dropdown items const dropdownLinks = dropdown.querySelectorAll('.dropdown-content a'); dropdownLinks.forEach((link, index) => { link.addEventListener('keydown', (e) => { if (e.key === 'ArrowDown') { e.preventDefault(); const nextLink = dropdownLinks[index + 1] || dropdownLinks[0]; nextLink.focus(); } else if (e.key === 'ArrowUp') { e.preventDefault(); const prevLink = dropdownLinks[index - 1] || dropdownLinks[dropdownLinks.length - 1]; prevLink.focus(); } else if (e.key === 'Escape') { e.preventDefault(); dropdown.querySelector('a').focus(); const dropdownContent = dropdown.querySelector('.dropdown-content'); dropdownContent.style.opacity = '0'; dropdownContent.style.visibility = 'hidden'; setTimeout(() => { dropdownContent.style.display = 'none'; }, 200); } }); }); }); } });