Home > Net >  Unable to remove objects from array , react.js
Unable to remove objects from array , react.js

Time:04-06

I'm trying to remove an item from a childArray that is nested into another Array.

This is How I'm trying.

const childArrayHandler = (childData, sub, questionId, data, btnId) => {
    // Manage color change on click
    const isInList = selectedBtnList.some((item) => item === btnId)
    if (isInList) {
      onSelectedBtnListChange(selectedBtnList.filter((item) => item !== btnId))
    } else {
      onSelectedBtnListChange([...selectedBtnList, btnId])
    }

    // Manage childData Array 
    // copy data to mutable object
    const currentChildData = [...childData]
    const hasId = currentChildData.find(({ id }) => sub.id === id)

    if (!hasId) {
      // add item to childArray if same index is not available in the childArray
      const newChild = { id: sub.id, sub_question: sub.sub_question, weightage: sub.weightage }
      currentChildData.push(newChild)
      setChildDataOnChange((current) => [...current, newChild])
    } else if (hasId) {
      // remove item from childArray if same index is available in the childArray
      const indexOfChild = currentChildData.indexOf(hasId)
      // console.log('currentChildData', currentChildData, 'indexOfChild', indexOfChild)
      currentChildData.slice(indexOfChild, 1)
      setChildDataOnChange(currentChildData)
    }

    const newData = [...data]

    // find parent of the child
    const parent = newData.find(({ parentId }) => questionId === parentId)

    // find index of parent
    const indexOfParent = newData.indexOf(parent)
    // update data with child related to parent
    newData[indexOfParent].child = currentChildData
    onDataChange(newData)
    localStorage.setItem('deviceReport', JSON.stringify(newData))
  }

The problem is in the else if block, I want if there's an index of object available in the child then it should remove it from the array. As far as I can see I'm using the correct approach as other articles suggested to handle but missing something which I cant see right now. But not able to find the proper result. If I console it doesn't change anything. means don't remove any item from the array if the index is already is there.

So how can I fix this, or what might be doing wrong, is there any other way to do it please also mention it? Thanks

CodePudding user response:

You have the problem with this slice

currentChildData.slice(indexOfChild, 1)

It does not initialize a new array for you (React's immutability)

The fix could be

currentChildData = currentChildData.slice(0, indexOfChild).concat(currentChildData.slice(indexOfChild   1))

If you feel it's too complicating, you can use filter instead

currentChildData = currentChildData.filter((item) => item !== hasId) //`hasId` is your found item with `find`

The 2nd problem here is

newData[indexOfParent].child = currentChildData

You cannot assign a value to a mutate object

The proper way should be

newData = newData.map((item) => item === parent ? {...item, child: currentChildData} : item)

The full code

const childArrayHandler = (childData, sub, questionId, data, btnId) => {
    // Manage color change on click
    const isInList = selectedBtnList.some((item) => item === btnId)
    if (isInList) {
      onSelectedBtnListChange(selectedBtnList.filter((item) => item !== btnId))
    } else {
      onSelectedBtnListChange([...selectedBtnList, btnId])
    }

    // Manage childData Array 
    // copy data to mutable object
    let currentChildData = [...childData]
    const hasId = currentChildData.find(({ id }) => sub.id === id)

    if (!hasId) {
      // add item to childArray if same index is not available in the childArray
      const newChild = { id: sub.id, sub_question: sub.sub_question, weightage: sub.weightage }
      currentChildData.push(newChild)
      setChildDataOnChange((current) => [...current, newChild])
    } else  {
      // console.log('currentChildData', currentChildData, 'indexOfChild', indexOfChild)
      currentChildData = currentChildData.filter((item) => item !== hasId)
      setChildDataOnChange(currentChildData)
    }

    //let newData = [...data]

    // find parent of the child
    //const parent = newData.find(({ parentId }) => questionId === parentId)

    // update data with child related to parent
    //newData = newData.map((item) => item === parent ? {...item, child: currentChildData} : item)

    //shorter version
    const newData = data.map((item) => item.parentId === questionId ? {...item, child: currentChildData} : item)
    
    onDataChange(newData)
    localStorage.setItem('deviceReport', JSON.stringify(newData))
  }
  • Related