How to do infinite scrolling with javascript only without jquery

前端 未结 6 1012
日久生厌
日久生厌 2021-02-01 10:13

I wish to implement infinite scrolling with javascript and without jquery.

I am new to javascript.

After searching all over the net, I have this code.

         


        
相关标签:
6条回答
  • 2021-02-01 10:52

    I used scrollHeight, scrollTop and clientHeight attribute of the element to find whether the scroll hit the bottom. Here is my code. I hope it helps.

    Click here for more information.

    Image describing scrollHeight, scrollTop and clientHeight.

    <html>
    <head>
    <title>Infinite Scroll</title>
    </head>
    <body>
      <h3>Infinite Scroll Example</h3>
      <div id="scrollContent" style="overflow-y: scroll; height: 100px; width: 500px">
        <div style="height: 300px; background-color: red">
        </div>
      <div>
    </body>
    
    <script type="text/javascript">
      document.addEventListener('DOMContentLoaded',function () {
        var elm = document.getElementById('scrollContent');
        elm.addEventListener('scroll',callFuntion);
    
        function callFuntion(){
          var scrollHeight = elm.scrollHeight;
          var scrollTop = elm.scrollTop;
          var clientHeight = elm.clientHeight;
    
          if(scrollHeight-scrollTop == clientHeight){
            elm.innerHTML += '<div style="height: 300px; background-color: blue"> New Element Added </div>' ;
          }
        }
    
      });
    </script>
    
    </html>

    0 讨论(0)
  • 2021-02-01 10:52

    Why whout jQuery? Some of the native properties like window.outerHeight actually can return not accurate results on some browsers. jQuery fixes that so you can rely that the methods you use returns the same results on any browser and is enough fast to use it.

    Here is a very simple way to achieve the infinite scroll without any performance impact:

    $(window).on('scroll', function() {
        var threshold = 120;
        if (window.pageYOffset > 0 && window.pageYOffset + $(window).outerHeight(false) >= $(document).outerHeight(false) - threshold) {
            // call your infinite scroll callback, like infiniteScrollDebounced($('#mytable'))
        }
    }).scroll();
    

    Notes: the condition in the if clause is intentionally like this, so if the user does not scroll, it will not calculate after window.pageYOffset > 0 and also get into the if (some micro-optimizations ;) ). The zero can be replaced with 20 or 100, so this is the threshold after the site will try to check if the user scrolls and need to do something about it.

    I use debounce to postpone the real call to load data (usually websites load data when infinite scrolls), demo: https://davidwalsh.name/function-debounce

    So I have this method:

    var infiniteScrollDebounced = _.debounce(function($table) {
        var params = $table.data('table-params');
        // Don't request any more if we have reached the end
        if (params.end)
            return;
    
        params.page++;
        params.append = true;
    
        GridHelper.reload($table, null, params);
    }, 100, true);
    

    My table have data attached to hold the current progress (page, sorting, filtering, etc) and this data is retrieved and passed into the query, so I get properly ordered and filtered results every time. GridHelper.reload() function handles the request and updates the params of the table when the data arrives (the new params are part of the response).

    0 讨论(0)
  • 2021-02-01 11:02

    For achieving that behaviour you don't need JQuery or a JQuery plugin. You just need Pure Css OR Css + Javascript, it depends on the % you want to support

    but... DON'T use onScroll: you can do all that just with Vanilla Javascript and the IntersectionObserver API.

    All you need to do is place elements and listen for when they become available in the screen. You can accomplish that with a few javascript & html lines and it's much more performant than listening for scroll events in the browsers

    I recently put together an article check it here about this

    0 讨论(0)
  • 2021-02-01 11:06

    What about replacing this line of code:

    if (getDocHeight() == getScrollXY()[1] + window.innerHeight)
    

    with the following:

    if (getDocHeight() - 20 <= getScrollXY()[1] + window.innerHeight) 
    

    Where 20 is the number how much pxs from bottom you want the trigger to execute.

    Fiddle

    0 讨论(0)
  • 2021-02-01 11:08

    first of all i don't think that you have to support netscape and ie6 anymore. So with that in mind I created following script

    document.addEventListener("scroll", function (event) {
        checkForNewDiv();
    });
    
    var checkForNewDiv = function() {
        var lastDiv = document.querySelector("#scroll-content > div:last-child");
        var lastDivOffset = lastDiv.offsetTop + lastDiv.clientHeight;
        var pageOffset = window.pageYOffset + window.innerHeight;
    
        if(pageOffset > lastDivOffset - 20) {
            var newDiv = document.createElement("div");
            newDiv.innerHTML = "my awesome new div";
            document.getElementById("scroll-content").appendChild(newDiv);
            checkForNewDiv();
        }
    };
    

    also see jsfiddle

    0 讨论(0)
  • 2021-02-01 11:13

    I use requestAnimationFrame instead of listening for scroll. I also added a throttle based on time so it doesn't overwork our page and batched the element additions:

    var numElementsToAdd = 10,
        offsetForNewContent = 20;
    
    function checkInfiniteScroll(parentSelector, childSelector) {
      var lastDiv = document.querySelector(parentSelector + childSelector),
          lastDivOffset = lastDiv.offsetTop + lastDiv.clientHeight,
          pageOffset = window.pageYOffset + window.innerHeight;
    
      if(pageOffset > lastDivOffset - offsetForNewContent ) {
        for(var i = 0; i < numElementsToAdd; i++) {
          var newDiv = document.createElement("div");
          newDiv.innerHTML = "my awesome new div";
          document.querySelector(parentSelector).appendChild(newDiv);
        }
        checkInfiniteScroll(parentSelector, childSelector);
      }
    };
    
    var lastScrollTime = Date.now(), 
        checkInterval = 50;
    
    function update() {
      requestAnimationFrame(update);
    
      var currScrollTime = Date.now();
      if(lastScrollTime + checkInterval < currScrollTime) {
        checkInfiniteScroll("#scroll-content", "> div:last-child");
        lastScrollTime = currScrollTime;
      }
    };
    
    update();
      #scroll-content > div {
          background: #c0c0c0;
          height: 40px;
          margin-bottom: 5px;
      }
    <div id="scroll-content">
        <div>test div</div>
    </div>

    Demo

    0 讨论(0)
提交回复
热议问题