You need to enable JavaScript to run this app. 如何实现网页仅向下滚动触发元素动画 修复JS上下滚动都触发的问题
优惠活动
大模型
产品
解决方案
定价
更多

如何实现网页仅向下滚动触发元素动画 修复JS上下滚动都触发的问题

问题根因

你当前的代码没有判断滚动方向,同时元素离开视口就会移除visible类,导致向上滚动时元素重新进入视口也会再次添加类触发动画。

改造后完整代码

var scroll = window.requestAnimationFrame || function(callback){
  window.setTimeout(callback,1000/60)
};
// 存储上一次滚动的纵坐标位置,初始值为0
let lastScrollY = 0;
var elements = document.querySelectorAll(".question-box");

function loop(){
  // 获取当前滚动位置
  const currentScrollY = window.pageYOffset || document.documentElement.scrollTop;
  // 仅向下滚动时执行元素类名操作
  if (currentScrollY > lastScrollY) {
    elements.forEach(element => {
      // 如果元素已在视口内且还没加visible类,才添加类触发动画
      if (isElementInViewport(element) && !element.classList.contains("visible")){
        element.classList.add("visible");
      }
    });
  }
  // 如果你需要向上滚动时隐藏元素、下次向下滚再重新触发动画,可以放开下面这段注释
  // else {
  //   elements.forEach(element => {
  //     if (!isElementInViewport(element)){
  //       element.classList.remove("visible");
  //     }
  //   })
  // }
  // 更新上一次滚动位置
  lastScrollY = currentScrollY;
  scroll(loop);
}

loop();

// 原有的视口判断工具函数
function isElementInViewport(el) {
  if (typeof jQuery === "function" && el instanceof jQuery) {
    el = el[0];
  }
  var rect = el.getBoundingClientRect();
  return (
    (rect.top <= 0
      && rect.bottom >= 0)
    ||
    (rect.bottom >= (window.innerHeight || document.documentElement.clientHeight) &&
      rect.top <= (window.innerHeight || document.documentElement.clientHeight))
    ||
    (rect.top >= 0 &&
      rect.bottom <= (window.innerHeight || document.documentElement.clientHeight))
  );
}

核心改动说明

  • 新增lastScrollY变量记录上一次滚动的位置,每次执行loop时和当前滚动位置对比,只有当前滚动位置大于上次位置(即向下滚动)时才执行类添加操作
  • 加类时增加了!element.classList.contains("visible")的判断,避免重复给已触发动画的元素加类
  • 默认注释了移除类的逻辑,保证元素动画触发后保持可见状态,如果需要每次向下滚动进入视口都重新触发动画,放开移除类的注释即可

内容的提问来源于stack exchange,提问作者Ajil P

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.16 06:27:00