CSS translateZ() Function

The CSS translateZ() function moves an element along the Z axis in three-dimensional space.

It is used with the transform property and accepts a length value. Positive values move an element toward the viewer, while negative values move it away. When perspective is applied, this movement can make the element appear larger or smaller.

Syntax

translateZ(tz)

The translateZ() function requires one length value that specifies movement along the Z axis.

Examples:

transform: translateZ(50px);
transform: translateZ(-50px);
transform: translateZ(100px);
transform: translateZ(2rem);
transform: translateZ(5vw);
transform: translateZ(0);

The function is used as a value of the transform property:

.box {
  transform: translateZ(80px);
}

This moves the element 80px along the positive Z axis.

Unlike translateX() and translateY(), the translateZ() function does not accept percentages.

Parameters

The translateZ() function accepts exactly one argument.

Parameter Description
tz Required. A CSS <length> value specifying the translation distance along the Z axis.

Accepted values include absolute lengths, relative lengths, and compatible CSS calculations.

For example:

translateZ(40px)
translateZ(-2rem)
translateZ(3em)
translateZ(10vw)
translateZ(calc(50px + 1rem))
translateZ(var(--depth, 0px))

Unitless zero is valid, but nonzero unitless numbers are not.

For example, translateZ(20) is invalid because it does not specify a length unit.

Percentage values such as translateZ(50%) are also invalid.

How It Works

The translateZ() function changes an element's position along the depth axis without changing its original position in normal document flow.

For example:

.box {
  transform: translateZ(100px);
}

This moves the element 100px toward the viewer in the normal, unrotated three-dimensional coordinate system.

However, without perspective, an isolated flat element may appear unchanged because movement along the Z axis does not automatically change its apparent size.

When perspective is applied, the browser projects the element's three-dimensional position onto the screen.

Positive Z translation can make an element appear larger, while negative Z translation can make it appear smaller.

The translation is represented internally by a four-by-four transformation matrix.

Like other transforms, it does not cause surrounding elements to rearrange around the translated position.

Understanding the Z Axis

CSS three-dimensional transforms use the X, Y, and Z axes.

Axis Positive Direction Negative Direction
X Right Left
Y Down Up
Z Toward the viewer Away from the viewer

The Z axis represents depth rather than horizontal or vertical movement.

For example:

transform: translateZ(100px);

This moves an element toward the viewer.

transform: translateZ(-100px);

This moves an element away from the viewer.

These directions describe the normal coordinate system. If the element is also rotated, the final direction of movement depends on the order of the transforms.

Z-axis translation is not the same as z-index, which controls stacking order within CSS stacking contexts.

Positive and Negative Values

Positive and negative values control the direction of movement along the Z axis.

Positive Values

.box {
  transform: translateZ(80px);
}

Moves the element 80px toward the viewer.

With perspective, the element generally appears larger.

Negative Values

.box {
  transform: translateZ(-80px);
}

Moves the element 80px away from the viewer.

With perspective, the element generally appears smaller.

Zero

.box {
  transform: translateZ(0);
}

Applies no depth displacement.

Although the translation distance is zero, the declaration still specifies a three-dimensional transform function.

Large positive values can move an element very close to or beyond the perspective viewing plane, producing extreme distortion or causing the element to disappear from view.

Length Values

The translateZ() function accepts CSS length values.

Pixels

.box {
  transform: translateZ(50px);
}

Moves the element 50px toward the viewer.

Font-Relative Units

.box {
  transform: translateZ(3rem);
}

The translation distance depends on the root element's font size.

.box {
  transform: translateZ(2em);
}

The translation distance depends on the element's computed font size.

Viewport Units

.box {
  transform: translateZ(10vw);
}

The depth distance is calculated from 10% of the viewport width.

Calculated Values

.box {
  transform: translateZ(calc(40px + 2rem));
}

The depth distance is calculated from the combined lengths.

Percentages are not accepted because Z translation requires a length rather than a length-percentage value.

Using Perspective

Perspective makes depth movement visible by changing the apparent size and position of elements according to their distance from the viewer.

For example:

.scene {
  perspective: 500px;
}
.box {
  transform: translateZ(100px);
}

The box appears larger because it is translated toward the viewer.

Changing the translation to a negative value:

.box {
  transform: translateZ(-100px);
}

The box appears smaller because it is translated away from the viewer.

Perspective Distance

The perspective distance affects the strength of the depth effect.

.scene {
  perspective: 300px;
}

A shorter positive perspective distance produces a stronger depth effect.

.scene {
  perspective: 1000px;
}

A longer perspective distance produces a more subtle effect.

Perspective Transform Function

Perspective can also be included in the transform list:

.box {
  transform: perspective(500px) translateZ(100px);
}

The perspective() function applies perspective within the element's transform list.

The perspective property instead establishes perspective for transformed descendants of the element on which it is declared.

Both approaches can produce depth effects, but their behavior differs when multiple elements or nested transforms are involved.

Comparing Translation Functions

CSS provides several translation functions for movement along different axes.

Function Movement Example
translateX() Horizontal translateX(40px)
translateY() Vertical translateY(20px)
translateZ() Depth translateZ(50px)
translate() Horizontal and vertical translate(40px, 20px)
translate3d() Horizontal, vertical, and depth translate3d(40px, 20px, 50px)

The following declarations produce equivalent Z-axis translations:

transform: translateZ(50px);
transform: translate3d(0, 0, 50px);

Use translateZ() when only depth movement is needed.

Use translate3d() when movement along all three axes needs to be specified together.

Combining Transform Functions

The translateZ() function can be combined with other three-dimensional transform functions, including rotateX(), rotateY(), and scale3d().

For example:

.box {
  transform: translateZ(80px) rotateY(30deg);
}

This combines depth translation with rotation around the Y axis.

The order of transform functions affects the final position.

Compare:

transform: translateZ(100px) rotateY(45deg);
transform: rotateY(45deg) translateZ(100px);

In the first declaration, the element rotates and then moves along the original Z axis.

In the second declaration, the translation occurs along a Z axis affected by the rotation.

Transform functions are composed in their written order, with their effects applied from right to left.

Perspective can make the differences between these transformations more apparent.

Preserving 3D Space

The transform-style property controls whether an element's children are rendered in a shared three-dimensional space or flattened into its plane.

For nested three-dimensional elements, preserve-3d can maintain their relative depth positions.

.scene {
  perspective: 600px;
}
.group {
  transform-style: preserve-3d;
}
.group .front {
  transform: translateZ(60px);
}
.group .back {
  transform: translateZ(-60px);
}

The front element is translated toward the viewer, while the back element is translated away.

Without a shared 3D rendering context, nested elements may be flattened, preventing the intended depth relationship from being preserved.

Some CSS properties, including certain overflow and opacity values, can cause flattening even when preserve-3d is specified.

For a single element using translateZ() with perspective, transform-style: preserve-3d is generally unnecessary.

CSS Custom Properties

CSS custom properties can store depth translation distances for reuse.

For example:

.box {
  --depth: 80px;
  transform: translateZ(var(--depth));
}

Changing --depth changes the Z-axis translation.

A fallback value can also be supplied:

.box {
  transform: translateZ(var(--depth, 0px));
}

If the custom property is not defined, the depth translation defaults to zero.

Custom properties are useful for interactive cards, layered designs, and reusable three-dimensional effects.

For example:

.card {
  --depth: 0px;
  transform: translateZ(var(--depth));
}
.card:hover {
  --depth: 60px;
}

When perspective is applied, the hovered card appears closer to the viewer.

Example

The following example demonstrates how translateZ() changes an element's depth while perspective controls its visible size.

HTML:

<div class="translatez-demo">
  <div class="translatez-box">Original</div>
  <div class="translatez-box translatez-forward">Forward</div>
</div>

CSS:

.translatez-demo {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  align-items: center;
  gap: 50px;
  min-height: 210px;
  padding: 30px;
  perspective: 500px;
  background-color: #f1f3f5;
}
.translatez-box {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 110px;
  height: 80px;
  color: #fff;
  background-color: #3498db;
}
.translatez-forward {
  background-color: #16a085;
  transform: translateZ(100px);
}
Browser Result
Original
Forward

The blue box remains at its original depth.

The green box moves 100px toward the viewer and appears larger because the container applies perspective.

Both boxes retain their original layout dimensions and positions.

Perspective Example

The following example compares negative, zero, and positive Z-axis translations.

HTML:

<div class="translatez-scene">
  <div class="translatez-depth-box" style="--depth: -100px;">Farther</div>
  <div class="translatez-depth-box" style="--depth: 0px;">Original</div>
  <div class="translatez-depth-box" style="--depth: 100px;">Closer</div>
</div>

CSS:

.translatez-scene {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  align-items: center;
  gap: 45px;
  min-height: 230px;
  padding: 30px;
  perspective: 500px;
  background-color: #f1f3f5;
}
.translatez-depth-box {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 100px;
  height: 80px;
  color: #fff;
  background-color: #8e44ad;
  transform: translateZ(var(--depth));
}
Browser Result
Farther
Original
Closer

All three boxes have the same CSS width and height.

The box at -100px appears smaller because it is farther away.

The box at zero retains its original apparent size.

The box at 100px appears larger because it is closer to the viewer.

The perspective distance of 500px determines the strength of the visual depth effect.

Transition Example

The translateZ() function can be animated with CSS transitions to create interactive depth effects.

HTML:

<div class="translatez-transition-scene">
  <button class="translatez-button" type="button">
    Hover or Focus
  </button>
</div>

CSS:

.translatez-transition-scene {
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: 180px;
  padding: 30px;
  perspective: 500px;
  background-color: #f1f3f5;
}
.translatez-button {
  padding: 18px 30px;
  border: none;
  color: #fff;
  background-color: #16a085;
  cursor: pointer;
  transform: translateZ(0);
  transition: transform 0.4s ease, background-color 0.3s ease;
}
.translatez-button:hover,
.translatez-button:focus-visible {
  transform: translateZ(80px);
  background-color: #117864;
}
.translatez-button:focus-visible {
  outline: 3px solid #f39c12;
  outline-offset: 5px;
}
@media (prefers-reduced-motion: reduce) {
  .translatez-button {
    transition: none;
  }
}
Browser Result

When hovered or focused, the button moves 80px toward the viewer.

The perspective makes it appear larger as it moves forward.

The transition animates the change in depth and background color.

Users who prefer reduced motion receive the state change without the animated transition.

Common Uses

The translateZ() function is useful when an element needs to move toward or away from the viewer in three-dimensional space.

  • 3D interfaces: Position elements at different depths.
  • Interactive cards: Move cards toward the viewer on hover or focus.
  • Perspective effects: Create apparent size differences based on depth.
  • 3D animations: Animate movement along the Z axis.
  • Layered designs: Separate elements within a three-dimensional rendering context.
  • Combined transforms: Move elements in depth while rotating or scaling them.
  • Custom properties: Reuse depth values across multiple components.

For example:

.scene {
  perspective: 600px;
}
.card {
  transform: translateZ(0);
  transition: transform 0.3s ease;
}
.card:hover {
  transform: translateZ(60px);
}

The card appears to move toward the viewer when hovered.

Use translateZ() when depth is part of the intended design. For ordinary horizontal or vertical movement, use translateX(), translateY(), or translate().

Limitations

The translateZ() function has several requirements and behaviors to consider.

  • It accepts exactly one length value.
  • Percentage values are invalid.
  • Nonzero unitless numbers are invalid.
  • It moves an element along the Z axis rather than directly along the X or Y axis.
  • Without perspective, depth movement may not produce an obvious visual change.
  • It does not change the element's original position in normal document flow.
  • Large positive depth values can produce extreme perspective distortion.
  • Transform order affects the final result when combined with other transforms.
  • Nested 3D elements may require transform-style: preserve-3d to retain their depth relationships.
  • Some CSS properties cause nested 3D elements to be flattened.
  • Using a 3D transform does not guarantee hardware acceleration or improved performance.
  • Animated depth effects may be distracting for some users.

Valid and Invalid Values

Valid declarations:

transform: translateZ(50px);
transform: translateZ(-100px);
transform: translateZ(2rem);
transform: translateZ(calc(40px + 1rem));
transform: translateZ(0);

Invalid declarations:

transform: translateZ();
transform: translateZ(20);
transform: translateZ(50%);
transform: translateZ(20px, 30px);
transform: translateZ(45deg);

These are invalid because they omit the argument, use a nonzero unitless number, use a percentage, provide too many arguments, or use an angle instead of a length.

Perspective Considerations

Perspective is not required for translateZ() to be valid, but it is usually needed to create a visible depth-scaling effect.

Avoid moving an element to or beyond the viewer's perspective plane unless that behavior is intentional.

Accessibility

Provide reduced-motion alternatives for animated depth effects when appropriate.

@media (prefers-reduced-motion: reduce) {
  .animated-3d {
    animation: none;
    transition: none;
  }
}

Ensure that interactive elements remain visible and usable with a keyboard after translation.

Browser Support

The CSS translateZ() function is Baseline Widely available and is supported by modern versions of Chrome, Edge, Firefox, Safari, and other major browsers.

Three-dimensional CSS transforms have been supported for many years. Older browsers may require vendor prefixes, but prefixes are unnecessary in current major browsers.

For current compatibility information, visit Can I Use? and search for CSS 3D transforms.

Specifications

The translateZ() function is defined in the CSS Transforms Module Level 2 specification.

The specification defines the function's length argument and its representation in a three-dimensional transformation matrix.

Related functions include translate(), translateX(), translateY(), translate3d(), perspective(), and rotate3d().