自定义导航组件上没有 Bootstrap 的简单 Scrollspy
Simple Scrollspy without Bootstrap on custom Nav Component
我有一个 Table 个 ID 为 #TableOfContents
的目录,其中每个 href
指向一个 h2 或 h3。
我遇到的问题是,一旦路口观察者观察到航向、h2 或 h3,通过添加 class [=14] 来 突出显示 条目=] 对于 #TableOfContents
中的 link,但是一旦标题后的长内容(例如 p
段落)出现在视口中 突出显示 该部分已删除 因为标题不在视口中。
这是一个问题,因为我希望部分 (h2, h3) 仍然突出显示,直到下一个 h2 或 h3 不超过视口的一半。
我能做什么?
window.addEventListener('DOMContentLoaded', () => {
const observer = new IntersectionObserver(entries => {
entries.forEach(entry => {
const id = entry.target.getAttribute('id');
if (entry.intersectionRatio > 0) {
document.querySelector(`#TableOfContents a[href="#${id}"]`).classList.add('side-active');
} else {
document.querySelector(`#TableOfContents a[href="#${id}"]`).classList.remove('side-active');
}
});
});
toc = document.querySelectorAll('#TableOfContents a');
// get content so that link refer to it
toc.forEach(function (link) {
var id = link.getAttribute("href");
var element = document.querySelector(id);
observer.observe(element);
});
});
在视口中标题时突出显示文本
标题不在视口中时文本不会突出显示
所以我们需要通过以下方式计算 containerBottom:
添加当前容器的顶部+下一个容器的顶部
或者如果是最后一个容器,
当前容器的顶部 + outerHeight()
曾经那个;如果第 i 个容器处于滚动位置,则向其添加 class 并从第 i 个容器之前的所有容器中删除 class(第 18-21 行)(反向循环)
$(function () {
// Table of contents (`ul`) that contains `a` tag in `li` which we want to highlight
var sectionIds = $('#TableOfContents a');
$(document).on('scroll', function(){
sectionIds.each(function(i, e){
var container = $(this).attr('href');
var containerOffset = $(container).offset().top; // container's top
var nextContainer = $(sectionIds[i+1]).attr('href')
if (i != sectionIds.length-1) {
// if this container isn't last container
var containerHeight = $(nextContainer).offset().top;
} else {
// last container's height will be outerHeight
var containerHeight = $(container).outerHeight();
}
var containerBottom = containerOffset + containerHeight;
var scrollPosition = $(document).scrollTop();
if(scrollPosition < containerBottom - 20 && scrollPosition >= containerOffset - 20){
for (var j = i; j >= 0; j--) {
$(sectionIds[j]).removeClass('active');
}
$(sectionIds[i]).addClass('active');
} else{
$(sectionIds[i]).removeClass('active');
}
});
});
});
检查突出显示的第一个标题(“直线方程” h1
)即使在下一个子标题("点到线的距离") 进入视野。
我有一个 Table 个 ID 为 #TableOfContents
的目录,其中每个 href
指向一个 h2 或 h3。
我遇到的问题是,一旦路口观察者观察到航向、h2 或 h3,通过添加 class [=14] 来 突出显示 条目=] 对于 #TableOfContents
中的 link,但是一旦标题后的长内容(例如 p
段落)出现在视口中 突出显示 该部分已删除 因为标题不在视口中。
这是一个问题,因为我希望部分 (h2, h3) 仍然突出显示,直到下一个 h2 或 h3 不超过视口的一半。
我能做什么?
window.addEventListener('DOMContentLoaded', () => {
const observer = new IntersectionObserver(entries => {
entries.forEach(entry => {
const id = entry.target.getAttribute('id');
if (entry.intersectionRatio > 0) {
document.querySelector(`#TableOfContents a[href="#${id}"]`).classList.add('side-active');
} else {
document.querySelector(`#TableOfContents a[href="#${id}"]`).classList.remove('side-active');
}
});
});
toc = document.querySelectorAll('#TableOfContents a');
// get content so that link refer to it
toc.forEach(function (link) {
var id = link.getAttribute("href");
var element = document.querySelector(id);
observer.observe(element);
});
});
在视口中标题时突出显示文本
标题不在视口中时文本不会突出显示
所以我们需要通过以下方式计算 containerBottom:
添加当前容器的顶部+下一个容器的顶部
或者如果是最后一个容器,
当前容器的顶部 + outerHeight()
曾经那个;如果第 i 个容器处于滚动位置,则向其添加 class 并从第 i 个容器之前的所有容器中删除 class(第 18-21 行)(反向循环)
$(function () {
// Table of contents (`ul`) that contains `a` tag in `li` which we want to highlight
var sectionIds = $('#TableOfContents a');
$(document).on('scroll', function(){
sectionIds.each(function(i, e){
var container = $(this).attr('href');
var containerOffset = $(container).offset().top; // container's top
var nextContainer = $(sectionIds[i+1]).attr('href')
if (i != sectionIds.length-1) {
// if this container isn't last container
var containerHeight = $(nextContainer).offset().top;
} else {
// last container's height will be outerHeight
var containerHeight = $(container).outerHeight();
}
var containerBottom = containerOffset + containerHeight;
var scrollPosition = $(document).scrollTop();
if(scrollPosition < containerBottom - 20 && scrollPosition >= containerOffset - 20){
for (var j = i; j >= 0; j--) {
$(sectionIds[j]).removeClass('active');
}
$(sectionIds[i]).addClass('active');
} else{
$(sectionIds[i]).removeClass('active');
}
});
});
});