React Transition Group:能否将类名应用到子组件内部元素?
如何将React Transition Group的CSSTransition类名应用到子组件的内层元素?
问题场景
当前代码结构如下:
父组件
<TransitionGroup> { items.map((child, index) => { // 其他逻辑 return ( <CSSTransition key={index} nodeRef={items.nodeRef} timeout={1000} classNames={'item'}> <ChildComponent key={index} item={item} /> </CSSTransition> }) } </TransitionGroup>
子组件
<div> {/* 动画类名当前会附加到这里 */} <div> {/* 希望动画类名附加到这个内层div上 */} {/* 组件内容 */} </div> </div>
需求是保留外层布局div的前提下,让CSSTransition的进入/退出类名作用于子组件的内层div,而非外层。
可行解决方案
方案1:通过forwardRef传递内层元素的Ref给父组件的CSSTransition
利用React的forwardRef让子组件暴露内层div的引用,父组件将该引用传递给CSSTransition的nodeRef属性,这样CSSTransition就会把动画类名直接应用到内层元素上。
修改后的子组件
import { forwardRef } from 'react'; const ChildComponent = forwardRef(({ item }, ref) => { return ( <div> {/* 保留外层布局div */} <div ref={ref}> {/* 内层div,动画类名将作用于此 */} {/* 组件内容 */} {item.content} </div> </div> ); });
修改后的父组件
import { TransitionGroup, CSSTransition } from 'react-transition-group'; import { useRef } from 'react'; const ParentComponent = ({ items }) => { return ( <TransitionGroup> {items.map((item, index) => { const innerElementRef = useRef(null); return ( <CSSTransition key={index} nodeRef={innerElementRef} timeout={1000} classNames="item" > <ChildComponent ref={innerElementRef} item={item} /> </CSSTransition> ); })} </TransitionGroup> ); };
方案2:将CSSTransition移入子组件内部
把CSSTransition逻辑封装到子组件中,让子组件直接包裹内层元素,同时接收TransitionGroup传递的动画控制props(如in、key等)。
修改后的子组件
import { CSSTransition } from 'react-transition-group'; const ChildComponent = ({ item, ...transitionProps }) => { return ( <div> {/* 保留外层布局div */} <CSSTransition {...transitionProps} classNames="item" timeout={1000}> <div> {/* 内层div,动画类名将作用于此 */} {/* 组件内容 */} {item.content} </div> </CSSTransition> </div> ); };
修改后的父组件
import { TransitionGroup, CSSTransition } from 'react-transition-group'; const ParentComponent = ({ items }) => { return ( <TransitionGroup> {items.map((item, index) => { return ( <CSSTransition key={index} timeout={1000}> <ChildComponent item={item} /> </CSSTransition> ); })} </TransitionGroup> ); };
注:如果之前尝试移入CSSTransition未成功,大概率是没有正确透传TransitionGroup传递的
in等核心props,通过...transitionProps将所有动画控制props传递给子组件内部的CSSTransition即可解决。
总结
两种方案都可以实现需求,方案1更适合需要在父组件统一控制动画逻辑的场景,方案2则更利于子组件的封装和解耦。
内容的提问来源于stack exchange,提问作者Darren Chiang
相关产品推荐
相关产品推荐

