react实现翻页切换效果
使用React实现翻页切换效果
React中实现翻页切换效果可以通过多种方式完成,包括使用CSS动画、第三方库或自定义组件。以下是几种常见方法:
基于CSS过渡的翻页效果
利用React状态管理和CSS过渡实现基础翻页动画:
import React, { useState } from 'react';
import './PageFlip.css';
function PageFlip() {
const [currentPage, setCurrentPage] = useState(0);
const pages = ['Page 1', 'Page 2', 'Page 3'];
const nextPage = () => {
setCurrentPage((prev) => (prev + 1) % pages.length);
};
const prevPage = () => {
setCurrentPage((prev) => (prev - 1 + pages.length) % pages.length);
};
return (
<div className="page-container">
<div className={`page ${currentPage ? 'flipped' : ''}`}>
{pages[currentPage]}
</div>
<button onClick={prevPage}>Previous</button>
<button onClick={nextPage}>Next</button>
</div>
);
}
配套CSS样式:
.page-container {
perspective: 1000px;
}
.page {
width: 300px;
height: 400px;
background: #fff;
border: 1px solid #ddd;
transition: transform 0.6s;
transform-style: preserve-3d;
}
.page.flipped {
transform: rotateY(180deg);
}
使用React Transition Group
React Transition Group提供更精细的过渡控制:
import { CSSTransition } from 'react-transition-group';
function PageTransition() {
const [page, setPage] = useState(0);
const pages = ['Page A', 'Page B', 'Page C'];
return (
<div>
<CSSTransition
in={true}
key={page}
timeout={500}
classNames="page"
unmountOnExit
>
<div className="page-content">{pages[page]}</div>
</CSSTransition>
<button onClick={() => setPage((p) => (p + 1) % pages.length)}>
Next
</button>
</div>
);
}
配套CSS:
.page-content {
transition: opacity 500ms, transform 500ms;
}
.page-enter {
opacity: 0;
transform: translateX(100%);
}
.page-enter-active {
opacity: 1;
transform: translateX(0);
}
.page-exit {
opacity: 1;
transform: translateX(0);
}
.page-exit-active {
opacity: 0;
transform: translateX(-100%);
}
使用Framer Motion动画库
Framer Motion提供声明式动画API:
import { motion, AnimatePresence } from 'framer-motion';
function FramerPageFlip() {
const [[page, direction], setPage] = useState([0, 0]);
const pages = ['Page X', 'Page Y', 'Page Z'];
const paginate = (newDirection) => {
setPage([(page + newDirection + pages.length) % pages.length, newDirection]);
};
return (
<div className="framer-container">
<AnimatePresence initial={false} custom={direction}>
<motion.div
key={page}
custom={direction}
variants={{
enter: (direction) => ({
x: direction > 0 ? 1000 : -1000,
opacity: 0
}),
center: {
x: 0,
opacity: 1
},
exit: (direction) => ({
x: direction < 0 ? 1000 : -1000,
opacity: 0
})
}}
initial="enter"
animate="center"
exit="exit"
transition={{
x: { type: 'spring', stiffness: 300, damping: 30 },
opacity: { duration: 0.2 }
}}
>
{pages[page]}
</motion.div>
</AnimatePresence>
<button onClick={() => paginate(-1)}>Previous</button>
<button onClick={() => paginate(1)}>Next</button>
</div>
);
}
实现3D翻页效果
结合CSS 3D变换创建更真实的翻页效果:
function PageFlip3D() {
const [flipped, setFlipped] = useState(false);
return (
<div className="book">
<div className={`page ${flipped ? 'flipped' : ''}`}>
<div className="front">Front Content</div>
<div className="back">Back Content</div>
</div>
<button onClick={() => setFlipped(!flipped)}>Flip Page</button>
</div>
);
}
配套CSS:
.book {
perspective: 1500px;
}
.page {
width: 200px;
height: 300px;
position: relative;
transform-style: preserve-3d;
transition: transform 1s;
}
.page .front,
.page .back {
position: absolute;
width: 100%;
height: 100%;
backface-visibility: hidden;
}
.page .back {
transform: rotateY(180deg);
}
.page.flipped {
transform: rotateY(180deg);
}
以上方法可根据具体需求选择,从简单过渡到复杂3D效果均可实现。关键点在于合理管理组件状态,配合CSS或动画库实现平滑过渡效果。







