Manipularea arborelui DOM este una dintre cele mai costisitoare operațiuni din browser. Fiecare modificare adusă nodurilor din pagină poate forța motorul de randare să recalculeze stilurile geometrice (Reflow / Layout) și să re-deseneze pixelii pe ecran (Repaint). Pentru a obține animații fluide la 60 sau 120 FPS, dezvoltatorii folosesc două tehnici esențiale: Event Delegation și DocumentFragment.
// SCENARIU GREȘIT: Adăugarea unui listener individual pe fiecare rând de tabel (consum masiv de RAM):
// document.querySelectorAll('.rand-tabel').forEach(el => el.addEventListener('click', ...));
// SCENARIU CORECT (Event Delegation):
// Atașăm un singur listener pe containerul părinte și folosim e.target.closest():
const containerTabel = document.querySelector('#tabel-utilizatori');
containerTabel.addEventListener('click', (event) => {
// Găsim cel mai apropiat element buton de acțiune:
const butonStergere = event.target.closest('.btn-sterge');
if (!butonStergere) return; // Click-ul a fost în altă parte a tabelului
const rand = butonStergere.closest('tr');
const id = rand.dataset.id;
console.log(`Ștergere utilizator ID: ${id}`);
rand.remove();
});
// Generarea a 10.000 de elemente fără a bloca interfața utilizator
const listaElemente = ['Produs 1', 'Produs 2', 'Produs 3', /* ... 10.000 elemente */];
const containerLista = document.querySelector('#lista-produse');
// Creăm un container virtual în memorie (nu face parte din DOM-ul vizibil):
const fragment = document.createDocumentFragment();
for (const text of listaElemente) {
const li = document.createElement('li');
li.textContent = text;
li.className = 'produs-item';
fragment.appendChild(li); // Zero cost de Reflow/Repaint!
}
// O SINGURĂ inserție în DOM-ul real pentru toate cele 10.000 de elemente:
containerLista.appendChild(fragment);
Ce este Layout Thrashing și cum îl eviți
Layout Thrashing apare când alternezi citirea și scrierea din DOM într-o buclă (de exemplu: citești offsetWidth, apoi modifici style.width, apoi citești din nou). Browserul este forțat să recalculeze geometria la fiecare iterație. Regula este: citește toate datele mai întâi (Batch Reads), apoi aplică toate modificările (Batch Writes), preferabil în interiorul unui requestAnimationFrame().