Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
425 views
in Technique[技术] by (71.8m points)

javascript - 图像因Intersection Observer API问题而延迟加载(Images lazy loading with Intersection Observer API issue)

everyone.(大家。)

I've got gallery of 1609 images and I'm trying to configure images lazy loading with Intersection observer API and stuck with the problem, that no matter what, I've got all of them to be uploaded instantly, meaning that lazy loading doesn't work.(我有1609张图像的库,并且我正在尝试使用Intersection Observer API配置图像延迟加载,并且遇到了问题,无论如何,我已将所有图像立即上传,这意味着延迟加载不会不行)

Here's full code listing for the simple testing page below:(以下是简单测试页面的完整代码清单:)
    <?php 

    $listOfFolders = scandir(__DIR__);
    $images = [];


    foreach ($listOfFolders as $folder) {
        if($folder == "." || $folder == ".." || $folder == "index.php")
        {
            continue;
        } else {
            $innerFolders = scandir("./".$folder);
            foreach ($innerFolders as $innerFolder) {
                if($innerFolder == "." || $innerFolder == ".." || $innerFolder == "index.php")
                {
                    continue;
                } else {
                    $imagesList = scandir('./'.$folder.'/'.$innerFolder);
                    foreach ($imagesList as $image) {
                        if($image == "." || $image == ".." || $image == "index.php"){
                            continue;
                        } else {
                            array_push($images, ($folder.'/'.$innerFolder.'/'.$image));
                        }
                    }
                }
            }
        }
    }
?>

<!DOCTYPE html>
<html>
<head>
    <title>Lazy Loading testing</title>
        <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>



        <style type="text/css">

            .images-wrapper
            {
                display: flex;
                flex-wrap: wrap;
            }

            .images-wrapper .image-wrapper
            {
                max-width: 25%;
                width: 100%;
                margin-bottom: 15px;
            }

            .images-wrapper .image-wrapper img
            {
                max-width: 100%;
                min-height: 100px;
                background-color: #000;
            }
        </style>


</head>
<body>
    <div class="container">
        <div class="row">
            <div class="col-xs-12">
                <div class="images-wrapper">
                    <?php foreach ($images as $image): ?>
                        <div class="image-wrapper">
                            <img data-src="<?php echo './'.$image; ?>">
                        </div>
                    <?php endforeach ?>
                </div>
            </div>
        </div>
    </div>

    <script type="text/javascript">
                let options = {
                    root: null,
                    rootMargin: "0px 0px -150px 0px",
                    threshold: 1.0
                }

                let observer = new IntersectionObserver(
                    (entries, self) => {
                        entries.forEach(entry => {
                            console.log(entry.isIntersecting);
                            if(entry.isIntersecting){
                                preloadImage(entry.target);
                                self.unobserve(entry.target);
                            }
                        });
                    }, options);

                let imgs = document.querySelectorAll('[data-src]');
                imgs.forEach(img => {
                    observer.observe(img);
                });

                function preloadImage(img)
                {
                    let imgDataSrcAttr = img.getAttribute('data-src');
                    img.setAttribute("src", imgDataSrcAttr);
                }
            </script>


    <link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.3.1/css/bootstrap.min.css">
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.0.0-alpha.4/js/bootstrap.min.js"></script>
</body>
</html>

First thing I checked was "isIntersecting" property and for some reason, all 1609 images returns "true" while only about 20-30 of them should have this value.(我检查的第一件事是“ isIntersecting”属性,由于某种原因,所有1609张图像均返回“ true”,而其中只有大约20-30张应具有此值。)

Run out of ideas why it behaves this way.(用尽想法为什么它会以这种方式运行。)

Any hint please?(有什么提示吗?)   ask by Drezor Warlock translate from so

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

Looks like I've found the source of problem: display:flex for parent container.(看来我已经找到问题的根源父容器的display:flex 。)

My guess is that as this CSS property initially lines up all images within one row and JS consider all images to be in designated rectangle to do images loading.(我的猜测是,由于此CSS属性最初将一行中的所有图像排列在一起,而JS认为所有图像都位于指定的矩形中以进行图像加载。)

It seems that use of flex-wrap: wrap doesn't change anything - just makes images look like there were splitted in rows - and for JS they're still lined up in on row within observed rectange(似乎使用了flex-wrap:wrap并没有改变任何东西-只是使图像看起来像被分成几行-对于JS,它们仍然在观察到的矩形内按行排列)

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...