Rendimiento de GSAP
Cuándo usar esta habilidad
Aplícala al optimizar animaciones GSAP para lograr 60 fps suaves, reducir el costo de layout/pintura, o cuando el usuario pregunte sobre rendimiento, tirones (jank) o mejores prácticas para animaciones rápidas.
Habilidades relacionadas: Crea animaciones con gsap-core (transformaciones, autoAlpha) y gsap-timeline; para rendimiento con ScrollTrigger consulta gsap-scrolltrigger.
Prefiere Transform y Opacity
Animar transform (x, y, scaleX, scaleY, rotation, rotationX, rotationY, skewX, skewY) y opacity mantiene el trabajo en el compositor y evita layout y la mayor parte de la pintura. Evita animar propiedades pesadas de layout cuando una transformación pueda lograr el mismo efecto.
- ✅ Prefiere: x, y, scale, rotation, opacity.
- ❌ Evita cuando sea posible: width, height, top, left, margin, padding (provocan layout y pueden causar tirones).
GSAP usa transformaciones (translate) por defecto para x e y; úsalos en lugar de left/top para movimiento.
will-change
Usa will-change en CSS en los elementos que se animarán. Indica al navegador que promocione la capa.
will-change: transform;
Agrupa lecturas y escrituras
GSAP agrupa las actualizaciones internamente. Al mezclar GSAP con lecturas/escrituras directas del DOM o código dependiente del layout, evita intercalar lecturas y escrituras de forma que se provoque un thrashing de layout repetido. Prefiere hacer primero todas las lecturas y luego todas las escrituras (o deja que GSAP maneje las escrituras de una sola vez).
Muchos elementos (Stagger, listas)
- Usa stagger en lugar de muchos tweens separados con retrasos manuales cuando la animación sea la misma; es más eficiente.
- Para listas largas, considera la virtualización o animar solo los elementos visibles; evita crear cientos de tweens simultáneos si causan tirones.
- Reutiliza timelines cuando sea posible; evita crear nuevos timelines cada frame.
Propiedades actualizadas frecuentemente (ej. seguidores de ratón)
Prefiere gsap.quickTo() para propiedades que se actualizan a menudo (ej. x/y de un seguidor de ratón). Reutiliza un solo tween en lugar de crear nuevos tweens en cada actualización.
let xTo = gsap.quickTo("#id", "x", { duration: 0.4, ease: "power3" }),
yTo = gsap.quickTo("#id", "y", { duration: 0.4, ease: "power3" });
document.querySelector("#container").addEventListener("mousemove", (e) => {
xTo(e.pageX);
yTo(e.pageY);
});
ScrollTrigger y rendimiento
- pin: true promociona el elemento anclado; ancla solo lo necesario.
- scrub con un valor pequeño (ej.
scrub: 1) puede reducir el trabajo durante el desplazamiento; prueba en dispositivos de gama baja. - Llama a ScrollTrigger.refresh() solo cuando el layout cambie realmente (ej. después de cargar contenido), no en cada redimensionamiento; aplica debounce cuando sea posible.
Reduce trabajo simultáneo
- Pausa o elimina animaciones fuera de pantalla o inactivas cuando no sean visibles (ej. cuando el usuario navega a otra sección).
- Evita animar un gran número de propiedades en muchos elementos a la vez; simplifica o secuencia si es necesario.
Mejores prácticas
- ✅ Anima transform y opacity; usa will-change en CSS solo en los elementos que se animan.
- ✅ Usa stagger en lugar de muchos tweens separados con retrasos manuales cuando la animación sea la misma.
- ✅ Usa gsap.quickTo() para propiedades actualizadas frecuentemente (ej. seguidores de ratón).
- ✅ Limpia o elimina animaciones fuera de pantalla; llama a ScrollTrigger.refresh() cuando cambie el layout, con debounce cuando sea posible.
No hagas
- ❌ Animes width/height/top/left para movimiento cuando x/y/scale puedan lograr el mismo aspecto.
- ❌ Establezcas will-change o force3D en cada elemento "por si acaso"; úsalos solo en elementos que realmente se animan.
- ❌ Crees cientos de tweens o ScrollTriggers superpuestos sin probar en dispositivos de gama baja.
- ❌ Ignores la limpieza; los tweens y ScrollTriggers huérfanos siguen ejecutándose y pueden perjudicar el rendimiento y la corrección.