1

I found lot's of solutions online, but I've done my best for a week and found no way to solve it. I believe the fault to be the reducer ADD_GOAL, that is why i left it empty.

Thanks alot! :)

I want to add objects to the goals array. I always want to initialize goals empty, but I want to be able to add and remove objects freely. The idea is to save the objects like this.

{
  list: {
    '0': {
      id: 0,
      dueDate: 'By May 28th I Will have: ',
      goals: [
        {0: {...}
         1: {...}
         3: {...}
}
      ]
    }
   '1':{
      id: 0,
      dueDate: 'By June 31st I Will have: ',
      goals: [
        {2: {...}
         4: {...}
  }
}

Reducer

export default (state = {}, action) => {
  let copyList = [{ description: '213', aim: 12, progress: 2, percentage: 20 }];
  switch (action.type) {
    case 'ADD_DUEDATE':
      return { ...state, [action.payload.id]: action.payload }
    case 'ADD_GOAL':
      return {

      }
    case 'DELETE_TODO':
      return state.filter((item, index) => index !== action.payload)
    default:
      return state;
  }
}

Component

import React from 'react';
import { connect } from 'react-redux';

class List extends React.Component {
  state = {
    id: 0,
    goalId: 0
  }

  createDueDate = () => {
    this.props.add({
      id: this.state.id,
      dueDate: "By May 28th I Will do something: ",
      goals: [{}]
    })
    this.setState({ id: this.state.id + 1 });
  }

  addGoal = () => {
    this.props.addToList({
      goals:
        [{ id: this.state.goalId, description: '213', aim: 12, progress: 2, percentage: 20 }]
    })
    this.setState({ goalId: this.state.goalId + 1 })

  }

  render() {
    return (
      <div>
        <div>
          <button className="btn btn-secondary" onClick={this.createDueDate}></button>
        </div>

        <div>
          <button className="btn btn-primary" onClick={this.addGoal}></button>
        </div>
      </div>
    );
  }
}

function mapStateToProps(state) {
  return {
    list: state.list
  }
}

function mapDispatchToProps(dispatch) {
  return {
    add: (value) => {
      dispatch({ type: 'ADD_DUEDATE', payload: value })
    },
    get: (id) => {
      dispatch({ type: 'GET_DUEDATE', payload: id })
    },
    addToList: (value) => {
      dispatch({ type: 'ADD_GOAL', payload: value })
    }
  }
}

export default connect(mapStateToProps, mapDispatchToProps)(List);
2
  • What are you trying to achieve? Trigger a re-render when a new goal is added and update the UI? Commented May 22, 2019 at 19:13
  • I am trying to add objects to the goals array by clicking a button. Commented May 22, 2019 at 19:30

1 Answer 1

4

Let's assume a nested array of items in our reducer:

const initialState = {
    items : {
        deepItem  :[1, 2, 2],
        reallyDeepItem: {
            a : [1,2,3]
            b : {'a', 'c'}
        }
    }
}

And now let's assume 2 actions, one to add an item on state.items.deepItem that we're gonna call ADD_DEEP_ITEM and another one to insert an item on state.items.reallyDeepItem.a called ADD_DEEPER_ITEM. Let's write our reducer:

const Reducer = (state = initialState, action) =>{
    switch(action.type){
        case 'ADD_DEEP_ITEM': return {
            ...state,
            items : {
                ...state.items,
                deepItem : state.items.deepItem.concat(action.data)
            }
        }

        case 'ADD_DEEPER_ITEM': return{
            ...state,
            items :{
                ...state.items,
                reallyDeepItem:{
                    ...state.items.reallyDeepItem,
                    a : state.itens.reallyDeepItem.a.concat(action.data)
                }
            }
        }
    }
}

That's it, properly updated! Just remember to always spread all properties and then override the ones you want.

Sign up to request clarification or add additional context in comments.

1 Comment

in case of "'ADD_DEEP_ITEM'" even we are using spread operator .reference of a and b will still point to old state reference as they are objects and not primitive type. by using spread operator reference of "reallyDeepItem" will be copied only . let me now my undestanding is correct or not ?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.