Atelier UI®

Read the docsGithub
Docs 0.7.0

Getting started

  • Browse Catalog
  • Installation
  • How to contribute
  • Code of conduct

Components (19)

  • Dither Flow
    pro
  • Glowing Fog
    pro
  • Halftone Glow
    pro
  • Fluid Distortion
    new
  • Image Trail
    new
  • Liquid Image
    new
  • Magnetic Dot Grid
    new
  • Pixel Trail
    new
  • Pixelated Text
    new
  • Simple Scramble
    new
  • Text Bounce
    new
  • Text Fluid
    pro
  • Text Roll
    new
  • Curve Image
    new
  • Elastic Stick
    pro
  • Infinite Gallery
    new
  • Infinite Parallax
    new
  • Infinite Zoom
    new
  • Scattered Scroll
    new
Atelier UI 0.7.0 ©2026
Star on githubBuy me a coffeellms.txt
  1. Docs
  2. /
  3. Components
  4. /
  5. Infinite Parallax

Infinite Parallax

Composable infinite parallax column effect with auto-scroll and repeating content.

Motion
Lenis
Tailwind CSS
https://atelier-ui.com/infinite-parallax

Settings

auto-scroll-speed
0.02
parallax-amount
2.0
See the documentation below for more options.

CLI Install

npx atelier-ui add infinite-parallax

Manual Install

npm install motion
infinite-parallax.tsx
import { motion, useAnimationFrame, useMotionValue, useScroll, useVelocity } from "motion/react"
import { type ComponentRef, useRef } from "react"

export type InfiniteParallaxProps = {
    reversed?: boolean
    autoScrollSpeed?: number
    parallaxAmount?: number
    children?: React.ReactNode
}

const REVERT_THRESHOLD = 50
const PARALLAX_SCALE = 0.0001

export function InfiniteParallax({
    reversed,
    autoScrollSpeed = 0.02,
    parallaxAmount = 2,
    children,
}: InfiniteParallaxProps) {
    const offsetRef = useRef(0)
    const measureRef = useRef<ComponentRef<"div">>(null)
    const y = useMotionValue(0)
    const { scrollY } = useScroll()
    const scrollVelocity = useVelocity(scrollY)
    const directionRef = useRef<1 | -1>(-1)

    useAnimationFrame((_, delta) => {
        if (!measureRef.current) return
        const height = measureRef.current.offsetHeight
        const velocity = scrollVelocity.get()

        if (Math.abs(velocity) > REVERT_THRESHOLD) {
            directionRef.current = velocity > 0 ? -1 : 1
        }

        const parallax = Math.abs(velocity) * parallaxAmount * PARALLAX_SCALE
        const step = delta * (autoScrollSpeed + parallax) * directionRef.current
        let next = offsetRef.current + step

        if (next <= -height) next = 0
        else if (next >= 0) next = -height + 1

        offsetRef.current = next
        y.set(reversed ? -next - height : next)
    })

    return (
        <motion.div style={{ y }} className="h-full w-full">
            <div ref={measureRef}>{children}</div>
            <div aria-hidden>{children}</div>
        </motion.div>
    )
}

API

NameTypeDefaultDescription
childrenReactNode—Items to render in the column.
reversedbooleanfalseReverse the column's scroll direction.
autoScrollSpeednumber0.02Auto-scroll speed. 0 to disable.
parallaxAmountnumber2Parallax intensity applied while scrolling.

Credits

Olivier Larose
Where this idea came from.

Motion
React animation library.

Lenis Smooth scroll library used in the demo.

  • CLI Install
  • Manual Install
  • API
  • Credits
Star on githubBuy me a coffeellms.txt