1

私は単一ページのサイトを持っています:

http://chiaroscuro.telegraphbranding.com/

各セクションは、ユーザーのウィンドウに基づいて動的にサイズ変更されます。リンクがクリックされたときにjQueryのスムーズスクロール機能を各セクションの一番上までスクロールさせる方法を理解しようとしています。最初のセクションである資金調達エリアでは単純な offset().top を使用しただけでうまく機能していますが、ウィンドウのサイズが常に異なるため、スクロールする距離がわからないため、他のセクションは機能していません。

offset() または position() を機能させようとしましたが、サイコロはありません。アドバイスをいただければ幸いです。

これが私のjQueryです:

`

$(document).ready(function () {
    var slowScrollFunding = $('#funding-areas').offset().top;
    var slowScrollAbout = $('#about-us').offset().top;
    var slowScrollProjects = $('#our-projects').offset().top + 600;
    panelOpen = true;
    $('#anchor-funding-areas').click(function(event) {
        event.preventDefault();
        if(panelOpen == true) {
            $('#slide-panel-content').stop(true, true).animate({height: '0px'}, 600, function() {
                $('#panel-content-container').hide();
                $('.scrollableArea').css('z-index', '11');
                // Scroll down to 'slowScrollTop'
                $('html, body, #home-wrap').animate({scrollTop:slowScrollFunding}, 1000);
                panelOpen = false;
            });
        }else{
            $('html, body, #home-wrap').animate({scrollTop:slowScrollFunding}, 1000);
        };
    });
    $('#anchor-aboutus').click(function(event) {
        event.preventDefault();
        if(panelOpen == true) {
            $('#slide-panel-content').stop(true, true).animate({height: '0px'}, 600, function() {
                $('#panel-content-container').hide();
                $('.scrollableArea').css('z-index', '11');
                // Scroll down to 'slowScrollTop'
                $('html, body, #aboutus-wrap').animate({scrollTop:slowScrollAbout}, 1000);
                panelOpen = false;
            });
        }else{
            $('html, body, #home-wrap').animate({scrollTop:slowScrollAbout}, 1000);
        };
    });
    $('#anchor-ourprojects').click(function(event) {
        event.preventDefault();
        if(panelOpen == true) {
            $('#slide-panel-content').stop(true, true).animate({height: '0px'}, 600, function() {
                $('#panel-content-container').hide();
                $('.scrollableArea').css('z-index', '11');
                // Scroll down to 'slowScrollTop'
                $('html, body, #home-wrap').animate({scrollTop:slowScrollProjects}, 1000);
                panelOpen = false;
            });
        }else{
            $('html, body, #home-wrap').animate({scrollTop:slowScrollProjects}, 1000);
        };
    });
    $('#header-logo').add('.homelink').click(function() {
        if(panelOpen == false) {
            $('.scrollableArea').css('z-index', '0');
            $('#panel-content-container').show();
            $('#slide-panel-content').stop(true, true).animate({height: '389px'}, 600, function() {
                // Scroll down to 'slowScrollTop'
                panelOpen = true;
            });
        };
    });
});

`

4

1 に答える 1

0

$.offset$.position特に、ページのように複雑なレイアウトがたくさん行われている場合は、少し信頼性が低くなる可能性があります。私が過去に使用したのは、次のトリックです。

var de = document.documentElement ? document.documentElement : document.body;
var elm = $('get_your_anchor_element').get(0);
var destScroll, curScroll = de.scrollTop;

/// check for the function scrollIntoView
if ( elm.scrollIntoView ) {
  /// get the browser to scrollIntoView (this wont show up yet)
  elm.scrollIntoView();
  /// however the new scrollTop is calculated
  destScroll = de.scrollTop;
  /// then set the scrollTop back to where we were
  de.scrollTop = curScroll;
  /// you now have your correct scrollTop value
  $(de).animate({scrollTop:destScroll});
}
else {
  /// most browsers support scrollIntoView so I didn't bother
  /// with a fallback, but you could just use window.location
  /// and jump to the anchor.
}

上記は、クリックイベントで発生する可能性があります。改善が必要なのは、さまざまなブラウザがさまざまな基本要素(bodyまたはhtml)をスクロールすることだけです。これを使用したとき、私はスクロール可能な独自の要素を持っていたので、エージェントが使用している要素を特定する必要はありませんでした...秒を取得すると、検出するための適切なコードを見つけることができるかどうかを確認します違い。

上記は、私がテストしたすべての最新のブラウザー(Firefox、Safari、Chrome)で機能しましたが、Internet Explorerをサポートする必要がなかったため、それについてはよくわかりません。

アップデート:

あなたの実装で何が起こっているのかよくわかりません-ページがコンテンツで非常に重く、実際に.scrollIntoView()起こっていることを見ることができる可能性があります-これは私の経験ではありませんでしたが、私はそれほど多くのことをしていませんでした画面上。そのことを念頭に置いて、必要な各追加パーツを使用して構築することをお勧めするベアボーンシステムを実装しました。

http://pebbl.co.uk/stackoverflow/13035183.html

そうすれば、最初から機能しているシステムがあることがわかり、システムが機能しなくなる原因を簡単に検出できます。chiaro.jsに関しては、実装は問題ないようです-ファイルの多くの異なる領域で少し爆発した場合-しかし、この部分は少し間違っています:

$('#anchor-aboutus').click(function() {
    event.preventDefault();
    if(panelOpen == true) {
        $('#slide-panel-content')
                      .stop(true, true)
                      .animate({height: '0px'}, 600, function() {
            $('#panel-content-container').hide();
            $('.scrollableArea').css('z-index', '11');
            elm.scrollIntoView(true)
                              .animate({scrollTop:destScroll}, 1000);
            panelOpen = false;
        });
    }else{
        elm.scrollIntoView(true).animate({scrollTop:destScroll});
    };
});

destScroll上記のコードでは、 ifの正しい値のみを取得しますpanelOpen === true。ああ、実際に私は別の問題も発見しました-それはなぜそれが機能しないのかを説明します:

elm.scrollIntoView(true)
  .animate({scrollTop:destScroll}, 1000);

上記のコードは純粋なJavaScriptとjQueryを混合しており、elmvarは通常のDOM要素です(これはscrollIntoViewメソッドをサポートします)。ただし、jQueryのメソッドをミックスにチェーンしようとしていanimateます。また、スクロールバーを担当する要素でanimateメソッドをトリガーする必要があります。使用する必要があるものは次のとおりです。

$('#anchor-aboutus').click(function(e) {
  var currentScroll, destScroll;
  e.preventDefault();
  if(panelOpen == true) {
    $('#slide-panel-content')
      .stop(true, true)
      .animate({height: '0px'}, 600, function() {
        $('#panel-content-container').hide();
        $('.scrollableArea').css('z-index', '11');
        currentScroll = de.scrollTop;
        elm.scrollIntoView(true);
        destScroll = de.scrollTop;
        de.scrollTop = currentScroll;
        $(de).animate({scrollTop:destScroll}, 1000);
        panelOpen = false;
      });
  }else{
    currentScroll = de.scrollTop;
    elm.scrollIntoView(true);
    destScroll = de.scrollTop;
    de.scrollTop = currentScroll;
    $(de).animate({scrollTop:destScroll}, 1000);
  };
});

deただし、要素が正しい要素(ブラウザに応じてhtmlまたはbody)を指していることを確認する必要もあります。これには、次を使用できます。

var de;

/// calculate which element is the scroller element
$('body, html').each(function(){
  if ( this.scrollHeight > this.offsetHeight ) {
    de = this;
    return false;
  }
});

alert( $(de).is('body') ) /// will be true for Chrome, false for Firefox.

次のコードの代わりにこのコードを使用する必要があります。

var de = document.documentElement ? document.documentElement : document.body;

使用していたコードを変更する理由は次のとおりです。

/// store the current scroll position from the de element
currentScroll = de.scrollTop;
/// get the browser to do the scrollTo calculation
elm.scrollIntoView(true);
/// store where the browser scrolled to behind the scenes
destScroll = de.scrollTop;
/// reset our scroll position to where we were before scrollIntoView()
/// if you don't reset then the animation will happen instantaneously
/// because that is what scrollIntoView does.
de.scrollTop = currentScroll;
/// wrap the normal dom element de with jquery and then animate
$(de).animate({scrollTop:destScroll}, 1000);
于 2012-10-23T17:31:06.223 に答える