我找到了这个用于平滑滚动的JavaScript代码
window.smoothScroll = function(target) {
var scrollContainer = target;
do { //find scroll container
scrollContainer = scrollContainer.parentNode;
if (!scrollContainer) return;
scrollContainer.scrollTop += 1;
} while (scrollContainer.scrollTop == 0);
var targetY = 0;
do { //find the top of target relatively to the container
if (target == scrollContainer) break;
targetY += target.offsetTop;
} while (target = target.offsetParent);
scroll = function(c, a, b, i) {
i++; if (i > 30) return;
c.scrollTop = a + (b - a) / 30 * i;
setTimeout(function(){ scroll(c, a, b, i); }, 20);
}
// start scrolling
scroll(scrollContainer, scrollContainer.scrollTop, targetY, 0);
}
并简单example here。
正如您所看到的那样,它滚动到红色部分,但它并没有排除导航栏的高度。红色部分的开始全部到达页面顶部,在导航栏下。
如何为此脚本添加偏移量,以便红色部分在点击导航栏时停止?填充不是一个选项,我已经尝试过,它看起来并不好看。此外,我需要在vanila javascript中使用它,而不是jquery。
提前致谢!
答案 0 :(得分:3)
看看这个,它会计算标题的高度,然后从滚动位置中减去它:
header = document.querySelectorAll('.navbar'),
space = header[0].clientHeight;
...
var targetY = -space;
更新 - 评论中要求的功能,以重新定义偏移量。为此,我将targetY
作为全局变量,可以通过执行函数来更新它。因此,在滚动的类切换的脚本中,在此之后只需添加一行headerSpace();
,它将重新计算高度。从我读到的内容来看,初始课程仍然保持不变,无需进一步调整即可。
按钮上的内联脚本也被删除,并成为一个事件监听器......
最终版本 - requestAnimationFrame
的实现,它将使动画更流畅,并且在CPU上也更容易。当功能不可用时,原始功能将作为后备保留。可以使用顶部的变量设置持续时间(600ms现在匹配之前设置的30ms的30步)。还认为将标题高度检查放在按钮单击事件处理程序中可能很方便。所以它总是在用户激活滚动动画时重新计算(并且不再需要将它直接挂钩到切换类中):
duration = 600
基本代码:
scroll = function(c, a, b, i) {
if (modern) {
var present = Date.now(),
elapsed = present-initial,
progress = Math.min(elapsed/duration, 1);
c.scrollTop = a + (b - a) * progress;
if (progress < 1) requestAnimationFrame(function() {
scroll(c, a, b, i);
});
}
else {
i++; if (i > 30) return;
c.scrollTop = a + (b - a) / 30 * i;
setTimeout(function() {scroll(c, a, b, i)}, 20);
}
}
作为旁注,单击按钮时第一次看起来似乎是非常突然的动画,但这是因为Codepen。我怀疑焦点是在窗口中有脚本而不是内容本身。因此,窗口必须首先“唤醒”,节能方面为requestAnimationFrame
。当首先点击内容中的任何其他位置时,这将消失。它也不应该在现场环境中发生。我可能会给他们发一条信息......
答案 1 :(得分:0)
请在此处找到我的解决方案:Fiddle
window.smoothScroll = function(target) {
var scrollContainer = target;
do { //find scroll container
scrollContainer = scrollContainer.parentNode;
if (!scrollContainer) return;
scrollContainer.scrollTop += 1;
} while (scrollContainer.scrollTop == 0);
var targetY = -1* document.getElementsByClassName("navbar")[0].offsetHeight;;
console.log (document.getElementsByClassName("navbar")[0].height);
do { //find the top of target relatively to the container
if (target == scrollContainer) break;
targetY += target.offsetTop;
} while (target = target.offsetParent);
scroll = function(c, a, b, i) {
i = i+ 0.125; if (i > 30) return;
c.scrollTop = a + (b - a) / 30 * i;
setTimeout(function(){ scroll(c, a, b, i); }, 50);
}
// start scrolling
scroll(scrollContainer, scrollContainer.scrollTop, targetY, 0);
}
我把putY放在:-1 * document.getElementsByClassName(“navbar”)[0] .offsetHeight;这解决了目标问题。至于顺利滚动,我已将动作的增量减少为:0.125。