为了账号安全,请及时绑定邮箱和手机立即绑定

使用 Intersectionobserver 和 InnerHTML 的无限滚动

使用 Intersectionobserver 和 InnerHTML 的无限滚动

繁花如伊 2023-02-24 15:22:35
我正在尝试进行无限滚动(不使用 jQuery)以在页面中显示更多结果。我正在使用 anIntersectionObserver来检测调用的 div #paginate,每次它进入屏幕时,#resultdiv 都会被刷新。var result = document.querySelector('#result');var paginate = document.querySelector('#paginate');var observer = new IntersectionObserver(entries => {if (entries.some(entry => entry.isIntersecting)){var pagination = 10;fetch('/kernel/search.php?pagination='+pagination).then((response) => {return response.text();}).then((html) => {result.innerHTML = html;});}});observer.observe(paginate);这是带有 HTML 的完整代码视图:<html><body><div class="row justify-content-sm-center justify-content-md-center justify-content-lg-center justify-content-xl-start no-gutters min-vw-100" id="result"><div class="col-sm-11 col-md-11 col-lg-9-result col-xl-4-result order-0"><div class="card mx-3 mt-3"><div class="card-body"><a class="text-decoration-none" href="?topic=result-1"><h5 class="card-title"> Result 1    </h5></a><p class="card-text text-truncate"> Result 1 description.</p></div></div><div class="card mx-3 mt-3"><div class="card-body"><a class="text-decoration-none" href="?topic=result-2"><h5 class="card-title"> Result 2    </h5></a><p class="card-text text-truncate"> Result 2 description.</p></div></div><div class="alert alert-light text-dark text-center border mx-3 my-3" id="paginate">More results</div></div></div><script>    var result = document.querySelector('#result');var paginate = document.querySelector('#paginate');var observer = new IntersectionObserver(entries => {if (entries.some(entry => entry.isIntersecting)){var pagination = 10;fetch('/kernel/search.php?pagination='+pagination).then((response) => {return response.text();}).then((html) => {result.innerHTML = html;});}});observer.observe(paginate);</script></body></html>它有效,但它只在第一次有效,之后不会刷新#resultdiv。我可以在Web Browser > Inspect > Networkfetch选项卡中看到工作,但在第一次刷新 div 后没有任何活动,这意味着它不再检测到div。#result#paginate这里发生了什么?我认为这是因为我正在使用 aninnerHTML并且在 div的第一次刷新之后observer以某种方式无法检测到div 。我该如何解决这个问题?#paginate#result
查看完整描述

4 回答

?
扬帆大鱼

TA贡献1799条经验 获得超9个赞

看来您是#paginate在第一次更新后删除的,因为它在#result.



查看完整回答
反对 回复 2023-02-24
?
翻过高山走不出你

TA贡献1875条经验 获得超3个赞

.scroll我用 jQuery 和函数完成了它,并像这样使用了 ajax,也许我的代码可以帮助您并使其适应您的需求。


$('#customersList').scroll(function () {

    if ($(this).scrollTop() + $(this).innerHeight() >= $(this)[0].scrollHeight - 5000) {

        // Do your stuff here.

        getCustomers();

    }

})



function getCustomers(){

    let $customerList = $('#customersList');

    let offset        = ($customerList.attr('data-offset')) ? 

    

    $customerList.attr('data-offset') : 0;


    if ($customerList.data('requestRunning')) {

        return;

    }

    $customerList.data('requestRunning', true);


    return $.ajax({

                  type: "GET",

                  data: {offset: offset},

                  url : routes.routes.customers.get

              })

        .done(function (data) {

            let _htmlCustomersList = ($customerList.is(':empty')) ? '' : $customerList.html();

            let response           = data.data;

            

            if (response) {

                for (const i in response) {

                    let v = JSON.parse(response[i]);

                    _htmlCustomersList += '<div class="client-group edit" data-id="' + v['id'] + '"></div><hr>';

                }


                offset = parseInt(offset) + 200;

                $customerList.attr('data-offset', offset).html(_htmlCustomersList);

            }

        })

        .always(function () {

            $customerList.data('requestRunning', false);

        });


}

我的 getCustomer 函数在到达页面末尾之前运行,并且每次加载 200 个以上的项目。


我希望这可以帮助你一点点



查看完整回答
反对 回复 2023-02-24
?
隔江千里

TA贡献1906条经验 获得超10个赞

#result div 是内容的主要包装器,使用 innerHTML 更新 div 的内容,将导致替换 div 内的整个内容...


除了 innerHTML 是绝对的,并且会删除任何 DOM 对象(及其事件)因此是不好的做法这一事实之外,它也不是一个好的解决方案,因为您希望在滚动时附加而不是替换数据


我建议在分页上方添加一个 div,它将保存添加的数据,例如:


...

<div id="result"></div>

<div class="alert alert-light text-dark text-center border mx-3 my-3" id="paginate">

More results

</div>

然后对添加的内容使用某种附加,例如:


.then((html) => {

let res = new DOMParser().parseFromString(html, "text/xml");

document.getElementById("result").appendChild(res);

});

希望有帮助


查看完整回答
反对 回复 2023-02-24
?
SMILET

TA贡献1796条经验 获得超4个赞

我已将其删除innerHTML并替换为insertAdjacentHTML.

因为似乎在第一次刷新后innerHTML重置/忘记了,所以无法再检测到触发下一次刷新。#paginate#resultobserver#paginate#result

我本可以使用innerHTMLwithappendChild来做同样的事情,但每次刷新appendChild都会添加一个新的,我不太喜欢。div#result

作为解决方案,我html在开始之前插入刷新的数据#paginate而不重置/忘记它是触发下一次刷新id所需的元素。observer#result

.then((html) => {
paginate.insertAdjacentHTML('beforebegin', html);
});


查看完整回答
反对 回复 2023-02-24
  • 4 回答
  • 0 关注
  • 166 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信