2017-09-06 22 views
1

ユーザーがスクロールしたときにナビゲーションをアニメーション化する(画面外に)アニメーションを作成し、ユーザーがスクロールアップしたときにアニメーションを戻すコードがあります。safari 'バウンス'問題を解決する

しかし、ユーザーが高速でスクロールすると、ページが一番上に「バウンス」して、ユーザーが一番上にあるときにナビゲーションがアニメーション化されます。これを解決する方法はありますか?

私のコード

jQuery(document).ready(function($){ 
var didScroll; 
var lastScrollTop = 0; 
var delta = 5; 
var navbarHeight = $('nav').outerHeight(true); 

$(window).scroll(function(event) { didScroll = true; }); 

setInterval(function() { 
if (didScroll) { 
    hasScrolled(); 
    didScroll = false; 
} 
}, 100); 

function hasScrolled() { 
if($(window).width() > 768) { 
    var st = $(this).scrollTop(); 
if (Math.abs(lastScrollTop - st) <= delta) 
    return; 
if (st > lastScrollTop) { 
    // Scroll Down 
     $('#screen-nav').removeClass('nav-down').addClass('nav-up'); 
    } else { 
     $('#screen-nav').removeClass('nav-up').addClass('nav-down'); 
    } 

} 
lastScrollTop = st; 
} 

}); 

答えて

1

それは非標準の技術なので、私は、実際にSafariがスクリプトへの負のoverscrollingを伝えることは非常に驚いています。しかし、私はあなたはそれを考慮して、あなたのスクロール状態を調整する必要があると思う:

if (st > lastScrollTop && lastScrollTop >= 0 && st > 0) { 

これら二つの追加のチェックは、現在のスクロール位置または以前のスクロールあればメニューが押し上げられませんことを保証しますポジションはマイナスだった。

私はSafariが上のテストする必要はありませんでしたので、私はそれから数100の代わりに、0に対してチェックすることにより、テストを実行すると、ページを取り、100pxにすることによって、その体を押し下げることによってそれをシミュレート:

jQuery("body")[0].id = "screen-nav"; 
jQuery("body").css("margin-top", "100px"); 

jQuery(document).ready(function($){ 
    var didScroll; 
    var lastScrollTop = 0; 
    var delta = 5; 
    var navbarHeight = $('nav').outerHeight(true); 

    $(window).scroll(function(event) { 
     didScroll = true; 
    }); 

    setInterval(function() { 
     if (didScroll) { 
     hasScrolled(); 
     didScroll = false; 
     } 
    }, 100); 

    function hasScrolled() { 
     if ($(window).width() > 768) { 
      var st = $(this).scrollTop(); 
      if (Math.abs(lastScrollTop - st) <= delta) { 
       return; 
      } 
      if (st > lastScrollTop && lastScrollTop >= 100 && st > 100) { 
       $('#screen-nav').removeClass('nav-down').addClass('nav-up'); 
      } else { 
       $('#screen-nav').removeClass('nav-up').addClass('nav-down'); 
      } 
     } 
     lastScrollTop = st; 
    } 
}); 

onscrollイベントの両方を100msタイマーで使用することについて少し混乱しています。どちらか一方を使用してソリューションを実装できますが、両方を組み合わせて使用​​する必要はありません。私はおそらくonscrollを使用します。ユーザーがスクロールしていないときにオーバーヘッドが少なくなるからです。ちょうど考慮すべき何か。

+0

私は、タイマーがスクロールイベントのデバウンスであると信じています。 –

+0

(これは不幸な用語の衝突です:私はスクロールジッタのようなレート制限のようなデバウンスを意味しませんでした) –

+0

はい、私はそれが周波数を減らし、スクロールがデルタに達するのを許す試みかもしれないと思った。スクロールイベントが発生したときに 'setTimeout'を開始し、既存のイベントをキャンセルすることで同じことができると思います。 – BoffinbraiN