No tienes acceso a esta clase

隆Contin煤a aprendiendo! 脷nete y comienza a potenciar tu carrera

Lazy Loading

7/20
Recursos

Aportes 10

Preguntas 4

Ordenar por:

驴Quieres ver m谩s aportes, preguntas y respuestas de la comunidad?

o inicia sesi贸n.

Mi aporte

El profesor utiliza el atributo data-src y comienza por 鈥渄ata-鈥 ya que hace referencia a los datasets que son atributos personalizados podr铆amos decir, para poder extraerlos luego en otra oportunidad, podemos colocar la cantidad de dataset que querramos y luegos podemos extraerlos con destructruaci贸n de objetos, por ejemplo s铆 usamos dos datasets data-src y data-alt m谩s adelante cuando querramos incrustar estas variables en la imagen mediante el trigger del observer podemos extraerlo de la siguiente manera:

const container = entry.target; // DIV
const image = container.querySelector('img');
const { src, alt } = image.dataset;

Referencia: HTMLElement.dataset
.
.
Siempre es buena pr谩ctiica que dentro del callback dentro de la instancia new IntersectionObserver suspendamos la observaci贸n del elemento una vez que la imagen ya halla cargado, de la siguiente manera.

const callback = (entries, observer) => {
	...
	observer.unobserve(target);
}

const observer = new IntersectionObserver(callback);

.
Si quieren agregar un efecto css al antes de cargar completamente la imagen pueden hacerlo jugando con las options de la instancia y con el par谩metro threshold y agregar el efecto en el triggers callback con como por ejemplo el efecto fade-in.
.
Referencia: Intersection Observer API
.
.

Mi propuesta

Repositorio del proyecto: Click aqu铆

Commit actual: Click aqu铆

Cambios en el commit: Click aqu铆

Tambi茅n si quieren evitar el problema que dice @JuanDC, en el que las im谩genes cargan peque帽as, la manera de solucionarlo es eliminando el CLS (Culmulative Layout Shift - Cambio de dise帽o acumulativo), que b谩sicamente es cuando un elemento mueve el dise帽o despu茅s de cargar el html base, y resulta molesto para los usuarios.

Para esto existen varias t茅cnicas, la mejor para m铆 es: Teniendo en cuenta el aspect ratio de la imagen, agregar un width y height fijo y proporcional al aspect ratio, para que con unas propiedades, css pueda calcular su tama帽o, y siempre mantenga la proporci贸n, tambi茅n sirve para agregar un skeleton loader responsive a las im谩genes.
驴Qu茅 es el aspect ratio?

驴Pero esto qu茅 significa, y c贸mo se hace?
Por ejemplo, en las im谩genes de nuestro proyecto, ya sea que pidamos una imagen de 200x300, 300x450 鈥 Etc. Estas im谩genes (de los cards) siempre tendr谩n un aspec ratio de 2:3, ahora utilizaremos esto en c贸digo:

<img className="img-responsive" alt="imagen" width="200" height="300" />						

Para que CSS pueda calcular la altura, necesita las propiedades: aspect-ratio: n/n;, height: auto; y el width que necesitemos, en este caso puede ser 100%, porque en el c贸digo utilizo un grid

.img-responsive {
	aspect-ratio: 2 / 3; // O tambi茅n 200 / 300
	border-radius: 1rem;
	height: auto;
	object-fit: cover;
	vertical-align: top;
	width: 100%;
}

Tambi茅n aqu铆 hay informaci贸n sobre el CLS, esta y otras t茅cnicas para solucionarlo, en el que seguro lo explican m谩s detallado, y mejor. 馃槄

Con esto, evitamos que cuando carguen las im谩genes, muevan todo lo que est谩 debajo de ellas, porque ya tienen su espacio asignado. 馃槂

Algo similar con el atributto loading, sin el intersectionObserver

movieImg.setAttribute('loading', 'lazy') 

Junto con el loading skeleton, el intersection observer, el evento onload de las im谩genes y una animaci贸n, se puede cubrir todo el proceso de carga de una imagen:
El c贸digo est谩 en React, pero sigue siendo JavaScript, por si a alguien le sirve:

Solamente importan el registerObserver, y le pasan la referencia de cada imagen, tambi茅n agregan las clases para las animaciones, y le agregan su loading skeleton 馃槃

antes del lazuLoading al verificar el performance de la aplicaci贸n con lighthouse mi rendimiento en mobile era del 3, despu茅s de implementarlo subi贸 al51

Si las imagenes ya estan cargadas ya no es necesario el observer so鈥

if (entry.isIntersecting) {
	entry.target.setAttribute('src', url)
	lazyLoader.unobserve(entry.target)
}

Al final el profe dice:
si el height de las im谩genes est谩 en 0 no va a tomar el lazy
.
Esto es lo que pasa con las im谩genes en la secci贸n categor铆a. Por eso cargan todas al mismo tiempo.
.
Mi soluci贸n fue agregar esto al css

.genericList-container .movie-container .movie-img {
    height: 270px;
    min-height: 270px;
    max-height: 270px;
    width: 170px;
    min-width: 170px;
    max-width: 170px;
}

Me acabo de enterar que hay un atributo en HTML llamado 鈥渓oading鈥 que se usa en etiquetas <img>
y <iframe> que acepta tres valores:

  • lazy: el recurso tiene carga diferida

  • eager: el recurso se carga lo antes posible

  • auto: el navegador decide cu谩ndo se carga el recurso

Esto nos ahorra el c贸digo en JavaScript! Como siempre, no todo puede ser perfecto, les dejo el enlace a CanIUse para que chequeen el soporte de cada navegador

https://caniuse.com/?search=loading

Le agregu茅 que deje de escuchar el nodo (imagen) cuando ya la carg贸.
Es decir, que no la vuelva a cargar.

const lazyLoader = new IntersectionObserver((entries)=>{
    entries.forEach((image)=>{
        if (image.isIntersecting ) {
            const url = image.target.getAttribute('data-img');
            image.target.setAttribute('src', url);
            lazyLoader.unobserve(image.target);
        }
    });
});

Segu铆 los pasos de esta clase

Me encanta la actitud de Juan los cursos aparte de interesantes y importantes, son divertidos n.n