我编写了一个函数,调用该函数时,页面将以平滑的方式向下滚动。
问题是滚动的量不精确。它可能会偏离一个像素左右,具体取决于滚动的距离和滚动的持续时间。
是否有更好的方法来做到这一点,以便滚动可以移动所需像素的确切数量?
const EASING = BezierEasing(0, .1, .1, 1); // Example values.
const DURATION = 1000; // ms.
document.addEventListener('DOMContentLoaded',
() => {
document.querySelector('#foo')
.addEventListener('click', onClick, false);
});
function onClick(e) {
scroll(400); // px.
e.preventDefault();
return false;
}
function scroll(distance) {
var start, travelled, html;
start = performance.now();
travelled = 0;
html = document.querySelector('html');
(function move(now) {
var fractionDone, dy, toMove;
fractionDone = (now-start) / DURATION;
if((1 - fractionDone) <= 0) {
return; // Done!
}
if(window.scrollY + window.innerHeight
=== html.offsetHeight) {
return; // At bottom of page.
}
dy = ((EASING.get(fractionDone)) * distance);
toMove = Math.floor((dy - travelled)); // `scrollBy` only accepts integers.
if(toMove > 0) {
window.scrollBy(0, toMove);
travelled += toMove;
}
requestAnimationFrame(move);
}(start));
}
<!DOCTYPE html>
<html>
<head>
<script src="https://rawgit.com/gre/bezier-easing/master/build.js"></script>
</head>
<body>
<a href id="foo">Click Me!</a>
<script>
/* print some numbers to
the DOM to help visualize
the scrolling */
var body = document.querySelector('body');
for(var x = 0; x < 50; x++) {
var div = document.createElement("div");
var text = document.createTextNode(x);
div.appendChild(text);
body.appendChild(div);
}
</script>
</body>
</html>
最佳答案
你能做这样的事情来解释最后一次迭代吗?
基本上,如果 toMove 向下舍入为 0,但距离尚未经过,是否强制它再滚动一次?
if(toMove > 0 || (toMove == 0 && travelled != distance) {
window.scrollBy(0, (toMove ? toMove : 1));
travelled += toMove;
}
关于javascript - 使用缓动功能滚动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33859148/