Mendeteksi ketika pengguna gulir ke bawah div dengan jQuery

218

Saya memiliki kotak div (disebut fluks) dengan jumlah konten yang bervariasi di dalamnya. Divbox ini telah meluap diatur ke otomatis.

Sekarang, apa yang saya coba lakukan adalah, ketika penggunaan gulir ke bagian bawah kotak-DIV ini, memuat lebih banyak konten ke halaman, saya tahu bagaimana melakukan ini (memuat konten) tetapi saya tidak tahu bagaimana caranya. mendeteksi kapan pengguna telah menggulir ke bagian bawah tag div? Jika saya ingin melakukannya untuk seluruh halaman, saya akan mengambil .scrollTop dan kurangi itu dari .height.

Tapi sepertinya saya tidak bisa melakukan itu di sini?

Saya sudah mencoba mengambil .scrollTop dari fluks, dan kemudian membungkus semua konten di dalam div yang disebut inner, tetapi jika saya mengambil innerHeight of flux ia mengembalikan 564px (div diatur ke 500 sebagai ketinggian) dan ketinggian 'innner' ia mengembalikan 1064, dan scrolltop, ketika di bagian bawah div mengatakan 564.

Apa yang dapat saya?

Eax
sumber

Jawaban:

420

Ada beberapa properti / metode yang dapat Anda gunakan:

$().scrollTop()//how much has been scrolled
$().innerHeight()// inner height of the element
DOMElement.scrollHeight//height of the content of the element

Jadi, Anda dapat mengambil jumlah dari dua properti pertama, dan ketika itu sama dengan properti terakhir, Anda telah mencapai akhirnya:

jQuery(function($) {
    $('#flux').on('scroll', function() {
        if($(this).scrollTop() + $(this).innerHeight() >= $(this)[0].scrollHeight) {
            alert('end reached');
        }
    })
});

http://jsfiddle.net/doktormolle/w7X9N/

Sunting: Saya telah memperbarui 'bind' ke 'on' sesuai:

Pada jQuery 1.7, metode .on () adalah metode yang disukai untuk melampirkan penangan acara ke dokumen.

Dr.Molle
sumber
2
Ini akan melakukan pengikatan ketika DOM siap untuk memastikan bahwa elemen # flux sudah tersedia.
Dr.Molle
1
Anda harus memperbarui jawaban Anda menggunakan ON alih-alih bind, bind tidak digunakan lagi karena On
ncubica
34
Catatan: Saat pengguna menggunakan level zoom di browser mereka, ini mungkin tidak berfungsi. Zoom menyebabkan innerHeight()melaporkan desimal. Dalam kasus pengguna melakukan zoom out, jumlah scrollTop()dan innerHeight()akan selalu setidaknya sebagian kecil dari scrollHeight. Saya akhirnya menambahkan zona penyangga 20px. Kondisional yang dihasilkan adalah di if(el.scrollTop() + el.innerHeight() >= el[0].scrollHeight - 20)mana elsama dengan $(this).
Nick
1
Ini adalah jawaban terbaik yang pernah bekerja dengan sangat baik untuk saya. Terima kasih
Ashish Yadav
1
Itu tidak berfungsi lagi, bisakah Anda mengonfirmasi mengapa itu tidak berhasil, Terima kasih
Umair Shah Yousafzai
50

Saya menemukan solusi bahwa ketika Anda menggulir jendela dan akhir div yang ditunjukkan dari bawah memberi Anda peringatan.

$(window).bind('scroll', function() {
    if($(window).scrollTop() >= $('.posts').offset().top + $('.posts').outerHeight() - window.innerHeight) {
        alert('end reached');
    }
});

Dalam contoh ini jika Anda gulir ke bawah ketika div ( .posts) selesai itu memberi Anda peringatan.

ehsan Aghaei
sumber
terima kasih untuk ini, tetapi bagaimana saya bisa membuat div hidup ketika mencapai bagian bawah div itu? juga ketika Anda gulir ke atas mendeteksi bagian atas div itu kemudian hidupkan juga. Sama seperti di sini di situs web ini lazada.com.ph/apple the sidebar behaviour Semoga Anda dapat membantu saya :)
Alyssa Reyes
Ini bekerja seperti sihir tetapi masalahnya adalah bahwa peringatan dijalankan dua kali jadi jika Anda memiliki panggilan fungsi di dalamnya akan dieksekusi dua kali
Afaf
1
@ 1616 Saya sudah var running = falsemendeklarasikan variabel sebelum ini. Di dalam kondisional, saya periksa if(!running) { running = true; // and continue logic } dengan cara ini hanya disebut sekali! Ketika AJAX selesai, aturrunning = false;
Jacob Raccuia
1
Ini tentang jendela, tetapi pertanyaannya adalah tentang div.
Alexander Volkov
42

Meskipun pertanyaan diajukan 5,5 tahun yang lalu, masih lebih relevan dalam konteks UI / UX saat ini. Dan saya ingin menambahkan dua sen saya.

var element = document.getElementById('flux');
if (element.scrollHeight - element.scrollTop === element.clientHeight)
    {
        // element is at the end of its scroll, load more content
    }

Sumber: https://developer.mozilla.org/en-US/docs/Web/API/Element/scrollHeight#Determine_if_an_element_has_been_totally_scrolled

Beberapa elemen tidak memungkinkan Anda untuk menggulir seluruh elemen. Dalam hal ini Anda dapat menggunakan:

var element = docuement.getElementById('flux');
if (element.offsetHeight + element.scrollTop === element.scrollHeight) {
  // element is at the end of its scroll, load more content
}
Berpikir
sumber
2
Ini adalah solusi yang Anda cari jika Anda tidak menggunakan jQuery.
Petter Pettersson
Ada pengatur acara?
Alexander Volkov
Onscroll @AlexanderVolkov adalah acara terkait.
Berpikir
9

Hanya catatan tambahan di sini karena saya menemukan ini ketika mencari solusi untuk div tetap yang ingin saya gulir. Untuk skenario saya, saya menemukan bahwa lebih baik memperhitungkan padding pada div sehingga saya dapat mencapai ujungnya dengan tepat. Jadi memperluas jawaban @ Dr.Molle saya menambahkan yang berikut ini

$('#flux').bind('scroll', function() {
    var scrollPosition = $(this).scrollTop() + $(this).outerHeight();
    var divTotalHeight = $(this)[0].scrollHeight 
                          + parseInt($(this).css('padding-top'), 10) 
                          + parseInt($(this).css('padding-bottom'), 10)
                          + parseInt($(this).css('border-top-width'), 10)
                          + parseInt($(this).css('border-bottom-width'), 10);

    if( scrollPosition == divTotalHeight )
    {
      alert('end reached');
    }
  });

Itu akan memberi Anda lokasi yang tepat, termasuk padding dan border

Alexander Millar
sumber
7

ini bekerja untuk saya

$(window).scroll(function() {
  if ($(window).scrollTop() >= (($(document).height() - $(window).height()) - $('#divID').innerHeight())) {
    console.log('div reached');
  }
});
Ricardo Rivas
sumber
3

Jika Anda perlu menggunakan ini pada div yang memiliki overflow-y sebagai tersembunyi atau gulir, sesuatu seperti ini mungkin yang Anda butuhkan.

if ($('#element').prop('scrollHeight') - $('#element').scrollTop() <= Math.ceil($('#element').height())) {
    at_bottom = true;
}

Saya menemukan ceil diperlukan karena prop scrollHeight tampaknya membulat, atau mungkin beberapa alasan lain menyebabkan ini mati kurang dari 1.

Angsa
sumber
3

Jika Anda tidak menggunakan fungsi Math.round () solusi yang disarankan oleh Dr.Molle tidak akan berfungsi dalam beberapa kasus ketika jendela browser memiliki zoom.

Misalnya $ (ini) .scrollTop () + $ (ini) .innerHeight () = 600

$ (ini) [0] .scrollHeight menghasilkan = 599.99998

600> = 599.99998 gagal.

Ini kode yang benar:

jQuery(function($) {
    $('#flux').on('scroll', function() {
        if(Math.round($(this).scrollTop() + $(this).innerHeight(), 10) >= Math.round($(this)[0].scrollHeight, 10)) {
            alert('end reached');
        }
    })
});

Anda juga dapat menambahkan beberapa piksel margin tambahan jika Anda tidak memerlukan kondisi yang ketat

var margin = 4

jQuery(function($) {
    $('#flux').on('scroll', function() {
        if(Math.round($(this).scrollTop() + $(this).innerHeight(), 10) >= Math.round($(this)[0].scrollHeight, 10) - margin) {
            alert('end reached');
        }
    })
});
Павел Гавриленко
sumber
2

Dalam penggunaan DOM sederhana, Anda dapat memeriksa kondisinya

element.scrollTop + element.clientHeight == element.scrollHeight

jika benar maka Anda telah mencapai akhir.

Louay Alosh
sumber
1

Jika ada yang mendapat scrollHeightsebagai undefined, kemudian pilih subelement 1 elemen:mob_top_menu[0].scrollHeight

Starwave
sumber
1

tidak yakin apakah itu membantu tetapi ini adalah bagaimana saya melakukannya.

Saya memiliki panel indeks yang lebih besar dari jendela dan saya membiarkannya menggulir sampai akhir indeks ini tercapai. Lalu saya perbaiki posisinya. Prosesnya terbalik setelah Anda menggulir ke bagian atas halaman.

Salam.

<style type="text/css">
    .fixed_Bot {    
            position: fixed;     
            bottom: 24px;    
        }     
</style>

<script type="text/javascript">
    $(document).ready(function () {
        var sidebarheight = $('#index').height();
        var windowheight = $(window).height();


        $(window).scroll(function () {
            var scrollTop = $(window).scrollTop();

            if (scrollTop >= sidebarheight - windowheight){
                $('#index').addClass('fixed_Bot');
            }
            else {
                $('#index').removeClass('fixed_Bot');
            }                   
        });
    });

</script>
Chapa Israel
sumber
1

Meskipun ini ditanyakan hampir 6 tahun lalu, masih menjadi topik hangat dalam desain UX, berikut ini cuplikan demo jika ada pemula yang ingin menggunakan

$(function() {

  /* this is only for demonstration purpose */
  var t = $('.posts').html(),
    c = 1,
    scroll_enabled = true;

  function load_ajax() {

    /* call ajax here... on success enable scroll  */
    $('.posts').append('<h4>' + (++c) + ' </h4>' + t);

    /*again enable loading on scroll... */
    scroll_enabled = true;

  }


  $(window).bind('scroll', function() {
    if (scroll_enabled) {

      /* if 90% scrolled */
    if($(window).scrollTop() >= ($('.posts').offset().top + $('.posts').outerHeight()-window.innerHeight)*0.9) {

        /* load ajax content */
        scroll_enabled = false;  
        load_ajax();
      }

    }

  });

});
h4 {
  color: red;
  font-size: 36px;
  background-color: yellow;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<div class="posts">
  Lorem ipsum dolor sit amet  Consectetuer augue nibh lacus at <br> Pretium Donec felis dolor penatibus <br> Phasellus consequat Vivamus dui lacinia <br> Ornare nonummy laoreet lacus Donec <br> Ut ut libero Curabitur id <br> Dui pretium hendrerit
  sapien Pellentesque <br> Lorem ipsum dolor sit amet <br> Consectetuer augue nibh lacus at <br> Pretium Donec felis dolor penatibus <br> Phasellus consequat Vivamus dui lacinia <br> Ornare nonummy laoreet lacus Donec <br> Ut ut libero Curabitur id <br>  Dui pretium hendrerit sapien Pellentesque <br> Lorem ipsum dolor sit amet <br> Consectetuer augue nibh lacus at <br> Pretium Donec felis dolor penatibus <br> Phasellus consequat Vivamus dui lacinia <br> Ornare nonummy laoreet lacus Donec <br> Ut ut
  libero Curabitur id <br> Dui pretium hendrerit sapien Pellentesque <br> Lorem ipsum dolor sit amet <br> Consectetuer augue nibh lacus at <br> Pretium Donec felis dolor penatibus <br> Phasellus consequat Vivamus dui lacinia <br> Ornare nonummy laoreet
  lacus Donec <br> Ut ut libero Curabitur id <br> Dui pretium hendrerit sapien Pellentesque
</div>

Akshay Hegde
sumber
0

Guys ini adalah solusi untuk masalah zoom, ini bekerja dengan semua level zoom, jika Anda membutuhkannya:

if ( Math.abs(elem.offset().top) + elem.height() + elem.offset().top >= elem.outerHeight() ) {
                    console.log("bottom");
                    // We're at the bottom!
                }
            });
        }
Liad Livnat
sumber
0
$(window).on("scroll", function() {
    //get height of the (browser) window aka viewport
    var scrollHeight = $(document).height();
    // get height of the document 
    var scrollPosition = $(window).height() + $(window).scrollTop();
    if ((scrollHeight - scrollPosition) / scrollHeight === 0) {
        // code to run when scroll to bottom of the page
    }
});

Ini adalah kode di github.

aki_sud
sumber
-1

Ini versi lain.

Kode kuncinya adalah fungsi scroller () yang mengambil input sebagai ketinggian div yang berisi bagian gulir, menggunakan overflow: gulir. Sekitar 5px dari atas atau 10px dari bawah seperti di atas atau bawah. Kalau tidak, terlalu sensitif. Sepertinya 10px adalah tentang minimum. Anda akan melihatnya menambahkan 10 ke ketinggian div untuk mendapatkan ketinggian bawah. Saya berasumsi 5px mungkin bekerja, saya tidak menguji secara ekstensif. YMMV. scrollHeight mengembalikan ketinggian area scrolling dalam, bukan ketinggian div yang ditampilkan, yang dalam hal ini adalah 400px.

<?php

$scrolling_area_height=400;
echo '
<script type="text/javascript">
          function scroller(ourheight) {
            var ourtop=document.getElementById(\'scrolling_area\').scrollTop;
            if (ourtop > (ourheight-\''.($scrolling_area_height+10).'\')) {
                alert(\'at the bottom; ourtop:\'+ourtop+\' ourheight:\'+ourheight);
            }
            if (ourtop <= (5)) {
                alert(\'Reached the top\');
            }
          }
</script>

<style type="text/css">
.scroller { 
            display:block;
            float:left;
            top:10px;
            left:10px;
            height:'.$scrolling_area_height.';
            border:1px solid red;
            width:200px;
            overflow:scroll; 
        }
</style>

$content="your content here";

<div id="scrolling_area" class="scroller">
onscroll="var ourheight=document.getElementById(\'scrolling_area\').scrollHeight;
        scroller(ourheight);"
        >'.$content.'
</div>';

?>
John Ostrowick
sumber
1
-1 karena menghasilkan kode javascript + css dari php adalah praktik yang buruk (sulit untuk dipertahankan, tidak dapat digunakan kembali, tidak ada optimasi situs web dll). Selanjutnya seperti yang ditunjukkan oleh @Alexander Millar, offset 10px dapat diperbaiki dengan memasukkan bantalan ke akun. Siapa pun yang mempertimbangkan untuk menggunakan kode ini harus berpikir dua kali ...
Kapitein Witbaard