Reputation: 1093
This is my simple react component. I set rooms
firstly in state in componentWillReceiveProps
and then on submit
I do set rooms
to data
in state as well.
Also on submit I do an api call by passing single object from the rooms
and when response come then I do slice
that object from the data (but not from rooms
) until the data
length is equal to 0.
Now problem is when I do slice
from the data
then it slices
the rooms
elements as well.
class EditRoom extends Component {
constructor() {
super()
this.state = {
rooms: [],
data: []
}
}
componentWillMount() {
const { fetchRooms } = this.props
fetchRooms()
}
componentWillReceiveProps(np) {
const { rooms, setNick, setNickName } = np
if (this.props.rooms !== rooms) {
console.log('ppppppppppppp')
this.setState({ rooms })
}
if (setNick) {
const data = this.state.data
data.splice(0, 1)
this.setState({ data }, () => {
if (data.length === 0) {
console.log('pppp542545455453864')
} else {
const room = _.first(this.state.data)
setNickName(room)
}
})
}
}
handleInputChange(e, i) {
const { rooms } = this.state
rooms[i].nickname = e.target.value
this.setState({ rooms })
}
onSaveClick() {
const { setNickName } = this.props
this.setState({ data: this.state.rooms }, () => {
const room = _.first(this.state.data)
setNickName(room)
})
}
render() {
const { rooms } = this.state
return (
<div>
<main id="EditRoom">
{rooms &&
rooms.map((room, i) => {
return (
<div className="barcode-box" key={i} style={{ backgroundColor: this.getRandomColor(i) }}>
<div className="edit-room-name">
<input
type="text"
className="form-control"
style={{ color: '#ffffff' }}
name="cardNumber"
placeholder="Nickname"
value={_.get(room, 'nickname') || ''}
onChange={e => this.handleInputChange(e, i)}
/>
</div>
</div>
)
})}
</main>
</div>
)
}
}
What I am missing here?
Thank you !!!
Upvotes: 0
Views: 226
Reputation: 7195
You should not modify this.state
directly, e.g. using array mutating methods like splice
. Instead of this, make a copy from this.state.data
sub-array, modify and pass it to setState()
.
Something like this:
const data = this.state.data.slice() // make a copy of data
data.splice(0, 1) // modify a copy
this.setState({ data }, ...) // pass to setState
[Update] Explanation of why changing one sub-array of state affects on another:
Arrays (as all objects) in JS are passed by reference. So if you do a simple assignment like arr2 = arr1
, splice
method will mutate the original array too. That's also true for nested arrays (objects) like in your case. data
sub-array is stored with rooms
together in state
. So mutating data will affect rooms
sub-array too.
Upvotes: 1