Skip to content

React animation difficult to write? Try transformjs of react version

dntzhang edited this page Dec 30, 2016 · 2 revisions

Introduction

transformjshas a wide range of applications out field of react. So react technology stack students can use it? The answer is possible.Junexie has create areact version

Animation implementation

there are three ways of traditional web animation

  • CSS3 Only :transition/animation+transform(such as animate.css)
  • JS + CSS3 transition or animation:Like the first one here, just add or remove animations via class add and remove in JS
  • Pure JS control timeline: the first and second are built-in timeline in CSS, using setInterval / setTimeout / requestAnimationFrame constantly modify the DOM style attributes to generate animation

In React

Use CSS3

  • Use ReactCSSTransitionGroup
  • Related animation class have corresponding state, modify state equivalent to increase or remove class, also equivalent to JS in add class and remove class to increase or remove the corresponding animation

Pure JS control timeline

  • Still use setInterval / setTimeout / requestAnimationFrame, modify a state value, and then mapped to component on the style.

It is obvious here that scenario 1 and scenario 2 can deal with simple scenarios (such as no prop change callbacks, etc.), Scenario 3 programmable maximum, most flexible, suitable for complex animation scene or withstand complex interactive scenarios.

Install

npm install css3transform-react

API

//set "translateX", "translateY", "translateZ", "scaleX", "scaleY", "scaleZ", "rotateX", "rotateY", "rotateZ", "skewX", "skewY", "originX", "originY", "originZ"
render() {
    return (
        <Transform
          translateX={100}
          scaleX={0.5}
          originX={0.5}>
          <div>sth</div>
        </Transform>
    );
}

// you can also use other porps, such as "className" or "style"
render() {
    return (
        <Transform
          translateX={100}
          className="ani"
          style={{width: '100px', background: 'red'}}
          <div>sth</div>
        </Transform>
    );
}

Through the above statement, you can set or read: "translateX", "translateY", "translateZ", "scaleX", "scaleY", "scaleZ", "rotateX", "rotateY", "rotateZ", "skewX", "skewY", "originX", "originY", "originZ"!

So easy!

Usage

import React, { Component } from 'react';
import { render } from 'react-dom';

import Transform from '../../transform.react.js';

class Root extends Component {

  constructor(props, context) {
    super(props, context);

    this.state = {
      el1: {rotateZ: 0},
      el2: {rotateY: 0}
    };

    this.animate = this.animate.bind(this);
  }

  animate() {
    this.setState({
      el1: {rotateZ: this.state.el1.rotateZ + 1},
      el2: {rotateY: this.state.el2.rotateY + 1}
    }, () => {
      requestAnimationFrame(this.animate);
    });

  }

  componentDidMount() {
    setTimeout(this.animate, 500);
  }

  render() {
    return (
      <div>
        <Transform rotateZ={this.state.el1.rotateZ} className="test" style={{'backgroundColor': 'green'}}>
          transformjs
        </Transform>

        <Transform rotateY={this.state.el2.rotateY} className="test" style={{'backgroundColor': 'red', 'left': '200px'}}>
          transformjs
        </Transform>

      </div>
    );
  }
}

render(
	<Root />,
	document.getElementById('root')
);

for more detail info you can visit here :https://github.com/AlloyTeam/AlloyTouch/blob/master/transformjs/react/example/src/index.jsx

Demo

http://alloyteam.github.io/AlloyTouch/transformjs/react/example/

Performance Comparison

Because there will be a diff progress of react, then apply diff to DOM state. state changing will not replace all html such as calling innerHTML. so the browser rendering is still very cheap, but the time-consuming process of diff in JS or need to profiles . if time cost serious, but not in webworker , UI will cause stuck thread running Carlton, interactive delay etc.. So take a look at the time-consuming CPU is still necessary. Comparison between above presentation and traditional presentationDirect manipulation of DOM mode.This is the traditional way:

var element1 = document.querySelector("#test1");
Transform(element1);
...
...
function animate() {
    element1.rotateZ++;
    ...
    requestAnimationFrame(animate);
}

animate();

See the result in chrome profiles,Look at the total time first

react:

传统方式:

  • React:In 8739ms CPU time consuming 1686ms
  • Traditional way:In 9254ms CPU time consuming 700ms

In the absence of profiles can imagine that react is bound to be slower, because state changes to go through the react life cycle again, but can see react time-consuming or acceptable range. However, we still want to find slow function. So which function is dragging back in the use of the transformjs react version? Expand profiles tree can see:

That's it.

/**
	   * Reconciles the properties by detecting differences in property values and
	   * updating the DOM as necessary. This function is probably the single most
	   * critical path for performance optimization.
	   *
	   * TODO: Benchmark whether checking for changed values in memory actually
	   *       improves performance (especially statically positioned elements).
	   * TODO: Benchmark the effects of putting this at the top since 99% of props
	   *       do not change for a given reconciliation.
	   * TODO: Benchmark areas that can be improved with caching.
	   *
	   * @private
	   * @param {object} lastProps
	   * @param {object} nextProps
	   * @param {?DOMElement} node
	   */
	  _updateDOMProperties: function (lastProps, nextProps, transaction) {

Open the corresponding code can see. Notes have been written this is the focus of optimization.

Start using transformjs of react version

HomePage:http://alloyteam.github.io/AlloyTouch/transformjs/

Github:https://github.com/AlloyTeam/AlloyTouch/tree/master/transformjs Any questions and comments are welcome to create new issue to us.