What Is FLIP?
FLIP is an acronym that stands for First, Last, Invert, Play. This technique provides a systematic approach to animating layout changes in a way that maintains high frame rates and smooth visual experiences Aerotwist - FLIP Your Animations.
The core insight behind FLIP is that animating layout properties like width, height, left, and top is expensive because it triggers layout recalculation and often causes repaints. Instead, FLIP transforms these costly animations into changes that the browser can handle efficiently using CSS transforms and opacity. For a deeper dive into CSS transitions, see our guide on using CSS transitions to understand how these properties work together.
The 100ms Response Window
The reason FLIP works is rooted in user perception. When a user interacts with your site, there's a window of about 100ms where you can perform work without them noticing any delay Aerotwist - FLIP Your Animations. This means you can perform the "expensive" measurement and calculation steps during this window, then animate using only compositor-friendly properties.
This perception window is the foundation of FLIP's performance strategy. By capturing element positions, calculating transformations, and applying animations within this brief timeframe, you create the illusion of instantaneous layout changes while actually performing complex calculations behind the scenes.
The Four Steps of FLIP
First
The First step involves recording the current position and dimensions of the element(s) before any changes are made. This is typically done using element.getBoundingClientRect(), which returns the size of an element and its position relative to the viewport Bram.us - Implement FLIP transitions easily with flipping.
// Capture the initial (First) position
const first = el.getBoundingClientRect();
This measurement captures the element's position, width, height, and other dimensional properties at its starting point.
Last
The Last step is where you actually make the change that will be animated. You apply whatever DOM changes cause the element to move or resize, then measure its new position Aerotwist - FLIP Your Animations.
// Apply the layout change
el.classList.add('expanded');
// Capture the final (Last) position
const last = el.getBoundingClientRect();
While this triggers a synchronous layout calculation, it happens before the animation begins, within the responsive window where users won't notice the brief computational work.
Invert
The Invert step is where FLIP shows its brilliance. Since the element is now in its final position, you calculate how much it moved and use CSS transforms to reverse that movement. This creates the illusion that the element is still in its original position Aerotwist - FLIP Your Animations.
// Calculate the difference
const deltaX = first.left - last.left;
const deltaY = first.top - last.top;
// Invert the movement
el.style.transform = `translate(${deltaX}px, ${deltaY}px)`;
At this point, the element is physically in its final position but visually appears unchanged because the transform counteracts the movement.
Play
The Play step is where the animation actually happens. You enable CSS transitions for the transform property and then remove the transform, allowing the browser to animate from the inverted state back to the natural position Aerotwist - FLIP Your Animations.
// Enable transitions
el.classList.add('animate-transform');
// Remove the transform - browser animates to natural position
el.style.transform = '';
Performance by the Numbers
60fps
Target frame rate for smooth animations
16ms
Maximum time per frame for 60fps
100ms
Response window for calculations
Performance Benefits
Compositor-Only Properties
The magic of FLIP lies in limiting animations to transform and opacity. These are the only CSS properties that browsers can animate efficiently on the compositor thread without triggering layout recalculations or repaints Aerotwist - FLIP Your Animations. This means the main thread is free to handle other work while animations run smoothly.
Achieving 60fps
Achieving 60 frames per second requires that each frame complete in approximately 16ms. When you animate layout properties like left, top, width, or height, the browser must recalculate the positions of all elements in the document, which is computationally expensive Motion.dev - Layout Animation React FLIP. FLIP avoids this by transforming expensive layout changes into cheap compositor operations.
| Animation Approach | Cost | Performance |
|---|---|---|
| Layout properties (left, top, width) | High - triggers reflow | Poor |
| CSS transforms | Low - compositor only | Excellent |
| FLIP technique | Medium - one-time calculation | 60fps |
Why Layout Properties Are Expensive
When you change a layout property, the browser must recalculate the positions of all elements in the document. This process, called layout reflow, cascades through your entire page. Every affected element must have its position and dimensions recomputed, and then repainted to the screen.
By contrast, CSS transforms and opacity changes bypass the layout phase entirely. The browser handles these animations on the GPU compositor thread, which can run in parallel with JavaScript execution on the main thread. This separation is what enables consistently smooth animations even on complex pages.
Implementing FLIP in JavaScript
Manual Implementation
Here's how you implement FLIP manually in vanilla JavaScript:
// Step 1: First - capture initial position
const first = element.getBoundingClientRect();
// Step 2: Last - apply changes and capture final position
element.classList.add('expanded');
const last = element.getBoundingClientRect();
// Step 3: Invert - calculate and apply reverse transform
const deltaX = first.left - last.left;
const deltaY = first.top - last.top;
element.style.transform = `translate(${deltaX}px, ${deltaY}px)`;
// Step 4: Play - animate to final position
requestAnimationFrame(() => {
element.classList.add('animating');
element.style.transform = '';
});
Using the Flipping Library
The flipping library by David Khourshid provides a higher-level API for FLIP animations Bram.us - Implement FLIP transitions easily with flipping. The library handles the reading of initial positions, executing layout changes, and performing the flip animation automatically:
import Flipping from 'flipping/adapters/web';
const flipping = new Flipping();
// First: read all initial bounds
flipping.read();
// Execute the change that causes elements to change bounds
doSomething();
// Last, Invert, Play: the flip() method does it all
flipping.flip();
The manual approach gives you full control over every step of the FLIP process, making it ideal for simple, focused animations. The library approach shines when you have multiple elements transitioning simultaneously or need features like staggered animations and interrupted transition handling.
FLIP in Modern Frameworks
React FLIP with Motion
Modern React animation libraries like Motion (formerly Framer Motion) automate FLIP transitions through the layout prop and layoutId attribute Motion.dev - Layout Animation React FLIP. When an element's position changes due to state updates, these libraries automatically capture the element's previous position, apply the state change, calculate the transform needed to maintain visual position, and animate the transform to zero.
<motion.div layout>
{content}
</motion.div>
Shared Element Transitions
Shared element transitions take FLIP further by allowing elements to maintain visual continuity across different views or component states Motion.dev - Layout Animation React FLIP. These transitions are a powerful tool for creating seamless user experiences, especially when combined with solid UX design principles. When two elements share the same layoutId, they appear to be the same element during transitions:
<motion.div layoutId="card-image">
<img src="thumbnail.jpg" />
</motion.div>
// Later, in a different component
<motion.div layoutId="card-image">
<img src="full-image.jpg" />
</motion.div>
Benefits of Framework Integration
Using FLIP through a framework library provides automatic cleanup of transforms after animation, support for interrupted animations, staggered animations for multiple elements, and seamless integration with React's component lifecycle. For projects using modern frontend frameworks, these libraries dramatically simplify FLIP implementation while providing additional animation capabilities that would require significant boilerplate code in vanilla JavaScript.
Where FLIP animations shine in real-world applications
List Reordering
Animated list reordering is a perfect FLIP use case. When items in a list swap positions, FLIP animates them smoothly between their old and new positions, creating a polished user experience [Aerotwist - FLIP Your Animations](https://aerotwist.com/blog/flip-your-animations/).
Modal and Dialog Transitions
Expanding cards and modals benefit greatly from FLIP. When a user clicks a card and it expands to fill the screen, FLIP can animate the transformation smoothly, making it feel like the card itself is growing rather than a new element appearing [Bram.us - Implement FLIP transitions easily with flipping](https://www.bram.us/2017/12/10/implement-flip-transitions-easily-with-flipping/).
Responsive Layout Changes
When layout changes due to window resizing or responsive breakpoints, FLIP can smooth the transition between different layouts, especially valuable for complex dashboards and media-heavy sites [Motion.dev - Layout Animation React FLIP](https://motion.dev/docs/react-layout-animations).
Filter and Sort Animations
When users filter or sort collections, FLIP animates elements to their new positions rather than having them instantly jump around the page. This maintains spatial context and helps users track items as they move.
Advanced Techniques
Animating Multiple Elements
When multiple elements need FLIP animations, orchestration becomes important. You should avoid triggering new FLIP calculations while animations are in progress, as this can cause visual glitches Aerotwist - FLIP Your Animations. Consider using animation completion callbacks before triggering new transitions, staggering animations for a more polished feel, and canceling in-flight animations gracefully when state changes.
Handling Content Changes
When layout changes occur alongside content changes, consider whether to animate them together or separately. Sometimes it's cleaner to let content update instantly while only animating position, or vice versa Motion.dev - Layout Animation React FLIP. The key is maintaining visual coherence while respecting user attention.
Performance Optimization Tips
- Cache measurements: Store element measurements when possible to avoid repeated
getBoundingClientRect()calls - Use CSS will-change: Hint to browsers that transforms are coming with
will-change: transform - Batch DOM reads and writes: Follow the browser's optimization patterns of read-write-read-write
- Limit transform complexity: Stick to translate, scale, and rotate for best performance
These optimization techniques become increasingly important as your animations grow more complex or your pages contain more transitioning elements.
FLIP Technique FAQ
Caveats and Best Practices
Performance Budget
The FLIP technique assumes you can complete your measurement and calculation work within the 100ms response window Aerotwist - FLIP Your Animations. Complex DOM structures or many transitioning elements may exceed this budget. Use browser DevTools to profile your FLIP implementations and ensure calculations complete quickly.
Content Distortion
When working with transforms at scale, some elements may appear distorted. As a best practice, restructure your markup when necessary to allow FLIP animations without distortion Aerotwist - FLIP Your Animations. This might mean extracting content into wrapper elements or using different animation strategies.
Accessibility Considerations
Always respect user preferences for reduced motion:
@media (prefers-reduced-motion: reduce) {
.animating {
transition: none;
transform: none;
}
}
Also ensure that animations don't interfere with assistive technology users or create confusing visual experiences for users with vestibular disorders.
Browser Compatibility
The FLIP technique works across all modern browsers. Some advanced features like the Web Animations API have good support with polyfills available for older browsers when needed.
Conclusion
The FLIP technique transforms how we think about layout animations. By capturing element positions, inverting changes with transforms, and playing animations that leverage the compositor thread, you can achieve buttery-smooth 60fps animations even when elements dramatically change position or size. Whether you're building animated lists, expanding cards, or complex responsive layouts, FLIP provides a systematic approach that prioritizes both visual quality and performance.
Combined with our expertise in responsive web design and performance optimization, implementing FLIP animations helps create digital experiences that feel polished and professional. Our web development services include comprehensive animation strategy and implementation to enhance user engagement across your digital presence.
Sources
- Aerotwist - FLIP Your Animations - Original FLIP technique by Paul Lewis, foundational concepts and performance approach
- Bram.us - Implement FLIP transitions easily with flipping - Practical JavaScript library implementation with code examples
- Motion.dev - Layout Animation React FLIP - Modern React FLIP animations with layoutId and shared element transitions