简体   繁体   中英

ReactJs - How to update state in array?

I'm creating a Page Builder with React.

I have a component which contains the structure of the page.

var LayoutPage = React.createClass({

getInitialState: function getInitialState() {
    return {
      items: {
          '78919613':{
              id: '78919613',
              component : 'OneColumn',
              cols:{
                  '565920458':{
                      id: '565920458',
                      content:{
                          '788062489':{
                              id: '788062489',
                              component : 'Text',
                              params: 'Lorem ipsum'
                           },
                           '640002213':{
                              id: '640002213',
                              component : 'Text',
                              params: 'Lorem ipsum'
                           }
                      }
                   }
               }
           }
        }
    };
},
.....
});

I have a system with drag'n drop to put a new element on the page and it works. But when the new element is dropped I want to update the state to add a new item in the array.

So how can I push a new item ? I did a test with that :

this.state.items.push({.....});

But I have an error :

TypeError: this.state.items.push is not a function

Can you help me ?

Thank you.

Instead of using an object in your state you should change it to the array like below :

    this.state = {
        items: [ // items array
        {
          id: 1,
          name: "Stack"
        },
        {
          id: 2,
          name: "Overflow"
        }],
        count: 3,  // another state
        textValue : ''  // and this is state too
    }

Where the items it's an array of objects. And then you will be able to add new items to an array.

const newItem = {
    id : this.state.count,
  name: this.state.textValue
};
const newArr = this.state.items.concat(newItem);
this.setState({
    items: newArr,
    textValue: '',
    count: this.state.count + 1
})

The whole example is here .

I hope it will help you!

Thanks

You'll start to get headaches if you directly mutate the state of your application. If you forget to call this.setState then it won't re-render!

Assuming you can't use an array (which would be easier), then you'll have to generate a unique key if you want to add another item to the object.

// create a new copy of items based on the current state
var newItems = Object.assign({}, this.state.items),
    newItem = { id: '', component: '', cols: {} },
    uniqueId = generateUniqueId();

// safely mutate the copy
newItems[uniqueId] = newItem;

// update the items property in state
this.setState({ items: newItems });

This is even easier with ES7/Babel .

const newItem = { id: '', component: '', cols: {} },
      uniqueId = generateUniqueId(),
      items = { [uniqueId]: newItem, ...this.state.items };

this.setState({ items });

You can generate a similar unique ID to the one you have there using Math.random .

function generateUniqueId() {
  // removing leading '0.' from number
  return Math.random()
    .toString()
    .slice(3);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM