22 CSS Transition Effects 02 / 22
Slide-In Animation on Scroll
Intersection Observer scroll reveal with six directions — left, right, bottom, top, scale-up and rotate-in — plus stagger delay classes.
This is a full-page demo — interact inside the frame above, or open it in the playground for the full-screen experience.
The code
<div class="hero">
<div class="reveal from-bottom" style="transition-delay:0s">
<div style="font-family:'Syne Mono';font-size:.75rem;letter-spacing:.3em;color:#a78bfa;margin-bottom:16px;text-transform:uppercase">Scroll animation demo</div>
</div>
<div class="reveal from-bottom delay-1">
<h1>Slide In<em>On Scroll</em></h1>
</div>
<div class="reveal from-bottom delay-2">
<p>Elements animate into view as you scroll down the page — six different entrance directions, all pure CSS transitions triggered by an Intersection Observer.</p>
</div>
<div class="reveal from-bottom delay-3">
<div class="hero-hint">↓ SCROLL DOWN ↓</div>
</div>
</div>
<section>
<div class="reveal from-left"><div class="section-label">Features</div></div>
<div class="reveal from-left delay-1"><h2 class="section-title">Six entrance styles</h2></div>
<div class="cards">
<div class="card reveal from-bottom delay-1"><div class="num">01</div><h3>Slide from Left</h3><p>Elements enter from the left edge with a smooth easing curve.</p></div>
<div class="card reveal from-bottom delay-2"><div class="num">02</div><h3>Slide from Right</h3><p>Content appears from the right, ideal for alternating layouts.</p></div>
<div class="card reveal from-bottom delay-3"><div class="num">03</div><h3>Slide from Bottom</h3><p>Classic upward reveal — the most widely used scroll animation.</p></div>
<div class="card reveal scale-up delay-4"><div class="num">04</div><h3>Scale Up</h3><p>Items grow from 88% to 100% for a subtle but satisfying pop.</p></div>
<div class="card reveal rotate-in delay-5"><div class="num">05</div><h3>Rotate In</h3><p>A slight rotation combined with scale creates a card-flip feel.</p></div>
<div class="card reveal from-top delay-6"><div class="num">06</div><h3>Slide from Top</h3><p>Dropping elements downward — great for headings and badges.</p></div>
</div>
<div class="feature reveal from-bottom">
<div>
<h2>Staggered delay system</h2>
<p>Add <code>.delay-1</code> through <code>.delay-6</code> to children for a choreographed cascade effect. Each step adds 100ms of delay, giving groups of elements a natural rhythm.</p>
</div>
<div class="feature-visual">
<div class="fv-box reveal scale-up delay-1">🎯</div>
<div class="fv-box reveal scale-up delay-2">✦</div>
<div class="fv-box reveal scale-up delay-3">◈</div>
<div class="fv-box reveal scale-up delay-4">⬡</div>
</div>
</div>
<div class="reveal from-left"><div class="section-label">Social proof</div></div>
<div class="reveal from-left delay-1"><h2 class="section-title">Used by thousands</h2></div>
<div class="testimonials">
<div class="testi reveal from-left delay-1"><p>"The stagger delays make the whole page feel alive. Replaced our GSAP dependency with this pure CSS approach."</p><div class="testi-author"><div class="testi-avatar">AK</div><div><div class="testi-name">Alex Kim</div><div class="testi-role">Lead Developer</div></div></div></div>
<div class="testi reveal from-bottom delay-2"><p>"Buttery smooth on mobile. The reduced-motion support is exactly what we needed for accessibility compliance."</p><div class="testi-author"><div class="testi-avatar">SL</div><div><div class="testi-name">Sara Liu</div><div class="testi-role">UX Engineer</div></div></div></div>
<div class="testi reveal from-right delay-3"><p>"Implemented in 20 minutes. The Intersection Observer approach means zero layout jank during scroll."</p><div class="testi-author"><div class="testi-avatar">MR</div><div><div class="testi-name">Marcus Reid</div><div class="testi-role">Frontend Architect</div></div></div></div>
</div>
<div class="stats reveal scale-up">
<div class="stat"><div class="big">98%</div><span>Lighthouse score</span></div>
<div class="stat"><div class="big">6</div><span>Animation types</span></div>
<div class="stat"><div class="big">0kb</div><span>Dependencies</span></div>
<div class="stat"><div class="big">A11y</div><span>Reduced motion</span></div>
</div>
</section> <div class="hero">
<div class="reveal from-bottom" style="transition-delay:0s">
<div style="font-family:'Syne Mono';font-size:.75rem;letter-spacing:.3em;color:#a78bfa;margin-bottom:16px;text-transform:uppercase">Scroll animation demo</div>
</div>
<div class="reveal from-bottom delay-1">
<h1>Slide In<em>On Scroll</em></h1>
</div>
<div class="reveal from-bottom delay-2">
<p>Elements animate into view as you scroll down the page — six different entrance directions, all pure CSS transitions triggered by an Intersection Observer.</p>
</div>
<div class="reveal from-bottom delay-3">
<div class="hero-hint">↓ SCROLL DOWN ↓</div>
</div>
</div>
<section>
<div class="reveal from-left"><div class="section-label">Features</div></div>
<div class="reveal from-left delay-1"><h2 class="section-title">Six entrance styles</h2></div>
<div class="cards">
<div class="card reveal from-bottom delay-1"><div class="num">01</div><h3>Slide from Left</h3><p>Elements enter from the left edge with a smooth easing curve.</p></div>
<div class="card reveal from-bottom delay-2"><div class="num">02</div><h3>Slide from Right</h3><p>Content appears from the right, ideal for alternating layouts.</p></div>
<div class="card reveal from-bottom delay-3"><div class="num">03</div><h3>Slide from Bottom</h3><p>Classic upward reveal — the most widely used scroll animation.</p></div>
<div class="card reveal scale-up delay-4"><div class="num">04</div><h3>Scale Up</h3><p>Items grow from 88% to 100% for a subtle but satisfying pop.</p></div>
<div class="card reveal rotate-in delay-5"><div class="num">05</div><h3>Rotate In</h3><p>A slight rotation combined with scale creates a card-flip feel.</p></div>
<div class="card reveal from-top delay-6"><div class="num">06</div><h3>Slide from Top</h3><p>Dropping elements downward — great for headings and badges.</p></div>
</div>
<div class="feature reveal from-bottom">
<div>
<h2>Staggered delay system</h2>
<p>Add <code>.delay-1</code> through <code>.delay-6</code> to children for a choreographed cascade effect. Each step adds 100ms of delay, giving groups of elements a natural rhythm.</p>
</div>
<div class="feature-visual">
<div class="fv-box reveal scale-up delay-1">🎯</div>
<div class="fv-box reveal scale-up delay-2">✦</div>
<div class="fv-box reveal scale-up delay-3">◈</div>
<div class="fv-box reveal scale-up delay-4">⬡</div>
</div>
</div>
<div class="reveal from-left"><div class="section-label">Social proof</div></div>
<div class="reveal from-left delay-1"><h2 class="section-title">Used by thousands</h2></div>
<div class="testimonials">
<div class="testi reveal from-left delay-1"><p>"The stagger delays make the whole page feel alive. Replaced our GSAP dependency with this pure CSS approach."</p><div class="testi-author"><div class="testi-avatar">AK</div><div><div class="testi-name">Alex Kim</div><div class="testi-role">Lead Developer</div></div></div></div>
<div class="testi reveal from-bottom delay-2"><p>"Buttery smooth on mobile. The reduced-motion support is exactly what we needed for accessibility compliance."</p><div class="testi-author"><div class="testi-avatar">SL</div><div><div class="testi-name">Sara Liu</div><div class="testi-role">UX Engineer</div></div></div></div>
<div class="testi reveal from-right delay-3"><p>"Implemented in 20 minutes. The Intersection Observer approach means zero layout jank during scroll."</p><div class="testi-author"><div class="testi-avatar">MR</div><div><div class="testi-name">Marcus Reid</div><div class="testi-role">Frontend Architect</div></div></div></div>
</div>
<div class="stats reveal scale-up">
<div class="stat"><div class="big">98%</div><span>Lighthouse score</span></div>
<div class="stat"><div class="big">6</div><span>Animation types</span></div>
<div class="stat"><div class="big">0kb</div><span>Dependencies</span></div>
<div class="stat"><div class="big">A11y</div><span>Reduced motion</span></div>
</div>
</section>@import url('https://fonts.googleapis.com/css2?family=Syne:wght@400;700;800&family=Syne+Mono&display=swap');
*{margin:0;padding:0;box-sizing:border-box}
body{font-family:'Syne',sans-serif;background:#f5f0e8;color:#1a1a1a;overflow-x:hidden}
/* scroll reveal base */
.reveal{opacity:0;transition:opacity .7s ease,transform .7s cubic-bezier(.22,1,.36,1)}
.reveal.from-left{transform:translateX(-60px)}
.reveal.from-right{transform:translateX(60px)}
.reveal.from-bottom{transform:translateY(50px)}
.reveal.from-top{transform:translateY(-50px)}
.reveal.scale-up{transform:scale(.88)}
.reveal.rotate-in{transform:rotate(-8deg) scale(.9)}
.reveal.visible{opacity:1 !important;transform:none !important}
/* delays */
.delay-1{transition-delay:.1s}.delay-2{transition-delay:.2s}.delay-3{transition-delay:.3s}
.delay-4{transition-delay:.4s}.delay-5{transition-delay:.5s}.delay-6{transition-delay:.6s}
/* page layout */
.hero{min-height:100vh;display:flex;flex-direction:column;align-items:center;justify-content:center;text-align:center;padding:40px 24px;background:linear-gradient(160deg,#0f0f1a,#1a0a2e)}
.hero h1{font-size:clamp(3rem,10vw,7rem);font-weight:800;color:#fff;letter-spacing:-.04em;line-height:.9;margin-bottom:24px}
.hero h1 em{color:#a78bfa;font-style:normal;display:block}
.hero p{color:#9ca3af;font-size:1.1rem;max-width:50ch;margin-bottom:32px}
.hero-hint{color:#6b7280;font-family:'Syne Mono';font-size:.8rem;letter-spacing:.2em;animation:trn02-bounce 2s ease-in-out infinite}
@keyframes trn02-bounce{0%,100%{transform:translateY(0)}50%{transform:translateY(8px)}}
section{padding:80px 24px;max-width:1100px;margin:0 auto}
.section-label{font-family:'Syne Mono';font-size:.75rem;letter-spacing:.3em;text-transform:uppercase;color:#a78bfa;margin-bottom:12px}
.section-title{font-size:clamp(2rem,5vw,3.5rem);font-weight:800;letter-spacing:-.03em;margin-bottom:40px;color:#1a1a1a}
/* card grid */
.cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(260px,1fr));gap:24px;margin-bottom:80px}
.card{background:#fff;border-radius:20px;padding:32px;box-shadow:0 4px 24px rgba(0,0,0,.07);position:relative;overflow:hidden}
.card::before{content:'';position:absolute;top:0;left:0;right:0;height:4px;background:var(--accent,#a78bfa)}
.card .num{font-size:3.5rem;font-weight:800;color:var(--accent,#a78bfa);opacity:.15;line-height:1;margin-bottom:8px}
.card h3{font-size:1.15rem;font-weight:700;margin-bottom:8px}
.card p{font-size:.9rem;color:#666;line-height:1.6}
.card:nth-child(1){--accent:#a78bfa}
.card:nth-child(2){--accent:#34d399}
.card:nth-child(3){--accent:#f97316}
.card:nth-child(4){--accent:#f472b6}
.card:nth-child(5){--accent:#38bdf8}
.card:nth-child(6){--accent:#fbbf24}
/* feature strip */
.feature{display:grid;grid-template-columns:1fr 1fr;gap:40px;align-items:center;margin-bottom:80px;padding:48px;background:#1a0a2e;border-radius:24px;color:#fff}
@media(max-width:640px){.feature{grid-template-columns:1fr}}
.feature h2{font-size:clamp(1.8rem,4vw,2.6rem);font-weight:800;letter-spacing:-.03em;margin-bottom:16px}
.feature p{color:#9ca3af;line-height:1.7}
.feature-visual{display:grid;grid-template-columns:1fr 1fr;gap:12px}
.fv-box{background:linear-gradient(135deg,var(--c1),var(--c2));border-radius:16px;aspect-ratio:1;display:grid;place-items:center;font-size:2rem}
.fv-box:nth-child(1){--c1:#7c3aed;--c2:#a78bfa}
.fv-box:nth-child(2){--c1:#0ea5e9;--c2:#38bdf8}
.fv-box:nth-child(3){--c1:#f97316;--c2:#fb923c}
.fv-box:nth-child(4){--c1:#10b981;--c2:#34d399}
/* testimonial row */
.testimonials{display:grid;grid-template-columns:repeat(auto-fit,minmax(240px,1fr));gap:20px;margin-bottom:80px}
.testi{background:#1a1a1a;border-radius:16px;padding:28px;color:#fff}
.testi p{font-size:.95rem;line-height:1.6;color:#d1d5db;margin-bottom:16px}
.testi-author{display:flex;align-items:center;gap:12px}
.testi-avatar{width:36px;height:36px;border-radius:50%;background:var(--c,#a78bfa);display:grid;place-items:center;font-size:.8rem;font-weight:700}
.testi:nth-child(1) .testi-avatar{--c:#7c3aed}
.testi:nth-child(2) .testi-avatar{--c:#0ea5e9}
.testi:nth-child(3) .testi-avatar{--c:#10b981}
.testi-name{font-size:.82rem;font-weight:700;color:#f9fafb}
.testi-role{font-size:.72rem;color:#6b7280}
/* stats */
.stats{display:grid;grid-template-columns:repeat(4,1fr);gap:20px;background:#fff;border-radius:24px;padding:40px;box-shadow:0 4px 30px rgba(0,0,0,.07)}
@media(max-width:640px){.stats{grid-template-columns:1fr 1fr}}
.stat{text-align:center}
.stat .big{font-size:clamp(2rem,5vw,3rem);font-weight:800;color:var(--c,#7c3aed)}
.stat:nth-child(1){--c:#7c3aed}
.stat:nth-child(2){--c:#0ea5e9}
.stat:nth-child(3){--c:#f97316}
.stat:nth-child(4){--c:#10b981}
.stat span{display:block;font-size:.8rem;color:#888;margin-top:4px}
@media (prefers-reduced-motion:reduce){.reveal{transition:none !important;opacity:1 !important;transform:none !important}} @import url('https://fonts.googleapis.com/css2?family=Syne:wght@400;700;800&family=Syne+Mono&display=swap');
*{margin:0;padding:0;box-sizing:border-box}
body{font-family:'Syne',sans-serif;background:#f5f0e8;color:#1a1a1a;overflow-x:hidden}
/* scroll reveal base */
.reveal{opacity:0;transition:opacity .7s ease,transform .7s cubic-bezier(.22,1,.36,1)}
.reveal.from-left{transform:translateX(-60px)}
.reveal.from-right{transform:translateX(60px)}
.reveal.from-bottom{transform:translateY(50px)}
.reveal.from-top{transform:translateY(-50px)}
.reveal.scale-up{transform:scale(.88)}
.reveal.rotate-in{transform:rotate(-8deg) scale(.9)}
.reveal.visible{opacity:1 !important;transform:none !important}
/* delays */
.delay-1{transition-delay:.1s}.delay-2{transition-delay:.2s}.delay-3{transition-delay:.3s}
.delay-4{transition-delay:.4s}.delay-5{transition-delay:.5s}.delay-6{transition-delay:.6s}
/* page layout */
.hero{min-height:100vh;display:flex;flex-direction:column;align-items:center;justify-content:center;text-align:center;padding:40px 24px;background:linear-gradient(160deg,#0f0f1a,#1a0a2e)}
.hero h1{font-size:clamp(3rem,10vw,7rem);font-weight:800;color:#fff;letter-spacing:-.04em;line-height:.9;margin-bottom:24px}
.hero h1 em{color:#a78bfa;font-style:normal;display:block}
.hero p{color:#9ca3af;font-size:1.1rem;max-width:50ch;margin-bottom:32px}
.hero-hint{color:#6b7280;font-family:'Syne Mono';font-size:.8rem;letter-spacing:.2em;animation:trn02-bounce 2s ease-in-out infinite}
@keyframes trn02-bounce{0%,100%{transform:translateY(0)}50%{transform:translateY(8px)}}
section{padding:80px 24px;max-width:1100px;margin:0 auto}
.section-label{font-family:'Syne Mono';font-size:.75rem;letter-spacing:.3em;text-transform:uppercase;color:#a78bfa;margin-bottom:12px}
.section-title{font-size:clamp(2rem,5vw,3.5rem);font-weight:800;letter-spacing:-.03em;margin-bottom:40px;color:#1a1a1a}
/* card grid */
.cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(260px,1fr));gap:24px;margin-bottom:80px}
.card{background:#fff;border-radius:20px;padding:32px;box-shadow:0 4px 24px rgba(0,0,0,.07);position:relative;overflow:hidden}
.card::before{content:'';position:absolute;top:0;left:0;right:0;height:4px;background:var(--accent,#a78bfa)}
.card .num{font-size:3.5rem;font-weight:800;color:var(--accent,#a78bfa);opacity:.15;line-height:1;margin-bottom:8px}
.card h3{font-size:1.15rem;font-weight:700;margin-bottom:8px}
.card p{font-size:.9rem;color:#666;line-height:1.6}
.card:nth-child(1){--accent:#a78bfa}
.card:nth-child(2){--accent:#34d399}
.card:nth-child(3){--accent:#f97316}
.card:nth-child(4){--accent:#f472b6}
.card:nth-child(5){--accent:#38bdf8}
.card:nth-child(6){--accent:#fbbf24}
/* feature strip */
.feature{display:grid;grid-template-columns:1fr 1fr;gap:40px;align-items:center;margin-bottom:80px;padding:48px;background:#1a0a2e;border-radius:24px;color:#fff}
@media(max-width:640px){.feature{grid-template-columns:1fr}}
.feature h2{font-size:clamp(1.8rem,4vw,2.6rem);font-weight:800;letter-spacing:-.03em;margin-bottom:16px}
.feature p{color:#9ca3af;line-height:1.7}
.feature-visual{display:grid;grid-template-columns:1fr 1fr;gap:12px}
.fv-box{background:linear-gradient(135deg,var(--c1),var(--c2));border-radius:16px;aspect-ratio:1;display:grid;place-items:center;font-size:2rem}
.fv-box:nth-child(1){--c1:#7c3aed;--c2:#a78bfa}
.fv-box:nth-child(2){--c1:#0ea5e9;--c2:#38bdf8}
.fv-box:nth-child(3){--c1:#f97316;--c2:#fb923c}
.fv-box:nth-child(4){--c1:#10b981;--c2:#34d399}
/* testimonial row */
.testimonials{display:grid;grid-template-columns:repeat(auto-fit,minmax(240px,1fr));gap:20px;margin-bottom:80px}
.testi{background:#1a1a1a;border-radius:16px;padding:28px;color:#fff}
.testi p{font-size:.95rem;line-height:1.6;color:#d1d5db;margin-bottom:16px}
.testi-author{display:flex;align-items:center;gap:12px}
.testi-avatar{width:36px;height:36px;border-radius:50%;background:var(--c,#a78bfa);display:grid;place-items:center;font-size:.8rem;font-weight:700}
.testi:nth-child(1) .testi-avatar{--c:#7c3aed}
.testi:nth-child(2) .testi-avatar{--c:#0ea5e9}
.testi:nth-child(3) .testi-avatar{--c:#10b981}
.testi-name{font-size:.82rem;font-weight:700;color:#f9fafb}
.testi-role{font-size:.72rem;color:#6b7280}
/* stats */
.stats{display:grid;grid-template-columns:repeat(4,1fr);gap:20px;background:#fff;border-radius:24px;padding:40px;box-shadow:0 4px 30px rgba(0,0,0,.07)}
@media(max-width:640px){.stats{grid-template-columns:1fr 1fr}}
.stat{text-align:center}
.stat .big{font-size:clamp(2rem,5vw,3rem);font-weight:800;color:var(--c,#7c3aed)}
.stat:nth-child(1){--c:#7c3aed}
.stat:nth-child(2){--c:#0ea5e9}
.stat:nth-child(3){--c:#f97316}
.stat:nth-child(4){--c:#10b981}
.stat span{display:block;font-size:.8rem;color:#888;margin-top:4px}
@media (prefers-reduced-motion:reduce){.reveal{transition:none !important;opacity:1 !important;transform:none !important}}const observer = new IntersectionObserver(entries => {
entries.forEach(e => { if(e.isIntersecting) { e.target.classList.add('visible'); observer.unobserve(e.target); } });
}, { threshold: 0.15 });
document.querySelectorAll('.reveal').forEach(el => observer.observe(el));
// Trigger hero items which are already in view
document.querySelectorAll('.hero .reveal').forEach(el => el.classList.add('visible')); const observer = new IntersectionObserver(entries => {
entries.forEach(e => { if(e.isIntersecting) { e.target.classList.add('visible'); observer.unobserve(e.target); } });
}, { threshold: 0.15 });
document.querySelectorAll('.reveal').forEach(el => observer.observe(el));
// Trigger hero items which are already in view
document.querySelectorAll('.hero .reveal').forEach(el => el.classList.add('visible'));More from 22 CSS Transition Effects
Staggered List AnimationCursor Trail EffectMagnetic Button EffectSplit Text Reveal TransitionProgress Bar AnimationButton Hover TransitionsFlip Card 3D TransitionText Reveal AnimationImage Zoom Hover TransitionBackground Color TransitionBorder Animation TransitionNavigation Hover Transition
View the full collection →