react-transition-group动画库

这个库包括3个组件:Transition,CSSTransition,TransitonGroup,今天做项目刚好用到了Transition组件,记录一下使用过程中的总结,另外两个组件用到了再做介绍。或者移步到react 官网动画库(react-transition-group)的新写法

CSS3的transition属性

该属性可以对元素里面的一个属性设置过渡动画,比如:transition: width 2s;

祥见:CSS3 transition 属性

  • transition-property 规定设置过渡效果的 CSS 属性的名称。
  • transition-duration 规定完成过渡效果需要多少秒或毫秒。
  • transition-timing-function规定速度效果的速度曲线。
  • transition-delay定义过渡效果何时开始。

Transition的属性

元素动画在出现和消失时各有3个阶段,可以为这些属性绑定自定义函数:

  • onEnter:进入(出现)开始时执行
  • onEntering:进入(出现)过程中执行
  • onEntered:进入(出现)结束执行
  • onExit:离开(消失)时执行
  • onExiting:离开(消失)过程中执行
  • onExited:离开(消失)结束执行

其他属性介绍:

  • addEndListener:属性可以监听出现的3个阶段执行完成或消失的3个阶段执行完成时执行该函数监听的自定义函数。
  • unmountOnExit:为true 代表退出的时候移除dom,也就是该元素dom动画执行完后直接删除该元素节点
  • appear:渲染的时候就直接执行动画,默认false
  • enter:设为true后,动画进入(出现)的三个阶段,前两个阶段onEnter,onEntering先执行,然后延迟一段时间再执行onEntered,可以简单的理解为动画进入(出现)时有个延迟
  • exit:设为true后,动画离开(消失)的三个阶段,前两个阶段onExit,onExiting先执行,然后延迟一段时间再执行onExited,可以简单的理解为动画离开(消失)时有个延迟
  • timeout:为上面的appear,enter,exit设置延迟时间
  • in:动画进入(出现),离开(消失)交替执行,点一下动画生效,再点一下动画失效

使用方法

<Transition>标签可是设置上面那些属性。标签内容包裹一个箭头函数,该函数有一个参数state(参数名随意设置),返回值就是要实现动画效果的元素,该元素可以设置style样式。

案例一

此案例是我测试的案例,通过下拉框的透明度实现一个下拉框出现和消失的效果:

import React from 'react';import {connect} from 'react-redux';//受到路由管控import {withRouter} from 'react-router-dom';import {Icon} from 'antd';//过渡动画import Transition from 'react-transition-group/Transition';//duration设置延迟时间,下面的timeout属性使用const duration = {         appear:3000,         enter: 3000,         exit: 3000};//默认样式const  defaultStyle = {        //ease-in-out规定以慢速开始和结束的过渡效果        transition:`opacity ${3000}ms ease-in-out`,        opacity:0,    };//过渡样式const  transitionStyles = {        //进入时2,3阶段动画,如果设置了延迟时间,会发现出现时立即透明度百分之"0.5",然后三秒后透明度才为"1"        //因为延迟时间timeout属性设置的``enter:3000``会在第三阶段生效        entering:{opacity: 0.5},        entered:{opacity:1},        //离开时2,3阶段        exiting: {opacity: 0.5},        exited: {opacity: 0}    };// 三个进入状态的事件,可以做你想做的事情let onEnter = (node, isAppearing) => {    console.log(isAppearing,node, 'onEnter')};let onEntering = (node, isAppearing) => {    console.log(isAppearing,node, 'onEntering')};let onEntered = (node, isAppearing) => {    console.log(isAppearing,node,'onEntered')};//测试动画执行过程,何时结束let done =() => {    console.log('结束了')};// 三个退出的状态的事件let onExit = (node) => {    console.log('onExit')};let onExiting = (node) => {    console.log('onExiting')};let onExited = (node) => {    console.log('onExited',node)};let addaddEndListener = (node) => { //原生时间transition运动的事件    node.addEventListener('transitionend', this.done, false);};class NavTop extends React.Component{    constructor(props,context){        super(props,context);        this.state = {          in:false        };    }    render() {        return <header className='headerNavBox'>            {/*首页导航*/}            <div className='homeBox'>                <div className='baseBox clearfix' >                    <h1 className='logo' >大鱼资源网</h1>                    <Icon className='icon' type='bars' style={{                    fontSize:'.6rem'                    }} onClick={ev=>{                        this.setState({                            in:!this.state.in                        })                    }} />                </div>                {/*下拉条,过渡动画*/}                <Transition                    onEnter={onEnter}                    onEntering={onEntering}                    onEntered={onEntered}                    onExit={onExit}                    onExiting={onExiting}                    onExited={onExited}                    addEndListener={this.addaddEndListener}//添加动画执行完后执行的函数                    unmountOnExit={true}//动画消失后,元素dom节点也消失                    appear={false}//组件渲染就出现动画                    enter={true}//动画效果出现时延迟,默认是true                    exit={true}//动画效果消失时延迟                    timeout={duration}//设置延迟时间,准确的说应该是动画出现和消失的第三阶段延迟时间,因为前两个阶段会立即执行                    in={this.state.in} >                    {                        state => {                            //打印状态变化分别是onEnter,onEntering...等6种,通过此处可以看出延迟时间是在第三阶段生效,前两个阶段会立即执行                            console.log(state,'###',{...defaultStyle, ...transitionStyles[state]}, '###');                            return <ul className='filterBox' style={{                                ...defaultStyle,                                //根据state的变化,过渡动画的透明度随着变化                                ...transitionStyles[state]                            }} >                                <li>全部课程</li>                                <li>react课程</li>                                <li>vue课程</li>                                <li>小程序课程</li>                            </ul>                        }                    }                </Transition>            </div>        </header>;    }}export default withRouter(connect()(NavTop));

案例一结束。

案例二

//自己简单的封装了一个,该有的参数都由了,可以自行粘贴在自己的代码里面去试试。class Fade extends React.Component {  constructor(props) {    super(props);  }  done =() => {    // console.log('结束了')  }  addaddEndListener = (node) => { //原生时间transition运动的事件    node.addEventListener('transitionend', this.done, false);  }  // 三个进入状态的事件,可以做你想做的事情  onEnter = (node, isAppearing) => {    console.log(isAppearing, 'onEnter')  }  onEntering = (node, isAppearing) => {    console.log(isAppearing, 'onEntering')  }  onEntered = (node, isAppearing) => {    console.log(isAppearing, 'onEntered')  }  // 三个退出的状态的事件  onExit = (node) => {    console.log('onExit')  }  onExiting = () => {    console.log('onExiting')  }  onExited = () => {    console.log('onExited')    this.props.self()  }  render() {    const { in: inProp, dur} = this.props;    const defaultStyle = {      transition: `transform ${300}ms ease-in-out, opacity ${300}ms ease-in-out`,      transform: 'translateX(100px)',      opacity: '0'    }    const transitionStyles = {      entering: { transform: 'translateX(100px)', opacity: '0'},      entered:  { transform: 'translateX(0px)', opacity: '1' },      exiting: {transform: 'translateX(0px)', opacity: '1'},      exited: {transform: 'translateX(0px)', opacity: '0'}    };    const duration = {      enter: 300,      exit: 300,    }    // 上面的都是基本参数,样式的转变以及时间的设定,具体的可以看官网文档    // 样式也可以写成className 例如<MyComponent className={`fade fade-${status}`} />    return (      <Transition         onEnter={this.onEnter}        onEntering={this.onEntering}        onEntered={this.onEntered}        onExit={this.onExit}        onExiting={this.onExiting}        onExited={this.onExited}        addEndListener={this.addaddEndListener}         in={inProp}         unmountOnExit={false} // 为true 代表退出的时候移除dom        appear={true} // 为true  渲染的时候就直接执行动画,默认false,        timeout={duration}      >        {          state => {            console.log(state, '###') //你可以很直观的看到组件加载和卸载时候的状态            return(              <div style={{                ...defaultStyle,                ...transitionStyles[state]              }}>                {this.props.children}              </div>            )          }        }      </Transition>    );  }}

案例二结束。

参考网址

官方案例

react官网动画库(react-transition-group)的新写法