簡體   English   中英

粘滯標題 - 滾動標簽

[英]Sticky Header - Scroll with Tabs

我的粘性標題的行為有問題。

期望的行為:

a)滾動到.nav底部到達section頂部的位置將active類添加到選項卡,它將保持active直到.nav到達下一部分的頂部。

b)單擊相應部分的.tab始終導航到該部分的頂部,並將active類添加到選項卡。

因此,無論是通過滾動還是單擊,都會始終保持選項卡的active狀態,直到.nav進入下section ,在這種情況下, active狀態將轉到該部分的選項卡等。

測試問題:

1)中途向下滾動Option Two.tabactive狀態丟失。

2)使用scrollTop滾動到.container的頂部而不是所選section的頂部。

 class StickyNavigation { constructor() { this.currentId = null; this.currentTab = null; let self = this; $(".tab").click(function() { self.onTabClick(event, $(this)); }); $(".container").scroll(() => { this.onScroll(); }); $(".container").resize(() => { this.onResize(); }); } /*Scrolls down to Tab selection*/ onTabClick(event, element) { event.preventDefault(); let scrollTop = $(element.attr("href")).offset().top; if (!$(".nav").hasClass("nav--top")) { scrollTop = scrollTop; } $(".container").animate({ scrollTop: scrollTop }, 600); } onScroll() { this.navPosition(); this.tabAnimation(); } navPosition() { let offset = $(".sticky").offset().top + $(".sticky").height(); if ($(".container").scrollTop() > offset) { $(".nav").addClass("nav--top"); } else { $(".nav").removeClass("nav--top"); } } tabAnimation() { $("section").each(function() { var actual = $(this), actualHeight = actual.height(), actualAnchor = $(".sticky").find('a[href="#' + actual.attr("id") + '"]'); if ( actual.offset().top <= $(".container").scrollTop() && actual.offset().top + actualHeight > $(".container").scrollTop() ) { actualAnchor.addClass("active"); } else { actualAnchor.removeClass("active"); } }); } } new StickyNavigation(); 
 body { position: fixed; display: flex; flex-direction: column; top: 0; bottom: 0; left: 0; right: 0; overflow: hidden; } section { height: 600px; border: 2px solid white; background: blue; } section:nth-child(2) { background: red; } .container { flex: 1; display: flex; position: relative; flex-direction: column; overflow: auto; } .long { height: 1200px; } .header { height: 75px; background: green; } .hero { background: silver; flex: 0; border: 1px solid; } .nav { background: white; width: 100%; display: flex; justify-content: center; align-items: center; position: relative; } .nav--top { position: fixed; top: 75px; } .sticky { background: white; display: flex; flex-direction: row; flex-wrap: wrap; position: relative; } .tab { padding: 30px 45px; position: relative; } .tab.active { background: #6567c5; color: white; } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <div class="header"> <h1>Header</h1> </div> <div class="container"> <div class="hero"> <h1>Hero</h1> </div> <div class="sticky"> <nav role="navigation" class="nav"> <a class="tab" href="#One">Option One</a> <a class="tab" href="#Two">Option Two</a> </nav> </div> <div class="main"> <section id="One"> </section> <section class="long" id="Two"> </section> </div> </div> </div> 

您的部分滾動到頂部的原因是由於添加和刪除粘性元素而導致的位置更改。 使用包裝代替粘性以始終占據粘性元素的高度,無論它是否存在。

 class StickyNavigation { constructor() { this.currentId = null; this.currentTab = null; this.setup(); this.onResize(); let self = this; $(".tab").click(function(event) { self.onTabClick(event, $(this)); }); $(".container").scroll(() => { this.onScroll(); }); $(window).resize(() => { this.onResize(); }); } setup() { this.$sticky = $('.sticky'); window.stk = this.$sticky; this.$stickyWrap = $('<div>').insertAfter(this.$sticky); this.$sticky.appendTo(this.$stickyWrap); } /*Scrolls down to Tab selection*/ onTabClick(event, element) { event.preventDefault(); let $targetElement = $(element.attr("href")); let positionTop = $targetElement.position().top; let scrollTop = $('.container').scrollTop(); $(".container").animate({ scrollTop: scrollTop - this.stickyOuterHeight + positionTop }, 600); } onScroll() { this.navPosition(); this.tabAnimation(); } onResize() { this.stickyOuterHeight = this.$sticky.outerHeight(); this.$sticky.width(this.$stickyWrap.width()); this.$stickyWrap.css('minHeight', this.stickyOuterHeight); } navPosition() { if (this.$stickyWrap.position().top < 0) { this.$sticky.addClass("fixed"); } else { this.$sticky.removeClass("fixed"); } } tabAnimation() { let desiredSpace = this.stickyOuterHeight + 10; $("section").each(function() { let actual = $(this), actualHeight = actual.height(), actualAnchor = $(".sticky").find('a[href="#' + actual.attr("id") + '"]'); let actualTop = actual.position().top; let actualBottom = actualTop + actualHeight; if (actualTop < desiredSpace && actualBottom > desiredSpace) { actualAnchor.addClass("active"); } else { actualAnchor.removeClass("active"); } }); } } $(function() { new StickyNavigation(); }); 
 body { position: fixed; display: flex; flex-direction: column; top: 0; bottom: 0; left: 0; right: 0; overflow: hidden; } section { height: 600px; border: 2px solid white; background: blue; } section:nth-child(2) { background: red; } .container { flex: 1; display: flex; position: relative; flex-direction: column; overflow: auto; } .long { height: 1200px; } .header { height: 75px; background: green; } .hero { background: silver; flex: 0; border: 1px solid; } .nav { background: white; width: 100%; display: flex; justify-content: center; align-items: center; position: relative; } .sticky { display: flex; flex-direction: row; flex-wrap: wrap; } .sticky.fixed { position: fixed; top: 83px; } .tab { padding: 30px 45px; position: relative; } .tab.active { background: #6567c5; color: white; } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <div class="header"> <h1>Header</h1> </div> <div class="container"> <div class="hero"> <h1>Hero</h1> </div> <div class="sticky"> <nav role="navigation" class="nav"> <a class="tab" href="#One">Option One</a> <a class="tab" href="#Two">Option Two</a> </nav> </div> <div class="main"> <section id="One"> Content One </section> <section class="long" id="Two"> Content Two </section> </div> </div> 

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM