Skip to main content
Transform properties are fundamental to creating smooth, performant animations. They allow you to manipulate elements without triggering layout recalculations, making them ideal for interactive animations.

Core transform properties

CSS provides four main transform functions that can be combined to create complex effects:

Translate

Translation moves elements horizontally (X-axis) and vertically (Y-axis). This is like sliding an object across a surface without changing its appearance.
.element {
  transform: translate(50px, 20px);
}
The element shifts 50px to the right and 20px down from its original position.

Scale

Scaling changes the size of an element. A value greater than 1 makes it larger, while a value less than 1 makes it smaller.
.element {
  transform: scale(1.2);
}
The element is now 1.2 times its original size. Scaling is uniform in both width and height unless you specify separate values:
.element {
  transform: scale(1.5, 0.8); /* 150% width, 80% height */
}

Rotate

Rotation turns an element around its center point by a specified angle in degrees.
.element {
  transform: rotate(45deg);
}
The element rotates 45 degrees clockwise. Negative values rotate counter-clockwise.

Skew

Skew tilts an element, creating a parallelogram shape. It can be applied to X-axis, Y-axis, or both.
.element {
  transform: skew(15deg, 10deg);
}
The element is skewed 15 degrees horizontally and 10 degrees vertically.

Combining transforms

Multiple transforms can be combined to create complex effects. The order of application matters when transforms are combined.
In CSS, multiple transforms are combined in a single transform property:
.element {
  transform: translate(50px, 20px) rotate(45deg) scale(1.2) skew(15deg, 10deg);
}
The order is important because each transform is applied to the result of the previous one.

React implementation example

Here’s how the Animation Playground implements interactive transforms using Framer Motion:
import { motion } from 'framer-motion'
import { useState } from 'react'

type TransformProperty = 'translate' | 'scale' | 'rotate' | 'skew'

export default function TransformDemo() {
  const [activeTransforms, setActiveTransforms] = useState<TransformProperty[]>([])

  const getTransformStyle = () => {
    const transforms = {
      translate: { x: 50, y: 20 },
      scale: { scale: 1.2 },
      rotate: { rotate: 45 },
      skew: { skewX: 15, skewY: 10 }
    }

    return Object.entries(transforms)
      .filter(([key]) => activeTransforms.includes(key as TransformProperty))
      .reduce((acc, [_, value]) => ({ ...acc, ...value }), {})
  }

  return (
    <motion.div
      animate={getTransformStyle()}
      transition={{ duration: 0.5 }}
      className="w-32 h-32 bg-blue-500 rounded-lg"
    >
      Transform Me
    </motion.div>
  )
}

Best practices

Avoid animating properties like top, left, width, or height. These trigger layout recalculations and can cause performance issues.

Use transform for position changes

Instead of:
.element {
  left: 100px;
  top: 50px;
}
Use:
.element {
  transform: translate(100px, 50px);
}

Set transform origin when needed

By default, transforms originate from the center of an element. You can change this:
.element {
  transform-origin: top left;
  transform: rotate(45deg);
}

Combine with hardware acceleration

For optimal performance, use transform with will-change or transform3d:
.element {
  will-change: transform;
  transform: translate(50px, 20px);
}

Order matters

Different orders produce different results:
transform: translate(100px, 0) rotate(45deg);
Moves right, then rotates in place.

Performance benefits

Transforms are hardware-accelerated by modern browsers because they:
  • Don’t trigger layout recalculations
  • Don’t affect surrounding elements
  • Can be handled by the GPU
  • Maintain smooth 60 FPS animations
Transform properties (transform and opacity) are the most performant CSS properties to animate.

Build docs developers (and LLMs) love