Делаем длинные списки быстрыми: Content Visibility против Виртуализации 📜⚡️
Content Visibility и виртуализация устраняют разные узкие места: как выбрать подход по Layout, Paint, размеру DOM и памяти.

Когда список из сотен или тысяч элементов начинает лагать при скролле или долго грузиться, разработчики обычно бегут внедрять одно из двух стандартных решений: content-visibility: auto в CSS или библиотеку для виртуализации (вроде TanStack Virtual).
Агустин Барриентос выкатил отличную статью, где подсвечивает главную ошибку: эти подходы решают совершенно разные узкие места (bottlenecks).
Content Visibility Auto
Браузер оставляет все DOM-узлы в дереве документа, но полностью пропускает этапы Layout, Style Calculation и Paint для блоков, которые вышли за пределы видимости (offscreen).
- Плюсы: Работает нативно в 1 строчку CSS, не ломает поиск по странице, сохраняет доступность, фокус по клавише Tab, прямые ссылки на элементы и внутреннее состояние DOM-узлов.
- Главный минус: Память и дерево DOM всё еще раздуваются.
Виртуализация
JS-код вообще не создает и не монтирует внеэкранные строки, выдергивая их из DOM и оставляя только те 10–20 штук, что помещаются на экране прямо сейчас.
- Плюсы: Единственное спасение, когда у вас 10 000+ элементов. Дерево DOM остается легким, а расходование памяти — минимальным.
- Главный минус: Как только вы выбираете виртуализацию, абсолютно все «бесплатные» браузерные функции (поиск по странице, навигация табуляцией, a11y, диплинки) превращаются в ваш личный код, который нужно проектировать, верстать и тестировать руками.
🛠 Как выбрать правильный подход?
Барриентос предлагает отталкиваться строго от профилирования:
-
Запишите Flamechart/Performance-профиль в DevTools на проблемной странице.
-
Проверьте, куда уходит львиная доля времени:
- Время уходит на Layout/Paint?
Ваша проблема — тяжелая вёрстка. Накатывайте
content-visibility: auto+contain-intrinsic-size, и в 90% случаев при списках в несколько сот элементов этого хватит с головой. - Время уходит на размер DOM?
У вас десятки тысяч элементов.
content-visibilityтут не спасете — придется пилить честную виртуализацию.
- Время уходит на Layout/Paint?
Ваша проблема — тяжелая вёрстка. Накатывайте
Читать статью с интерактивными бенчмарками
А какой подход вы обычно берете по умолчанию? Ставите нативную
content-visibilityдля быстрого буста или сразу тащите виртуализаторы? 👇