Free · Fast · Privacy-first

CSS transform-origin

The CSS transform-origin property defines the point around which a transform is applied.

Clickable origin grid for visual pivot selection

🔒

Supports keywords, percentages, and pixel values

Live preview shows how origin affects rotate and scale

Third Z-axis value for 3D transform origin positioning

Cost
Free forever
Sign-up
Not required
Processing
In your browser
Privacy
Files stay local
FreeNo signupWhite-label

Add this Transform Gen to your website

Drop the Transform Gen into any page — blog post, product docs, intranet, school portal — with a single line of HTML. Your visitors get the full tool, processed entirely in their browser. No backend, no uploads, no signup.

  • Files stay 100% in the visitor's browser
  • Responsive — adapts to any container width
  • Free forever, no API key needed

Embed code

<iframe
  src="https://www.fixtools.io/css-tool/transform-gen?embed=1"
  width="100%"
  height="780"
  frameborder="0"
  style="border:0;border-radius:16px;max-width:900px;"
  title="Transform Gen by FixTools"
  loading="lazy"
  allow="clipboard-write"
></iframe>

Attribution-friendly: a small "Powered by FixTools" link appears in the embed footer.

How transform-origin Changes Rotation and Scale Behavior with Keyword, Percentage, and Pixel Values

The transform-origin property controls which point of an element stays fixed while the transform is applied. For a rotate transform, the origin is the hinge point: the element rotates around it. For a scale transform, the origin is the anchor: the element grows or shrinks toward and away from that point. When transform-origin is at the default 50% 50%, the center of the element stays in place and the edges move. When transform-origin is at 0% 0%, the top-left corner stays fixed and the rest of the element moves around it. Visualizing transform-origin as a pin stuck through the element at the specified position makes its behavior intuitive.

Transform-origin accepts three syntax forms. Keyword values use CSS direction words: top, bottom, left, right, and center. Two keywords map to the X and Y axes: top left sets origin to the top-left corner, bottom center to the center of the bottom edge. Percentage values express the origin as a fraction of the element's own dimensions: 0% 0% is the top-left corner, 100% 100% is the bottom-right, and 25% 75% places the origin at one-quarter of the width and three-quarters of the height. Pixel values set the origin at a fixed distance from the top-left corner of the element regardless of its size. Mixing units is valid: transform-origin: 20px 50% places the origin 20 pixels from the left edge and halfway down the element.

The optional third value in transform-origin sets the Z-axis position of the origin in 3D transform contexts. This value only accepts length units, not keywords or percentages. A positive Z value moves the transform origin toward the viewer, which changes how rotateX and rotateY pivots appear in 3D space. For most UI 3D effects, the Z origin remains at its default value of 0. The Z origin is most relevant when building 3D objects where faces need to rotate around a specific depth position rather than the surface of the element. Setting a non-zero Z origin changes the apparent center of rotation in 3D space and is rarely needed for standard card flip or tilt effects.

transform-origin behavior across browsers is mostly stable, but there are quirks worth checking. Chrome and Edge calculate the origin against the element's border box by default, while Safari historically computed it against the padding box on certain inline elements. The difference is a few pixels at most and only visible on elements with thick borders. Firefox aligns with Chrome on this. For SVG, every engine has different historical defaults: older versions used the SVG viewport origin while newer versions match the HTML behavior. The fix that works everywhere is to set transform-origin and transform-box: fill-box on SVG children, which forces all engines to compute the origin against the element's own geometry. Always declare both properties together on SVG when precise pivot control matters.

How to use this tool

💡

Click a point on the origin grid to set the pivot position, or type custom X and Y values in the input fields. Choose a transform function to preview: rotation shows the hinge point, scale shows the growth anchor. Copy the transform-origin declaration alongside your chosen transform.

How It Works

Step-by-step guide to css transform-origin:

  1. 1

    Select the origin position

    Click one of the nine points on the origin grid (corners, edge midpoints, and center) or type custom X and Y values. The crosshair in the preview moves to show the selected origin.

  2. 2

    Choose a transform to preview

    Select rotate or scale to apply a sample transform and see how the origin affects it. Rotate shows the hinge behavior; scale shows the growth anchor.

  3. 3

    Fine-tune with custom values

    Enter specific percentages or pixel values for precise origins that fall outside the nine grid points. Mix units if needed, such as 20px for X and 50% for Y.

  4. 4

    Copy the origin declaration

    Click Copy Code to export the transform-origin value. Paste it into your CSS rule alongside the transform property.

Real-world examples

Common situations where this approach makes a real difference:

Hinge animation on accordion panel

An accordion uses a horizontal panel that folds up to close. The panel needs to rotate around its top edge. The developer sets transform-origin: top center, then applies rotateX(90deg) for the closed state and rotateX(0deg) for the open state, with transition: transform 300ms ease. The generator confirms the origin position with a live preview before the CSS is written to the component. The panel folds cleanly upward from the top edge.

Expanding tile in an image grid

An image gallery tile expands on click from a grid cell to a larger featured view. The expansion should appear to grow from the tile's position in the grid rather than from the center of the screen. The developer sets transform-origin to match the tile's position within the grid: top left for tiles in the first column, top right for the last column. The scale animation appears to originate from the tile corner nearest the grid boundary.

Fan-out card animation from a deck

A deck of cards fans out when hovered, with each card rotating by a different angle around the bottom center of the deck. All cards share transform-origin: bottom center. JavaScript applies unique rotate() values to each card with a slight delay stagger. The generator is used to confirm bottom center as the origin produces the correct fan-out pattern with the cards spreading upward from a shared pivot at the base.

Tooltip that scales from its anchor arrow

A tooltip positioned above its trigger has a small arrow pointing down at the trigger element. The tooltip entrance animation scales from scale(0) to scale(1) and should appear to grow from the arrow tip. The developer sets transform-origin: bottom center (assuming the arrow is at the bottom of the tooltip) so the tooltip grows upward and outward from its anchor point. The generator preview confirms the growth direction matches the tooltip's visual relationship to the trigger.

Pro tips

Get better results with these expert suggestions:

1

Clock hands need transform-origin at the bottom of the hand

A clock hand element should rotate around the center of the clock face, which corresponds to the bottom of the hand element. Set transform-origin: 50% 100% or transform-origin: center bottom so the bottom edge of the element stays fixed while the top sweeps around. Applying this to a thin div that represents the minute or second hand produces accurate clock rotation without any translation compensation.

2

Dropdown menus should scale from their trigger edge

A dropdown menu that opens below a button should have transform-origin: top center so it scales from its top edge downward. This creates the visual impression that the menu is emerging from behind the button. Without this origin setting, the menu scales from its center and appears to grow in all directions simultaneously, which looks less intentional.

3

For fold/unfold animations, use the fold edge as the origin

A panel that unfolds from the left side needs transform-origin: left center before rotateY(90deg) is applied to the folded state and rotateY(0deg) for the unfolded state. The panel then appears to hinge open from its left edge. If the fold should happen from the top, use transform-origin: top center with rotateX.

4

Test transform-origin at the exact element size that will be in production

Pixel values for transform-origin are fixed and do not adapt to element size changes. If the element changes size due to responsive layout, a pixel-value origin may land in the wrong relative position. Use percentage values for origins that should remain proportionally positioned across different element sizes. Pixel values are appropriate only for origins that must align with a fixed external reference point.

5

Set transform-origin before writing the transform value

The visual result of a rotation or scale depends entirely on where the origin is set. Decide the intended pivot or anchor first, set transform-origin, then determine the angle or scale value. Reversing this order results in trying to compensate for an incorrect pivot with translate offsets, which creates brittle CSS that breaks at different element sizes.

6

Use keyword values for common edge origins

For origins at the edges or corners of an element, keyword values like top left, bottom center, or right center are more readable than the equivalent percentages and produce identical results. Use percentage or pixel values only when the origin is at a non-standard position such as 33% 66% or a specific pixel offset from an edge.

7

Remember SVG elements default transform-origin differently

SVG elements default to transform-origin: 0 0 in older browsers instead of 50% 50%. If a rotation on an SVG element pivots from the top-left corner unexpectedly, add an explicit transform-origin: center center or 50% 50% to override the SVG default.

FAQ

Frequently asked questions

The default value is 50% 50% 0, which places the origin at the horizontal and vertical center of the element and at Z=0 depth. This means rotations spin the element around its center, and scale grows or shrinks from the center outward. For most standard HTML elements, this default is assumed by the browser and does not need to be explicitly set unless you want a non-center pivot point.
Yes. transform-origin: 20px 40px places the pivot 20 pixels from the left edge and 40 pixels from the top edge of the element. Pixel values are fixed and do not adapt when the element changes size. Use pixel values when the origin must align with a specific design element at a known fixed position, such as a connector dot in a diagram. Use percentage values when the origin should remain proportionally positioned as the element resizes.
For scale transforms, the transform-origin is the anchor point that stays fixed while the element grows or shrinks. With the default center origin, the element grows equally in all directions. With transform-origin: top left, the top-left corner stays fixed and the element grows toward the bottom-right. With transform-origin: bottom center, the bottom edge stays fixed and the element grows upward. This is the correct setting for a scale entrance animation where the element should appear to grow from a specific edge.
No. The transform-origin property has no effect on translate transforms. Translate moves the element by a fixed offset from its current position, and this offset is independent of the origin point. A translateX(100px) always moves the element 100px to the right regardless of transform-origin. The origin only affects transforms that pivot or anchor around a point, specifically rotate, scale, and skew. For skew, the origin changes which point remains fixed during the shearing operation.
Yes, transform-origin is animatable, but animating it is unusual and can produce confusing motion because both the transform and its pivot point change simultaneously. A common pattern where this is useful is a shape that expands from one corner to reveal content and then scales down from a different corner to hide it. This requires animating transform-origin between the two corner positions while also animating scale. Test this carefully in all target browsers as interpolation behavior can vary.
In a 3D context, transform-origin accepts a third value that sets the Z-axis position of the pivot. For example, transform-origin: 50% 50% 100px places the pivot 100px in front of the element's surface. This changes how rotateX and rotateY pivots appear in 3D space: a positive Z origin makes the rotation appear to orbit around a point in front of the element. For most UI card flips and tilts, the Z origin remains at the default 0 and only X and Y need to be set.
No. In older browsers, SVG elements default to transform-origin: 0 0 instead of 50% 50%. This means a rotate() on an SVG element will pivot from the top-left corner of the SVG viewport unless transform-origin is explicitly set. Modern browsers align SVG transform-origin defaults with HTML when using CSS transforms, but for compatibility with older Safari and Firefox versions, always explicitly declare transform-origin on SVG elements that use rotation or scale transforms.
Some developers achieve a non-center rotation by prepending a translate to the transform list: translate(-100px, 0) rotate(45deg) translate(100px, 0). This manually shifts the origin by translating to the desired pivot point, rotating, then translating back. The result is identical to setting transform-origin to the correct position. Using transform-origin is simpler and more readable. The manual translate pattern is sometimes seen in SVG transforms where the transform-origin property historically had limited support.
Wrap any animation that depends on transform-origin in @media (prefers-reduced-motion: no-preference) so the motion only runs when the user has not requested reduced motion. For users who have, skip the rotation or scale animation entirely and set the final state directly. Off-center rotations are especially disorienting because the element appears to swing through space rather than spinning in place, which is harder for vestibular-sensitive users to process. A non-animated state change communicates the same intent. The setting is read from the operating system and applied through the media query without any JavaScript.
transform-origin alone does not create a stacking context, but applying a transform with any non-default value does. Once you set a transform value that uses your custom origin, the element becomes its own stacking context regardless of which origin you chose. Children with high z-index can no longer escape that context to stack above siblings outside the transformed element. The fix is identical to other transforms: portal floating descendants like tooltips and dropdowns to document.body so they live outside the stacking context. Changing only transform-origin without applying a transform does not trigger this behavior on its own.

Related guides

More use-case guides for the same tool:

Ready to get started?

Open the full Transform Gen — free, no account needed, works on any device.

Open Transform Gen →

Free · No account needed · Works on any device