Rendering Pipeline
Modern web performance starts with understanding how the browser actually turns your HTML, CSS, and JavaScript into pixels on the screen. This lesson reveals the rendering pipeline, reflow/repaint costs, and professional optimization techniques used by Meta, Google, Netflix, and Airbnb.
Part of the free JavaScript course at LearnCodingFast — hands-on lessons with examples you run in your browser, plus practice exercises and a quick quiz.
What You'll Learn in This Lesson
💡 Running Code Locally: While this online editor runs real JavaScript, some advanced examples may have limitations. For the best experience:
- Download Node.js to run JavaScript on your computer
- Use your browser's Developer Console (Press F12) to test code snippets
- Create a .html file with <script> tags and open it in your browser
A single line of code—changing width, reading offsetHeight, or triggering layout—can destroy 60 FPS performance. Learn to write code that keeps your UI smooth even on low-power devices.
🚀 The Browser Rendering Pipeline
The browser doesn't magically draw pixels. It follows a detailed sequence every frame:
1. HTML → DOM Tree
Browser parses HTML and creates nodes representing every tag.
2. CSS → CSSOM Tree
Browser parses stylesheets, computes rules, builds CSS Object Model.
3. Render Tree
DOM + CSSOM merge into structure defining what's visible.
4. Layout (Reflow) 🟥 EXPENSIVE
Every visible element receives size, position, geometry, box model values.
5. Paint (Repaint) 🟨 COSTLY
Colors, borders, shadows, backgrounds, text are drawn.
6. Compositing 🟩 FAST
Layers are merged into final image on your screen (GPU-accelerated).
This entire cycle repeats every time something changes visually. A smooth 60 FPS requires all tasks to fit inside a 16.6ms frame budget!
🟥 What Causes Reflow (Most Expensive)
Reflow recalculates layout—the most expensive operation. Common triggers:
- Changing element size: width , height
- Changing margin , padding , border
- Changing font-size
- Adding/removing elements
- Changing position , display , flex , grid
- Setting scroll position
- Querying layout properties (forced reflow)
🔥 Forced Reflow Properties (Dangerous in Loops)
These force the browser to apply pending layout changes before returning a value!
🟨 What Causes Repaint (Cheaper but Not Free)
Repaint happens when appearance changes but geometry does not:
- Changing color
- Changing background-color
- Changing visibility
- Changing box-shadow
- Changing outline
🟩 Best Case: Compositor-Only Changes
Using transform or opacity avoids both reflow and repaint. These changes happen on the GPU compositor thread—extremely fast!
This is why all modern animation libraries use transform and opacity. Always prefer these for smooth 60 FPS animations.
🧨 Layout Thrashing: The Performance Killer
Layout thrashing happens when you repeatedly mix layout reads and writes in the same execution cycle. This causes hundreds of reflows!
Batch all reads together, then batch all writes together. This avoids thrashing and reduces reflows massively.
🎯 Efficient vs Inefficient Animations
The difference between laggy and smooth animations often comes down to which properties you animate:
Why transform is faster:
- No recalculating of layout
- No reflow triggered
- Runs on GPU compositor thread
- Main thread stays free for JavaScript
🕹️ Real-World: Smooth Scroll Performance
Scroll events fire hundreds of times per second. Without optimization, they destroy performance:
🔥 DocumentFragment: Batch DOM Changes
When adding multiple elements, use DocumentFragment to avoid multiple reflows:
🧬 Compositor Layers & GPU Acceleration
Modern browsers split the page into layers. Certain properties automatically create a new layer:
- CSS transform
- CSS will-change
- Canvas, video, iframes
- position: fixed in some scenarios
Force GPU layer for animation:
Don't overuse will-change . Too many layers consume GPU memory. Only use on elements that actually animate frequently.
🧠 Chrome DevTools Performance Debugging
Professional engineers use these techniques to find performance bottlenecks:
1. Performance Panel
- Press F12 → Performance → Start Recording
- Interact with your page
- Stop recording
- Look for large purple blocks (Layout) or green blocks (Paint)
2. Enable Paint Flashing
- Open DevTools
- Press Ctrl+Shift+P
- Search "Show paint flashing"
- Your screen flashes green every time browser repaints
3. Rendering → Layout Shift Regions
Highlights areas causing layout shifts—essential for Core Web Vitals optimization.
🏁 Professional Performance Checklist
Follow this checklist to achieve near-professional performance:
✅ Always Do
- Use transform and opacity for animations
- Batch DOM reads before writes
- Use requestAnimationFrame for visual updates
- Throttle/debounce high-frequency events
- Use IntersectionObserver for lazy loading
- Promote animating elements with will-change
❌ Never Do
- Animate top , left , width , height
- Query layout inside loops
- Mix reads and writes in same cycle
- Use complex CSS selectors
- Poll layout with setInterval
- Add elements one-by-one in loops
🎓 Practice Challenges
Challenge 1: Fix the Laggy Slider
Optimize this mousemove slider to use transforms and throttling for 60 FPS performance.
Challenge 2: Optimize Infinite Scroll
Refactor an infinite scroll implementation to use DocumentFragment and IntersectionObserver instead of scroll events and individual DOM appends.
Challenge 3: Parallax Without Jank
Create a smooth parallax scrolling effect using transforms and requestAnimationFrame that maintains 60 FPS even on mobile devices.
🎯 Key Takeaways
- • The browser rendering pipeline has 6 stages: DOM → CSSOM → Render Tree → Layout → Paint → Compositing
- • Reflow (layout) is the most expensive operation—avoid changing layout properties in animations
- • Layout thrashing occurs when mixing reads and writes—always batch reads before writes
- • Use transform and opacity for animations—they run on GPU compositor thread
- • Throttle/debounce high-frequency events like scroll, resize, and mousemove
- • Use Chrome DevTools Performance panel and Paint Flashing to identify bottlenecks
- • DocumentFragment batches DOM changes to avoid multiple reflows
- • Professional performance = understanding what your code does to the rendering pipeline
📋 Quick Reference
Concept
Impact
Reflow
Expensive — recalculates layout geometry
Repaint
Cheaper — redraws pixels without layout
transform/opacity
GPU-accelerated, no reflow
offsetWidth
Forces layout — use sparingly
DocumentFragment
Batch DOM changes into one reflow
Lesson Complete!
You now understand the full browser rendering pipeline and how to write code that keeps UIs smooth at 60 FPS.
Up next: Virtual DOM Concepts — learn how React and modern frameworks avoid unnecessary DOM updates.
Practice quiz
What is the correct order of the browser's rendering pipeline?
- Paint → Layout → DOM → Compositing
- CSSOM → Paint → DOM → Layout
- DOM → CSSOM → Render Tree → Layout → Paint → Compositing
- Render Tree → DOM → Paint → Layout
Answer: DOM → CSSOM → Render Tree → Layout → Paint → Compositing. The pipeline is DOM → CSSOM → Render Tree → Layout (Reflow) → Paint → Compositing.
Which step is the most expensive according to the lesson?
- Layout (Reflow)
- Compositing
- Paint
- Parsing HTML
Answer: Layout (Reflow). Layout (Reflow) recalculates element geometry and is the most expensive operation.
What is layout thrashing?
- Animating with transform
- Loading too many images
- Using too much CSS
- Repeatedly mixing layout reads and writes in the same cycle, causing many reflows
Answer: Repeatedly mixing layout reads and writes in the same cycle, causing many reflows. Layout thrashing happens when you interleave layout reads and writes, forcing hundreds of reflows.
What is the golden rule to avoid layout thrashing?
- Avoid all CSS
- Batch all reads together, then batch all writes together
- Use setInterval for updates
- Read layout inside loops
Answer: Batch all reads together, then batch all writes together. Batch all reads first, then all writes, to avoid interleaving that triggers repeated reflows.
Which CSS properties avoid both reflow and repaint by running on the GPU compositor?
- transform and opacity
- width and height
- top and left
- margin and padding
Answer: transform and opacity. transform and opacity changes happen on the GPU compositor thread, avoiding layout and paint.
Which of these forces a synchronous (forced) reflow when read?
- element.className
- element.dataset
- element.offsetHeight
- element.id
Answer: element.offsetHeight. Reading layout properties like offsetHeight forces the browser to apply pending layout before returning a value.
What causes a repaint without a reflow?
- Changing width
- Changing background-color or color (appearance without geometry change)
- Adding elements
- Changing display
Answer: Changing background-color or color (appearance without geometry change). Changing appearance like color or background-color repaints but does not change geometry, so no reflow.
Why use a DocumentFragment when adding many elements?
- It encrypts the DOM
- It speeds up the network
- It styles the elements
- It batches the additions into a single reflow instead of one per element
Answer: It batches the additions into a single reflow instead of one per element. Appending to a DocumentFragment off-DOM and inserting it once causes a single reflow instead of many.
To hit smooth 60 FPS, how much time does each frame have?
- About 100ms
- About 16.6ms
- About 1 second
- About 5ms
Answer: About 16.6ms. 60 FPS requires all work to fit inside roughly a 16.6ms frame budget.
What is a downside of overusing will-change?
- It disables animations
- It triggers reflow every frame
- Too many layers consume GPU memory
- It blocks the network
Answer: Too many layers consume GPU memory. will-change promotes elements to GPU layers; overusing it creates too many layers that consume GPU memory.
Continue this course
- Previous: Debouncing & Throttling
- Next: Virtual DOM Concepts