NativeON/aesthetic-haven
0
1class AestheticNavbar extends HTMLElement {2 constructor() {3 super();4 this.menuOpen = false;5 }6 7 connectedCallback() {8 this.attachShadow({ mode: 'open' });9 this.shadowRoot.innerHTML = `10 <style>11 :host {12 display: block;13 width: 100%;14 position: sticky;15 top: 0;16 z-index: 50;17 background: rgba(255, 255, 255, 0.95);18 backdrop-filter: blur(10px);19 box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1);20 }21 22 .navbar-container {23 max-width: 1280px;24 margin: 0 auto;25 padding: 1rem 1.5rem;26 }27 28 .navbar-content {29 display: flex;30 justify-content: space-between;31 align-items: center;32 }33 .logo {34 font-family: 'Playfair Display', serif;35 font-size: 1.5rem;36 font-weight: 500;37 color: #1a202c;38 text-decoration: none;39 display: flex;40 align-items: center;41 gap: 0.5rem;42 }43 44 .logo-image {45 height: 32px;46 width: auto;47 display: inline-block;48 vertical-align: middle;49 }50 51 @media (max-width: 768px) {52 .logo-image {53 height: 28px;54 }55 }56.nav-links {57 display: flex;58 gap: 2rem;59 align-items: center;60 }61 62 .nav-link {63 color: #4a5568;64 text-decoration: none;65 font-weight: 400;66 font-size: 0.95rem;67 transition: color 0.2s;68 position: relative;69 }70 71 .nav-link:hover {72 color: #1a202c;73 }74 75 .nav-link::after {76 content: '';77 position: absolute;78 width: 0;79 height: 1px;80 bottom: -2px;81 left: 0;82 background-color: #1a202c;83 transition: width 0.3s;84 }85 86 .nav-link:hover::after {87 width: 100%;88 }89 90 .nav-icons {91 display: flex;92 gap: 1.5rem;93 align-items: center;94 }95 96 .icon-link {97 color: #4a5568;98 text-decoration: none;99 position: relative;100 display: flex;101 align-items: center;102 justify-content: center;103 width: 24px;104 height: 24px;105 }106 107 .icon-link:hover {108 color: #1a202c;109 }110 111 .cart-count {112 position: absolute;113 top: -6px;114 right: -6px;115 background-color: #1a202c;116 color: white;117 font-size: 0.6rem;118 width: 16px;119 height: 16px;120 border-radius: 50%;121 display: flex;122 align-items: center;123 justify-content: center;124 }125 126 .menu-toggle {127 display: none;128 background: none;129 border: none;130 color: #4a5568;131 cursor: pointer;132 padding: 0.5rem;133 }134 135 @media (max-width: 768px) {136 .nav-links {137 position: fixed;138 top: 70px;139 left: 0;140 right: 0;141 background: white;142 flex-direction: column;143 padding: 2rem;144 gap: 1.5rem;145 box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);146 transform: translateY(-100%);147 opacity: 0;148 transition: transform 0.3s, opacity 0.3s;149 pointer-events: none;150 }151 152 .nav-links.active {153 transform: translateY(0);154 opacity: 1;155 pointer-events: all;156 }157 158 .menu-toggle {159 display: block;160 }161 162 .nav-icons {163 gap: 1rem;164 }165 }166 167 @media (max-width: 640px) {168 .navbar-container {169 padding: 1rem;170 }171 }172 </style>173 174 <nav class="navbar-container">175 <div class="navbar-content">176 <a href="/" class="logo">177 <i data-feather="heart"></i>178 Aesthetic Haven179 </a>180 181 <div class="nav-links" id="mobileMenu">182 <a href="/" class="nav-link">Home</a>183 <a href="/shop.html" class="nav-link">Shop</a>184 <a href="/collections.html" class="nav-link">Collections</a>185 <a href="/about.html" class="nav-link">About</a>186 <a href="/contact.html" class="nav-link">Contact</a>187 </div>188 189 <div class="nav-icons">190 <a href="/search.html" class="icon-link" aria-label="Search">191 <i data-feather="search"></i>192 </a>193 <a href="/account.html" class="icon-link" aria-label="Account">194 <i data-feather="user"></i>195 </a>196 <a href="/cart.html" class="icon-link" aria-label="Cart">197 <i data-feather="shopping-bag"></i>198 <span class="cart-count" data-cart-count>0</span>199 </a>200 <button class="menu-toggle" data-toggle-menu aria-label="Toggle menu">201 <i data-feather="menu"></i>202 </button>203 </div>204 </div>205 </nav>206 `;207 208 // Initialize feather icons in shadow DOM209 setTimeout(() => {210 if (window.feather) {211 window.feather.replace({ 'stroke-width': 1.5 });212 }213 }, 100);214 215 // Add event listeners216 this.shadowRoot.querySelector('[data-toggle-menu]').addEventListener('click', () => this.toggleMenu());217 218 // Close menu when clicking outside on mobile219 document.addEventListener('click', (e) => {220 if (window.innerWidth <= 768 && !this.contains(e.target) && this.menuOpen) {221 this.closeMenu();222 }223 });224 }225 226 toggleMenu() {227 const mobileMenu = this.shadowRoot.getElementById('mobileMenu');228 this.menuOpen = !this.menuOpen;229 230 if (this.menuOpen) {231 mobileMenu.classList.add('active');232 } else {233 mobileMenu.classList.remove('active');234 }235 }236 237 closeMenu() {238 const mobileMenu = this.shadowRoot.getElementById('mobileMenu');239 mobileMenu.classList.remove('active');240 this.menuOpen = false;241 }242}243 244customElements.define('aesthetic-navbar', AestheticNavbar);