我想创建一个div,它位于一个内容块的下面,但一旦页面已经滚动到足以接触其顶部边界,就会固定在原地并与页面滚动。


当前回答

这里还有一个版本供那些对其他版本有问题的人尝试。它结合了这个重复问题中讨论的技术,并动态生成所需的帮助器div,因此不需要额外的HTML。

CSS:

.sticky { position:fixed; top:0; }

JQuery:

function make_sticky(id) {
    var e = $(id);
    var w = $(window);
    $('<div/>').insertBefore(id);
    $('<div/>').hide().css('height',e.outerHeight()).insertAfter(id);
    var n = e.next();
    var p = e.prev();
    function sticky_relocate() {
      var window_top = w.scrollTop();
      var div_top = p.offset().top;
      if (window_top > div_top) {
        e.addClass('sticky');
        n.show();
      } else {
        e.removeClass('sticky');
        n.hide();
      }
    }
    w.scroll(sticky_relocate);
    sticky_relocate();
}

要使元素具有粘性,请执行以下操作:

make_sticky('#sticky-elem-id');

当元素变得粘滞时,代码管理剩余内容的位置,以防止它跳到粘滞元素留下的间隙中。当滚动到粘滞元素上方时,它还将粘滞元素返回到其原始的非粘滞位置。

其他回答

这里还有一个版本供那些对其他版本有问题的人尝试。它结合了这个重复问题中讨论的技术,并动态生成所需的帮助器div,因此不需要额外的HTML。

CSS:

.sticky { position:fixed; top:0; }

JQuery:

function make_sticky(id) {
    var e = $(id);
    var w = $(window);
    $('<div/>').insertBefore(id);
    $('<div/>').hide().css('height',e.outerHeight()).insertAfter(id);
    var n = e.next();
    var p = e.prev();
    function sticky_relocate() {
      var window_top = w.scrollTop();
      var div_top = p.offset().top;
      if (window_top > div_top) {
        e.addClass('sticky');
        n.show();
      } else {
        e.removeClass('sticky');
        n.hide();
      }
    }
    w.scroll(sticky_relocate);
    sticky_relocate();
}

要使元素具有粘性,请执行以下操作:

make_sticky('#sticky-elem-id');

当元素变得粘滞时,代码管理剩余内容的位置,以防止它跳到粘滞元素留下的间隙中。当滚动到粘滞元素上方时,它还将粘滞元素返回到其原始的非粘滞位置。

我使用了上面的一些工作来创建这项技术。我改进了它,并认为我将分享我的工作。希望这能有所帮助。

jsfiddle 代码

function scrollErrorMessageToTop() {
    var flash_error = jQuery('#flash_error');
    var flash_position = flash_error.position();

    function lockErrorMessageToTop() {
        var place_holder = jQuery("#place_holder");
        if (jQuery(this).scrollTop() > flash_position.top && flash_error.attr("position") != "fixed") {
            flash_error.css({
                'position': 'fixed',
                'top': "0px",
                "width": flash_error.width(),
                "z-index": "1"
            });
            place_holder.css("display", "");
        } else {
            flash_error.css('position', '');
            place_holder.css("display", "none");
        }

    }
    if (flash_error.length > 0) {
        lockErrorMessageToTop();

        jQuery("#flash_error").after(jQuery("<div id='place_holder'>"));
        var place_holder = jQuery("#place_holder");
        place_holder.css({
            "height": flash_error.height(),
            "display": "none"
        });
        jQuery(window).scroll(function(e) {
            lockErrorMessageToTop();
        });
    }
}
scrollErrorMessageToTop();​

这是一种更动态的滚动方式。它确实需要一些工作,我会在某个时候把它变成一个插头,但这是我工作几个小时后想出的。

为回答这个问题提供的信息可能对你有帮助,埃文:

检查滚动后元素是否可见

基本上,只有在验证document.body.scrollTop值等于或大于元素的顶部之后,才希望修改元素的样式,将其设置为fixed。

你可以添加额外的3行,这样当用户滚动回顶部时,div将保持在原来的位置:

代码如下:

if ($(this).scrollTop() < 200 && $el.css('position') == 'fixed'){
    $('.fixedElement').css({'position': 'relative', 'top': '200px'});
}

最简单的解决方案(没有js): 演示

.container {
  position: relative;
}
.sticky-div {
    position: sticky;
    top: 0;
}
<div class="container">
  <h1>
    relative container & sticky div
  </h1>
  <div class="sticky-div"> this row is sticky</div>
  <div>
    content
  </div>
</div>