I have a modified Bootstrap 4 carousel that has multiple items and scrolls one-by-one using this JavaScript:
$('.carousel[data-type="multi"] .carousel-item').each(function() {
var next = $(this).next();
if (!next.length) {
next = $(this).siblings(':first');
}
next.children(':first-child').clone().appendTo($(this));
for (var i = 0; i < 2; i++) {
next = next.next();
if (!next.length) {
next = $(this).siblings(':first');
}
next.children(':first-child').clone().appendTo($(this));
}
});
This creates a clone of each carousel-item with multiple carousel-columns, like this:
<div class="carousel-item active">
<div class="carousel-col">
<img src="" class="lazy" /> <!-- This image loads -->
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
</div>
<div class="carousel-item">
<div class="carousel-col">
<img src="" class="lazy" /> <!-- This image loads -->
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
<div class="carousel-col">
<img src="" class="lazy" />
</div>
</div>
I'm trying to implement lazy-loading with the Intersection Observer API, however inside the carousel it only works on the image in the first carousel-col in each carousel-item. I'm guessing this is due to the cloning but I'm not sure how to remedy the conflict. The API doesn't see to recognize that the cloned images exist.
Does anyone have any insight as to how I might go about fixing this?
Here's the JavaScript I'm using for lazyloading:
document.addEventListener("DOMContentLoaded", function() {
var lazyloadImages;
if ("IntersectionObserver" in window) {
lazyloadImages = document.querySelectorAll(".lazy");
var imageObserver = new IntersectionObserver(function(entries, observer) {
entries.forEach(function(entry) {
if (entry.isIntersecting) {
var image = entry.target;
image.src = image.dataset.src;
image.classList.remove("lazy");
imageObserver.unobserve(image);
}
});
});
lazyloadImages.forEach(function(image) {
imageObserver.observe(image);
});
} else {
var lazyloadThrottleTimeout;
lazyloadImages = document.querySelectorAll(".lazy");
function lazyload () {
if(lazyloadThrottleTimeout) {
clearTimeout(lazyloadThrottleTimeout);
}
lazyloadThrottleTimeout = setTimeout(function() {
var scrollTop = window.pageYOffset;
lazyloadImages.forEach(function(img) {
if(img.offsetTop < (window.innerHeight + scrollTop)) {
img.src = img.dataset.src;
img.classList.remove('lazy');
}
});
if(lazyloadImages.length == 0) {
document.removeEventListener("scroll", lazyload);
window.removeEventListener("resize", lazyload);
window.removeEventListener("orientationChange", lazyload);
}
}, 20);
}
document.addEventListener("scroll", lazyload);
window.addEventListener("resize", lazyload);
window.addEventListener("orientationChange", lazyload);
}
});