<div class="grid-gallery-container">
<div class="filter-tabs">
<button class="filter-btn active" data-filter="all">All</button>
<button class="filter-btn" data-filter="nature">Nature</button>
<button class="filter-btn" data-filter="city">City</button>
<button class="filter-btn" data-filter="people">People</button>
</div>
<div class="grid-gallery">
<div class="grid-item" data-category="nature">
<img src="https://images.unsplash.com/photo-1506905925346-21bda4d32df4?w=300&h=300&fit=crop" alt="Mountain" />
<div class="item-overlay">
<h4>Mountain Peak</h4>
<span class="category-tag">Nature</span>
</div>
</div>
<div class="grid-item" data-category="city">
<img src="https://images.unsplash.com/photo-1449824913935-59a10b8d2000?w=300&h=300&fit=crop" alt="City" />
<div class="item-overlay">
<h4>Urban Lights</h4>
<span class="category-tag">City</span>
</div>
</div>
<div class="grid-item" data-category="people">
<img src="https://images.unsplash.com/photo-1507003211169-0a1dd7228f2d?w=300&h=300&fit=crop" alt="Portrait" />
<div class="item-overlay">
<h4>Portrait</h4>
<span class="category-tag">People</span>
</div>
</div>
<div class="grid-item" data-category="nature">
<img src="https://images.unsplash.com/photo-1441974231531-c6227db76b6e?w=300&h=300&fit=crop" alt="Forest" />
<div class="item-overlay">
<h4>Forest Path</h4>
<span class="category-tag">Nature</span>
</div>
</div>
<div class="grid-item" data-category="city">
<img src="https://images.unsplash.com/photo-1480714378408-67cf0d13bc1f?w=300&h=300&fit=crop" alt="Architecture" />
<div class="item-overlay">
<h4>Architecture</h4>
<span class="category-tag">City</span>
</div>
</div>
<div class="grid-item" data-category="people">
<img src="https://images.unsplash.com/photo-1472099645785-5658abf4ff4e?w=300&h=300&fit=crop" alt="Team" />
<div class="item-overlay">
<h4>Team Work</h4>
<span class="category-tag">People</span>
</div>
</div>
</div>
</div>
.grid-gallery-container {
background: #f8f9fa;
padding: 30px;
border-radius: 15px;
}
.filter-tabs {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 30px;
flex-wrap: wrap;
}
.filter-btn {
padding: 10px 20px;
border: 2px solid #e9ecef;
background: white;
color: #6c757d;
border-radius: 25px;
cursor: pointer;
transition: all 0.3s ease;
font-weight: 500;
font-size: 14px;
}
.filter-btn:hover {
border-color: #667eea;
color: #667eea;
transform: translateY(-2px);
}
.filter-btn.active {
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
border-color: #667eea;
color: white;
box-shadow: 0 4px 15px rgba(102, 126, 234, 0.3);
}
.grid-gallery {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
gap: 20px;
max-width: 1200px;
margin: 0 auto;
}
.grid-item {
position: relative;
border-radius: 12px;
overflow: hidden;
cursor: pointer;
transition: all 0.4s ease;
background: white;
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
}
.grid-item:hover {
transform: translateY(-8px);
box-shadow: 0 12px 30px rgba(0, 0, 0, 0.15);
}
.grid-item img {
width: 100%;
height: 250px;
object-fit: cover;
transition: transform 0.4s ease;
}
.grid-item:hover img {
transform: scale(1.1);
}
.item-overlay {
position: absolute;
bottom: 0;
left: 0;
right: 0;
background: linear-gradient(
to top,
rgba(0, 0, 0, 0.8) 0%,
rgba(0, 0, 0, 0.4) 50%,
transparent 100%
);
color: white;
padding: 20px;
transform: translateY(100%);
transition: transform 0.3s ease;
}
.grid-item:hover .item-overlay {
transform: translateY(0);
}
.item-overlay h4 {
margin: 0 0 8px 0;
font-size: 18px;
font-weight: 600;
}
.category-tag {
display: inline-block;
background: rgba(255, 255, 255, 0.2);
padding: 4px 12px;
border-radius: 15px;
font-size: 12px;
font-weight: 500;
backdrop-filter: blur(10px);
border: 1px solid rgba(255, 255, 255, 0.3);
}
/* Filter animations */
.grid-item.hide {
opacity: 0;
transform: scale(0.8);
pointer-events: none;
}
.grid-item.show {
opacity: 1;
transform: scale(1);
pointer-events: auto;
}
/* Responsive design */
@media (max-width: 768px) {
.grid-gallery-container {
padding: 20px;
}
.grid-gallery {
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 15px;
}
.grid-item img {
height: 200px;
}
.filter-tabs {
gap: 8px;
}
.filter-btn {
padding: 8px 16px;
font-size: 13px;
}
}
@media (max-width: 480px) {
.grid-gallery {
grid-template-columns: 1fr 1fr;
gap: 10px;
}
.grid-item img {
height: 150px;
}
.item-overlay {
padding: 15px;
}
.item-overlay h4 {
font-size: 16px;
}
}
/* Loading animation */
.grid-item {
animation: fadeInScale 0.6s ease-out;
}
.grid-item:nth-child(1) { animation-delay: 0.1s; }
.grid-item:nth-child(2) { animation-delay: 0.2s; }
.grid-item:nth-child(3) { animation-delay: 0.3s; }
.grid-item:nth-child(4) { animation-delay: 0.4s; }
.grid-item:nth-child(5) { animation-delay: 0.5s; }
.grid-item:nth-child(6) { animation-delay: 0.6s; }
@keyframes fadeInScale {
from {
opacity: 0;
transform: scale(0.8);
}
to {
opacity: 1;
transform: scale(1);
}
}
document.addEventListener('DOMContentLoaded', function() {
const filterBtns = document.querySelectorAll('.filter-btn');
const gridItems = document.querySelectorAll('.grid-item');
// Filter functionality
filterBtns.forEach(btn => {
btn.addEventListener('click', function() {
const filter = this.getAttribute('data-filter');
// Update active button
filterBtns.forEach(b => b.classList.remove('active'));
this.classList.add('active');
// Filter items
filterItems(filter);
});
});
function filterItems(filter) {
gridItems.forEach((item, index) => {
const category = item.getAttribute('data-category');
if (filter === 'all' || category === filter) {
// Show item with delay
setTimeout(() => {
item.classList.remove('hide');
item.classList.add('show');
}, index * 100);
} else {
// Hide item
item.classList.remove('show');
item.classList.add('hide');
}
});
}
// Initialize all items as visible
gridItems.forEach(item => {
item.classList.add('show');
});
// Click handlers for items
gridItems.forEach(item => {
item.addEventListener('click', function() {
const img = this.querySelector('img');
const title = this.querySelector('h4').textContent;
const category = this.querySelector('.category-tag').textContent;
// Add click animation
this.style.transform = 'scale(0.95)';
setTimeout(() => {
this.style.transform = '';
}, 150);
// You can add lightbox or modal functionality here
console.log(`Clicked: ${title} (${category})`);
// Example: Show alert with image info
showImageInfo(title, category, img.src);
});
});
function showImageInfo(title, category, imageSrc) {
// Create a simple modal
const modal = document.createElement('div');
modal.style.cssText = `
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.8);
display: flex;
align-items: center;
justify-content: center;
z-index: 1000;
animation: fadeIn 0.3s ease;
`;
modal.innerHTML = `
<div style="
background: white;
padding: 30px;
border-radius: 15px;
text-align: center;
max-width: 400px;
animation: scaleIn 0.3s ease;
">
<img src="${imageSrc}" style="
width: 100%;
height: 200px;
object-fit: cover;
border-radius: 10px;
margin-bottom: 20px;
" />
<h3 style="margin: 0 0 10px 0; color: #333;">${title}</h3>
<p style="margin: 0 0 20px 0; color: #666;">Category: ${category}</p>
<button onclick="this.closest('div').parentElement.remove()" style="
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
color: white;
border: none;
padding: 10px 20px;
border-radius: 25px;
cursor: pointer;
font-weight: 500;
">Close</button>
</div>
`;
document.body.appendChild(modal);
// Close on backdrop click
modal.addEventListener('click', function(e) {
if (e.target === modal) {
modal.remove();
}
});
}
// Add required animations to head
const animations = `
@keyframes fadeIn {
from { opacity: 0; }
to { opacity: 1; }
}
@keyframes scaleIn {
from { transform: scale(0.8); opacity: 0; }
to { transform: scale(1); opacity: 1; }
}
`;
const styleSheet = document.createElement('style');
styleSheet.textContent = animations;
document.head.appendChild(styleSheet);
});