You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

GSAP ScrollTrigger分屏固定效果异常:固定元素消失移位求助

React中GSAP ScrollTrigger分屏固定滚动问题求助

我在React项目中使用GSAP ScrollTrigger实现分屏固定滚动效果,预期文本滚动时图片保持固定并随文本切换,但当触发元素(文本元素)到达start标记时,图片消失并出现在文本底部,调整scrub值后问题仍未解决,特此求助。

原代码

JSX代码

import { useEffect } from 'react';
import './Facilities.css'
import gsap from 'gsap';
import ScrollTrigger from 'gsap/ScrollTrigger';

function Facilities() {
  const imagesUrl = ["imgs/mechines/cardio.jpg","imgs/mechines/weight.jpg","imgs/mechines/rope.jpg","imgs/mechines/sauna.jpg"]

  useEffect(()=>{
    gsap.registerPlugin(ScrollTrigger);
    gsap.to(".imagesectionfacilities",{duration:1,scrollTrigger:{
    trigger:".txtFacilities",
    start:"top top",
    end:"bottom bottom",
    markers:true,
    pin:".imagesectionfacilities",

  }})},[])
  return (
    <div className='facilites'>
      <div className='txtFacilities'>
        <div className="cardioFacilities">Cardio</div>
        <div className="cardioFacilities">Strength</div>
        <div className="cardioFacilities">Functional</div>
        <div className="cardioFacilities">Amenities</div>

      </div>
      <div className="imagesectionfacilities">
        <img src={imagesUrl[0]} alt="" className='cardImg'/>
      </div>
    </div>
  )
}

export default Facilities

CSS代码

.facilites{
    height: auto;
    width: 100%;
    display: flex;
    justify-content: center;
    gap:40%;
    border: 1px solid rgb(0, 255, 21);
}
.cardImg{
    height: 250px;
    width: 350px;
    border: none;
    border-radius: 10px;
    object-fit: cover;
}
.txtFacilities{
    border: 1px solid rgb(255, 0, 0);
}

.cardioFacilities{
    display: flex;
    font-size: 50px;
    color: white;
    font-weight: 500;
    align-items: center;
    justify-content: center;
    height: 100vh;
}
.imagesectionfacilities{
    display: flex;
    font-size: 50px;
    color: white;
    font-weight: 500;
    align-items: center;
    justify-content: center;
    height: 100vh;
    border: 1px solid blue;
}

问题原因及修复方案

  1. 布局冲突:原flex布局下,pin操作会打乱flex排列规则,导致图片容器移位。需将图片容器脱离flex流,改用绝对定位。
  2. 滚动范围不匹配:原end:"bottom bottom"未准确匹配文本块总滚动长度,导致固定逻辑失效。
  3. 缺少图片切换逻辑:原代码未实现文本滚动时的图片切换,需添加GSAP时间线动画配合滚动触发。

修改后的完整代码

JSX代码
import { useEffect, useRef } from 'react';
import './Facilities.css'
import gsap from 'gsap';
import ScrollTrigger from 'gsap/ScrollTrigger';

function Facilities() {
  const imagesUrl = ["imgs/mechines/cardio.jpg","imgs/mechines/weight.jpg","imgs/mechines/rope.jpg","imgs/mechines/sauna.jpg"];
  const imgRef = useRef(null);

  useEffect(()=>{
    gsap.registerPlugin(ScrollTrigger);
    
    // 创建图片切换时间线
    const tl = gsap.timeline({
      scrollTrigger: {
        trigger: ".txtFacilities",
        start: "top top",
        end: "+=300vh", // 4个100vh区块,总滚动距离为3个屏幕高度
        scrub: 1,
        markers: true,
        pin: ".imagesectionfacilities",
        pinSpacing: false // 取消自动添加的padding,避免布局偏移
      }
    });

    // 为每个文本区块添加图片切换动画
    imagesUrl.forEach((_, index) => {
      if (index > 0) {
        tl.to(imgRef.current, {
          duration: 1,
          attr: { src: imagesUrl[index] },
          ease: "none"
        });
      }
    });

  }, []);
  
  return (
    <div className='facilites'>
      <div className='txtFacilities'>
        <div className="cardioFacilities">Cardio</div>
        <div className="cardioFacilities">Strength</div>
        <div className="cardioFacilities">Functional</div>
        <div className="cardioFacilities">Amenities</div>
      </div>
      <div className="imagesectionfacilities">
        <img ref={imgRef} src={imagesUrl[0]} alt="" className='cardImg'/>
      </div>
    </div>
  )
}

export default Facilities
CSS代码
.facilites{
    position: relative; /* 作为图片容器的定位基准 */
    height: auto;
    width: 100%;
    display: flex;
    justify-content: flex-start; /* 调整为靠左对齐文本 */
    padding-left: 10%; /* 给文本留出左侧空间 */
    border: 1px solid rgb(0, 255, 21);
}
.cardImg{
    height: 250px;
    width: 350px;
    border: none;
    border-radius: 10px;
    object-fit: cover;
}
.txtFacilities{
    border: 1px solid rgb(255, 0, 0);
}

.cardioFacilities{
    display: flex;
    font-size: 50px;
    color: white;
    font-weight: 500;
    align-items: center;
    justify-content: center;
    height: 100vh;
}
.imagesectionfacilities{
    position: absolute; /* 脱离flex布局 */
    right: 10%; /* 固定在右侧 */
    top: 50%;
    transform: translateY(-50%); /* 垂直居中 */
    display: flex;
    align-items: center;
    justify-content: center;
    height: auto; /* 取消固定高度,适应图片 */
    border: 1px solid blue;
}

关键修改点说明

  • 布局调整:父容器设为relative,图片容器设为absolute并固定在右侧,避免flex布局干扰固定逻辑。
  • 滚动范围修正:end值设为+=300vh,匹配4个100vh文本块的滚动总长度。
  • 图片切换逻辑:使用GSAP时间线,配合scrub实现滚动时平滑切换图片。
  • 取消pinSpacing:避免ScrollTrigger自动添加padding导致的布局偏移。

内容的提问来源于stack exchange,提问作者NINJA GAMER

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.30 16:40:39