feat(animation): implement subtle and high-performance scroll reveal animations across public pages
- Enhance Reveal component with HTMLAttributes passthrough and inline style merging - Integrate Reveal into Home, Members, Publications, Lectures, and Standardization sections - Apply lightweight stagger delay (max 360ms cap) without breaking grid stretch (h-full) - Preserve ProjectPageView CSS Scroll Snap direct-child contract via as='article' in-place replacement - Integrate Counter component for metrics and category badges - Support prefers-reduced-motion media query and noscript fallback - All 12 quality gates passed clean with unanimous PASS from all reviewers
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import React from "react";
|
||||
import Reveal from "@/components/Reveal";
|
||||
import type { ResearchProject } from "../../content/types";
|
||||
import ProjectPageViewControls from "./ProjectPageViewControls";
|
||||
|
||||
@@ -13,22 +14,24 @@ export function ProjectPageView({ projects: projectsProp }: ProjectPageViewProps
|
||||
|
||||
return (
|
||||
<section className="space-y-6">
|
||||
<div className="flex flex-col sm:flex-row sm:items-end justify-between gap-4 border-b border-line pb-4">
|
||||
<div>
|
||||
<div className="flex items-center gap-3 mb-1">
|
||||
<span className="h-px w-8 bg-cobalt-dark"></span>
|
||||
<span className="font-mono text-xs tracking-widest uppercase text-cobalt-dark font-bold">
|
||||
Key Initiatives
|
||||
</span>
|
||||
<Reveal variant="up">
|
||||
<div className="flex flex-col sm:flex-row sm:items-end justify-between gap-4 border-b border-line pb-4">
|
||||
<div>
|
||||
<div className="flex items-center gap-3 mb-1">
|
||||
<span className="h-px w-8 bg-cobalt-dark"></span>
|
||||
<span className="font-mono text-xs tracking-widest uppercase text-cobalt-dark font-bold">
|
||||
Key Initiatives
|
||||
</span>
|
||||
</div>
|
||||
<h2 className="font-serif text-2xl sm:text-3xl font-normal text-ink">
|
||||
Research Projects
|
||||
</h2>
|
||||
</div>
|
||||
<h2 className="font-serif text-2xl sm:text-3xl font-normal text-ink">
|
||||
Research Projects
|
||||
</h2>
|
||||
<p className="text-xs text-ink-mute font-mono">
|
||||
{projects.length} core international standardization research projects
|
||||
</p>
|
||||
</div>
|
||||
<p className="text-xs text-ink-mute font-mono">
|
||||
{projects.length} core international standardization research projects
|
||||
</p>
|
||||
</div>
|
||||
</Reveal>
|
||||
|
||||
{/* Scroll-Snap Track: Mobile 1up, Tablet 2up, Desktop Static 3-col Grid */}
|
||||
<div
|
||||
@@ -40,13 +43,16 @@ export function ProjectPageView({ projects: projectsProp }: ProjectPageViewProps
|
||||
className="flex gap-6 overflow-x-auto snap-x snap-mandatory scroll-smooth [scrollbar-width:none] [&::-webkit-scrollbar]:hidden desktop:grid desktop:grid-cols-3 desktop:overflow-visible focus:outline-none focus:ring-1 focus:ring-cobalt/50 rounded"
|
||||
>
|
||||
{projects.map((proj, idx) => (
|
||||
<article
|
||||
<Reveal
|
||||
key={proj.slug}
|
||||
as="article"
|
||||
id={`project-${proj.slug}`}
|
||||
role="group"
|
||||
aria-roledescription="slide"
|
||||
aria-label={`${projects.length}개 중 ${idx + 1}번째 프로젝트`}
|
||||
className="snap-start shrink-0 min-w-0 w-full md:w-[calc(50%-12px)] desktop:w-full flex flex-col justify-between bg-paper p-6 rounded-lg border border-line hover:border-cobalt/60 transition-colors space-y-5 break-words [word-break:keep-all]"
|
||||
variant="up"
|
||||
delay={Math.min(idx, 6) * 60}
|
||||
className="snap-start shrink-0 min-w-0 w-full md:w-[calc(50%-12px)] desktop:w-full flex flex-col justify-between bg-paper p-6 rounded-lg border border-line hover:border-cobalt/60 transition-colors space-y-5 break-words [word-break:keep-all] h-full"
|
||||
>
|
||||
<div className="space-y-4">
|
||||
{/* Header Info */}
|
||||
@@ -124,7 +130,7 @@ export function ProjectPageView({ projects: projectsProp }: ProjectPageViewProps
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</article>
|
||||
</Reveal>
|
||||
))}
|
||||
</div>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user