React Spring logo

React Spring

A spring-physics based animation library designed to create fluid, interruptible, and natural-feeling UI interactions.

npm install react-spring
29.0K757.7K/weekv10.0.38.17 KBMIT133 issues
Last updated: 2025-09-18
Star history chart for pmndrs/react-spring

TL;DR

A cross-platform animation library that relies on physics (mass, tension, friction) rather than fixed durations to drive motion.

Famous for its 'interruptibility', allowing animations to reverse or change course instantly without the jarring jumps seen in time-based CSS transitions.

Why React Spring?

React Spring takes a fundamentally different approach to animation than most other libraries. Instead of telling an element to "move from A to B in 0.5 seconds," you define the physical properties of the motion (how heavy the object is, how tight the spring is).

  • Physics-First Philosophy: By using spring dynamics, animations feel "weighty" and real. There are no arbitrary curves to select; the motion is calculated based on the energy you inject into the system.
  • True Interruptibility: Because the animation is driven by continuous physics simulation, you can stop, reverse, or redirect a moving object at any point. The library calculates the momentum and smoothly transitions to the new target, eliminating "jump cuts."
  • Imperative API: While it supports declarative props, the api object returned by hooks allows you to trigger animations without causing React re-renders, which is crucial for high-frequency events like scroll or drag.
  • Platform Agnostic: The core logic is platform-independent. It powers @react-spring/web (DOM), @react-spring/native (React Native), and even @react-spring/three (React Three Fiber), making it the go-to for cross-platform logic.
  • Interpolation Power: It can animate virtually anything—numbers, colors, SVG paths, and even string patterns—by interpolating between the from and to states.

Code Snippet

This example shows the declarative usage of useSpring. Notice how we don't define a duration. We simply change the toggle state, and the physics engine handles the rest.

import { useSpring, animated, config } from '@react-spring/web'
import { useState } from 'react'

export default function ToggleCard() {
  const [isFlipped, setIsFlipped] = useState(false)

  // Define the spring behavior
  const { transform, opacity } = useSpring({
    opacity: isFlipped ? 1 : 0,
    transform: `perspective(600px) rotateX(${isFlipped ? 180 : 0}deg)`,
    config: config.wobbly, // Pre-defined physics preset
  })

  return (
    <div onClick={() => setIsFlipped(!isFlipped)}>
      <animated.div
        style={{
          opacity: opacity.to(o => 1 - o),
          transform,
          position: 'absolute'
        }}
      >
        Front
      </animated.div>
      <animated.div
        style={{
          opacity,
          transform: transform.to(t => `${t} rotateX(180deg)`),
          position: 'absolute'
        }}
      >
        Back
      </animated.div>
    </div>
  )
}

The .to() interpolation function (often aliased as interpolate in older docs) allows you to chain values, enabling complex transformations from a single spring source.

Pros and Cons

No library is perfect; understanding the trade-offs is key to selecting the right tool.

Pros

  • Natural Feel: The motion simply looks better and more organic than standard easing curves (ease-in-out), especially for interactive elements.
  • Performance: Animations can often run outside the React render cycle, communicating directly with the DOM for 60fps performance.
  • Universal: Learning one API lets you animate DOM elements, Native components, and 3D scenes in WebGL.

Cons

  • Steep Learning Curve: The API surface is vast and can be confusing. Understanding the difference between useSpring, useTransition, and useChain takes time.
  • Verbose for Sequencing: Orchestrating a complex timeline (Step A -> Step B -> Step C) is significantly harder than in Framer Motion or GSAP.
  • Documentation Fragmentation: Due to major changes between versions (v8 to v9), searching for solutions online often yields outdated syntax.

Comparison with Other Animation Libraries

The table below outlines the positioning differences between React Spring and other popular animation libraries to help you make an informed decision:

LibraryDesign PhilosophyBest ForPain Points
React SpringPhysics Simulation
Motion is driven by spring dynamics (tension, friction, mass).
Interactive UIs
Drag-and-drop, swipeable cards, and 3D scenes where momentum matters.
Sequencing
Creating complex, multi-step choreographies is difficult and verbose.
Framer MotionDeclarative & CSS-like
Abstracts animations into simple initial and animate props.
Product Layouts
Page transitions, shared layout animations, and standard UI components.
Physics Limitations
While it has springs, they are less configurable and performant than React Spring's engine.
GSAPTimeline-based
The industry standard for scripted, robust animation timelines.
Marketing Sites
Award-winning websites with complex, scripted storytelling animations.
React Overhead
Strictly imperative; requires manual ref management to play nice with React.

Verdict: When to Adopt

React Spring is the best choice when "feel" is your priority. If you are building a game-like interface, a highly interactive dashboard with drag-and-drop, or working with 3D (React Three Fiber), nothing beats the fluidity of its physics engine.

However, for standard UI transitions (modals, dropdowns, page fades), it is often overkill. In those cases, Framer Motion offers a much faster developer experience with significantly less boilerplate.