我对GSAP提出了一个问题并做出反应,正如我从一些教程中读到的那样,他们都使用react-transition-group,并且他们中的许多人都使用ref作为GSAP的替代选择器,如果我在我的情况下使用ref ,整个页面都会动画,我只想要一个元素来设置动画,所以我使用id选择器,它就像这样完美地工作
import React from 'react';
import { TweenMax } from 'gsap';
import uuid from 'uuid';
import '../styles/homePage.css';
class HomePage extends React.Component{
startAnimation=(pic)=>{
TweenMax.from(`#${pic.id}`, 1, {
opacity: 0,
x: -100,
y: -100
});
}
render(){
const PicsNum = 15;
let pics = [];
let pic = {};
for (let i = 5; i <= PicsNum; i++) {
const picPath = `/pictures/testingPics/${i}.jpg`
pic={id:`a${uuid()}`, picPath}
pics.push(pic)
}
const renderPics = pics.map((p, i) => (
<div
key={i}
className='img-container'
>
<img src={p.picPath} className='pic' id={p.id}/>
<button onClick={()=>{this.startAnimation(p)}}>click</button>
</div>
))
return (
<div className='pics'>
{renderPics}
</div>
)
}
}
export default HomePage;
有人可以告诉我为什么我应该使用react-transition-group,如果我想使用没有它的动画会出现什么问题呢?非常感谢你
答案 0 :(得分:1)
所以,你在这里做的事情对于简单的动画来说绝对没问题。只有当你的逻辑和动画开始变得越来越复杂时,你才会发现它有缺点。
随着逻辑/动画复杂性的增加,您可能遇到的主要问题是您实际上现在正在使用两个不同的库来定位dom。 React希望完全控制dom,以便它可以做到这一点。然而,GSAP现在也在寻找dom中的一个元素并控制它的状态,并且反应不知道如此,现在事情可能会失去同步。当用户已经触发淡出时,React可能会重新渲染该组件,将不透明度重置为1。
React-transition-group可以成为简化处理动画组件进出的有用工具,但它不是唯一的方法,也不是所有动作的结束动画,所以感觉不像你有来使用它。或许可以研究一下如何简化您为每个想要动画制作的组件编写的代码。 (它为您提供了进出动画的特定生活方式,以及用于删除组件后期动画的回调,这是组件转换的大部分样板。)
在我提到的第一个问题的情况下,Transition-group在这里非常有用,因为你的所有动画代码都包含在它提供的帮助器中,所以反应知道:1)你的动画......除了你之外什么都不做已经完成... 2)现在你已经完成了,我又回到了控制之中。
但 过渡组之外的其他选项来处理dom控制的这种二分法:
你可以尝试超级智能并声明它...使用refs访问元素并将它们传递给由state / props触发和控制的gsap动画。
但是有一些出色的图书馆可以避免担心状态和动画以及像https://github.com/azazdeaz/react-gsap-enhancer
这样的事情。这是一个很棒的高阶组件,它可以确保gsap对元素所做的任何更改都会在反应重新呈现和状态更改时被注意到并保留。
老实说,这有点神奇,让使用react和GSAP非常愉快。
还要回答你关于'为什么引用'的问题而不是有用的问题'只需将ID的字符串传递给gsap函数':
这里没有错误的权利。 ref in react将在内存中存储指向该Dom元素的指针。使其方便查找。它的主要优点是对该元素的引用不会在反应重新呈现时到期。如果您使用GetElementById手动选择元素,并且该Dom节点被反应重新渲染替换,那么您的变量引用将变为未定义,您将不得不再次调用GetElementById。 GetElementById在性能方面非常便宜,它不是关于性能,只是避免在每次重新渲染后必须“找到”对Dom元素的新引用的样板。