如何在主窗口使用react-spring parallax且仅保留窗口原生滚动条
解决方案
方案1:使用Parallax组件原生配置适配全局滚动
@react-spring/parallax的Parallax组件默认会生成独立滚动容器,你可以通过scrollingContainer属性将滚动监听绑定到全局窗口滚动条,同时调整组件样式避免生成独立滚动条,修改后的代码如下:
import { useEffect, useState } from 'react' import { Parallax, ParallaxLayer } from '@react-spring/parallax' const Cards = () => { const [scrollContainer, setScrollContainer] = useState(null) useEffect(() => { // 绑定全局滚动容器 setScrollContainer(document.documentElement) }, []) return ( <> <Titlebar title= 'Three major ethnic groups' /> {scrollContainer && ( <Parallax pages={3} scrollingContainer={scrollContainer} // 禁用组件自带的滚动能力,高度与pages数值对应,pages为3则高度为3倍视口高度 style={{ overflow: 'hidden', height: '300vh' }} > <ParallaxLayer sticky={{ start: 1, end: 3 }} style={{ justifyContent: 'flex-start' }}> <Test text='bole' paragraph='gimme that bole' source= {igbo} alter='igbo' /> </ParallaxLayer> <ParallaxLayer offset={0} speed={0.5} style={{ justifyContent: 'flex-end' }}> <p >Scroll down</p> </ParallaxLayer> <ParallaxLayer offset={1.5} speed={1.5} style={{ justifyContent: 'flex-end' }}> <div> <p>I'm not</p> </div> </ParallaxLayer> </Parallax> )} </> ) } export default Cards
注意:offset属性的计算规则保持不变,1对应1倍视口高度的滚动偏移量,你可以根据实际页面布局调整pages和对应高度的数值
方案2:手动实现局部视差效果(更适合局部场景)
如果只需要小范围的视差效果,不需要用到sticky等复杂能力,可以直接用react-spring的useSpring监听全局滚动事件手动实现,不会引入额外容器冲突:
import { useSpring, animated } from '@react-spring/web' import { useEffect, useState } from 'react' const Cards = () => { const [scrollY, setScrollY] = useState(0) useEffect(() => { const handleScroll = () => setScrollY(window.scrollY) window.addEventListener('scroll', handleScroll) return () => window.removeEventListener('scroll', handleScroll) }, []) // 自定义不同元素的滚动速度,speed数值越小视差效果越明显 const slowAnim = useSpring({ y: scrollY * 0.5 }) const fastAnim = useSpring({ y: scrollY * 1.5 }) return ( <> <Titlebar title= 'Three major ethnic groups' /> <div style={{ height: '300vh', position: 'relative' }}> <animated.div style={{ ...slowAnim, position: 'absolute', bottom: 0 }}> <p>Scroll down</p> </animated.div> <animated.div style={{ ...fastAnim, position: 'absolute', bottom: 0 }}> <div> <p>I'm not</p> </div> </animated.div> <div style={{ position: 'sticky', top: 0, height: '100vh' }}> <Test text='bole' paragraph='gimme that bole' source= {igbo} alter='igbo' /> </div> </div> </> ) } export default Cards
内容的提问来源于stack exchange,提问作者maesstro
相关产品推荐
相关产品推荐

