react 学习 - 4 react-transition-group 插件

在 react 里,有个专门的库是用来处理动画的,那就是 react-transition-group

js 部分如下

import React, { Component, Fragment } from "react";
import { CSSTransition } from "react-transition-group"; // 引入组件
import "./style.css";

class TransitionGroup extends Component {
  constructor(props) {
    super(props);
    this.state = {
      show: true
    };
    this.clickBtn = this.clickBtn.bind(this);
  }
  render() {
    const { show } = this.state;
    return (
      <Fragment>
         <CSSTransition
          in={show} 		// 切换 class 的控制器
          timeout={500}		// 过渡时间
          classNames="fade"	// 过渡 class 名称前缀
          unmountOnExit		// 如果需要移除该 DOM,可以加此属性
          onEntered={el => (el.style.color = "blue")} // 动画钩子
          appear={true} 	// 第一次显示的时候是否做动画1
        >          
          <div className="box">我是一个盒子</div>
        </CSSTransition>
        <button className="btn" onClick={this.clickBtn}>
          点击我
        </button>
      </Fragment>
    );
  }

  clickBtn() {
    this.setState(prev => ({
      show: !prev.show
    }));
  }
}

export default TransitionGroup;

css 部分如下

.box {
  width: 100px;
  height: 100px;
  background: lightblue;
  color: white;
  font-size: 12px;
  line-height: 100px;
  text-align: center;
  border-radius: 4px;
  transition: all 0.4s ease;
}

.btn {
  width: 100px;
  line-height: 30px;
  border: none;
  background: lightcoral;
  margin-top: 10px;
  border-radius: 4px;
  color: white;
  outline: none;
}
/* 入场开始 首次进场开始 */
.fade-enter, .fade-appear {
  opacity: 0;
}
/* 入场过程 首次进场过程 */
.fade-enter-active, .fade-appear-active {
  opacity: 1;
  transition: all 0.5s ease;
}
/* 入场结束 */
.fade-enter-done {
  opacity: 1;
}
/* 出场开始 */
.fade-exit {
  opacity: 1;
}
/* 出场过程 */
.fade-exit-active {
  opacity: 0;
  transition: all 0.5s ease;
}
/* 出场结束 */
.fade-exit-done {
  opacity: 0;
}

这样,一个动画就完成了

如果动画是循环的组件,可以使用 TransitionGroup

js 部分如下

import React, { Component, Fragment } from "react";
import { TransitionGroup, CSSTransition } from "react-transition-group";
import "./ref-comp.css";

class InputComp extends Component {
  constructor(props) {
    super(props);
    this.state = {};
  }
  render() {
    const { inputEle, changeInput, value } = this.props;
    return <input ref={inputEle} onChange={changeInput} value={value} />;
  }
}

class ListItem extends Component {
  constructor(props) {
    super(props);
    this.state = {};
  }
  shouldComponentUpdate(prevState) {
    return prevState !== this.props;
  }
  render() {
    const { item, index, removeItem } = this.props;
    return <li onClick={removeItem.bind(this, index)}>{item}</li>;
  }
}

class RefComp extends Component {
  constructor(props) {
    super(props);
    this.state = {
      list: ["123", "234"],
      inputValue: ""
    };
    this.inputEle = null;
    this.removeItem = this.removeItem.bind(this);
  }
  render() {
    return (
      <Fragment>
        <InputComp
          inputEle={el => (this.inputEle = el)}
          changeInput={this.changeInput}
          value={this.state.inputValue}
        ></InputComp>
        <button onClick={this.addList}>增加</button>
        <ul>
          <TransitionGroup>{this.getList()}</TransitionGroup>
        </ul>
      </Fragment>
    );
  }

  getList = () => {
    return this.state.list.map((item, index) => {
      return (
	    // 暂时不知道怎么做移除的退出动画,先留个标注,后面解决了再回来补上。
        <CSSTransition
          key={index}
          in={true}
          classNames="fade"
          timeout={500}
          appear={true}
        >
          <ListItem index={index} item={item} removeItem={this.removeItem} />
        </CSSTransition>
      );
    });
  };

  removeItem = index => {
    let list = [...this.state.list];
    list.splice(index, 1);

    this.setState({ list });
  };

  changeInput = () => {
    let value = this.inputEle.value;

    this.setState(_ => ({
      inputValue: value
    }));
  };

  addList = () => {
    this.setState(prev => ({
      list: [...prev.list, this.state.inputValue],
      inputValue: ""
    }));
  };
}

export default RefComp;

css 部分如下

.fade-enter,
.fade-appear {
  opacity: 0;
}

.fate-enter-active,
.fade-appear-active {
  opacity: 1;
  transition: all 0.5s ease;
}

.fade-exit {
  opacity: 1;
}

.fade-exit-active {
  opacity: 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值