React slowly with lots of text fields (but not text input fields)

With a lot of text fields, my (albeit large) form becomes sluggish.

However, instead of text input fields, everything is fast.

I created two flattened minimum test files: one with text fields and one with input fields. Press the toggle button to show / hide the group to see the problem. With Chrome, at least the group is switching very slowly in the textarea version.

2500 text fields: http://jsbin.com/wudujusoji/edit?html,js,output

2500 text input fields: http://jsbin.com/rezudotojo/edit?html,js,output

What am I doing wrong here? Shouldn't text fields and text fields be about the same?

+4
source share
1 answer

Let make the test reasonable and add toComponentUpdate to the input component in each.

var Input = React.createClass({
  shouldComponentUpdate: function(nextProps){
    return nextProps.value !== this.props.value;
  },

console.time() well, if you are trying to measure some math or the like, but to really see what is happening here, we need to use a profiler.

Let's start with <input>s. I have done this several times, and it is always about 14 ms for me.

The gray bar on the right with the inscription "(program)" is a browser that does its own job after JS returns. Here it takes about 17 ms to prepare for rendering. After that, he stands idle, where he does almost nothing but painting. Cool, that's not bad considering the number of elements.

profiling the input example in chrome dev tools

. 30 , , , . , 500 .

profiling the textarea example in chrome dev toolsanother profile of textareayet another textarea profile

, React -, , () MutationObserver.

var mObserver = new MutationObserver(function(mutations) {
  mutations.forEach(function(mutation, i) {
    console.log('mutation ' + i + ': ' 
                + mutation.type 
                + ', at ' 
                + mutation.target.parentNode.tagName 
                + ' > ' 
                + mutation.target.tagName 
                + '[' 
                + [].indexOf.call(mutation.target.parentNode.children, mutation.target) 
                + ']'
                + ', on attribute ' + mutation.attributeName
                + ', from ' + mutation.oldValue 
                + ' to ' + mutation.target.getAttribute(mutation.attributeName)
               );

  });    
});
var moConfig = { attributes: true, childList: true, characterData: true, subtree: true };

React.render(React.createElement(Editor, null),
    document.querySelector('.editor'), 
    function(){
        var root = document.getElementById('root');
        if (!root) throw new Error('no root');
        mObserver.observe(root, moConfig);
    }
);

:

mutation 0: attributes, at DIV > DIV[0], on attribute class, from null to category
mutation 1: childList, at DIV > BUTTON[0], on attribute null, from null to null

, ... , div, 500 . , , .


, " 2000 , X" 2000 ; X (, React) .

, 5000 , ?

+7

All Articles