我创建了一个可以动态更改动画的代码。我的想法是复制this animation。
我想知道为什么当我触发下一个动画时,我的DOM元素只是眨眼吗?
在我看来,通过更改props.animation的名称,我的元素应该重做整个循环。
在我看来,我的代码很公平,所以我不知道出什么问题了。除了那个样式化组件之外,还有一个很棒的工具,所以我认为这与我的代码结构有关,而与库无关。
Here a sandbox,如果您想查看我的组件的运行情况。
这是我的reactJS代码段:
import React from "react";
import ReactDOM from "react-dom"
import styled from 'styled-components';
import style from "./App.module.css"
import { keyframes } from "styled-components";
/*****
*
* SET STYLED-COMPONENTS
*
* *****/
//animations
const enterDownAnimation = keyframes`
from{
opacity:0;
}
50%{
opacity:1;
}
to{
transform:translate(0, 5vh);
opacity:1;
}
`
const enterSideAnimation = keyframes`
from{
transform:translate(3vw);
opacity:0;
}
to{
transform:translate(0);
opacity:1;
}
`
const exitDownAnimation = keyframes`
from{
transform:"translate(0, 35vh)";
opacity:1;
}
50%{
transform:"translate(0, 35vh)";
opacity:1;
}
to{
transform:"translate(0, 45vh)";
opacity:0;
}`
const exitSideAnimation = keyframes`
from{
transform:"translate(0, 35vh)";
opacity:1;
}
50%{
transform:"translate(0, 35vh)";
opacity:1;
}
to{
transform:"translate(0, 45vh)";
opacity:0;
}`
// page_view
const ImageHolder = styled.div`
position:absolute;
width:510vw;
left: ${props => props.viewPosition};
transition:left 1s ease-in 0.2s;
display:flex;
overflow: hidden;
margin:0;
`;
const ViewOne = styled.div`
width: 102vw;
height:100vh;
background: #E36300;
`;
const ViewTwo = styled.div`
width:102vw;
height:100vh;
background: #8AD300;
`;
// slide_content
const TextFirstLine = styled.div`
position:absolute;
top: 32vh;
opacity:0;
animation: ${props => props.animation} 0.6s cubic-bezier(.11,.91,1,1.03) .1s 1 normal forwards;
`
const TextSecondLine = styled.div`
position:absolute;
top: 45vh;
opacity:0;
margin-top:5vh;
animation: ${props => props.animation} 0.6s cubic-bezier(.11,.91,1,1.03) .7s 1 normal forwards;
`
const ViewImage = styled.img`
position: absolute;
font-size: 7vw;
opacity:0;
top: 25%;
width: 36vw;
margin-top:5vh;
right:3vw;
animation: ${props => props.animation} 0.6s cubic-bezier(.11,.91,1,1.03) 1.3s 1 normal forwards;
`
const MoveViewButtonContainer = styled.div`
`
const MoveViewButton = styled.div`
`
export default class App extends React.Component {
state = {
exitLoop: true,
currentView: 0,
nextView: 0,
elementType: "text",
viewPosition: "0vw",
textAnimation: enterDownAnimation,
imageAnimation: enterSideAnimation
}
animationPrepare = (index) => {
if (this.state.exitLoop) {
this.updateButton(index);
this.updateNextView(index);
}
this.textAnimation();
}
updateButton = (index) => {
var buttonToTransparent = this.refs["button" + this.state.currentView];
buttonToTransparent.style.backgroundColor = "transparent";
var buttonCurrentView = this.refs["button" + index];
buttonCurrentView.style.backgroundColor = "black";
}
updateNextView = (nextView) => {
this.setState({ nextView })
}
textAnimation = () => {
this.setState({ elementType: "text" },
() => this.routeAnimationPosition());
var textSecondLine = this.refs.textSecondLine
textSecondLine.addEventListener("animationend", (e) => this.imageAnimation(e));
}
imageAnimation = () => {
this.setState({ elementType: "image" },
() => this.routeAnimationPosition());
var viewImage = this.refs.viewImage
viewImage.addEventListener("animationend", (e) => this.moveView(e));
}
routeAnimationPosition = () => {
if (this.state.exitLoop) {
this.setExitAnimation();
} else {
this.setEnterAnimation();
}
}
setEnterAnimation = () => {
if (this.state.elementType === "text") {
if (this.state.currentView % 2 == 0) {
this.setState({ textAnimation: this.enterDownAnimation });
} else {
this.setState({ textAnimation: this.enterUpAnimation })
}
} else {
switch (this.state.currentView) {
case 0:
this.setState({ imageAnimation: this.enterSideAnimation });
break;
case 1:
this.setState({ imageAnimation: this.enterUpAnimation });
break;
case 2:
this.setState({ imageAnimation: this.enterDownAnimation });
break;
case 3:
this.setState({ imageAnimation: this.enterSideAnimation });
break;
case 4:
this.setState({ imageAnimation: this.enterUpAnimation });
break;
default:
console.log("no animation found")
break; // test return
}
}
}
setExitAnimation = () => {
if (this.state.elementType === "text") {
if (this.state.currentView % 2 == 0) {
this.setState({ textAnimation: exitDownAnimation });
} else {
this.setState({ textAnimation: exitUpAnimation })
}
} else {
switch (this.state.currentView) {
case 0:
this.setState({ imageAnimation: this.exitSideAnimation });
break;
case 1:
this.setState({ imageAnimation: this.exitUpAnimation });
break;
case 2:
this.setState({ imageAnimation: this.exitDownAnimation });
break;
case 3:
this.setState({ imageAnimation: this.exitSideAnimation });
break;
case 4:
this.setState({ imageAnimation: this.exitUpAnimation });
break;
default:
console.log("no animation found")
break; // test return
}
}
}
moveView = () => {
var newView = -(102 + (102 * this.state.nextView))
this.setState({ viewPosition: newView + "vw" });
var viewImage = this.refs.viewImage;
viewImage.addEventListener("transitionend", () => {
console.log("transition achieved")
this.updateSlideData();
}, false);
}
updateSlideData = () => {
if (this.state.exitLoop) {
// prepare nextView
// text => todo
this.setState({
currentView: this.state.nextView,
exitLoop: true,
imageSource: nextViewImage,
// portfolioUrl:nextViewUrl,
// firstLineText: nextViewFirstLine,
// secondLineText:nextViewSecondLine
},
// inner_callback to ensure updated state
() => this.animationPrepare()
)
} else {
// prepare the next pageView animation
this.setState({
exitLoop: false,
isArrow: null
})
return
}
}
// move background
// animation enter
render() {
var buttonTab = [0, 1, 2, 3, 4]
return (
<div>
<ImageHolder
viewPosition={this.state.viewPosition}
animation={this.state.animation}
ref="imageHolder"
>
<ViewOne />
<ViewTwo />
</ImageHolder>
{/* { this.generateButton(buttonTab)} */}
<div
className={style.button_holder}
>
<MoveViewButtonContainer
className={style.button_view_container}
>
<MoveViewButton ref="button0" id={style.first_button} className={style.button_view} onClick={() => this.animationPrepare(0)} />
<MoveViewButton ref="button1" className={style.button_view} onClick={() => this.animationPrepare(1)} />
</MoveViewButtonContainer>
</div>
<div
id={style.text_wrapper}
>
<TextFirstLine
ref="textFirstLine"
animation={this.state.textAnimation}
>
FirstLine
</TextFirstLine>
<TextSecondLine
ref="textSecondLine"
animation={this.state.textAnimation}
>
SecondLine
</TextSecondLine>
</div>
<ViewImage
ref="viewImage"
animation={this.state.imageAnimation}
alt="here an image"/>
</div>
);
}
}
const rootElement = document.getElementById("root");
ReactDOM.render(<App />, rootElement);
任何提示都会很棒, 谢谢