Explain React - how does this simple TODO list work?

This is from the REact documentation…I don’t understand how the input element’s value gets added to the items array, and why the entire app doesn’t end up as a list of input elements.

Can anyone explain this to me?

http://jsfiddle.net/2h6th4ju/

Studying it more…it IS a list of input elements, but how does it know to not re-render the old todo input itmes…is it because there is no ‘set state’?

This is React’s “secret sauce”. Every time there is a state change, it compares the old state to the new state and makes the fewest possible changes to the DOM to render the new state.

Quoting from this nice overview of the advantages of React:

React creates its own virtual DOM where your components actually live. This approach gives you enormous flexibility and amazing gains in performance because React calculates what changes need to be made in the DOM beforehand and updates the DOM tree accordingly. This way, React avoids costly DOM operations and makes updates in a very efficient manner.

Check out this SO discussion for more info about how Virtual DOMs work.

And one more explanation, for good measure.

1 Like

I thought I understood virtual DOM, but this is a weird little app. Maybe because it is so weird it demonstrates the idea.

on setState, it should rerender. on render, it loops through the {items} array which is NOT a list of text…it’s a list of numbers, is that correct? So i = 0 to 4, output an input box. Does it just say "I’ve already got 0 through 3 on the DOM so I’ll just add #4. and leave the other stuff there?

The description of “dirty” kind of fits because it’s like not sweepign the floor.

I am still not 100% sure why there is not a list of 5 empty input boxes with the placeholder text, but trying to wrap min mind around it.

On “How the input element’s value gets added to the items array”:
It is not being added. When you click the button, the app adds empty input box and nothing more. User input remains because previous input boxes are not re-rendered.

On your follow up question, “setState should re-render but why is it preserving previous input elements?”:
React uses key attribute to determine re-rendering of elements. In this example, changing the ‘count’ state does not affect the key of previously generated list items. Hence, React does not re-render them.
However, if keys were assigned randomly, React will re-render the previous list items. You can check this simply by changing the key to a random number.

I’m not following the question, "Why the entire app doesn’t end up as a list of input elements."
Why should they be?

I’m not following the question, “Why there are not a list of 5 empty input boxes”.
There will be 5 empty input boxes, if, you click the button enough times.

It might be helpful to walk through the code for the TextBoxList component:

The first time through we have a state variable called count that is set to 1.

var TextBoxList = React.createClass({
  getInitialState: function() {
    return {count: 1};
  },

The add function will increment the value of count by one each time it is called.

  add: function() {
    this.setState({count: this.state.count + 1});
  },

The render function starts by creating an empty array called items.

  render: function() {
    var items = [];

then loops count times. So, the first render, the loop runs only once, since count is 1.

    for (var i = 0; i < this.state.count; i++) {

adding an input element to the items array each iteration.

      items.push(
        <li key={i}>
          <input type="text" placeholder="change me!" />
        </li>
      );
    }

and finally rendering our items array along with an add button

    return (
      <ul>
        {items}
        <input type="button" value="Add an item" onClick={this.add} />
      </ul>
    );
  }
});

When the add button is clicked.The process starts over and count is set to 2 meaning that we will now add two input elements to our items array.

React compares this new state (2 input elements) to the previous state (1 input element) and notices that only 1 input has changed. So, it adds only 1 input to the actual DOM, preserving the previous input since it hasn’t changed.

Each time we click the add button, React notices that there is only 1 new input so it leaves the others and only adds the new one.

Hope that helps.

1 Like

this is really helplful, thank you.

As for the following 2 paragraphs in your answer, both of those questions have been answered with this one. Thanks!

1 Like

Thanks for taking the time to type that all out! It’s making more and more sense.

1 Like

are there any books that explain React and Javascript just like you explained it?

@EgoDominusVos

Wes Bos has some courses that do a good job of breaking down code and explaining it.

Start with his free JavaScript30 course and then consider buying his React for Beginners course if you like his teaching style.

Also, the React docs are quite good now, worth rereading if you haven’t looked in a while.

1 Like

Thanks Bill … Wes’ React course looks cool

1 Like

I’m doing his javascript30 course, just as filler for days when I want a break from FCC projects which these days feel pretty time consuming (react & full stack). There is always more to learn and wes’ projects are short and sweet.

1 Like

The way you explained this is so clear. I wonder if you do tutorials

Thank you!

Eventually, I plan to start doing some online courses. At the moment, I just have a weekly newsletter that I send out which you can sign up for at https://devmastery.com

You can also read my stuff on Medium (including on the FCC blog)

And you can also watch a recent webinar of mine where I answered a ton of questions from developers.

just to add something to the mix and make your head hurt a little more xD!!!
check out this
more accurately the item > shouldComponentUpdate in action. that bit gives you a overview of how will it update and how the guard method( that’s what is called in various frameworks api’s) should work.