> Optimise page redering performance: Lower TBT with CSS content-visibility
- Publication
- Author
- Florian Thoma
- Categories
- Services
- Reading time
- 2 minutes
Modern websites are increasingly built from modular blocks. In Silverstripe, the Elemental module makes it easy to compose rich, flexible pages by stacking multiple content elements. But the more elements you add, the longer the page becomes, and the heavier the browser’s rendering workload.
I came across this idea twice within just a couple of weeks: once at performance.now() and again at the Web Directions Dev Summit. I had heard of content-visibility before, but never really paid it any attention. Curious, I've since tried it out on several sites with long, block-based layouts, and the results are striking. Rendering long tasks dropped dramatically, and pages that previously felt sluggish have suddenly become smooth and responsive. It is one of those rare CSS discoveries that immediately proved its worth in real-world projects.
The problem: Long pages, heavy rendering
Browsers need to calculate the full length of a page to display things like the scrollbar thumb size. That means they must render every block, even those far below the fold that a user may never scroll to.
On very long pages, this can lead to:
- Long tasks in the rendering pipeline
- High Total Blocking Time (TBT), which hurts Google Web Vitals
- A sluggish feel for users, especially on mobile devices
The solution: CSS content-visibility
The CSS property content-visibility allows developers to defer rendering of off-screen elements. Combined with contain-intrinsic-size, it provides a placeholder height so the browser can calculate the layout without rendering the actual content.
content-visibility: auto;contain-intrinsic-size: 800px;
content-visibility: auto;defers rendering until the element is near the viewport.contain-intrinsic-size: 800px;provides a placeholder height (here 800px as an example) so the browser can calculate layout and scrollbar size without rendering the actual content.
This works much like lazy loading for rendering, and it’s not limited to Silverstripe. Any website with long, block-based layouts can benefit.
Why it matters
- Performance boost: The browser skips expensive paint and layout work until needed.
- Lower TBT: Long tasks are broken up, improving responsiveness.
- Better Web Vitals: Faster interaction and smoother scrolling.
- User experience: Pages feel snappy, even when packed with rich content.
Browser compatibility
According to Can I Use, the property content-visibility is in Baseline 2024 and available across all major browser engines:
- Chrome: Supported from version 85+, August 2020
- Edge: Supported from version 85+, August 2020
- Firefox: Supported from version 125+, April 2024
- Safari: Supported from version 18.0+, September 2024
- Opera: Supported from version 71+, September 2020
And if a browser doesn't support it, it just falls back to rendering the elements as normal. Which means that there is really no reason not to use this.
Implementation example
It's really very simple: You can add these styles globally to block-like elements:
.block {content-visibility: auto;contain-intrinsic-size: 800px;}
Adjust the intrinsic size to match the average height of your blocks. If some blocks are smaller or taller, the browser will correct the layout once they’re rendered.
Caveats & considerations
- SEO: Content remains in the DOM, so search engines can index it.
- Accessibility: Screen readers may behave differently: test carefully.
- Design consistency: Placeholder heights should be chosen thoughtfully to avoid layout shifts.
Whether you’re building with Silverstripe Elemental or any other block-based CMS, content-visibility is a powerful tool to keep long pages fast and responsive.
If you’d like to discuss implementation on your site, contact us. We’d love to hear from you.