jQuery 粘性侧边栏失败

Jac*_*ack 4 javascript jquery sticky

首先我没有写这段代码。我在别人的网站上找到了它,我想通过自己尝试从中学习。但是我不能让它工作。我已经用谷歌搜索了代码,以防它是一个免费提供的 jQuery 插件或任何东西,但我无法在网络上的任何地方找到它。

我有我的侧边栏(带有 id #sidebar)并给了它“粘性”类,我在页面顶部包含了 jQuery,并且我已经把这段代码放在了头部:

<!-- Floating sidebar jQuery --> 
        <script type="text/javascript"> 
            var Sticky = function( $obj, opts ){

               $(window).scroll( 
                  function(e){
                     Sticky.onScroll(e, $obj, opts );
                  });

            }
            Sticky.onScroll = function( e, $o, opts ){

               var iScrollTop = $(window).scrollTop();
               var sClass = "sticky";

               //set original data
               if( !$o.data(sClass) ){
                  $o.data(sClass, {css:{position:$o.css('position'),top:$o.css('top')}, offset:$o.offset()} );
               }
               var oOrig = $o.data(sClass);
               var bIsSticky = $o.hasClass(sClass);

               if( iScrollTop > oOrig.offset.top && !bIsSticky ){
                  $o.css({position:'fixed',top:0}).addClass(sClass);
               }else if(iScrollTop < oOrig.offset.top && bIsSticky){
                  $o.css(oOrig.css).removeClass(sClass);
               }   

            }

            Sticky( $('#sidebar') );

        </script> 
Run Code Online (Sandbox Code Playgroud)

如您所见,最后的 JS 行在Sticky( $('#sidebar') );#sidebar 元素上触发。但是,当您向下滚动时,此错误会写入 Chrome 的日志:

未捕获的类型错误:无法读取未定义的属性“偏移量”

Firebug 有点冗长,它说:

oOrig 未定义: if( iScrollTop > oOrig.offset.top && !bIsSticky ){

我正在尽力理解这一点,但有人可以帮我看看为什么它不起作用吗?

谢谢!

杰克

Bob*_*mer 5

哇,新答案...谢谢felix

将函数调用包装在就绪函数中。

$(function() {
    Sticky($('#sidebar'));
});
Run Code Online (Sandbox Code Playgroud)

当您调用Sticky($('#sidebar'))时,dom 很可能还没有准备好,因此当 .data 用于在$o其上设置数据时,实际上什么都不做:

$o.data(sClass, {css:{position:$o.css('position'),top:$o.css('top')}, offset:$o.offset()} );].  
Run Code Online (Sandbox Code Playgroud)

所以当它在线获取数据时:

var oOrig = $o.data(sClass);
Run Code Online (Sandbox Code Playgroud)

它实际上无法获取数据。

这是因为 dom 元素还没有准备好被操纵,因为 dom 还没有准备好。

旧答案(不对!)

$.offset 是一个函数。

该行的问题:

if( iScrollTop > oOrig.offset.top && !bIsSticky ){
Run Code Online (Sandbox Code Playgroud)

就是:oOrig.offset是一个函数,而不是一个变量。所以oOrig.offset.top是无效的。只需调用该函数,它就会返回一个具有 top 属性的变量,您可以访问它:

if( iScrollTop > oOrig.offset().top && !bIsSticky ){
Run Code Online (Sandbox Code Playgroud)

说明:

oOrig.offset是对函数的引用(jquery 中的偏移函数)。

您必须调用该函数才能访问该.top属性。

  • 这个答案是错误的。为什么是那些赞成票?`offset` 不是 `oOrig` 上的函数。如果你仔细观察,那么 `oOrig` 是存储在 `$o.data(sClass)` 中的对象,它是 `{css:{position:$o.css('position'),top:$o.css ('top')}, offset:$o.offset()}`。即使它是一个函数,它也会抛出另一个错误,并且*不* *`oOrig` 是未定义的*。 (3认同)