Layout thrashing: bir karede tekrarlanan reflow'lar ve nasıl durdurulur
Ne oluyor
Tarayıcı layout'u kare başına bir kez yeniden hesaplamaya çalışır. Ama kodunuz bir stil yazıp sonra bir geometri özelliği (offsetWidth, getBoundingClientRect) okur ve tekrar yazarsa — bir döngüde — her okuma sayfanın yeni, senkron bir layout'unu zorlar. 100 öğe üzerinde bir döngü tek bir karede 100 tam reflow tetikleyebilir.
Maliyet DOM boyutuyla orantılıdır, dolayısıyla küçük bir sayfada sorunsuz olan aynı kod, binlerce düğümlü bir sayfada INP'yi mahveder.
Nasıl tanınır
- INP dökümünde presentation delay (işleyiciden sonraki render işi) baskındır.
- DevTools Performance bir kare içinde çok sayıda mor Layout bloğu gösterir, sıklıkla “Forced reflow” olarak işaretlenir.
- Kod bir döngü içinde okumaları (offsetTop, clientHeight, getComputedStyle) ve yazmaları (style, classList) dönüşümlü yapar.
Nasıl düzeltilir
- Önce tüm okumaları, sonra tüm yazmaları grupla — bir döngüde asla iç içe geçirme.
- Yazmaları requestAnimationFrame'e taşı, böylece bir sonraki boyamadan hemen önce uygulanır.
- Öğeleri JS'te ölçüp konumlandırmak yerine CSS çözümlerini (sınıflar, transform, flex/grid) tercih et.
Sorun
items.forEach((el) => {
el.style.width = base + "px" // write
const h = el.offsetHeight // read → forced reflow, every iteration
el.style.height = h * 2 + "px" // write
})
Çözüm
const heights = items.map((el) => el.offsetHeight) // all reads
requestAnimationFrame(() => {
items.forEach((el, i) => { // all writes
el.style.width = base + "px"
el.style.height = heights[i] * 2 + "px"
})
})
Sitenizi ücretsiz tarayın →