feat: implement portfolio dashboard with skill, experience, and message management features

This commit is contained in:
Yolando
2026-04-03 17:02:54 +07:00
parent ef6b44604a
commit e0f6e4bd8b
34 changed files with 2128 additions and 435 deletions

View File

@@ -64,6 +64,21 @@ export function ProjectsSection({ initialProjects }: { initialProjects?: any[] }
</div>
</AnimatedSection>
{/* Empty state */}
{filteredProjects.length === 0 ? (
<AnimatedSection delay={0.2}>
<div className="flex flex-col items-center justify-center py-20 text-center">
<div className="w-20 h-20 rounded-2xl bg-muted/50 border border-border/50 flex items-center justify-center mb-6">
<Layers size={32} className="text-muted-foreground/40" />
</div>
<h3 className="text-lg font-bold mb-2">Belum ada project</h3>
<p className="text-sm text-muted-foreground max-w-sm">
Project sedang dalam persiapan. Nantikan case study yang akan datang!
</p>
</div>
</AnimatedSection>
) : (
<>
{/* Projects grid */}
<motion.div
layout
@@ -79,7 +94,7 @@ export function ProjectsSection({ initialProjects }: { initialProjects?: any[] }
exit={{ opacity: 0, scale: 0.9 }}
transition={{ duration: 0.3 }}
>
<div className="group relative h-full flex flex-col p-6 rounded-2xl bg-card border border-border/50 hover:border-accent/30 transition-all duration-500 hover:shadow-lg hover:shadow-accent/5">
<div className="project-card group relative h-full flex flex-col p-6 rounded-2xl bg-card border border-border/50 hover:border-accent/30 transition-all duration-500">
{/* Category badge */}
<div className="flex items-center justify-between mb-4">
<span
@@ -123,12 +138,13 @@ export function ProjectsSection({ initialProjects }: { initialProjects?: any[] }
{/* Image banner */}
{project.imageUrl && (
<div className="w-full h-40 mb-4 rounded-xl overflow-hidden bg-muted/20 relative group-hover:shadow-md transition-shadow">
<div className="w-full h-40 mb-4 rounded-xl overflow-hidden bg-muted/20 relative">
<img
src={project.imageUrl}
alt={project.title}
className="w-full h-full object-cover group-hover:scale-105 transition-transform duration-500"
className="w-full h-full object-cover group-hover:scale-110 transition-transform duration-700"
/>
<div className="absolute inset-0 bg-gradient-to-t from-card/40 to-transparent opacity-0 group-hover:opacity-100 transition-opacity duration-500" />
</div>
)}
@@ -166,6 +182,8 @@ export function ProjectsSection({ initialProjects }: { initialProjects?: any[] }
))}
</AnimatePresence>
</motion.div>
</>
)}
</div>
</section>
);