Spaces:
Running
Running
File size: 2,757 Bytes
b2d9c8d | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 |
// Theme switcher functionality
document.addEventListener('DOMContentLoaded', () => {
// Check for saved theme preference or use system preference
const savedTheme = localStorage.getItem('theme') ||
(window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light');
document.documentElement.classList.toggle('dark', savedTheme === 'dark');
// Theme toggle button
document.querySelectorAll('[data-theme-toggle]').forEach(btn => {
btn.addEventListener('click', () => {
const isDark = document.documentElement.classList.toggle('dark');
localStorage.setItem('theme', isDark ? 'dark' : 'light');
// Update all theme toggle buttons
document.querySelectorAll('[data-theme-toggle]').forEach(el => {
const icon = el.querySelector('[data-feather]');
if (icon) {
icon.setAttribute('data-feather', isDark ? 'sun' : 'moon');
feather.replace();
}
});
});
});
// Smooth scroll for anchor links
document.querySelectorAll('a[href^="#"]').forEach(anchor => {
anchor.addEventListener('click', function (e) {
e.preventDefault();
document.querySelector(this.getAttribute('href')).scrollIntoView({
behavior: 'smooth'
});
});
});
// Copy code snippet functionality
document.addEventListener('click', (e) => {
if (e.target.closest('[data-copy-btn]')) {
const btn = e.target.closest('[data-copy-btn]');
const code = btn.parentElement.querySelector('code').innerText;
navigator.clipboard.writeText(code).then(() => {
const originalHtml = btn.innerHTML;
btn.innerHTML = '<span>Copied!</span>';
setTimeout(() => {
btn.innerHTML = originalHtml;
}, 2000);
});
}
});
});
// Intersection Observer for animations
const animateOnScroll = () => {
const observers = [];
const fadeUpObserver = new IntersectionObserver((entries) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
entry.target.classList.add('animate-fade-up');
fadeUpObserver.unobserve(entry.target);
}
});
}, { threshold: 0.1 });
document.querySelectorAll('[data-animate="fade-up"]').forEach(el => {
fadeUpObserver.observe(el);
});
observers.push(fadeUpObserver);
return () => observers.forEach(obs => obs.disconnect());
};
document.addEventListener('DOMContentLoaded', animateOnScroll);
|