react 实现滚动
滚动到指定元素
使用 useRef 和 scrollIntoView 方法可以滚动到页面中的特定元素。在 React 中创建一个 ref 并将其附加到目标元素上,通过调用 scrollIntoView 实现滚动效果。
import { useRef } from 'react';
function ScrollToElement() {
const targetRef = useRef(null);
const scrollToTarget = () => {
targetRef.current.scrollIntoView({ behavior: 'smooth' });
};
return (
<div>
<button onClick={scrollToTarget}>Scroll to Target</button>
<div style={{ height: '1000px' }}></div>
<div ref={targetRef}>Target Element</div>
</div>
);
}
滚动到顶部/底部
通过 window.scrollTo 方法可以实现页面整体滚动到顶部或底部。结合 smooth 行为参数可以让滚动过程更流畅。

function ScrollToTop() {
const scrollToTop = () => {
window.scrollTo({ top: 0, behavior: 'smooth' });
};
const scrollToBottom = () => {
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
};
return (
<div>
<button onClick={scrollToTop}>Scroll to Top</button>
<button onClick={scrollToBottom}>Scroll to Bottom</button>
<div style={{ height: '2000px' }}></div>
</div>
);
}
自定义滚动容器
对于非窗口滚动(如 div 容器内的滚动),需要使用容器的 scrollTop 属性。通过 ref 获取容器元素并控制其滚动位置。
import { useRef } from 'react';
function CustomScrollContainer() {
const containerRef = useRef(null);
const scrollToMiddle = () => {
const container = containerRef.current;
container.scrollTo({
top: container.scrollHeight / 2,
behavior: 'smooth'
});
};
return (
<div>
<button onClick={scrollToMiddle}>Scroll to Middle</button>
<div
ref={containerRef}
style={{
height: '300px',
overflow: 'auto',
border: '1px solid #ccc'
}}
>
<div style={{ height: '900px' }}>Scrollable Content</div>
</div>
</div>
);
}
滚动事件监听
通过 useEffect 添加和移除滚动事件监听器,可以响应页面滚动行为并执行相应操作。

import { useEffect, useState } from 'react';
function ScrollListener() {
const [scrollY, setScrollY] = useState(0);
useEffect(() => {
const handleScroll = () => {
setScrollY(window.scrollY);
};
window.addEventListener('scroll', handleScroll);
return () => window.removeEventListener('scroll', handleScroll);
}, []);
return (
<div style={{ height: '2000px' }}>
<div style={{ position: 'fixed', top: '20px', left: '20px' }}>
Current Scroll Position: {scrollY}px
</div>
</div>
);
}
滚动位置恢复
在页面导航时保持滚动位置,可以使用 useLayoutEffect 在组件挂载时恢复之前保存的滚动位置。
import { useLayoutEffect } from 'react';
import { useLocation } from 'react-router-dom';
function ScrollRestoration() {
const location = useLocation();
const scrollPositions = useRef({});
useLayoutEffect(() => {
const key = location.pathname;
const savedPosition = scrollPositions.current[key];
if (savedPosition !== undefined) {
window.scrollTo(0, savedPosition);
}
return () => {
scrollPositions.current[key] = window.scrollY;
};
}, [location]);
}
无限滚动加载
结合 Intersection Observer API 实现无限滚动加载更多内容的效果。
import { useState, useEffect, useRef } from 'react';
function InfiniteScroll() {
const [items, setItems] = useState(Array(20).fill(0));
const loaderRef = useRef(null);
useEffect(() => {
const observer = new IntersectionObserver((entries) => {
if (entries[0].isIntersecting) {
setItems(prev => [...prev, ...Array(10).fill(0)]);
}
});
if (loaderRef.current) {
observer.observe(loaderRef.current);
}
return () => observer.disconnect();
}, []);
return (
<div>
{items.map((_, i) => (
<div key={i} style={{ height: '100px', border: '1px solid #eee' }}>
Item {i + 1}
</div>
))}
<div ref={loaderRef}>Loading more...</div>
</div>
);
}






