ユーザーがjQueryを使用してdivの下部にスクロールしたときの検出


218

内部に可変量のコンテンツを持つdivボックス(fluxと呼ばれます)があります。このdivboxのオーバーフローは自動に設定されています。

さて、私がやろうとしていることは、このDIVボックスの下部までスクロールを使用して、ページにさらにコンテンツをロードするとき、これを行う方法(コンテンツをロードする)はわかりますが、方法はわかりませんユーザーがdivタグの下部までスクロールしたことを検出しますか?ページ全体に適用したい場合は、.scrollTopを取り、それを.heightから差し引きます。

しかし、私はここでそれをすることができないように思えますか?

フラックスから.scrollTopを取得し、すべてのコンテンツをinnerというdiv内にラップしようとしましたが、フラックスのinnerHeightを取得すると、564px(divは高さとして500に設定されています)と 'innner'の高さを返しますdivの下部に564と表示されている場合は、1064とスクロールトップを返します。

私に何ができる?

回答:


420

使用できるプロパティ/メソッドがいくつかあります:

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

したがって、最初の2つのプロパティの合計を取ることができ、それが最後のプロパティと等しい場合、最後に達しています。

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

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

編集:私は次のように「バインド」を「オン」に更新しました:

jQuery 1.7以降、.on()メソッドは、イベントハンドラーをドキュメントに添付するための推奨メソッドです。


2
DOMが#flux-elementがすでに使用可能であることを確認する準備ができている場合、バインディングを実行します。
Dr.Molle、2012年

1
bindの代わりにONを使用して回答を更新する必要があります
。bind

34
注:ユーザーがブラウザでズームレベルを使用している場合、これは機能しない可能性があります。ズームによりinnerHeight()、小数が報告されます。ユーザの場合、の和をズームアウトscrollTop()し、innerHeight()常にの少なくとも画分短くなりますscrollHeight。20pxのバッファゾーンを追加してしまいました。結果の条件はif(el.scrollTop() + el.innerHeight() >= el[0].scrollHeight - 20)el等しい場所$(this)でした。
ニック

1
これは私にとって非常にうまくいった今までで最高の答えです。ありがとう
Ashish Yadav

1
それはもう機能していません。なぜ機能しないのか確認していただけますか、ありがとう
Umair Shah Yousafzai

50

ウィンドウをスクロールすると、下から表示されるdivの最後にアラートが表示されるという解決策を見つけました。

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

この例では、div(.posts)が終了したときに下にスクロールすると、アラートが表示されます。


これをありがとうございますが、divの下部に到達したときに、divをアニメーション化するにはどうすればよいですか?また、上にスクロールすると、そのdivの上部が検出され、アニメーション化されます。このWebサイトのlazada.com.ph/appleと同じように、サイドバーの動作をお願いします:)
Alyssa Reyes

魔法のように機能しますが、アラートが2回実行されるという問題があるため、内部で関数の呼び出しがある場合、2回実行されます
Afaf

1
@ 1616 var running = falseこれより前に宣言された変数があります。条件の中で、私はif(!running) { running = true; // and continue logic } これをチェックします。AJAXが完了したら、次のように設定しますrunning = false;
Jacob Raccuia

1
ウィンドウについてですが、質問はdivについてです。
Alexander Volkov

42

質問は5.5年前に行われましたが、それでも今日のUI / UXコンテキストでは十分に関連しています。そして私は私の2セントを追加したいと思います。

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

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

一部の要素では、要素の高さ全体をスクロールできません。そのような場合は、以下を使用できます。

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

2
これは、jQueryを使用していない場合に探しているソリューションです。
Petter Pettersson

イベントハンドラはありますか?
Alexander Volkov

@AlexanderVolkov onscrollは関連イベントです。
考える

9

スクロールしたい固定divの解決策を探しているときにこれを見つけたので、ここで追加の注意事項を示します。私のシナリオでは、終わりに正確に到達できるように、divのパディングを考慮することが望ましいことがわかりました。@ Dr.Molleの答えを拡張して、以下を追加します

$('#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');
    }
  });

これにより、パディングやボーダーを含む正確な位置がわかります


7

これは私のためにうまくいった

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

3

これを非表示またはスクロールとしてオーバーフローyを持つdivで使用する必要がある場合は、このようなものが必要な場合があります。

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

小道具scrollHeightが丸みを帯びているように見えるため、またはおそらくこれが1未満でずれている他の何らかの理由でceilが必要であることがわかりました。


3

Math.round()関数を使用していない場合、ブラウザーウィンドウにズームがある場合、Dr.Molleによって提案されたソリューション機能しない場合があります。

たとえば、$(this).scrollTop()+ $(this).innerHeight()= 600

$(this)[0] .scrollHeightの結果= 599.99998

600> = 599.99998は失敗します。

正しいコードは次のとおりです。

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

厳密な条件が必要ない場合は、余白ピクセルを追加することもできます

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');
        }
    })
});

2

単純なDOMの使用法では、状態を確認できます

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

trueの場合、最後に達しています。


1

誰かがscrollHeightとして取得した場合undefined、要素の最初のサブ要素を選択します。mob_top_menu[0].scrollHeight


1

それが何か助けになるかどうかはわかりませんが、これが私がやる方法です。

ウィンドウよりも大きなインデックスパネルがあり、このインデックスに到達するまでスクロールさせます。次に、位置を固定します。ページの上部に向かってスクロールすると、プロセスが逆になります。

よろしく。

<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>

1

これはほぼ6年前に尋ねられましたが、UXデザインではまだホットなトピックですが、初心者が使用したい場合のデモスニペットを次に示します

$(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>


0

みんなこれがズームの問題の解決策です、あなたがそれを必要とする場合、それはすべてのズームレベルで動作します:

if ( Math.abs(elem.offset().top) + elem.height() + elem.offset().top >= elem.outerHeight() ) {
                    console.log("bottom");
                    // We're at the bottom!
                }
            });
        }

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
    }
});

これはgithubのコードです。


-1

ここに別のバージョンがあります。

重要なコードは、関数scroller()です。これは、overflow:scrollを使用して、スクロールセクションを含むdivの高さとして入力を受け取ります。上または下と同じように、上から5pxまたは下から10pxに近似します。そうでなければ、それはあまりにも敏感です。10pxが最低限のようです。下部の高さを取得するために、divの高さに10が追加されていることがわかります。5pxはうまくいくと思いますが、広範囲にわたるテストはしていません。YMMV。scrollHeightは、divの表示された高さではなく、内側のスクロール領域の高さを返します。この場合は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>';

?>

1
phpからjavascript + cssコードを生成することは悪い習慣であるため(-1は維持が難しい、再利用性がない、Webサイトの最適化がないなど)。さらに、@ Alexander Millarが指摘したように、10pxのオフセットは、パディングを考慮に入れることで修正できます。このコードの使用を検討している人は誰でも2度考えるべきです...
Kapitein Witbaard
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.