
Animar elementos HTML al hacer scroll
Seguramente en numerosas páginas Web habeis visto un efecto que consiste en animar elementos HTML al hacer scroll. Por lo general, este tipo de animaciones consisten en que los elementos van apareciendo desde diferentes direcciones, o se hacen grandes o pequeños al aparecer.
En este artículo vamos a implementar una versión muy sencilla de este tipo de efectos. Concretamente, vamos a implementar algo como lo que se puede apreciar en la siguiente imagen animada:
Tal y como se puede apreciar, al hacer scroll, van apareciendo algunos elementos que inicialmente no eran visibles.
El grueso de este efecto se puede realizar solo con HTML y CSS, pero es necesario un poquito de JavaScript ( que ya os proporcionaré yo, así que no os preocupéis ).
El HTML de nuestro ejemplo
Para este ejemplo voy a hacer una pagina HTML que incluirá varias secciones como las siguientes:
<section id="hero" class="paused"> <div class="wrapper"> <h1 class="anim-down">Lorem, ipsum dolor sit amet consectetur adipisicing elit. Id, suscipit!</h1> <p class="anim-up">Lorem ipsum dolor sit amet ...</p> </div> </section> <section id="features" class="paused"> <div class="wrapper"> <h1 class="anim-left">Lorem ipsum dolor sit amet consectetur adipisicing elit. Explicabo, obcaecati.</h1> <p class="anim-right">Lorem, ipsum dolor sit amet ...</p> <ul> <li class="anim-fade-in anim-pause-2">Lorem ipsum, dolor sit amet consectetur...</li> <li class="anim-fade-in anim-pause-3">Ullam et consequuntur maiores...</li> <li class="anim-fade-in anim-pause-4">Veniam atque consequuntur tenetur...</li> <li class="anim-fade-in anim-pause-5">Voluptatem, veniam sit mollitia...</li> </ul> </div> </section>
Tal y como se puede observar, hemos definido varias secciones con la clase paused, y dentro, tendemos varios elementos con clases llamadas anim-noseque.
Las clases anim-left, anim-right, anim-up y anim-down, simplemente tienen asignadas unas animaciones CSS que hacen que el elemento se mueva en una dirección al mismo tiempo que su opacidad pasa de 0 (transparente) a 1 (opaco). La clase anim-fade-in simplemente realiza esto último (cambiar la opacidad).
Todas las clases las he configurado con unos mismos tiempos, pero es posible cambiar la pausa que se realiza antes de empezar la animación mediante las clases anim-pause-*. Por eso, esos 4 elementos iran apareciendo uno detrás de otro, y no aparecerán todos a la vez.
El sistema de este ejemplo es bastante sencillito, se puede ampliar bastante más, con más efectos de animación y más características sin mucho esfuerzo.
Obviamente, si queremos probar bien el ejemplo, deberemos de incluir mas contenido HTML. De lo contrario hay tan poco contenido que no podremos hacer scroll y apreciar el efecto en su totalidad. En mi caso me he limitado a añadir, justo encima, otra sección con varias decenas de párrafos con textos «lorem ipsum».
Como vamos a animar elementos HTML al hacer scroll
El mecanismo que vamos a usar es el siguiente. Inicialmente todos los elementos que se encuentren dentro de un elemento con la clase paused, tendrán sus animaciones pausadas.
Con el siguiente código JavaScript, haremos lo siguiente: cada vez que el usuario haga scroll, buscaremos si alguna de estas secciones está visible en pantalla. En caso afirmativo, le quitaremos la clase paused, por lo que las animaciones que tenga dentro se pondrán en marcha automáticamente.
// esta funcion comprueba si un elemento esta visible en pantalla function isVisible(elm) { var rect = elm.getBoundingClientRect(); var viewHeight = Math.max(document.documentElement.clientHeight, window.innerHeight); return !(rect.bottom < 0 || rect.top - viewHeight >= 0); } // cuando se carga la página... window.addEventListener('DOMContentLoaded', (ev0) => { // asignamos un evento scroll... window.addEventListener('scroll', (ev1) => { // y a todos los elementos con la clase paused... document.querySelectorAll(".paused").forEach(elm => { if (isVisible(elm)) // que sean visibles... elm.classList.remove("paused"); // les quitamos la clase paused }) }); });
Este código JavaScript lo puedes colocar dentro de una etiqueta <script> en el <head> de tu documento HTML.
Las animaciones CSS que vamos a usar
Las animaciones CSS que he usado en mi ejemplo son las siguientes:
/* primero un poco de CSS muy básico */ body { font-family: sans-serif; overflow-x: hidden; /* para que nada sobresalga en horizontal */ } .wrapper { max-width: 1000px; margin: 0 auto; padding: 32px; } /* a partir de aqui el CSS de las animaciones */ @keyframes anim-fade-in { from { opacity: 0; } to { opacity: 1 } } @keyframes anim-up { from { opacity: 0; transform: translateY(100px); } to { opacity: 1; transform: translateY(0px); } } @keyframes anim-down { from { opacity: 0; transform: translateY(-100px); } to { opacity: 1; transform: translateY(0px); } } @keyframes anim-left { from { opacity: 0; transform: translateX(100px); } to { opacity: 1; transform: translateX(0px); } } @keyframes anim-right { from { opacity: 0; transform: translateX(-100px); } to { opacity: 1; transform: translateX(0px); } } .anim-up, .anim-down, .anim-left, .anim-right, .anim-fade-in { animation-duration: 1s; /* la animacion dura X segundos */ animation-delay: 0.5s; /* esperamos X segundos antes de hacer la animacion */ animation-fill-mode: both; /* aplica estilos de la animacion antes y despues de reproducirla */ } .anim-up { animation-name: anim-up; } .anim-down { animation-name: anim-down; } .anim-left { animation-name: anim-left; } .anim-right { animation-name: anim-right; } .anim-fade-in { animation-name: anim-fade-in; } .anim-pause-2 { animation-delay: 2s; } /* la animacion empieza en 2 seg. */ .anim-pause-3 { animation-delay: 3s; } /* la animacion empieza en 3 seg. */ .anim-pause-4 { animation-delay: 4s; } /* la animacion empieza en 4 seg. */ .anim-pause-5 { animation-delay: 5s; } /* la animacion empieza en 5 seg. */ /* todas las animaciones pausadas */ .paused * { animation-play-state: paused; }
El código CSS en si es bastante sencillito, así que asumo que no requiere mayores explicaciones que las que ofrecen los propios comentarios.
Conclusiones
Como puedes ver este llamativo efecto es bastante sencillo de implementar, pero si tienes cualquier duda, déjala en tu comentario a continuación.