// Theme toggle functionality
const themeToggle = document.getElementById('themeToggle');
const html = document.documentElement;
// Add null check for themeToggle
if (themeToggle) {
const icon = themeToggle.querySelector('i');
// Check for saved theme preference or default to dark
const currentTheme = localStorage.getItem('theme') || 'dark';
html.classList.toggle('dark', currentTheme === 'dark');
updateThemeIcon(currentTheme);
function updateThemeIcon(theme) {
if (theme === 'dark') {
icon.setAttribute('data-feather', 'sun');
} else {
icon.setAttribute('data-feather', 'moon');
}
feather.replace();
}
themeToggle.addEventListener('click', () => {
const newTheme = html.classList.contains('dark') ? 'light' : 'dark';
html.classList.toggle('dark');
localStorage.setItem('theme', newTheme);
updateThemeIcon(newTheme);
});
}
// Initialize on page load
document.addEventListener('DOMContentLoaded', () => {
feather.replace();
// Add loading animation
document.body.classList.add('animate-fade-in');
// Initialize tooltips or other interactive elements
console.log('Khmer23 Luxury Real Estate Platform Initialized');
// Ensure navbar component is loaded
const navbar = document.querySelector('custom-navbar');
const backupNav = document.getElementById('backup-nav');
if (navbar) {
console.log('Navbar component found and loaded');
// Hide backup nav if component loads
if (backupNav) {
backupNav.classList.add('hidden');
}
} else {
console.error('Navbar component not found! Using backup navigation');
// Show backup nav if component fails
if (backupNav) {
backupNav.classList.remove('hidden');
}
// Adjust body padding for backup nav
document.body.style.paddingTop = '80px';
}
});
// Live activity feed
const activities = [
{ type: 'sale', location: 'Kep', price: '$2.4M', status: 'closed' },
{ type: 'rental', location: 'Phnom Penh', price: '$8,500/mo', status: 'signed' },
{ type: 'sale', location: 'Sihanoukville', price: '$3.1M', status: 'pending' },
{ type: 'rental', location: 'Kampot', price: '$6,200/mo', status: 'closed' },
{ type: 'sale', location: 'Phnom Penh', price: '$5.2M', status: 'closed' },
{ type: 'rental', location: 'Kep', price: '$12,000/mo', status: 'signed' }
];
function addActivityItem() {
const feed = document.getElementById('activityFeed');
if (!feed) return;
const activity = activities[Math.floor(Math.random() * activities.length)];
const item = document.createElement('div');
item.className = 'activity-item flex items-center justify-between py-2 border-b border-slate-800 last:border-0';
const icon = activity.type === 'sale' ? '🏠' : '🔑';
const color = activity.status === 'closed' ? 'text-emerald-400' : activity.status === 'signed' ? 'text-amber-400' : 'text-slate-500';
item.innerHTML = `
${icon}
${activity.type} • ${activity.location}
${activity.price}
${formatTime(Date.now())}
`;
feed.insertBefore(item, feed.firstChild);
// Keep only last 4 activities
while (feed.children.length > 4) {
feed.removeChild(feed.lastChild);
}
}
function formatTime(timestamp) {
const now = new Date();
const time = new Date(timestamp);
const diff = Math.floor((now - time) / 1000);
if (diff < 60) return 'Just now';
if (diff < 3600) return `${Math.floor(diff / 60)}m ago`;
if (diff < 86400) return `${Math.floor(diff / 3600)}h ago`;
return `${Math.floor(diff / 86400)}d ago`;
}
// Initialize activity feed
if (document.getElementById('activityFeed')) {
// Add initial activities
for (let i = 0; i < 3; i++) {
addActivityItem();
}
// Add new activity every 10 seconds
setInterval(addActivityItem, 10000);
}
// Contact form handling
const contactForm = document.getElementById('contactForm');
if (contactForm) {
contactForm.addEventListener('submit', (e) => {
e.preventDefault();
// Show success message
const formContainer = contactForm.parentElement;
formContainer.innerHTML = `
Request Received
Your inquiry has been submitted for review. Our membership committee will contact qualified candidates within 72 hours.
Next Steps:
- • Preliminary qualification review (24-48 hours)
- • Background verification (additional 24 hours)
- • Personal consultation by invitation only
- • Access to exclusive property portfolio
Return to Home
`;
feather.replace();
});
}
// Smooth scroll for anchor links
document.querySelectorAll('a[href^="#"]').forEach(anchor => {
anchor.addEventListener('click', function (e) {
e.preventDefault();
const target = document.querySelector(this.getAttribute('href'));
if (target) {
target.scrollIntoView({
behavior: 'smooth',
block: 'start'
});
}
});
});
// Intersection Observer for fade-in animations
const observerOptions = {
threshold: 0.1,
rootMargin: '0px 0px -50px 0px'
};
const observer = new IntersectionObserver((entries) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
entry.target.classList.add('animate-fade-in');
observer.unobserve(entry.target);
}
});
}, observerOptions);
// Observe elements for animation
document.querySelectorAll('section').forEach(section => {
observer.observe(section);
});
// Property filter functionality
const filterSelects = document.querySelectorAll('select');
filterSelects.forEach(select => {
select.addEventListener('change', () => {
// Add filter animation
const cards = document.querySelectorAll('.group.cursor-pointer');
cards.forEach((card, index) => {
setTimeout(() => {
card.classList.add('animate-fade-in');
}, index * 100);
});
});
});
// Load more functionality
const loadMoreBtn = document.querySelector('button:has([text="Load More"])');
if (loadMoreBtn) {
loadMoreBtn.addEventListener('click', () => {
loadMoreBtn.innerHTML = 'Loading...';
setTimeout(() => {
loadMoreBtn.innerHTML = 'No More Properties';
loadMoreBtn.disabled = true;
loadMoreBtn.classList.add('opacity-50', 'cursor-not-allowed');
}, 1500);
});
}
// Parallax effect for hero images
window.addEventListener('scroll', () => {
const scrolled = window.pageYOffset;
const parallaxElements = document.querySelectorAll('.parallax');
parallaxElements.forEach(element => {
const speed = element.dataset.speed || 0.5;
element.style.transform = `translateY(${scrolled * speed}px)`;
});
});
// Initialize on page load
document.addEventListener('DOMContentLoaded', () => {
feather.replace();
// Add loading animation
document.body.classList.add('animate-fade-in');
// Initialize tooltips or other interactive elements
console.log('Khmer23 Luxury Real Estate Platform Initialized');
});
// Performance optimization - lazy loading images
if ('IntersectionObserver' in window) {
const imageObserver = new IntersectionObserver((entries, observer) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
const img = entry.target;
img.src = img.dataset.src;
img.classList.remove('lazy');
imageObserver.unobserve(img);
}
});
});
document.querySelectorAll('img[data-src]').forEach(img => {
imageObserver.observe(img);
});
}