W3docs

Animaciones CSS

Aprende las animaciones CSS y cómo controlarlas desde JavaScript: alterna clases para iniciarlas y detenerlas, y reacciona a los eventos transitionend, animationend y animationiteration con ejemplos ejecutables.

Las animaciones CSS ofrecen una manera sofisticada de mejorar la experiencia del usuario con transiciones y efectos visuales suaves y atractivos. En esta guía completa, profundizamos en los matices de las animaciones CSS, proporcionando explicaciones detalladas, ejemplos y buenas prácticas para crear diseños dinámicos y responsivos.

Introducción a las animaciones CSS

Las animaciones CSS permiten a los desarrolladores web animar elementos HTML sin depender de JavaScript. Se definen mediante keyframes, que especifican los estilos en distintos puntos de la secuencia de animación.

Ejemplo básico de animación CSS

<div class="animated-box"></div>

<style>
  .animated-box {
    width: 100px;
    height: 100px;
    background-color: red;
    animation: move 4s infinite;
  }

  @keyframes move {
    0% { transform: translateX(0); }
    50% { transform: translateX(200px); }
    100% { transform: translateX(0); }
  }
</style>
Advertencia

Prueba siempre las animaciones en diferentes dispositivos y navegadores para garantizar un rendimiento fluido.

Propiedades clave de las animaciones CSS

  • animation-name: Especifica el nombre de los keyframes.
  • animation-duration: Define la duración de la animación.
  • animation-timing-function: Establece la curva de velocidad de la animación.
  • animation-delay: Retrasa el inicio de la animación.
  • animation-iteration-count: Define el número de veces que debe reproducirse la animación.
  • animation-direction: Especifica si la animación debe reproducirse en sentido inverso en ciclos alternos.

Aplicar múltiples animaciones

Puedes aplicar múltiples animaciones a un mismo elemento separándolas con comas.

<div class="multi-animated-box"></div>

<style>
  .multi-animated-box {
    width: 100px;
    height: 100px;
    background-color: blue;
    animation: move 4s infinite, rotate 2s infinite;
  }

  @keyframes move {
    0% { transform: translateX(0); }
    50% { transform: translateX(200px); }
    100% { transform: translateX(0); }
  }

  @keyframes rotate {
    0% { transform: rotate(0deg); }
    100% { transform: rotate(360deg); }
  }
</style>

Técnicas avanzadas

Animaciones responsivas

Asegúrate de que las animaciones sean responsivas y se adapten a diferentes tamaños de pantalla.

<div class="responsive-box"></div>

<style>
  .responsive-box {
    width: 50vw;
    height: 50vw;
    background-color: green;
    animation: resize 4s infinite;
  }

  @keyframes resize {
    0% { width: 50vw; height: 50vw; }
    50% { width: 70vw; height: 70vw; }
    100% { width: 50vw; height: 50vw; }
  }
</style>

Combinar transformaciones

Combina múltiples propiedades de transformación para crear animaciones complejas.

<div class="complex-transform-box"></div>

<style>
  .complex-transform-box {
    width: 100px;
    height: 100px;
    background-color: yellow;
    animation: complexTransform 5s infinite;
  }

  @keyframes complexTransform {
    0% {
      transform: translateX(0) rotate(0deg) scale(1);
    }
    50% {
      transform: translateX(200px) rotate(180deg) scale(1.5);
    }
    100% {
      transform: translateX(0) rotate(360deg) scale(1);
    }
  }
</style>

Modos de relleno de animación

La propiedad animation-fill-mode define cómo una animación CSS aplica estilos a su objetivo antes y después de su ejecución.

<div class="fill-mode-box"></div>

<style>
  .fill-mode-box {
    width: 100px;
    height: 100px;
    background-color: purple;
    animation: fillMode 3s forwards;
  }

  @keyframes fillMode {
    0% { background-color: purple; }
    100% { background-color: orange; }
  }
</style>

Retrasos y funciones de temporización de animación

Usa retrasos y funciones de temporización para controlar el ritmo y el inicio de las animaciones.

<div class="timing-function-box"></div>

<style>
  .timing-function-box {
    width: 100px;
    height: 100px;
    background-color: pink;
    animation: timingFunction 4s ease-in-out infinite;
  }

  @keyframes timingFunction {
    0% { transform: translateY(0); }
    50% { transform: translateY(200px); }
    100% { transform: translateY(0); }
  }
</style>

Buenas prácticas para animaciones CSS

  1. Minimiza el uso de CPU: Mantén las animaciones simples para evitar un uso excesivo de CPU, lo que puede degradar el rendimiento, especialmente en dispositivos móviles.
  2. Usa aceleración por hardware: Utiliza las propiedades transform y opacity para aprovechar la aceleración por GPU.
  3. Alternativas: Proporciona estilos alternativos para navegadores que no admitan animaciones.
  4. Pruebas de rendimiento: Prueba las animaciones en diferentes dispositivos y navegadores para garantizar un rendimiento fluido.
Información

Puedes usar JavaScript para crear animaciones más interactivas. Consulta Animaciones JavaScript.

Ejemplo de una animación bien optimizada

<div class="optimized-box"></div>

<style>
  .optimized-box {
    width: 100px;
    height: 100px;
    background-color: cyan;
    animation: optimizedMove 3s ease-in-out infinite;
  }

  @keyframes optimizedMove {
    0% { transform: translateY(0) scale(1); }
    50% { transform: translateY(200px) scale(1.2); }
    100% { transform: translateY(0) scale(1); }
  }
</style>

Controlar animaciones CSS desde JavaScript

CSS se encarga del renderizado de una animación de forma eficiente, pero no sabe cuándo debe ejecutarse ni qué debe ocurrir después de que termine. Esa lógica de decisión corresponde a JavaScript. El patrón más común es: definir la animación en CSS y dejar que JavaScript añada o elimine una clase para iniciarla o detenerla.

Esto mantiene la reproducción suave y acelerada por GPU en CSS, mientras tu código conserva el control sobre el tiempo y las acciones posteriores.

Iniciar y detener con un alternado de clase

Coloca la animación en una clase en lugar del selector base y alterna esa clase:

<button id="play">Play</button>
<div id="box"></div>

<style>
  #box {
    width: 100px;
    height: 100px;
    background: teal;
  }
  /* The animation only runs while this class is present */
  #box.run {
    animation: slide 1s ease-in-out;
  }
  @keyframes slide {
    from { transform: translateX(0); }
    to   { transform: translateX(200px); }
  }
</style>

<script>
  const box = document.getElementById('box');
  document.getElementById('play').onclick = () => {
    // Toggle: add the class to play, the CSS animation does the rest
    box.classList.add('run');
  };
</script>

Como la animación vive en la clase .run, eliminar la clase la detiene de inmediato y restaurarla la reproduce desde el principio.

Información

Añadir y eliminar clases de animación es una tarea de estilos. Para el conjunto completo de herramientas, lee Estilos y clases y Trabajar con estilos en el DOM.

Escuchar el final: transitionend y animationend

La principal ventaja de controlar animaciones desde JavaScript es que el navegador dispara eventos DOM a los que puedes reaccionar. Esto te permite encadenar pasos, limpiar clases o ejecutar código exactamente cuando un efecto termina, sin recurrir a setTimeout con tiempos estimados.

  • Para las transiciones CSS, el evento transitionend se dispara cuando una transición finaliza.
  • Para las animaciones CSS (@keyframes), se disparan tres eventos: animationstart, animationiteration (una vez por cada bucle) y animationend.
<button id="fade">Fade out</button>
<div id="panel">Hello</div>

<style>
  #panel {
    width: 150px;
    padding: 20px;
    background: gold;
    transition: opacity 0.5s;
  }
  #panel.hidden { opacity: 0; }
</style>

<script>
  const panel = document.getElementById('panel');

  document.getElementById('fade').onclick = () => panel.classList.add('hidden');

  // Runs the moment the fade completes — not a guessed delay
  panel.addEventListener('transitionend', (event) => {
    console.log(`Transition of "${event.propertyName}" finished`);
    panel.style.display = 'none'; // safe to hide only now
  });
</script>

Cuando la transición termina, la consola muestra:

Transition of "opacity" finished

Leer detalles del evento: propertyName y animationName

Los eventos de animación contienen datos útiles. Cuando hay varias propiedades o animaciones involucradas, a menudo necesitas saber cuál acaba de terminar.

  • event.propertyName — la propiedad CSS que realizó la transición (en transitionend).
  • event.animationName — el nombre de @keyframes (en los tres eventos de animación).
  • event.elapsedTime — segundos de tiempo de ejecución, excluyendo cualquier animation-delay.
<div id="bouncer">Watch the console</div>

<style>
  #bouncer { animation: bounce 0.6s ease 3; }
  @keyframes bounce {
    0%, 100% { transform: translateY(0); }
    50%      { transform: translateY(-30px); }
  }
</style>

<script>
  const el = document.getElementById('bouncer');

  el.addEventListener('animationstart', (e) =>
    console.log(`start: ${e.animationName}`));

  el.addEventListener('animationiteration', (e) =>
    console.log(`loop of ${e.animationName} at ${e.elapsedTime}s`));

  el.addEventListener('animationend', (e) =>
    console.log(`end: ${e.animationName} (total ${e.elapsedTime}s)`));
</script>

Con animation: bounce 0.6s ease 3 (tres iteraciones), la consola muestra start, dos eventos animationiteration (cuando comienzan los bucles 2 y 3) y luego end con 1.8s en total.

Advertencia

animationiteration se dispara entre bucles, por lo que una animación que se repite N veces lo dispara N − 1 veces, nunca después del último bucle. Usa animationend para saber cuándo "ha terminado todo".

Animación controlada por JS vs. controlada por CSS: ¿cuál elegir?

Usa animación controlada por CSS (keyframes/transiciones) cuando…Usa animación controlada por JS cuando…
El movimiento es fijo y declarativo (hovers, loaders, entradas).Los valores dependen de datos en tiempo de ejecución (posición de arrastre, scroll, física).
Quieres el mejor rendimiento con el mínimo código.Necesitas control fotograma a fotograma o pausar/reanudar a mitad de la animación.
El navegador puede delegar el trabajo a la GPU (transform, opacity).Debes animar propiedades que CSS no puede expresar fácilmente.

El mejor enfoque práctico es un híbrido: CSS describe el efecto, JavaScript decide cuándo se ejecuta y qué ocurre después mediante los eventos anteriores. Cuando realmente necesites control por fotograma, recurre a Animaciones JavaScript con requestAnimationFrame, o a la API de Animaciones Web para construir y controlar animaciones íntegramente en código.

Conclusión

Las animaciones CSS son una herramienta poderosa para crear experiencias web dinámicas y atractivas. Al dominar los keyframes, las propiedades de animación y las técnicas avanzadas, los desarrolladores pueden producir animaciones de nivel profesional que mejoran la interacción del usuario. Experimenta con diferentes animaciones, prueba a fondo y sigue las buenas prácticas para obtener los mejores resultados.

Práctica

Práctica
¿Cuáles de las siguientes afirmaciones sobre las animaciones CSS son correctas?
¿Cuáles de las siguientes afirmaciones sobre las animaciones CSS son correctas?
Was this page helpful?