diff --git a/revati-kadam-portfolio/assets/images/profile.jpg b/revati-kadam-portfolio/assets/images/profile.jpg new file mode 100644 index 0000000..372ae91 Binary files /dev/null and b/revati-kadam-portfolio/assets/images/profile.jpg differ diff --git a/revati-kadam-portfolio/css/style.css b/revati-kadam-portfolio/css/style.css index 2b76e2b..964ef79 100644 --- a/revati-kadam-portfolio/css/style.css +++ b/revati-kadam-portfolio/css/style.css @@ -1,3 +1,5 @@ +@import url('https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:wght@300;400;500;600;700;800&display=swap'); + /* ================= CSS VARIABLES ================= */ :root { --bg: #0f172a; @@ -17,7 +19,7 @@ html { scroll-behavior: smooth; } body { - font-family: 'Segoe UI', sans-serif; + font-family: 'Plus Jakarta Sans', 'Segoe UI', -apple-system, BlinkMacSystemFont, sans-serif; background: var(--bg); color: var(--text); line-height: 1.7; @@ -39,63 +41,341 @@ body { /* ── NAVBAR ── */ .navbar { position: fixed; - top: 0; left: 0; + top: 0; left: 0; right: 0; + margin: 0 auto; width: 100%; - height: 64px; - background: rgba(10, 17, 32, 0.9); - backdrop-filter: blur(14px); - border-bottom: 1px solid var(--border); + height: 80px; + background: transparent; + z-index: 1000; + display: flex; + justify-content: center; + transition: all 0.4s cubic-bezier(0.16, 1, 0.3, 1); + will-change: transform, background-color, backdrop-filter, box-shadow, height, width, top, border-radius; +} + +.navbar.scrolled { + top: 20px; + width: calc(100% - 40px); + max-width: 1200px; + height: 70px; + background: rgba(15, 23, 42, 0.65); + backdrop-filter: blur(24px); + -webkit-backdrop-filter: blur(24px); + box-shadow: 0 15px 40px -10px rgba(0,0,0,0.5), inset 0 1px 1px rgba(255,255,255,0.15); + border-radius: 40px; + border: 1px solid rgba(255, 255, 255, 0.08); +} + +.nav-bg-gradient { + position: absolute; + inset: 0; + background: linear-gradient(90deg, rgba(59, 130, 246, 0.08) 0%, transparent 50%, rgba(59, 130, 246, 0.08) 100%); + opacity: 0; + transition: opacity 0.4s ease; + pointer-events: none; + border-radius: inherit; +} + +.navbar.scrolled .nav-bg-gradient { + opacity: 1; +} + +.nav-container { display: flex; justify-content: space-between; align-items: center; + width: 100%; + max-width: 1440px; + height: 100%; padding: 0 40px; - z-index: 1000; + position: relative; + transition: padding 0.4s ease; +} + +.navbar.scrolled .nav-container { + padding: 0 30px; } .logo { - font-size: 20px; + font-size: 26px; font-weight: 700; + color: var(--text); + letter-spacing: 1px; + z-index: 1001; + cursor: pointer; +} + +.logo-accent { color: var(--primary); + text-shadow: 0 0 8px rgba(59, 130, 246, 0.6), 0 0 16px rgba(59, 130, 246, 0.4); } -.hamburger { - font-size: 26px; - cursor: pointer; - color: var(--text); - display: none; - transition: color 0.2s; +.desktop-nav { + display: flex; + align-items: center; +} + +.nav-actions { + display: flex; + align-items: center; + gap: 16px; +} + +.resume-btn-nav { + display: inline-flex; + align-items: center; + justify-content: center; + padding: 8px 18px; + background: rgba(99, 102, 241, 0.1); + border: 1px solid rgba(99, 102, 241, 0.3); + border-radius: 20px; + color: #fff; + font-size: 14px; + font-weight: 600; + text-decoration: none; + transition: all 0.3s ease; +} + +.resume-btn-nav:hover { + background: rgba(99, 102, 241, 0.25); + box-shadow: 0 0 15px rgba(99, 102, 241, 0.4); + border-color: rgba(99, 102, 241, 0.6); } -.hamburger:hover { color: var(--primary); } .nav-links { list-style: none; display: flex; flex-direction: row; - gap: 4px; - padding: 0; - margin: 0; + gap: 8px; + position: relative; +} + +.nav-indicator { + position: absolute; + bottom: 0px; + width: 6px; + height: 6px; + background: #3b82f6; + border: none; + border-radius: 50%; + z-index: 5; + pointer-events: none; + opacity: 0; + box-shadow: 0 0 10px #3b82f6, 0 0 20px #3b82f6; + will-change: transform, opacity; } .nav-links li { + position: relative; + z-index: 1; +} + +.nav-link { + color: var(--text-muted-1); + text-decoration: none; + font-size: 15px; + font-weight: 600; + letter-spacing: 0.5px; + padding: 10px 20px; + display: block; + transition: color 0.3s ease, text-shadow 0.3s ease; + position: relative; + border-radius: 20px; +} + +.nav-link::after { + display: none; +} + +.nav-link:hover, .nav-link.active { + color: #fff; + text-shadow: 0 0 10px rgba(255, 255, 255, 0.3); +} + +.hamburger { + display: none; + background: transparent; + border: none; cursor: pointer; + padding: 10px; + z-index: 1001; + width: 44px; + height: 44px; + position: relative; +} + +.hamburger .line { + display: block; + width: 24px; + height: 2px; + background-color: var(--text); + margin-bottom: 5px; + border-radius: 2px; + transition: transform 0.3s ease, opacity 0.3s ease, background-color 0.3s ease; + transform-origin: center; + position: absolute; + left: 10px; +} + +.hamburger .line-1 { top: 14px; } +.hamburger .line-2 { top: 21px; } +.hamburger .line-3 { top: 28px; } + +.hamburger.is-active .line-1 { transform: translateY(7px) rotate(45deg); } +.hamburger.is-active .line-2 { opacity: 0; } +.hamburger.is-active .line-3 { transform: translateY(-7px) rotate(-45deg); } + +.nav-overlay { + position: fixed; + inset: 0; + background: rgba(0, 0, 0, 0.4); + backdrop-filter: blur(6px); + -webkit-backdrop-filter: blur(6px); + z-index: 9998; + opacity: 0; + visibility: hidden; + pointer-events: none; +} + +.sidebar-drawer { + position: fixed; + top: 0; right: 0; + width: 80vw; + max-width: 340px; + height: 100vh; + background: rgba(10, 15, 30, 0.95); + backdrop-filter: blur(20px); + -webkit-backdrop-filter: blur(20px); + z-index: 9999; + transform: translateX(100%); + display: flex; + flex-direction: column; + padding: 40px 30px; + border-left: 1px solid rgba(255, 255, 255, 0.05); + will-change: transform; +} + +.sidebar-header { + display: flex; + justify-content: space-between; + align-items: center; + margin-bottom: 60px; +} + +.sidebar-logo { + font-size: 22px; + font-weight: 700; color: var(--text); - font-size: 15px; - padding: 7px 16px; - border-radius: 8px; - transition: background 0.2s, color 0.2s; - white-space: nowrap; } -.nav-links li a { + +.close-sidebar { + background: transparent; + border: none; color: var(--text); + font-size: 36px; + cursor: pointer; + line-height: 1; + transition: color 0.3s ease; +} + +.close-sidebar:hover { + color: var(--primary); +} + +.sidebar-links { + list-style: none; + display: flex; + flex-direction: column; + gap: 2rem; + margin: 0; + padding: 0; + flex: 1; +} + +.sidebar-link { + color: var(--text-muted-1); text-decoration: none; - display: block; - width: 100%; - height: 100%; + font-size: clamp(1.3rem, 3vw, 1.8rem); + font-weight: 500; + min-height: 56px; + display: flex; + align-items: center; + position: relative; + padding: 0 20px; + margin-bottom: 8px; + border-radius: 16px; + transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1); + overflow: hidden; + will-change: transform, background, color; +} + +.sidebar-link::after { + content: ''; + position: absolute; + inset: 0; + background: linear-gradient(90deg, rgba(59, 130, 246, 0.15), transparent); + opacity: 0; + transition: opacity 0.3s ease; + border-radius: 16px; + z-index: -1; } -.nav-links li:hover, -.nav-links li:hover a { + +.sidebar-link::before { + content: ''; + position: absolute; + left: 0; + top: 50%; + transform: translateY(-50%); + height: 0; + width: 4px; background: var(--primary); + border-radius: 0 4px 4px 0; + opacity: 0; + transition: height 0.4s cubic-bezier(0.4, 0, 0.2, 1), opacity 0.3s ease; + box-shadow: 0 0 10px rgba(59, 130, 246, 0); +} + +.sidebar-link:hover, .sidebar-link.active { color: #fff; + transform: translateX(8px); + text-shadow: 0 0 15px rgba(255, 255, 255, 0.3); +} + +.sidebar-link:hover::after, .sidebar-link.active::after { + opacity: 1; +} + +.sidebar-link:hover::before, .sidebar-link.active::before { + height: 60%; + opacity: 1; + box-shadow: 0 0 10px rgba(59, 130, 246, 0.6); +} + +.sidebar-social { + display: flex; + gap: 20px; + margin-top: auto; +} + +.sidebar-social a { + color: var(--text-muted-2); + text-decoration: none; + font-weight: 600; + font-size: 15px; + transition: color 0.3s ease; +} + +.sidebar-social a:hover { + color: var(--primary); +} + +.nav-link:focus-visible, +.sidebar-link:focus-visible, +.hamburger:focus-visible, +.close-sidebar:focus-visible { + outline: 2px solid var(--primary); + outline-offset: 4px; + border-radius: 4px; } /* ── SECTION BASE ── */ @@ -131,180 +411,528 @@ body { border-radius: 2px; } -/* ── HERO ── */ -#home { +/* ══════════════════════════════════════ + HERO V2 — ELITE CINEMATIC REDESIGN + ══════════════════════════════════════ */ + +/* ── Section Shell ── */ +.hero-v2 { + position: relative; min-height: 100vh; display: flex; align-items: center; - padding: 100px 80px 60px; - background: linear-gradient(135deg, var(--bg) 0%, var(--section-alt) 60%, var(--bg) 100%); - position: relative; overflow: hidden; + background: #030712; + padding: 120px 80px 60px; } -#home::before { - content: ""; +/* ── Background Layers ── */ +.hv2-mesh { + position: absolute; inset: 0; z-index: 0; + background: + radial-gradient(ellipse 80% 60% at 0% 0%, rgba(99,102,241,0.12) 0%, transparent 60%), + radial-gradient(ellipse 60% 50% at 100% 100%, rgba(168,85,247,0.10) 0%, transparent 60%), + radial-gradient(ellipse 40% 40% at 50% 50%, rgba(14,165,233,0.05) 0%, transparent 70%); +} + +.hv2-radial { + position: absolute; border-radius: 50%; + filter: blur(90px); pointer-events: none; z-index: 0; opacity: 0; + will-change: transform, opacity; +} +.hv2-radial--a { width: 560px; height: 560px; top: -15%; right: 5%; background: rgba(99,102,241,0.18); } +.hv2-radial--b { width: 420px; height: 420px; bottom: 0; left: -8%; background: rgba(168,85,247,0.14); } +.hv2-radial--c { width: 300px; height: 300px; top: 60%; right: 35%; background: rgba(236,72,153,0.08); } + +.hv2-noise { + position: absolute; inset: 0; z-index: 1; pointer-events: none; + opacity: 0.035; mix-blend-mode: overlay; + background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 256 256' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='4' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E"); +} + +/* ── Layout ── */ +.hv2-layout { + position: relative; z-index: 2; + display: flex; flex-direction: column; + align-items: center; gap: 40px; + width: 100%; max-width: 1400px; margin: 0 auto; +} + +.hv2-main-grid { + display: grid; + grid-template-columns: 1.1fr 0.9fr; + align-items: center; + gap: 80px; + width: 100%; +} + +.hv2-canvas { position: absolute; inset: 0; - background-image: - linear-gradient(var(--border) 1px, transparent 1px), - linear-gradient(90deg, var(--border) 1px, transparent 1px); - background-size: 60px 60px; - opacity: 0.4; + width: 100%; + height: 100%; pointer-events: none; + z-index: 1; } -.hero-content { +/* Stats Panel & Scroll Indicator */ +.hero-stats-panel { display: flex; + justify-content: space-around; align-items: center; - justify-content: space-between; - gap: 48px; width: 100%; - position: relative; - z-index: 1; + padding: 24px 32px; + margin-top: 20px; + border-radius: 24px; + background: rgba(255, 255, 255, 0.02); + backdrop-filter: blur(16px); + -webkit-backdrop-filter: blur(16px); + border: 1px solid rgba(255, 255, 255, 0.06); + box-shadow: 0 20px 40px rgba(0, 0, 0, 0.4), inset 0 1px 0 rgba(255, 255, 255, 0.05); + z-index: 2; + opacity: 0; } - -.hero-text { flex: 1; } - -.hello-tag { - color: var(--primary); +.stat-segment { + display: flex; + align-items: center; + gap: 16px; +} +.stat-icon-wrap { + display: flex; + align-items: center; + justify-content: center; + width: 44px; + height: 44px; + border-radius: 12px; + background: rgba(99, 102, 241, 0.1); + border: 1px solid rgba(99, 102, 241, 0.2); + color: #6366f1; +} +.stat-content { + display: flex; + flex-direction: column; +} +.stat-num { + font-size: 24px; + font-weight: 700; + color: #fff; + line-height: 1.2; +} +.stat-lbl { font-size: 13px; - font-weight: 600; - letter-spacing: 3px; + color: rgba(148, 163, 184, 0.8); + font-weight: 500; +} +.stat-divider { + width: 1px; + height: 40px; + background: rgba(255, 255, 255, 0.06); +} + +.scroll-down-indicator { + display: flex; + flex-direction: column; + align-items: center; + gap: 10px; + margin-top: 10px; + opacity: 0; + z-index: 2; +} +.scroll-label { + font-size: 11px; text-transform: uppercase; - margin-bottom: 16px; + letter-spacing: 2px; + font-weight: 600; + color: rgba(148, 163, 184, 0.6); } +.mouse-icon { + width: 24px; + height: 38px; + border-radius: 12px; + border: 2px solid rgba(148, 163, 184, 0.4); + display: flex; + justify-content: center; + padding-top: 6px; +} +.mouse-wheel { + width: 4px; + height: 8px; + background-color: #3b82f6; + border-radius: 2px; + animation: scrollDown 1.5s ease-in-out infinite; +} +@keyframes scrollDown { + 0% { transform: translateY(0); opacity: 1; } + 100% { transform: translateY(12px); opacity: 0; } +} + +/* ══ LEFT: TEXT ══ */ +.hv2-text { max-width: 580px; } -.hero-text h1 { - font-size: clamp(36px, 5vw, 60px); +/* Eyebrow */ +.hv2-eyebrow-wrap { margin-bottom: 28px; opacity: 0; } +.hv2-eyebrow { + display: inline-flex; align-items: center; gap: 10px; + padding: 6px 14px; border-radius: 100px; + border: 1px solid rgba(59, 130, 246, 0.3); + background: rgba(59, 130, 246, 0.08); + backdrop-filter: blur(10px); +} +.hv2-eyebrow-dot { + width: 7px; height: 7px; border-radius: 50%; + background: #3b82f6; + box-shadow: 0 0 8px rgba(59, 130, 246, 0.8); + animation: hv2Pulse 2s ease-in-out infinite; +} +@keyframes hv2Pulse { + 0%,100% { opacity:1; transform:scale(1); } + 50% { opacity:0.5; transform:scale(0.7); } +} +.hv2-eyebrow-label { + font-size: 11px; font-weight: 600; + letter-spacing: 2px; text-transform: uppercase; + color: rgba(96, 165, 250, 0.9); +} + +/* Heading */ +.hv2-heading { + font-size: clamp(44px, 5.5vw, 72px); font-weight: 800; color: var(--text); - line-height: 1.1; - margin-bottom: 16px; + margin: 0 0 24px; line-height: 1.08; + letter-spacing: -2.5px; opacity: 0; +} +.hv2-name { + display: inline-block; + font-size: clamp(48px, 6vw, 80px); + font-weight: 800; + color: #3b82f6; + background: linear-gradient(135deg, #3b82f6 0%, #60a5fa 100%); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; + filter: drop-shadow(0 0 25px rgba(59, 130, 246, 0.45)); } -.hero-text h2 { +/* Typing Section */ +.hv2-typing-wrap { font-size: clamp(20px, 2.5vw, 28px); - font-weight: 400; - color: var(--text); - margin-bottom: 20px; + font-weight: 500; + color: rgba(255, 255, 255, 0.95); + margin-bottom: 32px; + display: flex; + align-items: center; + gap: 8px; + opacity: 0; } - -/* remove underline bar on hero h2 */ -.hero-text h2::after { display: none; } - -#typing { - color: var(--primary); +.hv2-typed-text { + color: #3b82f6; font-weight: 600; - border-right: 2px solid var(--primary); - padding-right: 4px; - animation: blink 0.75s step-end infinite; + text-shadow: 0 0 10px rgba(59, 130, 246, 0.3); } - -@keyframes blink { 50% { border-color: transparent; } } - -.hero-desc { - font-size: 15px; - color: var(--text-muted-3); - max-width: 420px; - line-height: 1.8; - margin-bottom: 32px; +.hv2-cursor { + color: #3b82f6; + font-weight: 300; + animation: cursorBlink 1.0s infinite; +} +@keyframes cursorBlink { + 0%, 100% { opacity: 0; } + 50% { opacity: 1; } } -.hero-btns { - display: flex; - gap: 14px; - flex-wrap: wrap; - margin-bottom: 32px; +/* Description */ +.hv2-desc { + font-size: clamp(15px, 1.5vw, 18px); + line-height: 1.85; color: rgba(148,163,184,0.85); + margin-bottom: 44px; max-width: 500px; + opacity: 0; } -.btn-primary { - background: var(--primary); +/* CTA Cluster */ +.hv2-cta-cluster { + display: flex; gap: 16px; margin-bottom: 44px; + opacity: 0; +} +.hv2-btn { + position: relative; display: inline-flex; align-items: center; + gap: 9px; padding: 14px 30px; + border-radius: 12px; font-weight: 600; font-size: 15px; + text-decoration: none; overflow: hidden; + transition: transform 0.35s cubic-bezier(0.34,1.56,0.64,1), box-shadow 0.35s ease; + will-change: transform; +} +.hv2-btn--solid { + background: #2563eb; color: #fff; - padding: 12px 28px; - border-radius: 8px; - text-decoration: none; - font-weight: 600; - font-size: 15px; - transition: 0.3s; - box-shadow: 0 4px 15px rgba(59,130,246,0.35); + border: 1px solid rgba(255, 255, 255, 0.1); + box-shadow: 0 8px 24px -4px rgba(37, 99, 235, 0.5); } - -.btn-primary:hover { - transform: translateY(-2px); - box-shadow: 0 8px 25px rgba(59,130,246,0.5); +.hv2-btn--solid:hover { transform: translateY(-3px); background: #1d4ed8; box-shadow: 0 14px 30px -4px rgba(37, 99, 235, 0.7); } +.hv2-btn-glow { + position: absolute; inset: -1px; border-radius: 13px; + background: linear-gradient(135deg, rgba(255,255,255,0.2), transparent); + pointer-events: none; +} +.hv2-btn--ghost { + background: rgba(15, 23, 42, 0.4); + color: #fff; + border: 1px solid rgba(255, 255, 255, 0.1); + backdrop-filter: blur(12px); } +.hv2-btn--ghost:hover { transform: translateY(-3px); background: rgba(255, 255, 255, 0.05); border-color: rgba(255, 255, 255, 0.2); } -.btn-outline { - background: transparent; - color: var(--primary); - border: 1.5px solid var(--primary); - padding: 11px 28px; - border-radius: 8px; +/* Connect with me section */ +.hv2-connect-wrap { + display: flex; + flex-direction: column; + gap: 16px; + align-items: flex-start; + opacity: 0; +} +.hv2-connect-label { + font-size: 11px; + font-weight: 700; + letter-spacing: 2px; + color: rgba(148, 163, 184, 0.6); + text-transform: uppercase; +} +.hv2-social-bar { + display: flex; + align-items: center; + gap: 16px; +} +.hv2-social-link { + position: relative; width: 44px; height: 44px; + display: flex; align-items: center; justify-content: center; + color: rgba(148, 163, 184, 0.7); border-radius: 50%; + border: 1px solid rgba(255,255,255,0.08); + background: rgba(255,255,255,0.02); + transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1); text-decoration: none; - font-weight: 600; - font-size: 15px; - transition: 0.3s; +} +.hv2-social-link:hover { + color: #fff; border-color: rgba(59, 130, 246, 0.5); + background: rgba(59, 130, 246, 0.1); + transform: translateY(-3px); + box-shadow: 0 8px 20px -4px rgba(59, 130, 246, 0.3); +} +.hv2-social-link::after { + content: attr(data-tip); position: absolute; top: -34px; left: 50%; + transform: translateX(-50%) translateY(6px); + font-size: 11px; font-weight: 600; letter-spacing: 1px; white-space: nowrap; + background: rgba(15,23,42,0.95); color: #60a5fa; + padding: 4px 10px; border-radius: 6px; + border: 1px solid rgba(59, 130, 246, 0.2); + opacity: 0; visibility: hidden; transition: 0.25s ease; pointer-events: none; +} +.hv2-social-link:hover::after { opacity: 1; visibility: visible; transform: translateX(-50%) translateY(0); } + +/* ══ RIGHT: ORBITAL PORTRAIT SYSTEM ══ */ +.hv2-portrait-scene { + flex-shrink: 0; position: relative; + width: clamp(340px, 35vw, 480px); + height: clamp(400px, 42vw, 580px); + display: flex; + align-items: center; + justify-content: center; + perspective: 1200px; + opacity: 0; } -.btn-outline:hover { - background: var(--primary); - color: #fff; - transform: translateY(-2px); +/* L1 — Ambient Glow (reactive) */ +.hv2-portrait-glow { + position: absolute; inset: -30px; border-radius: 50%; + background: radial-gradient(circle, rgba(59, 130, 246, 0.25) 0%, rgba(139, 92, 246, 0.12) 40%, transparent 70%); + filter: blur(50px); z-index: 0; pointer-events: none; + will-change: transform; transition: opacity 0.8s ease; } -.hero-social { +/* L2 — Concentric Orbital Rings */ +.hv2-orbital-container { + position: absolute; + inset: -50px; display: flex; - gap: 14px; + align-items: center; + justify-content: center; + pointer-events: none; + z-index: 0; +} +.hv2-orbital-ring { + position: absolute; + border-radius: 50%; + border: 1px dashed rgba(59, 130, 246, 0.2); + will-change: transform; +} +.hv2-orbital-ring--1 { + width: clamp(280px, 30vw, 360px); + height: clamp(280px, 30vw, 360px); + border: 1px solid rgba(59, 130, 246, 0.08); +} +.hv2-orbital-ring--2 { + width: clamp(340px, 36vw, 430px); + height: clamp(340px, 36vw, 430px); + border: 1px dashed rgba(59, 130, 246, 0.25); +} +.hv2-orbital-ring--3 { + width: clamp(400px, 42vw, 500px); + height: clamp(400px, 42vw, 500px); + border: 1px dotted rgba(59, 130, 246, 0.15); +} + +/* Orbiting Dots */ +.hv2-orbit-dot { + position: absolute; + border-radius: 50%; + transform: translate(-50%, -50%); + will-change: transform; +} +.hv2-orbit-dot--active { + top: 50%; + left: 100%; + width: 14px; + height: 14px; + background: #fff; + border: 3px solid #3b82f6; + box-shadow: 0 0 15px rgba(59, 130, 246, 0.8); +} +.hv2-orbit-dot--blue { + top: 0%; + left: 50%; + width: 8px; + height: 8px; + background: #60a5fa; + box-shadow: 0 0 10px rgba(96, 165, 250, 0.8); +} +.hv2-orbit-dot--white { + top: 100%; + left: 50%; + width: 8px; + height: 8px; + background: #fff; + box-shadow: 0 0 8px rgba(255, 255, 255, 0.8); +} + +/* L3 — Center Circular Frame */ +.hv2-circular-frame { + position: relative; + width: clamp(220px, 24vw, 290px); + height: clamp(220px, 24vw, 290px); + border-radius: 50%; + padding: 8px; + background: rgba(255, 255, 255, 0.02); + box-shadow: 0 20px 50px rgba(0, 0, 0, 0.6), inset 0 1px 0 rgba(255, 255, 255, 0.05); + z-index: 2; + transform-style: preserve-3d; + will-change: transform; +} +.hv2-frame-glow { + position: absolute; + inset: 0; + border-radius: 50%; + border: 2px solid rgba(59, 130, 246, 0.4); + box-shadow: 0 0 30px rgba(59, 130, 246, 0.25); + pointer-events: none; + z-index: 1; + animation: frameGlowPulse 4s ease-in-out infinite; +} +@keyframes frameGlowPulse { + 0%, 100% { transform: scale(1); opacity: 0.8; } + 50% { transform: scale(1.02); opacity: 1; box-shadow: 0 0 40px rgba(59, 130, 246, 0.4); } +} +.hv2-circular-img-wrap { + width: 100%; + height: 100%; + border-radius: 50%; + overflow: hidden; + position: relative; + z-index: 2; +} +.hv2-circular-img-wrap img { + width: 100%; + height: 100%; + object-fit: cover; + transition: transform 0.6s cubic-bezier(0.2, 0.8, 0.2, 1); + display: block; +} +.hv2-circular-frame:hover img { + transform: scale(1.08); } -.hero-social a { - width: 42px; height: 42px; +/* L4 — Code Symbol Badge */ +.hv2-code-badge { + position: absolute; + top: 15%; + right: 8%; + width: 36px; + height: 36px; border-radius: 50%; - border: 1px solid var(--border); - background: var(--card); + background: rgba(10, 16, 30, 0.85); + border: 1px solid rgba(59, 130, 246, 0.35); + color: #60a5fa; display: flex; align-items: center; justify-content: center; - transition: 0.3s; + box-shadow: 0 8px 24px rgba(0, 0, 0, 0.4), 0 0 15px rgba(59, 130, 246, 0.25); + z-index: 5; + animation: floatAnimation 3s ease-in-out infinite alternate; } - -.hero-social a:hover { - background: var(--primary); - border-color: var(--primary); - transform: translateY(-3px); +@keyframes floatAnimation { + 0% { transform: translateY(0) rotate(0deg); } + 100% { transform: translateY(-8px) rotate(5deg); } } -.hero-social img { - width: 20px; height: 20px; - filter: brightness(10); +/* L5 — Floating Status Card */ +.hv2-status-card { + position: absolute; + bottom: 12%; + left: 5%; + display: flex; + align-items: center; + gap: 12px; + padding: 12px 18px; + border-radius: 12px; + background: rgba(3, 7, 18, 0.7); + border: 1px solid rgba(255, 255, 255, 0.08); + box-shadow: 0 12px 32px rgba(0, 0, 0, 0.6); + backdrop-filter: blur(12px); + -webkit-backdrop-filter: blur(12px); + z-index: 6; + opacity: 0; + will-change: transform, opacity; } - -.hero-image { flex-shrink: 0; } - -.hero-img-circle { - width: 220px; height: 220px; - border-radius: 50%; - background: linear-gradient(135deg, #1e3a5f, #2563eb); - border: 4px solid rgba(59,130,246,0.5); +.hv2-status-dot-wrap { display: flex; align-items: center; justify-content: center; - font-size: 52px; +} +.hv2-status-pulse { + width: 10px; + height: 10px; + border-radius: 50%; + background: #10b981; + box-shadow: 0 0 12px #10b981; + animation: pulseStatus 2s cubic-bezier(0.4, 0, 0.6, 1) infinite; +} +@keyframes pulseStatus { + 0%, 100% { opacity: 1; transform: scale(1); } + 50% { opacity: .5; transform: scale(1.15); } +} +.hv2-status-info { + display: flex; + flex-direction: column; + gap: 2px; +} +.hv2-status-label { + font-size: 9px; font-weight: 700; + color: rgba(148, 163, 184, 0.6); + letter-spacing: 1px; +} +.hv2-status-text { + font-size: 13px; + font-weight: 600; color: #fff; - letter-spacing: 2px; - box-shadow: 0 0 60px rgba(59,130,246,0.25), 0 0 0 8px rgba(59,130,246,0.08); - overflow: hidden; } -.hero-img-circle img { - width: 100%; - height: 100%; - object-fit: cover; - border-radius: 50%; - display: block; -} /* ── ABOUT ── */ .about-grid { @@ -1100,35 +1728,71 @@ form button:disabled { .section { opacity: 1; transform: none; transition: none; } } +/* ── RESPONSIVE STYLES ── */ +@media (max-width: 1024px) { + .nav-container { padding: 0 40px; } + .nav-links { gap: 10px; } + .nav-link { padding: 8px 16px; font-size: 15px; } + .nav-indicator { display: block; } + .logo { font-size: 24px; } +} + /* ── MOBILE ── */ -@media (max-width: 768px) { - .navbar { padding: 0 20px; } +@media (max-width: 767px) { + .nav-container { padding: 0 24px; } .hamburger { display: block; } - .nav-links { - position: absolute; - top: 64px; right: 20px; - background: var(--card); - backdrop-filter: blur(12px); - border: 1px solid var(--border); - border-radius: 12px; - flex-direction: column; - padding: 16px; - width: 180px; - box-shadow: 0 10px 30px var(--shadow); - display: none; - } + .desktop-nav { display: none; } - .nav-links.show { display: flex; } + /* Adjust Logo for Mobile */ + .logo { font-size: 22px; } #home { padding: 100px 24px 60px; } .section { padding: 70px 24px; } - .hero-content { flex-direction: column-reverse; text-align: center; } - .hero-desc { max-width: 100%; } - .hero-btns { justify-content: center; } - .hero-social { justify-content: center; } - .hero-img-circle { width: 160px; height: 160px; font-size: 36px; } + /* Hero V2 Mobile */ + .hero-v2 { padding: 100px 24px 80px; } + .hv2-layout { flex-direction: column; gap: 48px; } + .hv2-main-grid { display: flex; flex-direction: column-reverse; gap: 48px; } + .hv2-text { max-width: 100%; text-align: center; align-items: center; display: flex; flex-direction: column; } + .hv2-heading { letter-spacing: -1.5px; } + .hv2-desc { max-width: 100%; text-align: center; } + .hv2-role-item { justify-content: center; } + .hv2-cta-cluster { flex-direction: column; width: 100%; } + .hv2-btn { justify-content: center; width: 100%; } + .hv2-social-bar { justify-content: center; } + .hv2-portrait-scene { width: 320px; height: 360px; margin: 0 auto; } + .hv2-circular-frame { + width: 200px; + height: 200px; + } + .hv2-orbital-container { + inset: -30px; + } + .hv2-orbital-ring--1 { + width: 240px; + height: 240px; + } + .hv2-orbital-ring--2 { + width: 280px; + height: 280px; + } + .hv2-orbital-ring--3 { + width: 320px; + height: 320px; + } + .hv2-code-badge { + top: 18%; + right: 12%; + } + .hv2-status-card { + bottom: 8%; + left: -2%; + } + + .hero-stats-panel { flex-direction: column; gap: 16px; padding: 20px; } + .stat-divider { width: 80%; height: 1px; } + .stat-segment { width: 100%; justify-content: flex-start; } .about-grid { grid-template-columns: 1fr; gap: 32px; } .about-right { grid-template-columns: 1fr 1fr; } @@ -1140,9 +1804,16 @@ form button:disabled { .settings { bottom: 16px; right: 16px; } } -@media (min-width: 769px) { +/* ── VERY SMALL MOBILE ── */ +@media (max-width: 380px) { + .nav-container { padding: 0 16px; } + .logo { font-size: 20px; } + .hamburger { transform: scale(0.9); } + .nav-link { font-size: 22px; } +} + +@media (min-width: 768px) { .hamburger { display: none; } - .nav-links { display: flex !important; } } /* ══════════════════════════════════════════ LIGHT THEME OVERRIDES @@ -1162,28 +1833,80 @@ body.light-theme { } /* Navbar stays light-background-aware */ -body.light-theme .navbar { - background: rgba(248,250,252,0.95); - border-bottom: 1px solid rgba(0,0,0,0.1); +body.light-theme .navbar.scrolled { + background: rgba(248, 250, 252, 0.85); + border: 1px solid rgba(0, 0, 0, 0.08); + box-shadow: 0 15px 40px -10px rgba(0,0,0,0.1), inset 0 1px 1px rgba(255,255,255,0.8); +} + +body.light-theme .nav-overlay { + background: rgba(255, 255, 255, 0.3); +} + +body.light-theme .sidebar-drawer { + background: rgba(248, 250, 252, 0.98); + border-left: 1px solid rgba(0, 0, 0, 0.05); } /* Nav links: dark text on light bg, white on hover/active */ -body.light-theme .nav-links li { - color: #0f172a; +body.light-theme .nav-link, +body.light-theme .sidebar-link { + color: var(--text-muted-1); } -body.light-theme .nav-links li:hover, -body.light-theme .nav-links li.nav-active { - background: var(--primary); - color: #fff; + +/* Hero Light Theme Overrides */ +body.light-theme .hero-bg-mesh { + background: radial-gradient(at 0% 0%, rgba(59, 130, 246, 0.05) 0px, transparent 50%), + radial-gradient(at 100% 100%, rgba(165, 180, 252, 0.05) 0px, transparent 50%); +} + +body.light-theme .hero-bg-radial.glow-1 { + background: rgba(59, 130, 246, 0.08); +} + +body.light-theme .hero-bg-radial.glow-2 { + background: rgba(165, 180, 252, 0.06); +} + +body.light-theme .glass-frame { + background: linear-gradient(135deg, rgba(255,255,255,0.8), rgba(255,255,255,0.4)); + border: 1px solid rgba(0,0,0,0.05); + box-shadow: 0 30px 60px rgba(0,0,0,0.08); +} + +body.light-theme .social-dock { + background: rgba(255, 255, 255, 0.8); + border: 1px solid rgba(0, 0, 0, 0.08); + box-shadow: 0 10px 30px rgba(0,0,0,0.05); +} + +body.light-theme .dock-icon { + color: var(--text-muted-1); +} + +body.light-theme .dock-icon:hover { + background: rgba(59, 130, 246, 0.1); + color: var(--primary); +} + +body.light-theme .name-split { + background: linear-gradient(135deg, #0f172a 0%, #3b82f6 100%); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; } -body.light-theme .hamburger { +body.light-theme .nav-link:hover, +body.light-theme .nav-link.active { color: #0f172a; + text-shadow: 0 0 10px rgba(0, 0, 0, 0.1); } -/* Mobile dropdown bg */ -body.light-theme .nav-links { - background: #f1f5f9; - border-color: rgba(0,0,0,0.1); +body.light-theme .sidebar-link:hover, +body.light-theme .sidebar-link.active { + color: #0f172a; + text-shadow: 0 0 15px rgba(0, 0, 0, 0.1); +} +body.light-theme .hamburger .line { + background-color: #0f172a; } /* Section headings (About, Projects, etc.) stay dark, not pure black */ @@ -1252,4 +1975,360 @@ body.light-theme .menu button { background: #e2e8f0; color: #0f172a; border-color: rgba(0,0,0,0.15); -} \ No newline at end of file +} + +/* ── Hero V2 Light Theme Overrides ── */ +body.light-theme .hero-v2 { + background: var(--bg); +} +body.light-theme .hv2-mesh { + background: + radial-gradient(ellipse 80% 60% at 0% 0%, rgba(59, 130, 246, 0.05) 0%, transparent 60%), + radial-gradient(ellipse 60% 50% at 100% 100%, rgba(165, 180, 252, 0.05) 0%, transparent 60%), + radial-gradient(ellipse 40% 40% at 50% 50%, rgba(59, 130, 246, 0.02) 0%, transparent 70%); +} +body.light-theme .hv2-radial--a { + background: rgba(59, 130, 246, 0.08); +} +body.light-theme .hv2-radial--b { + background: rgba(165, 180, 252, 0.06); +} +body.light-theme .hv2-radial--c { + background: rgba(236, 72, 153, 0.04); +} +body.light-theme .hv2-desc { + color: var(--text-muted-1); +} +body.light-theme .hv2-typing-wrap { + color: #0f172a; +} +body.light-theme .hv2-connect-label { + color: var(--text-muted-2); +} +body.light-theme .hv2-social-link { + color: var(--text-muted-1); + border-color: rgba(0, 0, 0, 0.08); + background: rgba(0, 0, 0, 0.02); +} +body.light-theme .hv2-social-link:hover { + color: var(--primary); + border-color: rgba(59, 130, 246, 0.4); + background: rgba(59, 130, 246, 0.08); +} +body.light-theme .hv2-circular-frame { + background: rgba(255, 255, 255, 0.85); + box-shadow: 0 20px 50px rgba(0, 0, 0, 0.08), inset 0 1px 0 rgba(255, 255, 255, 0.9); +} +body.light-theme .hv2-code-badge { + background: rgba(255, 255, 255, 0.9); + border-color: rgba(59, 130, 246, 0.25); + color: #2563eb; + box-shadow: 0 8px 24px rgba(0, 0, 0, 0.06), 0 0 15px rgba(59, 130, 246, 0.15); +} +body.light-theme .hv2-status-card { + background: rgba(255, 255, 255, 0.9); + border-color: rgba(0, 0, 0, 0.08); + box-shadow: 0 12px 32px rgba(0, 0, 0, 0.08); +} +body.light-theme .hv2-status-info .hv2-status-label { + color: var(--text-muted-3); +} +body.light-theme .hv2-status-info .hv2-status-text { + color: #0f172a; +} +body.light-theme .hero-stats-panel { + background: rgba(255, 255, 255, 0.8); + border-color: rgba(0, 0, 0, 0.08); + box-shadow: 0 20px 40px rgba(0, 0, 0, 0.06); +} +body.light-theme .stat-divider { + background: rgba(0, 0, 0, 0.08); +} +body.light-theme .stat-num { + color: #0f172a; +} +body.light-theme .stat-lbl { + color: var(--text-muted-2); +} +body.light-theme .scroll-label { + color: var(--text-muted-2); +} +body.light-theme .mouse-icon { + border-color: var(--text-muted-2); +} +body.light-theme .hv2-btn--ghost { + color: #0f172a; + border-color: rgba(0, 0, 0, 0.15); + background: rgba(255, 255, 255, 0.4); +} +body.light-theme .hv2-btn--ghost:hover { + background: rgba(0, 0, 0, 0.05); + border-color: #0f172a; +} + +/* ================= PRELOADER ANIMATION ================= */ +body.loading { + overflow: hidden; + height: 100vh; +} + +#preloader { + position: fixed; + inset: 0; + z-index: 9999; + background: transparent; + display: flex; + align-items: center; + justify-content: center; + overflow: hidden; +} + +.preloader-curtain { + position: absolute; + top: 0; + height: 100%; + width: 56vw; /* Overlap slightly for skews */ + will-change: transform; +} + +.preloader-curtain--left { + left: 0; + transform-origin: top left; +} + +.preloader-curtain--right { + right: 0; + transform-origin: bottom right; +} + +/* Three separate layers of panels */ +.preloader-curtain--layer1 { + background: #030712; + z-index: 3; +} + +.preloader-curtain--layer2 { + background: linear-gradient(135deg, var(--primary), #6366f1, #a855f7); + z-index: 2; +} + +.preloader-curtain--layer3 { + background: rgba(15, 23, 42, 0.45); + backdrop-filter: blur(15px); + -webkit-backdrop-filter: blur(15px); + z-index: 1; +} + +.preloader-curtain--left.preloader-curtain--layer3 { + border-right: 1px solid rgba(255, 255, 255, 0.05); +} + +.preloader-curtain--right.preloader-curtain--layer3 { + border-left: 1px solid rgba(255, 255, 255, 0.05); +} + +/* Background glows for the loader */ +.preloader-radial { + position: absolute; + border-radius: 50%; + filter: blur(100px); + pointer-events: none; + opacity: 0.7; + z-index: 4; /* Render on top of curtains but under text content */ +} +.preloader-radial--1 { + width: 400px; + height: 400px; + top: -10%; + left: -10%; + background: rgba(99, 102, 241, 0.15); +} +.preloader-radial--2 { + width: 500px; + height: 500px; + bottom: -15%; + right: -10%; + background: rgba(168, 85, 247, 0.12); +} + +.preloader-content { + display: flex; + flex-direction: column; + align-items: center; + position: relative; + z-index: 10; + width: 90%; + max-width: 450px; +} + +.preloader-logo { + font-size: clamp(24px, 4vw, 36px); + font-weight: 700; + letter-spacing: 2px; + color: #fff; + margin-bottom: 28px; + display: flex; + overflow: hidden; +} + +/* Character animation defaults */ +.pl-char, .pl-char-accent, .pl-space { + display: inline-block; + opacity: 0; + transform: translateY(30px); + will-change: transform, opacity; +} + +.pl-char-accent { + color: var(--primary); + text-shadow: 0 0 10px rgba(59, 130, 246, 0.6); +} + +/* Dashboard & Circle Progress Ring */ +.preloader-dashboard { + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; +} + +.preloader-circle-wrapper { + position: relative; + width: 140px; + height: 140px; + display: flex; + align-items: center; + justify-content: center; + margin-bottom: 16px; +} + +.preloader-svg-circle { + position: absolute; + inset: 0; + width: 100%; + height: 100%; + transform: rotate(-90deg); /* Start trace at 12 o'clock */ +} + +.circle-bg { + fill: none; + stroke: rgba(255, 255, 255, 0.03); + stroke-width: 3; +} + +.circle-progress { + fill: none; + stroke: var(--primary); + stroke-width: 4; + stroke-linecap: round; + stroke-dasharray: 282.7; + stroke-dashoffset: 282.7; + filter: drop-shadow(0 0 6px var(--primary)); + will-change: stroke-dashoffset; +} + +/* Odometer mechanical rolling percentage ticker */ +.preloader-percentage { + position: relative; + z-index: 2; +} + +.ticker-wrapper { + display: flex; + align-items: flex-start; + height: 36px; + overflow: hidden; + line-height: 36px; + font-size: 32px; + font-weight: 700; + color: #fff; + font-family: monospace; +} + +.ticker-column { + display: flex; + flex-direction: column; + will-change: transform; +} + +.ticker-column--hundreds { + opacity: 0; + width: 0; + transition: opacity 0.3s cubic-bezier(0.25, 1, 0.5, 1), width 0.3s cubic-bezier(0.25, 1, 0.5, 1); +} + +.ticker-column--hundreds.visible { + opacity: 1; + width: 20px; +} + +.ticker-column span { + display: block; + height: 36px; + text-align: center; +} + +.ticker-percent { + color: var(--primary); + font-size: 18px; + margin-left: 2px; + align-self: flex-start; + line-height: 28px; + font-weight: 600; + text-shadow: 0 0 6px rgba(59, 130, 246, 0.4); +} + +/* Dynamic status telemetry log */ +.preloader-status { + font-family: monospace; + font-size: 10px; + color: var(--text-muted-2); + letter-spacing: 2px; + text-transform: uppercase; + height: 16px; + min-width: 280px; + text-align: center; + opacity: 0.8; + text-shadow: 0 0 5px rgba(255, 255, 255, 0.05); + transition: opacity 0.15s ease; +} + +/* ── Light Theme Preloader Overrides ── */ +body.light-theme .preloader-curtain--layer1 { + background: #f8fafc; +} + +body.light-theme .preloader-curtain--layer3 { + background: rgba(241, 245, 249, 0.45); +} + +body.light-theme .preloader-curtain--left.preloader-curtain--layer3 { + border-right: 1px solid rgba(0, 0, 0, 0.05); +} + +body.light-theme .preloader-curtain--right.preloader-curtain--layer3 { + border-left: 1px solid rgba(0, 0, 0, 0.05); +} + +body.light-theme .preloader-radial--1 { + background: rgba(59, 130, 246, 0.08); +} +body.light-theme .preloader-radial--2 { + background: rgba(165, 180, 252, 0.06); +} +body.light-theme .preloader-logo { + color: #0f172a; +} +body.light-theme .pl-char-accent { + color: var(--primary); + text-shadow: 0 0 8px rgba(59, 130, 246, 0.2); +} +body.light-theme .circle-bg { + stroke: rgba(0, 0, 0, 0.04); +} +body.light-theme .ticker-wrapper { + color: #0f172a; +} +body.light-theme .preloader-status { + color: var(--text-muted-1); +} \ No newline at end of file diff --git a/revati-kadam-portfolio/index.html b/revati-kadam-portfolio/index.html index 1bf2a0c..1a442c2 100644 --- a/revati-kadam-portfolio/index.html +++ b/revati-kadam-portfolio/index.html @@ -7,58 +7,290 @@ + - + + + +
+ +
+
+
+ + +
+
+
+ +
+
+ +
+ + +
+
+ + + + +
+
+
+ 0 + 1 +
+
+ 0 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9 +
+
+ 0 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9 +
+ % +
+
+
+
CONNECTING TO HOST...
+
+
+
- + + +
-
-
-
-

HELLO!

-

I am Revati Kadam

-

I am a

-

- A passionate Computer Science student who loves building clean, - responsive web apps and solving real-world problems through code. -

-
- View Projects - Download Resume +
+ + +
+
+
+
+
+ + +
+ +
+ +
+
+ + + WELCOME TO MY PORTFOLIO + +
+ +

+ I'm Revati
Kadam. +

+ +
+ I build digital| +
+ +

+ A passionate Computer Science student who loves building clean, + responsive web apps and solving real-world problems through code. +

+ + + +
+
CONNECT WITH ME
+ +
-
- - GitHub - - - LinkedIn - - - LeetCode - + + +
+ +
+ + +
+
+
+
+
+
+
+
+
+
+ + +
+
+
+ Revati Kadam — Portfolio +
+
+ + +
+ +
+ + +
+
+ +
+
+ STATUS + Available for Opportunities +
+
-
-
-
- Rkimg + + +
+
+
+ +
+
+ 15+ + Projects Completed +
+
+
+
+
+ +
+
+ 2+ + Years Coding
-
+
+
+
+
+ +
+
+ 10+ + Technologies +
+
+
+
+
+ +
+
+ Web / DSA + Current Focus +
+
+ + +
+ Scroll Down +
+
+
+
+
@@ -215,5 +447,7 @@

Contact Me

+ + \ No newline at end of file diff --git a/revati-kadam-portfolio/js/hero.js b/revati-kadam-portfolio/js/hero.js new file mode 100644 index 0000000..6f06731 --- /dev/null +++ b/revati-kadam-portfolio/js/hero.js @@ -0,0 +1,293 @@ +/* ═══════════════════════════════════════════ + HERO V2 — Immersive Motion Engine (GSAP & Canvas) + Staggered Load, Orbital Physics, Magnetic Hooks, Canvas Repulsion + ═══════════════════════════════════════════ */ + +const prefersReduced = window.matchMedia('(prefers-reduced-motion: reduce)').matches; +const isMobile = window.matchMedia('(max-width: 767px)').matches; + +// Decoupled trigger: initHeroV2() is now called by the preloader script on loading completion. + + +function initHeroV2() { + if (prefersReduced) { + showAllInstant(); + return; + } + + // 1. Entrance Staggered Orchestration + const tl = gsap.timeline({ defaults: { ease: 'power3.out' } }); + + // Activate glows and meshes + tl.to('.hv2-radial--a', { opacity: 1, duration: 2.0 }, 0.0) + .to('.hv2-radial--b', { opacity: 1, duration: 2.0 }, 0.2) + .to('.hv2-radial--c', { opacity: 1, duration: 1.5 }, 0.4); + + // Stagger Header Navigation items + tl.fromTo('.navbar .logo', + { y: -20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 0.2); + + tl.fromTo('.desktop-nav .nav-link', + { y: -20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.6, stagger: 0.08 }, 0.3); + + tl.fromTo('.nav-actions', + { y: -20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 0.5); + + // Left Content Text Elements + tl.fromTo('.hv2-eyebrow-wrap', + { y: 24, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 0.4); + + tl.fromTo('.hv2-heading', + { y: 35, opacity: 0 }, + { y: 0, opacity: 1, duration: 1.0 }, 0.6); + + tl.fromTo('.hv2-typing-wrap', + { y: 20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 0.95); + + tl.fromTo('.hv2-desc', + { y: 20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 1.1); + + tl.fromTo('#hv2CTA', + { y: 20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 1.25); + + tl.fromTo('#hv2Social', + { y: 15, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, 1.35); + + // Right Centerpiece Portrait Scene + tl.fromTo('#hv2Portrait', + { scale: 0.88, opacity: 0, rotationY: -15, y: 30 }, + { scale: 1, opacity: 1, rotationY: 0, y: 0, duration: 1.5, ease: 'power4.out' }, + 0.85); + + tl.fromTo('#statusBadge', + { y: 20, opacity: 0, scale: 0.85 }, + { y: 0, opacity: 1, scale: 1, duration: 0.8, ease: 'back.out(1.4)' }, + 1.4); + + // Bottom Stats Panel + tl.fromTo('#heroStatsPanel', + { y: 30, opacity: 0 }, + { y: 0, opacity: 1, duration: 1.0, ease: 'power3.out' }, + 1.4); + + // Scroll Down Indicator + tl.fromTo('#scrollIndicator', + { y: 15, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8 }, + 1.6); + + // Loop & Ambient Handlers Initialization + tl.add(() => { + initOrbitRotation(); + if (!isMobile) { + initParallax(); + initMagneticInteractivity(); + } + initCanvasMesh(); + }, 1.8); +} + +function showAllInstant() { + gsap.set([ + '.hv2-radial', '.navbar .logo', '.desktop-nav .nav-link', '.nav-actions', + '.hv2-eyebrow-wrap', '.hv2-heading', '.hv2-typing-wrap', '.hv2-desc', + '#hv2CTA', '#hv2Social', '#hv2Portrait', '#statusBadge', + '#heroStatsPanel', '#scrollIndicator' + ], { opacity: 1, y: 0, scale: 1, rotationY: 0, skewX: 0 }); +} + +/* ── GSAP CONTINUOUS ORBIT ROTATION ── */ +function initOrbitRotation() { + gsap.to('#portraitOrbital', { + rotation: 360, + duration: 20, + repeat: -1, + ease: 'none' + }); + gsap.to('#portraitOrbital2', { + rotation: -360, + duration: 30, + repeat: -1, + ease: 'none' + }); +} + +/* ── MULTI-DEPTH MOUSE PARALLAX ── */ +function initParallax() { + const scene = document.querySelector('.hero-v2'); + const chassis = document.getElementById('portraitChassis'); + const glow = document.getElementById('portraitGlow'); + const img = document.getElementById('portraitImg'); + const badge = document.getElementById('statusBadge'); + + if (!scene || !chassis) return; + + let mx = 0, my = 0, raf = null; + + function update() { + gsap.to(chassis, { + rotationY: mx * 12, rotationX: -my * 10, + x: mx * 12, y: my * 12, + duration: 1.2, ease: 'power2.out', overwrite: 'auto' + }); + gsap.to(img, { + x: -mx * 10, y: -my * 8, + duration: 1.4, ease: 'power2.out', overwrite: 'auto' + }); + gsap.to(glow, { + x: mx * 30, y: my * 24, + duration: 1.8, ease: 'power2.out', overwrite: 'auto' + }); + gsap.to(badge, { + x: mx * 20, y: my * 15, + duration: 1.0, ease: 'power2.out', overwrite: 'auto' + }); + raf = null; + } + + scene.addEventListener('mousemove', e => { + const r = scene.getBoundingClientRect(); + mx = ((e.clientX - r.left) / r.width - 0.5) * 2; + my = ((e.clientY - r.top) / r.height - 0.5) * 2; + if (!raf) raf = requestAnimationFrame(update); + }); + + scene.addEventListener('mouseleave', () => { + mx = 0; my = 0; + gsap.to([chassis, img, glow, badge], { + x: 0, y: 0, rotationX: 0, rotationY: 0, + duration: 1.6, ease: 'elastic.out(1, 0.35)', overwrite: 'auto' + }); + }); +} + +/* ── MAGNETIC HOOKS INTERACTIVITY ── */ +function initMagneticInteractivity() { + const magneticElements = document.querySelectorAll('.magnetic-btn, .hv2-circular-frame, .hv2-status-card'); + + magneticElements.forEach(elem => { + elem.addEventListener('mousemove', e => { + const r = elem.getBoundingClientRect(); + const pullStrength = elem.classList.contains('hv2-circular-frame') ? 0.08 : 0.22; + const dx = (e.clientX - r.left - r.width / 2) * pullStrength; + const dy = (e.clientY - r.top - r.height / 2) * pullStrength; + + gsap.to(elem, { + x: dx, + y: dy, + duration: 0.4, + ease: 'power2.out', + overwrite: 'auto' + }); + }); + + elem.addEventListener('mouseleave', () => { + gsap.to(elem, { + x: 0, + y: 0, + duration: 0.9, + ease: 'elastic.out(1, 0.3)', + overwrite: 'auto' + }); + }); + }); +} + +/* ── KINETIC CANVAS PARTICLE MESH (Repulsion Physics) ── */ +function initCanvasMesh() { + const canvas = document.getElementById('heroCanvas'); + if (!canvas) return; + const ctx = canvas.getContext('2d'); + let particles = []; + const spacing = 40; + let mouse = { x: -1000, y: -1000 }; + let animationFrameId; + + function resizeCanvas() { + canvas.width = canvas.parentElement.offsetWidth; + canvas.height = canvas.parentElement.offsetHeight; + generateGrid(); + } + + function generateGrid() { + particles = []; + const cols = Math.floor(canvas.width / spacing) + 2; + const rows = Math.floor(canvas.height / spacing) + 2; + + // We only generate grid points for the bottom half to create a floor grid wave + const startRow = Math.floor(rows * 0.55); + + for (let r = startRow; r < rows; r++) { + for (let c = 0; c < cols; c++) { + particles.push({ + baseX: c * spacing, + baseY: r * spacing, + x: c * spacing, + y: r * spacing, + vx: 0, + vy: 0 + }); + } + } + } + + window.addEventListener('resize', resizeCanvas); + resizeCanvas(); + + const scene = document.querySelector('.hero-v2'); + scene.addEventListener('mousemove', e => { + const r = canvas.getBoundingClientRect(); + mouse.x = e.clientX - r.left; + mouse.y = e.clientY - r.top; + }); + + scene.addEventListener('mouseleave', () => { + mouse.x = -1000; + mouse.y = -1000; + }); + + function animate() { + ctx.clearRect(0, 0, canvas.width, canvas.height); + ctx.fillStyle = 'rgba(99, 102, 241, 0.25)'; + + particles.forEach(p => { + const dx = mouse.x - p.x; + const dy = mouse.y - p.y; + const dist = Math.sqrt(dx * dx + dy * dy); + const maxDist = 180; + + if (dist < maxDist) { + const force = (maxDist - dist) / maxDist; + p.vx -= (dx / dist) * force * 1.2; + p.vy -= (dy / dist) * force * 1.2; + } + + // Spring physics back to grid coordinate anchor + p.vx += (p.baseX - p.x) * 0.05; + p.vy += (p.baseY - p.y) * 0.05; + + // Friction damping + p.vx *= 0.83; + p.vy *= 0.83; + + p.x += p.vx; + p.y += p.vy; + + ctx.beginPath(); + ctx.arc(p.x, p.y, 1.5, 0, Math.PI * 2); + ctx.fill(); + }); + + animationFrameId = requestAnimationFrame(animate); + } + + animate(); +} diff --git a/revati-kadam-portfolio/js/navigation.js b/revati-kadam-portfolio/js/navigation.js index 28e9c4d..20e16bd 100644 --- a/revati-kadam-portfolio/js/navigation.js +++ b/revati-kadam-portfolio/js/navigation.js @@ -1,73 +1,256 @@ -// ── Show/hide sections (existing logic kept) ────────────────────────────── -function showSection(id) { - document.getElementById(id).scrollIntoView({ - behavior: "smooth" - }); +// ── DOM Elements +const navbar = document.getElementById("navbar"); +const navIndicator = document.getElementById("navIndicator"); +const desktopNavLinks = document.querySelectorAll(".desktop-nav .nav-link"); +const sidebarLinks = document.querySelectorAll(".sidebar-link"); +const allNavLinks = [...desktopNavLinks, ...sidebarLinks]; +const hamburger = document.getElementById("hamburger"); +const closeSidebarBtn = document.getElementById("closeSidebar"); +const sidebarDrawer = document.getElementById("sidebarDrawer"); +const navOverlay = document.getElementById("navOverlay"); +const sections = document.querySelectorAll(".section"); +let isMenuOpen = false; - updateActiveNav(id); -} +// ── Accessibility Closures +document.addEventListener("keydown", (e) => { + if (e.key === "Escape" && isMenuOpen) { + closeMenu(); + hamburger.focus(); + } +}); -// ── Active nav link highlight ────────────────────────────────────────────── -function updateActiveNav(activeId) { - document.querySelectorAll(".nav-links li").forEach(li => { - li.classList.remove("nav-active"); +if (navOverlay) { + navOverlay.addEventListener("click", () => { + if (isMenuOpen) closeMenu(); }); +} - // match the li whose onclick calls showSection('activeId') - document.querySelectorAll(".nav-links li").forEach(li => { - const onclick = li.getAttribute("onclick") || ""; - if (onclick.includes(`'${activeId}'`)) { - li.classList.add("nav-active"); +// ── Navbar Scroll Behavior +function handleScroll() { + const scrollTop = window.scrollY || document.documentElement.scrollTop; + + if (scrollTop > 50) { + navbar.classList.add("scrolled"); + } else { + navbar.classList.remove("scrolled"); + } + + let currentSection = ""; + sections.forEach(sec => { + const sectionTop = sec.offsetTop; + if (scrollTop >= sectionTop - 250) { + currentSection = sec.getAttribute("id"); } }); -} -// ── Scroll progress bar ──────────────────────────────────────────────────── -function initScrollProgress() { - const bar = document.getElementById("scroll-progress"); - if (!bar) return; + if (currentSection) { + updateActiveIndicator(currentSection); + } +} - const main = document.querySelector(".main"); - if (!main) return; +window.addEventListener("scroll", handleScroll); - main.addEventListener("scroll", () => { - const scrollTop = main.scrollTop; - const scrollMax = main.scrollHeight - main.clientHeight; - const pct = scrollMax > 0 ? (scrollTop / scrollMax) * 100 : 0; - bar.style.width = pct + "%"; +// ── Update Active Indicator +function updateActiveIndicator(activeId) { + allNavLinks.forEach(link => { + if (link.dataset.section === activeId) { + link.classList.add("active"); + + // If desktop/tablet, animate the sliding pill + if (window.innerWidth >= 768 && link.classList.contains("nav-link")) { + const linkRect = link.getBoundingClientRect(); + const navRect = document.getElementById("desktopNavLinks").getBoundingClientRect(); + const dotWidth = 6; + const centerX = (linkRect.left - navRect.left) + (linkRect.width / 2) - (dotWidth / 2); + + gsap.to(navIndicator, { + x: centerX, + width: dotWidth, + opacity: 1, + duration: 0.4, + ease: "power3.out", + overwrite: "auto" + }); + } + } else { + link.classList.remove("active"); + } }); } -// ── Section entrance animations via IntersectionObserver ────────────────── -function initSectionAnimations() { - // respect reduced-motion preference +// ── GSAP Navbar Entrance Animation +function animateNavbarEntrance() { if (window.matchMedia("(prefers-reduced-motion: reduce)").matches) return; + + gsap.fromTo(navbar, + { y: -100, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.8, ease: "power3.out" } + ); - const observer = new IntersectionObserver( - (entries) => { - entries.forEach(entry => { - if (entry.isIntersecting) { - entry.target.classList.add("section-visible"); - observer.unobserve(entry.target); // animate only once - } + if (window.innerWidth >= 768) { + gsap.fromTo(desktopNavLinks, + { y: -15, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.6, stagger: 0.1, ease: "power3.out", delay: 0.3 } + ); + } +} + +// ── Smooth Sliding Pill Hover Effect +desktopNavLinks.forEach(link => { + link.addEventListener("mouseenter", () => { + if (window.innerWidth >= 768) { + const linkRect = link.getBoundingClientRect(); + const navRect = document.getElementById("desktopNavLinks").getBoundingClientRect(); + const dotWidth = 6; + const centerX = (linkRect.left - navRect.left) + (linkRect.width / 2) - (dotWidth / 2); + + gsap.to(navIndicator, { + x: centerX, + width: dotWidth, + opacity: 1, + duration: 0.3, + ease: "power2.out", + overwrite: "auto" }); - }, - { threshold: 0.15 } + } + }); + + link.addEventListener("click", (e) => { + e.preventDefault(); + document.getElementById(link.dataset.section).scrollIntoView({ behavior: "smooth" }); + }); +}); + +const desktopNavContainer = document.getElementById("desktopNavLinks"); +if (desktopNavContainer) { + desktopNavContainer.addEventListener("mouseleave", () => { + if (window.innerWidth >= 768) { + const activeLink = document.querySelector(".desktop-nav .nav-link.active"); + if (activeLink) { + const linkRect = activeLink.getBoundingClientRect(); + const navRect = desktopNavContainer.getBoundingClientRect(); + const dotWidth = 6; + const centerX = (linkRect.left - navRect.left) + (linkRect.width / 2) - (dotWidth / 2); + + gsap.to(navIndicator, { + x: centerX, + width: dotWidth, + opacity: 1, + duration: 0.4, + ease: "power3.out", + overwrite: "auto" + }); + } else { + gsap.to(navIndicator, { opacity: 0, duration: 0.3 }); + } + } + }); +} + +const logoLink = document.querySelector(".logo"); +if (logoLink) { + logoLink.addEventListener("click", () => { + window.scrollTo({ top: 0, behavior: "smooth" }); + }); +} + +// ── Sidebar Clicks +sidebarLinks.forEach(link => { + link.addEventListener("click", (e) => { + e.preventDefault(); + closeMenu(); + document.getElementById(link.dataset.section).scrollIntoView({ behavior: "smooth" }); + }); +}); + +// ── Mobile Sidebar Drawer GSAP Logic +function openMenu() { + isMenuOpen = true; + document.body.style.overflow = "hidden"; // Prevent scroll + + hamburger.classList.add("is-active"); + hamburger.setAttribute("aria-expanded", "true"); + sidebarDrawer.setAttribute("aria-hidden", "false"); + + gsap.to(navOverlay, { autoAlpha: 1, duration: 0.4, ease: "power2.inOut" }); + gsap.to(sidebarDrawer, { x: "0%", duration: 0.6, ease: "power3.out" }); + + gsap.fromTo(sidebarLinks, + { y: 20, opacity: 0 }, + { y: 0, opacity: 1, duration: 0.4, stagger: 0.08, ease: "power2.out", delay: 0.2 } ); +} - document.querySelectorAll(".section").forEach(sec => observer.observe(sec)); +function closeMenu() { + isMenuOpen = false; + document.body.style.overflow = ""; // Restore scroll + + hamburger.classList.remove("is-active"); + hamburger.setAttribute("aria-expanded", "false"); + sidebarDrawer.setAttribute("aria-hidden", "true"); + + gsap.to(sidebarLinks, { + y: 20, opacity: 0, duration: 0.2, stagger: { each: 0.03, from: "end" }, ease: "power2.in" + }); + + gsap.to(sidebarDrawer, { x: "100%", duration: 0.5, ease: "power3.inOut", delay: 0.1 }); + gsap.to(navOverlay, { autoAlpha: 0, duration: 0.4, ease: "power2.inOut", delay: 0.2 }); } -// ── Toggle hamburger menu ────────────────────────────────────────────────── -function toggleNavbar() { - const nav = document.getElementById("navLinks"); - nav.classList.toggle("show"); +if (hamburger) { + hamburger.addEventListener("click", () => { + if (isMenuOpen) closeMenu(); + else openMenu(); + }); +} + +if (closeSidebarBtn) { + closeSidebarBtn.addEventListener("click", closeMenu); +} + +// ── Handle Resize +window.addEventListener("resize", () => { + if (window.innerWidth >= 768 && isMenuOpen) { + closeMenu(); + } + if (window.innerWidth >= 768) { + const activeLink = document.querySelector(".desktop-nav .nav-link.active"); + if (activeLink) updateActiveIndicator(activeLink.dataset.section); + } +}); + +// ── Scroll Progress & Observer Initialization +function initScrollProgress() { + const bar = document.getElementById("scroll-progress"); + if (!bar) return; + + window.addEventListener("scroll", () => { + const scrollTop = window.scrollY || document.documentElement.scrollTop; + const scrollMax = document.documentElement.scrollHeight - document.documentElement.clientHeight; + const pct = scrollMax > 0 ? (scrollTop / scrollMax) * 100 : 0; + bar.style.width = pct + "%"; + }); +} + +function initSectionAnimations() { + if (window.matchMedia("(prefers-reduced-motion: reduce)").matches) return; + const observer = new IntersectionObserver((entries) => { + entries.forEach(entry => { + if (entry.isIntersecting) { + entry.target.classList.add("section-visible"); + observer.unobserve(entry.target); + } + }); + }, { threshold: 0.15 }); + + sections.forEach(sec => observer.observe(sec)); } -// ── Init on DOM ready ────────────────────────────────────────────────────── +// ── Init on DOM ready document.addEventListener("DOMContentLoaded", () => { - // show home by default and highlight its nav link - showSection("home"); + gsap.set(sidebarDrawer, { x: "100%" }); // Initialize drawer position + animateNavbarEntrance(); + handleScroll(); initScrollProgress(); initSectionAnimations(); }); \ No newline at end of file diff --git a/revati-kadam-portfolio/js/preloader.js b/revati-kadam-portfolio/js/preloader.js new file mode 100644 index 0000000..15da046 --- /dev/null +++ b/revati-kadam-portfolio/js/preloader.js @@ -0,0 +1,210 @@ +const prefersReducedMotion = window.matchMedia('(prefers-reduced-motion: reduce)').matches; + +document.addEventListener('DOMContentLoaded', () => { + if (prefersReducedMotion) { + const loader = document.getElementById("preloader"); + if (loader) loader.style.display = "none"; + document.body.classList.remove("loading"); + if (typeof initHeroV2 === "function") { + initHeroV2(); + } + return; + } + + startPreloaderAnimation(); +}); + +function startPreloaderAnimation() { + const circleEl = document.getElementById("preloaderCircle"); + + // Set up GSAP timeline + const tl = gsap.timeline(); + + // 1. Premium Logo Character Reveal (Staggered scale, translation, and rotational flip) + tl.fromTo('.preloader-logo span', + { y: 40, rotateX: -60, opacity: 0 }, + { y: 0, rotateX: 0, opacity: 1, duration: 0.8, stagger: 0.04, ease: "back.out(1.5)" } + ); + + // Status messages and transition tracking variables + const statusMessages = [ + { min: 0, max: 20, text: "CONNECTING TO PORTFOLIO NODE..." }, + { min: 20, max: 45, text: "INITIALIZING DIGITAL GRIDS..." }, + { min: 45, max: 70, text: "RESOLVING IMMERSIVE PHYSICS..." }, + { min: 70, max: 90, text: "STABILIZING GRAPHICS MESH..." }, + { min: 90, max: 100, text: "PREPARING INTERFACE..." } + ]; + + let lastHundreds = -1; + let lastTens = -1; + let lastOnes = -1; + let lastStatusText = ""; + + // Progress tracker object + const progressObj = { value: 0 }; + + // 2. Count progress from 0 to 100 + tl.to(progressObj, { + value: 100, + duration: 2.2, + ease: "power2.out", + onUpdate: () => { + const roundedVal = Math.floor(progressObj.value); + + // A. Update Circular Progress Stroke + if (circleEl) { + // stroke-dasharray is 282.7 (2 * PI * r) + const offset = 282.7 - (roundedVal / 100) * 282.7; + circleEl.style.strokeDashoffset = offset; + } + + // B. Calculate digits for mechanical rolling ticker + const hundreds = Math.floor(roundedVal / 100); + const tens = Math.floor((roundedVal % 100) / 10); + const ones = roundedVal % 10; + + // C. Animate Hundreds Digit Column (only visible at >= 100%) + if (hundreds !== lastHundreds) { + lastHundreds = hundreds; + const col = document.getElementById("tickerHundreds"); + if (col) { + if (hundreds > 0) { + col.classList.add("visible"); + } + gsap.to(col, { y: -hundreds * 36, duration: 0.4, ease: "back.out(1.2)" }); + } + } + + // D. Animate Tens Digit Column + if (tens !== lastTens) { + lastTens = tens; + const col = document.getElementById("tickerTens"); + if (col) { + gsap.to(col, { y: -tens * 36, duration: 0.35, ease: "back.out(1.2)" }); + } + } + + // E. Animate Ones Digit Column + if (ones !== lastOnes) { + lastOnes = ones; + const col = document.getElementById("tickerOnes"); + if (col) { + gsap.to(col, { y: -ones * 36, duration: 0.15, ease: "power1.out" }); + } + } + + // F. Smooth change transition for status messages + const activeMsg = statusMessages.find(m => roundedVal >= m.min && roundedVal <= m.max)?.text || ""; + if (activeMsg !== lastStatusText) { + lastStatusText = activeMsg; + const statusEl = document.getElementById("preloaderStatus"); + if (statusEl) { + gsap.to(statusEl, { + opacity: 0, + y: -5, + duration: 0.1, + onComplete: () => { + statusEl.innerText = activeMsg; + gsap.to(statusEl, { opacity: 0.8, y: 0, duration: 0.15 }); + } + }); + } + } + }, + onComplete: dismissPreloader + }, "-=0.2"); +} + +function dismissPreloader() { + const exitTimeline = gsap.timeline({ + onComplete: () => { + const loader = document.getElementById("preloader"); + if (loader) loader.style.display = "none"; + document.body.classList.remove("loading"); + } + }); + + // 1. Stagger letters out upwards with tilt rotation + exitTimeline.to('.preloader-logo span', { + y: -40, + rotateX: 45, + opacity: 0, + duration: 0.45, + stagger: 0.02, + ease: "power2.in" + }, 0); + + // 2. Fade out other loading dashboard components + exitTimeline.to(['.preloader-dashboard', '.preloader-radial'], { + opacity: 0, + scale: 0.9, + duration: 0.4, + ease: "power2.in" + }, 0); + + // 3. Staggered, skewed diagonal curtain split reveals + + // LAYER 1: Frontmost solid curtains + exitTimeline.to('.preloader-curtain--left.preloader-curtain--layer1', { + xPercent: -105, + skewX: -10, + duration: 1.1, + ease: "power3.inOut" + }, 0.2); + + exitTimeline.to('.preloader-curtain--right.preloader-curtain--layer1', { + xPercent: 105, + skewX: 10, + duration: 1.1, + ease: "power3.inOut" + }, "<"); + + // LAYER 2: Middle colored gradient curtains + exitTimeline.to('.preloader-curtain--left.preloader-curtain--layer2', { + xPercent: -105, + skewX: -7, + duration: 1.25, + ease: "power3.inOut" + }, 0.28); + + exitTimeline.to('.preloader-curtain--right.preloader-curtain--layer2', { + xPercent: 105, + skewX: 7, + duration: 1.25, + ease: "power3.inOut" + }, "<"); + + // LAYER 3: Backmost glassmorphic blur curtains + exitTimeline.to('.preloader-curtain--left.preloader-curtain--layer3', { + xPercent: -105, + skewX: -4, + duration: 1.4, + ease: "power3.inOut" + }, 0.36); + + exitTimeline.to('.preloader-curtain--right.preloader-curtain--layer3', { + xPercent: 105, + skewX: 4, + duration: 1.4, + ease: "power3.inOut" + }, "<"); + + // 4. Hero Cinematic Handoff + const heroEl = document.querySelector('.hero-v2'); + if (heroEl) { + gsap.set(heroEl, { scale: 0.96, filter: "blur(8px)" }); + exitTimeline.to(heroEl, { + scale: 1, + filter: "blur(0px)", + duration: 1.5, + ease: "power2.out" + }, 0.36); // Starts exactly when the glassmorphic layer begins to pull back + } + + // Trigger standard hero element staggers mid-reveal + exitTimeline.call(() => { + if (typeof initHeroV2 === "function") { + initHeroV2(); + } + }, null, 0.44); +} diff --git a/revati-kadam-portfolio/js/script.js b/revati-kadam-portfolio/js/script.js index 660aad5..96a708a 100644 --- a/revati-kadam-portfolio/js/script.js +++ b/revati-kadam-portfolio/js/script.js @@ -2,13 +2,15 @@ function showSection(id) { document.getElementById(id).scrollIntoView({ behavior: "smooth" }); } -const roles = ["Web Developer", "Programmer", "Problem Solver", "Website Designer", "Tech Enthusiast"]; +const roles = ["digital products", "web applications", "modern websites", "interactive UIs", "clean code"]; let i = 0, j = 0, del = false; function type() { + const el = document.getElementById("typing"); + if (!el) return; // Hero V2 uses role drum instead let text = roles[i]; j = del ? j - 1 : j + 1; - document.getElementById("typing").innerText = text.substring(0, j); + el.innerText = text.substring(0, j); if (!del && j === text.length) { del = true; return setTimeout(type, 1500); @@ -21,6 +23,7 @@ function type() { } type(); + (function() { const saved = localStorage.getItem("theme"); if (saved === "light") document.body.classList.add("light-theme");